@umituz/react-native-video-editor 1.1.15 → 1.1.17
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +1 -1
- package/src/player/infrastructure/services/video-cache.service.ts +1 -1
- package/src/player/presentation/components/VideoPlayer.tsx +7 -14
- package/src/presentation/components/DraggableLayer.tsx +1 -1
- package/src/presentation/components/EditorHeader.tsx +1 -1
- package/src/presentation/components/EditorPreviewArea.tsx +1 -1
- package/src/presentation/components/EditorTimeline.tsx +1 -1
- package/src/presentation/components/EditorToolPanel.tsx +1 -1
- package/src/presentation/components/LayerActionsMenu.tsx +1 -1
- package/src/presentation/components/SceneActionsMenu.tsx +1 -1
- package/src/presentation/components/text-layer/TextInputSection.tsx +0 -1
- package/src/presentation/hooks/useAnimationLayerForm.ts +2 -2
- package/src/presentation/hooks/useAudioLayerForm.ts +2 -2
- package/src/presentation/hooks/useEditorActions.tsx +2 -2
- package/src/presentation/hooks/useEditorHistory.ts +2 -2
- package/src/presentation/hooks/useEditorLayers.ts +1 -1
- package/src/presentation/hooks/useEditorPlayback.ts +2 -2
- package/src/presentation/hooks/useEditorScenes.ts +1 -1
- package/src/presentation/hooks/useExport.ts +1 -1
- package/src/presentation/hooks/useExportActions.tsx +2 -2
- package/src/presentation/hooks/useExportForm.ts +2 -2
- package/src/presentation/hooks/useImageLayerForm.ts +2 -2
- package/src/presentation/hooks/useImageLayerOperations.ts +2 -2
- package/src/presentation/hooks/useLayerActions.tsx +2 -2
- package/src/presentation/hooks/useLayerManipulation.ts +2 -2
- package/src/presentation/hooks/useMenuActions.tsx +2 -2
- package/src/presentation/hooks/useSceneActions.tsx +2 -2
- package/src/presentation/hooks/useShapeLayerForm.ts +1 -1
- package/src/presentation/hooks/useShapeLayerOperations.ts +2 -2
- package/src/presentation/hooks/useTextLayerForm.ts +1 -1
- package/src/presentation/hooks/useTextLayerOperations.ts +2 -2
- package/src/presentation/components/draggable-layer/index.ts +0 -7
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@umituz/react-native-video-editor",
|
|
3
|
-
"version": "1.1.
|
|
3
|
+
"version": "1.1.17",
|
|
4
4
|
"description": "Professional video editor with layer-based timeline, text/image/shape/audio/animation layers, and export functionality",
|
|
5
5
|
"main": "./src/index.ts",
|
|
6
6
|
"types": "./src/index.ts",
|
|
@@ -130,7 +130,7 @@ export const clearVideoCache = async (): Promise<void> => {
|
|
|
130
130
|
/**
|
|
131
131
|
* Delete a specific cached video
|
|
132
132
|
*/
|
|
133
|
-
export const deleteSpecificCachedVideo = (url: string): boolean => {
|
|
133
|
+
export const deleteSpecificCachedVideo = async (url: string): Promise<boolean> => {
|
|
134
134
|
if (!url || url.startsWith("file://")) return false;
|
|
135
135
|
return deleteCachedFile(url, getVideoCacheDir());
|
|
136
136
|
};
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
* Reusable video player with caching, thumbnail and controls
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
import React, { useState, useCallback, useMemo
|
|
6
|
+
import React, { useState, useCallback, useMemo } from "react";
|
|
7
7
|
import { View, TouchableOpacity, StyleSheet, type ViewStyle } from "react-native";
|
|
8
8
|
import { Image } from "expo-image";
|
|
9
9
|
import { VideoView } from "expo-video";
|
|
@@ -43,7 +43,8 @@ export const VideoPlayer: React.FC<VideoPlayerProps> = ({
|
|
|
43
43
|
// IMPORTANT: Call useResponsive BEFORE useAppDesignTokens to maintain hook order
|
|
44
44
|
const { width: screenWidth, horizontalPadding } = useResponsive();
|
|
45
45
|
const tokens = useAppDesignTokens();
|
|
46
|
-
const [
|
|
46
|
+
const [userTriggeredPlay, setUserTriggeredPlay] = useState(false);
|
|
47
|
+
const showVideo = autoPlay || userTriggeredPlay;
|
|
47
48
|
|
|
48
49
|
// Cache the video first (downloads if needed)
|
|
49
50
|
const { localUri, isDownloading, downloadProgress, error } = useVideoCaching(source);
|
|
@@ -53,24 +54,16 @@ export const VideoPlayer: React.FC<VideoPlayerProps> = ({
|
|
|
53
54
|
source: localUri,
|
|
54
55
|
loop,
|
|
55
56
|
muted,
|
|
56
|
-
autoPlay
|
|
57
|
+
autoPlay,
|
|
57
58
|
});
|
|
58
59
|
|
|
59
|
-
useEffect(() => {
|
|
60
|
-
if (showVideo && state.isPlayerValid && player) {
|
|
61
|
-
if (__DEV__) {
|
|
62
|
-
console.log("[VideoPlayer] Starting playback from:", localUri);
|
|
63
|
-
}
|
|
64
|
-
controls.play();
|
|
65
|
-
}
|
|
66
|
-
}, [showVideo, state.isPlayerValid, player, controls, localUri]);
|
|
67
|
-
|
|
68
60
|
const handlePlay = useCallback(() => {
|
|
69
61
|
if (__DEV__) {
|
|
70
62
|
console.log("[VideoPlayer] handlePlay, localUri:", localUri);
|
|
71
63
|
}
|
|
72
|
-
|
|
73
|
-
|
|
64
|
+
setUserTriggeredPlay(true);
|
|
65
|
+
controls.play();
|
|
66
|
+
}, [localUri, controls]);
|
|
74
67
|
|
|
75
68
|
// Calculate dimensions
|
|
76
69
|
const videoWidth = getWidthFromStyle(style as ViewStyle) ?? (screenWidth - horizontalPadding * 2);
|
|
@@ -18,7 +18,7 @@ const { width } = Dimensions.get("window");
|
|
|
18
18
|
const PREVIEW_ASPECT_RATIO = 16 / 9;
|
|
19
19
|
const PREVIEW_HEIGHT = width / PREVIEW_ASPECT_RATIO;
|
|
20
20
|
|
|
21
|
-
|
|
21
|
+
interface EditorPreviewAreaProps {
|
|
22
22
|
scene: Scene;
|
|
23
23
|
selectedLayerId: string | null;
|
|
24
24
|
isPlaying: boolean;
|
|
@@ -13,7 +13,7 @@ import {
|
|
|
13
13
|
import { useLocalization } from "@umituz/react-native-settings";
|
|
14
14
|
import type { VideoProject, Scene } from "../../domain/entities";
|
|
15
15
|
|
|
16
|
-
|
|
16
|
+
interface EditorTimelineProps {
|
|
17
17
|
project: VideoProject;
|
|
18
18
|
currentSceneIndex: number;
|
|
19
19
|
onSceneSelect: (index: number) => void;
|
|
@@ -18,7 +18,7 @@ import {
|
|
|
18
18
|
} from "@umituz/react-native-design-system";
|
|
19
19
|
import { useLocalization } from "@umituz/react-native-settings";
|
|
20
20
|
|
|
21
|
-
|
|
21
|
+
interface EditorToolPanelProps {
|
|
22
22
|
onAddText: () => void;
|
|
23
23
|
onAddImage: () => void;
|
|
24
24
|
onAddShape: () => void;
|
|
@@ -13,7 +13,7 @@ import {
|
|
|
13
13
|
import { useLocalization } from "@umituz/react-native-settings";
|
|
14
14
|
import type { Layer } from "../../domain/entities";
|
|
15
15
|
|
|
16
|
-
|
|
16
|
+
interface LayerActionsMenuProps {
|
|
17
17
|
layer: Layer;
|
|
18
18
|
onEditText: () => void;
|
|
19
19
|
onEditImage: () => void;
|
|
@@ -7,14 +7,14 @@ import { useState, useCallback } from "react";
|
|
|
7
7
|
import type { Animation, AnimationType } from "../../domain/entities";
|
|
8
8
|
import type { Easing } from "../../infrastructure/constants/animation-layer.constants";
|
|
9
9
|
|
|
10
|
-
|
|
10
|
+
interface AnimationLayerFormState {
|
|
11
11
|
animationType: AnimationType;
|
|
12
12
|
duration: number;
|
|
13
13
|
delay: number;
|
|
14
14
|
easing: Easing;
|
|
15
15
|
}
|
|
16
16
|
|
|
17
|
-
|
|
17
|
+
interface UseAnimationLayerFormReturn {
|
|
18
18
|
formState: AnimationLayerFormState;
|
|
19
19
|
setAnimationType: (type: AnimationType) => void;
|
|
20
20
|
setDuration: (duration: number) => void;
|
|
@@ -6,14 +6,14 @@
|
|
|
6
6
|
import { useState, useCallback } from "react";
|
|
7
7
|
import type { Audio } from "../../domain/entities";
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
interface AudioLayerFormState {
|
|
10
10
|
audioUri: string;
|
|
11
11
|
volume: number;
|
|
12
12
|
fadeIn: number;
|
|
13
13
|
fadeOut: number;
|
|
14
14
|
}
|
|
15
15
|
|
|
16
|
-
|
|
16
|
+
interface UseAudioLayerFormReturn {
|
|
17
17
|
formState: AudioLayerFormState;
|
|
18
18
|
setAudioUri: (uri: string) => void;
|
|
19
19
|
setVolume: (volume: number) => void;
|
|
@@ -12,7 +12,7 @@ import { useSceneActions } from "./useSceneActions";
|
|
|
12
12
|
import { useMenuActions } from "./useMenuActions";
|
|
13
13
|
import { useExportActions } from "./useExportActions";
|
|
14
14
|
|
|
15
|
-
|
|
15
|
+
interface UseEditorActionsParams {
|
|
16
16
|
project: VideoProject | undefined;
|
|
17
17
|
selectedLayerId: string | null;
|
|
18
18
|
currentScene: any;
|
|
@@ -22,7 +22,7 @@ export interface UseEditorActionsParams {
|
|
|
22
22
|
onExportComplete: (settings: any, uri?: string) => void;
|
|
23
23
|
}
|
|
24
24
|
|
|
25
|
-
|
|
25
|
+
interface UseEditorActionsReturn {
|
|
26
26
|
handleAddText: () => void;
|
|
27
27
|
handleEditLayer: () => void;
|
|
28
28
|
handleAddImage: () => void;
|
|
@@ -6,13 +6,13 @@
|
|
|
6
6
|
import { useCallback, useState } from "react";
|
|
7
7
|
import type { VideoProject } from "../../domain/entities";
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
interface UseEditorHistoryParams {
|
|
10
10
|
project: VideoProject | undefined;
|
|
11
11
|
projectId: string; // Kept for interface compatibility, used for reset if needed
|
|
12
12
|
onUpdateProject: (updates: Partial<VideoProject>) => void;
|
|
13
13
|
}
|
|
14
14
|
|
|
15
|
-
|
|
15
|
+
interface UseEditorHistoryReturn {
|
|
16
16
|
undo: () => void;
|
|
17
17
|
redo: () => void;
|
|
18
18
|
canUndo: boolean;
|
|
@@ -15,7 +15,7 @@ import type {
|
|
|
15
15
|
} from "../../domain/entities";
|
|
16
16
|
import type { TextLayer, ImageLayer, Animation } from "../../domain/entities";
|
|
17
17
|
|
|
18
|
-
|
|
18
|
+
interface UseEditorLayersParams {
|
|
19
19
|
projectId: string;
|
|
20
20
|
scenes: any[];
|
|
21
21
|
sceneIndex: number;
|
|
@@ -6,11 +6,11 @@
|
|
|
6
6
|
import { useState, useEffect, useCallback } from "react";
|
|
7
7
|
import type { Scene } from "../../domain/entities";
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
interface UseEditorPlaybackParams {
|
|
10
10
|
currentScene: Scene | undefined;
|
|
11
11
|
}
|
|
12
12
|
|
|
13
|
-
|
|
13
|
+
interface UseEditorPlaybackReturn {
|
|
14
14
|
isPlaying: boolean;
|
|
15
15
|
currentTime: number;
|
|
16
16
|
playPause: () => void;
|
|
@@ -9,7 +9,7 @@ import { useLocalization } from "@umituz/react-native-settings";
|
|
|
9
9
|
import { sceneOperationsService } from "../../infrastructure/services/scene-operations.service";
|
|
10
10
|
import type { Scene, Audio } from "../../domain/entities";
|
|
11
11
|
|
|
12
|
-
|
|
12
|
+
interface UseEditorScenesParams {
|
|
13
13
|
scenes: Scene[];
|
|
14
14
|
currentSceneIndex: number;
|
|
15
15
|
onUpdateScenes: (scenes: Scene[]) => void;
|
|
@@ -8,13 +8,13 @@ import { ExportDialog } from "../components/ExportDialog";
|
|
|
8
8
|
import type { VideoProject, ExportSettings } from "../../domain/entities";
|
|
9
9
|
import type { UseEditorBottomSheetReturn } from "./useEditorBottomSheet";
|
|
10
10
|
|
|
11
|
-
|
|
11
|
+
interface UseExportActionsParams {
|
|
12
12
|
project: VideoProject | undefined;
|
|
13
13
|
bottomSheet: UseEditorBottomSheetReturn;
|
|
14
14
|
onExportComplete: (settings: ExportSettings, uri?: string) => void;
|
|
15
15
|
}
|
|
16
16
|
|
|
17
|
-
|
|
17
|
+
interface UseExportActionsReturn {
|
|
18
18
|
handleExport: () => void;
|
|
19
19
|
handleSave: () => void;
|
|
20
20
|
}
|
|
@@ -16,14 +16,14 @@ import {
|
|
|
16
16
|
QUALITY_MULTIPLIERS,
|
|
17
17
|
} from "../../infrastructure/constants/export.constants";
|
|
18
18
|
|
|
19
|
-
|
|
19
|
+
interface ExportFormState {
|
|
20
20
|
resolution: Resolution;
|
|
21
21
|
quality: Quality;
|
|
22
22
|
format: Format;
|
|
23
23
|
includeWatermark: boolean;
|
|
24
24
|
}
|
|
25
25
|
|
|
26
|
-
|
|
26
|
+
interface UseExportFormReturn {
|
|
27
27
|
formState: ExportFormState;
|
|
28
28
|
setResolution: (resolution: Resolution) => void;
|
|
29
29
|
setQuality: (quality: Quality) => void;
|
|
@@ -6,12 +6,12 @@
|
|
|
6
6
|
import { useState, useCallback } from "react";
|
|
7
7
|
import type { ImageLayer } from "../../domain/entities";
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
interface ImageLayerFormState {
|
|
10
10
|
imageUri: string;
|
|
11
11
|
opacity: number;
|
|
12
12
|
}
|
|
13
13
|
|
|
14
|
-
|
|
14
|
+
interface UseImageLayerFormReturn {
|
|
15
15
|
formState: ImageLayerFormState;
|
|
16
16
|
setImageUri: (uri: string) => void;
|
|
17
17
|
setOpacity: (opacity: number) => void;
|
|
@@ -9,14 +9,14 @@ import { useLocalization } from "@umituz/react-native-settings";
|
|
|
9
9
|
import { layerOperationsService } from "../../infrastructure/services/layer-operations.service";
|
|
10
10
|
import type { AddImageLayerData, Scene, ImageLayer } from "../../domain/entities";
|
|
11
11
|
|
|
12
|
-
|
|
12
|
+
interface UseImageLayerOperationsParams {
|
|
13
13
|
scenes: Scene[];
|
|
14
14
|
sceneIndex: number;
|
|
15
15
|
onUpdateScenes: (scenes: Scene[]) => void;
|
|
16
16
|
onCloseBottomSheet: () => void;
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
-
|
|
19
|
+
interface UseImageLayerOperationsReturn {
|
|
20
20
|
addImageLayer: (data: AddImageLayerData) => void;
|
|
21
21
|
editImageLayer: (layerId: string, data: Partial<ImageLayer>) => void;
|
|
22
22
|
}
|
|
@@ -13,14 +13,14 @@ import type { Scene, ImageLayer, Layer } from "../../domain/entities";
|
|
|
13
13
|
import type { UseEditorLayersReturn } from "./useEditorLayers";
|
|
14
14
|
import type { UseEditorBottomSheetReturn } from "./useEditorBottomSheet";
|
|
15
15
|
|
|
16
|
-
|
|
16
|
+
interface UseLayerActionsParams {
|
|
17
17
|
selectedLayerId: string | null;
|
|
18
18
|
currentScene: Scene | undefined;
|
|
19
19
|
layers: UseEditorLayersReturn;
|
|
20
20
|
bottomSheet: UseEditorBottomSheetReturn;
|
|
21
21
|
}
|
|
22
22
|
|
|
23
|
-
|
|
23
|
+
interface UseLayerActionsReturn {
|
|
24
24
|
handleAddText: () => void;
|
|
25
25
|
handleEditLayer: () => void;
|
|
26
26
|
handleAddImage: () => void;
|
|
@@ -9,7 +9,7 @@ import { useLocalization } from "@umituz/react-native-settings";
|
|
|
9
9
|
import { layerOperationsService } from "../../infrastructure/services/layer-operations.service";
|
|
10
10
|
import type { Scene, LayerOrderAction, Animation } from "../../domain/entities";
|
|
11
11
|
|
|
12
|
-
|
|
12
|
+
interface UseLayerManipulationParams {
|
|
13
13
|
scenes: Scene[];
|
|
14
14
|
sceneIndex: number;
|
|
15
15
|
onUpdateScenes: (scenes: Scene[]) => void;
|
|
@@ -17,7 +17,7 @@ export interface UseLayerManipulationParams {
|
|
|
17
17
|
onLayerDeleted?: () => void;
|
|
18
18
|
}
|
|
19
19
|
|
|
20
|
-
|
|
20
|
+
interface UseLayerManipulationReturn {
|
|
21
21
|
deleteLayer: (layerId: string) => void;
|
|
22
22
|
changeLayerOrder: (layerId: string, action: LayerOrderAction) => void;
|
|
23
23
|
duplicateLayer: (layerId: string) => void;
|
|
@@ -8,7 +8,7 @@ import { LayerActionsMenu } from "../components/LayerActionsMenu";
|
|
|
8
8
|
import type { UseEditorLayersReturn } from "./useEditorLayers";
|
|
9
9
|
import type { UseEditorBottomSheetReturn } from "./useEditorBottomSheet";
|
|
10
10
|
|
|
11
|
-
|
|
11
|
+
interface UseMenuActionsParams {
|
|
12
12
|
layers: UseEditorLayersReturn;
|
|
13
13
|
bottomSheet: UseEditorBottomSheetReturn;
|
|
14
14
|
handleEditLayer: () => void;
|
|
@@ -16,7 +16,7 @@ export interface UseMenuActionsParams {
|
|
|
16
16
|
handleAnimate: (layerId: string) => void;
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
-
|
|
19
|
+
interface UseMenuActionsReturn {
|
|
20
20
|
handleLayerActionsPress: (layer: any) => void;
|
|
21
21
|
}
|
|
22
22
|
|
|
@@ -9,13 +9,13 @@ import { SceneActionsMenu } from "../components/SceneActionsMenu";
|
|
|
9
9
|
import type { UseEditorScenesReturn } from "./useEditorScenes";
|
|
10
10
|
import type { UseEditorBottomSheetReturn } from "./useEditorBottomSheet";
|
|
11
11
|
|
|
12
|
-
|
|
12
|
+
interface UseSceneActionsParams {
|
|
13
13
|
currentScene: any;
|
|
14
14
|
scenes: UseEditorScenesReturn;
|
|
15
15
|
bottomSheet: UseEditorBottomSheetReturn;
|
|
16
16
|
}
|
|
17
17
|
|
|
18
|
-
|
|
18
|
+
interface UseSceneActionsReturn {
|
|
19
19
|
handleAudio: () => void;
|
|
20
20
|
handleSceneLongPress: (index: number, canDelete: boolean) => void;
|
|
21
21
|
}
|
|
@@ -16,7 +16,7 @@ export interface ShapeLayerFormState {
|
|
|
16
16
|
opacity: number;
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
-
|
|
19
|
+
interface UseShapeLayerFormReturn {
|
|
20
20
|
formState: ShapeLayerFormState;
|
|
21
21
|
setShape: (shape: ShapeType) => void;
|
|
22
22
|
setFillColor: (color: string) => void;
|
|
@@ -9,7 +9,7 @@ import { useLocalization } from "@umituz/react-native-settings";
|
|
|
9
9
|
import { layerOperationsService } from "../../infrastructure/services/layer-operations.service";
|
|
10
10
|
import type { AddShapeLayerData, Scene } from "../../domain/entities";
|
|
11
11
|
|
|
12
|
-
|
|
12
|
+
interface UseShapeLayerOperationsParams {
|
|
13
13
|
scenes: Scene[];
|
|
14
14
|
sceneIndex: number;
|
|
15
15
|
onUpdateScenes: (scenes: Scene[]) => void;
|
|
@@ -17,7 +17,7 @@ export interface UseShapeLayerOperationsParams {
|
|
|
17
17
|
defaultColor: string;
|
|
18
18
|
}
|
|
19
19
|
|
|
20
|
-
|
|
20
|
+
interface UseShapeLayerOperationsReturn {
|
|
21
21
|
addShapeLayer: (data: AddShapeLayerData) => void;
|
|
22
22
|
}
|
|
23
23
|
|
|
@@ -16,7 +16,7 @@ export interface TextLayerFormState {
|
|
|
16
16
|
textAlign: "left" | "center" | "right";
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
-
|
|
19
|
+
interface UseTextLayerFormReturn {
|
|
20
20
|
formState: TextLayerFormState;
|
|
21
21
|
setText: (text: string) => void;
|
|
22
22
|
setFontSize: (size: number) => void;
|
|
@@ -9,7 +9,7 @@ import { useLocalization } from "@umituz/react-native-settings";
|
|
|
9
9
|
import { layerOperationsService } from "../../infrastructure/services/layer-operations.service";
|
|
10
10
|
import type { AddTextLayerData, Scene, TextLayer } from "../../domain/entities";
|
|
11
11
|
|
|
12
|
-
|
|
12
|
+
interface UseTextLayerOperationsParams {
|
|
13
13
|
scenes: Scene[];
|
|
14
14
|
sceneIndex: number;
|
|
15
15
|
onUpdateScenes: (scenes: Scene[]) => void;
|
|
@@ -17,7 +17,7 @@ export interface UseTextLayerOperationsParams {
|
|
|
17
17
|
defaultColor: string;
|
|
18
18
|
}
|
|
19
19
|
|
|
20
|
-
|
|
20
|
+
interface UseTextLayerOperationsReturn {
|
|
21
21
|
addTextLayer: (data: AddTextLayerData) => void;
|
|
22
22
|
editTextLayer: (layerId: string, data: Partial<TextLayer>) => void;
|
|
23
23
|
}
|