@umituz/react-native-ai-generation-content 1.20.1 → 1.20.3
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/features/hd-touch-up/index.ts +2 -8
- package/src/features/hd-touch-up/presentation/hooks/index.ts +1 -5
- package/src/features/hd-touch-up/presentation/hooks/useHDTouchUpFeature.ts +5 -28
- package/src/features/image-to-image/domain/types/partials/hook.types.ts +1 -3
- package/src/features/image-to-image/presentation/hooks/useSingleImageFeature.ts +10 -7
- package/src/features/image-to-video/presentation/hooks/useImageToVideoFeature.ts +37 -27
- package/src/features/photo-restoration/index.ts +2 -10
- package/src/features/photo-restoration/presentation/hooks/index.ts +1 -5
- package/src/features/photo-restoration/presentation/hooks/usePhotoRestoreFeature.ts +5 -28
- package/src/features/remove-background/presentation/hooks/index.ts +1 -6
- package/src/features/remove-background/presentation/hooks/useRemoveBackgroundFeature.ts +4 -12
- package/src/features/text-to-video/presentation/hooks/useTextToVideoFeature.ts +138 -66
- package/src/features/upscaling/presentation/hooks/index.ts +1 -2
- package/src/features/upscaling/presentation/hooks/useUpscaleFeature.ts +4 -9
- package/src/features/image-to-video/presentation/hooks/useImageToVideoFeature.constants.ts +0 -15
- package/src/features/image-to-video/presentation/hooks/useImageToVideoFeature.types.ts +0 -27
- package/src/features/text-to-video/presentation/hooks/textToVideoExecution.ts +0 -134
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@umituz/react-native-ai-generation-content",
|
|
3
|
-
"version": "1.20.
|
|
3
|
+
"version": "1.20.3",
|
|
4
4
|
"description": "Provider-agnostic AI generation orchestration for React Native with result preview components",
|
|
5
5
|
"main": "src/index.ts",
|
|
6
6
|
"types": "src/index.ts",
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
/**
|
|
2
|
-
export * from "./presentation/components";
|
|
3
2
|
* HD Touch Up Feature
|
|
4
3
|
* Provider-agnostic HD enhancement feature
|
|
5
4
|
*/
|
|
@@ -16,12 +15,7 @@ export type {
|
|
|
16
15
|
} from "./domain";
|
|
17
16
|
|
|
18
17
|
// Presentation Hooks
|
|
19
|
-
export { useHDTouchUpFeature } from "./presentation";
|
|
20
|
-
export type {
|
|
21
|
-
UseHDTouchUpFeatureProps,
|
|
22
|
-
UseHDTouchUpFeatureReturn,
|
|
23
|
-
} from "./presentation";
|
|
18
|
+
export { useHDTouchUpFeature, type UseHDTouchUpFeatureProps } from "./presentation";
|
|
24
19
|
|
|
25
20
|
// Presentation Components
|
|
26
|
-
export { HDTouchUpFeature } from "./presentation";
|
|
27
|
-
export type { HDTouchUpFeatureProps } from "./presentation";
|
|
21
|
+
export { HDTouchUpFeature, type HDTouchUpFeatureProps } from "./presentation";
|
|
@@ -1,15 +1,10 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* useHDTouchUpFeature Hook
|
|
3
3
|
* Uses base single image hook for HD touch up
|
|
4
|
-
* Uses centralized orchestrator for credit/error handling
|
|
5
4
|
*/
|
|
6
5
|
|
|
7
|
-
import {
|
|
8
|
-
|
|
9
|
-
type BaseSingleImageHookReturn,
|
|
10
|
-
} from "../../../image-to-image";
|
|
11
|
-
import type { AlertMessages } from "../../../../presentation/hooks/generation";
|
|
12
|
-
import type { HDTouchUpFeatureConfig } from "../../domain/types";
|
|
6
|
+
import { useSingleImageFeature, type BaseSingleImageHookReturn } from "../../../image-to-image";
|
|
7
|
+
import type { HDTouchUpFeatureConfig, HDTouchUpResult } from "../../domain/types";
|
|
13
8
|
|
|
14
9
|
export interface UseHDTouchUpFeatureProps {
|
|
15
10
|
config: HDTouchUpFeatureConfig;
|
|
@@ -18,29 +13,11 @@ export interface UseHDTouchUpFeatureProps {
|
|
|
18
13
|
onBeforeProcess?: () => Promise<boolean>;
|
|
19
14
|
}
|
|
20
15
|
|
|
21
|
-
export
|
|
22
|
-
/** Alert messages for error handling */
|
|
23
|
-
alertMessages?: AlertMessages;
|
|
24
|
-
/** User ID for credit operations */
|
|
25
|
-
userId?: string;
|
|
26
|
-
/** Callback when credits are exhausted */
|
|
27
|
-
onCreditsExhausted?: () => void;
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
export interface UseHDTouchUpFeatureReturn extends BaseSingleImageHookReturn {}
|
|
31
|
-
|
|
32
|
-
export function useHDTouchUpFeature(
|
|
33
|
-
props: UseHDTouchUpFeatureProps,
|
|
34
|
-
options?: UseHDTouchUpFeatureOptions,
|
|
35
|
-
): UseHDTouchUpFeatureReturn {
|
|
16
|
+
export function useHDTouchUpFeature(props: UseHDTouchUpFeatureProps): BaseSingleImageHookReturn {
|
|
36
17
|
const { config, onSelectImage, onSaveImage, onBeforeProcess } = props;
|
|
37
18
|
|
|
38
|
-
|
|
39
|
-
return useSingleImageFeature(
|
|
19
|
+
return useSingleImageFeature<HDTouchUpFeatureConfig, HDTouchUpResult>(
|
|
40
20
|
{ config: config as never, onSelectImage, onSaveImage, onBeforeProcess },
|
|
41
|
-
{
|
|
42
|
-
buildInput: (imageBase64) => ({ imageBase64 }),
|
|
43
|
-
...options,
|
|
44
|
-
},
|
|
21
|
+
{ buildInput: (imageBase64) => ({ imageBase64 }) },
|
|
45
22
|
);
|
|
46
23
|
}
|
|
@@ -9,9 +9,7 @@ import type { BaseSingleImageState, BaseDualImageState } from "./state.types";
|
|
|
9
9
|
/**
|
|
10
10
|
* Base hook props for single image features
|
|
11
11
|
*/
|
|
12
|
-
export interface BaseSingleImageHookProps<
|
|
13
|
-
TConfig extends SingleImageConfig = SingleImageConfig,
|
|
14
|
-
> {
|
|
12
|
+
export interface BaseSingleImageHookProps<TConfig = SingleImageConfig> {
|
|
15
13
|
config: TConfig;
|
|
16
14
|
onSelectImage: () => Promise<string | null>;
|
|
17
15
|
onSaveImage: (imageUrl: string) => Promise<void>;
|
|
@@ -19,7 +19,7 @@ import type {
|
|
|
19
19
|
BaseImageResult,
|
|
20
20
|
} from "../../domain/types";
|
|
21
21
|
|
|
22
|
-
export interface SingleImageFeatureOptions<TConfig
|
|
22
|
+
export interface SingleImageFeatureOptions<TConfig = SingleImageConfig> {
|
|
23
23
|
buildInput?: (imageBase64: string, config: TConfig) => Record<string, unknown>;
|
|
24
24
|
/** Alert messages for error handling */
|
|
25
25
|
alertMessages?: AlertMessages;
|
|
@@ -43,13 +43,16 @@ interface SingleImageInput {
|
|
|
43
43
|
}
|
|
44
44
|
|
|
45
45
|
export function useSingleImageFeature<
|
|
46
|
-
TConfig
|
|
47
|
-
TResult
|
|
46
|
+
TConfig = SingleImageConfig,
|
|
47
|
+
TResult = BaseImageResult,
|
|
48
48
|
>(
|
|
49
49
|
props: BaseSingleImageHookProps<TConfig>,
|
|
50
50
|
options?: SingleImageFeatureOptions<TConfig>,
|
|
51
51
|
): BaseSingleImageHookReturn {
|
|
52
|
-
const { config, onSelectImage, onSaveImage, onBeforeProcess } = props;
|
|
52
|
+
const { config: rawConfig, onSelectImage, onSaveImage, onBeforeProcess } = props;
|
|
53
|
+
|
|
54
|
+
// Cast config to base type for internal usage
|
|
55
|
+
const config = rawConfig as unknown as SingleImageConfig;
|
|
53
56
|
|
|
54
57
|
// Image selection state (separate from orchestrator state)
|
|
55
58
|
const [imageUri, setImageUri] = useState<string | null>(null);
|
|
@@ -73,7 +76,7 @@ export function useSingleImageFeature<
|
|
|
73
76
|
// Notify completion with creationId
|
|
74
77
|
const creationId = creationIdRef.current;
|
|
75
78
|
if (creationId) {
|
|
76
|
-
config.onProcessingComplete?.({ ...result, creationId } as
|
|
79
|
+
config.onProcessingComplete?.({ ...result, creationId } as BaseImageResult);
|
|
77
80
|
}
|
|
78
81
|
|
|
79
82
|
return result.imageUrl;
|
|
@@ -124,14 +127,14 @@ export function useSingleImageFeature<
|
|
|
124
127
|
const imageBase64 = await config.prepareImage(imageUri);
|
|
125
128
|
|
|
126
129
|
const input: SingleImageInput = options?.buildInput
|
|
127
|
-
? { imageBase64, options: options.buildInput(imageBase64,
|
|
130
|
+
? { imageBase64, options: options.buildInput(imageBase64, rawConfig) }
|
|
128
131
|
: { imageBase64 };
|
|
129
132
|
|
|
130
133
|
await orchestrator.generate(input);
|
|
131
134
|
} catch (error) {
|
|
132
135
|
// Error already handled by orchestrator
|
|
133
136
|
}
|
|
134
|
-
}, [imageUri, config, options, onBeforeProcess, orchestrator]);
|
|
137
|
+
}, [imageUri, config, rawConfig, options, onBeforeProcess, orchestrator]);
|
|
135
138
|
|
|
136
139
|
const save = useCallback(async () => {
|
|
137
140
|
if (!orchestrator.result) return;
|
|
@@ -6,24 +6,47 @@
|
|
|
6
6
|
import { useState, useCallback, useMemo } from "react";
|
|
7
7
|
import { useGenerationExecution } from "./useGenerationExecution";
|
|
8
8
|
import { validateImageToVideoGeneration } from "./useImageToVideoValidation";
|
|
9
|
-
import { INITIAL_IMAGE_TO_VIDEO_STATE } from "./useImageToVideoFeature.constants";
|
|
10
|
-
import type {
|
|
11
|
-
UseImageToVideoFeatureProps,
|
|
12
|
-
UseImageToVideoFeatureReturn,
|
|
13
|
-
} from "./useImageToVideoFeature.types";
|
|
14
9
|
import type {
|
|
15
10
|
ImageToVideoFeatureState,
|
|
16
|
-
|
|
11
|
+
ImageToVideoFeatureConfig,
|
|
17
12
|
ImageToVideoResult,
|
|
13
|
+
ImageToVideoFeatureCallbacks,
|
|
14
|
+
ImageToVideoGenerateParams,
|
|
18
15
|
} from "../../domain/types";
|
|
19
16
|
|
|
20
17
|
declare const __DEV__: boolean;
|
|
21
18
|
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
19
|
+
// Initial state (inlined from constants file)
|
|
20
|
+
const INITIAL_STATE: ImageToVideoFeatureState = {
|
|
21
|
+
imageUri: null,
|
|
22
|
+
motionPrompt: "",
|
|
23
|
+
videoUrl: null,
|
|
24
|
+
thumbnailUrl: null,
|
|
25
|
+
isProcessing: false,
|
|
26
|
+
progress: 0,
|
|
27
|
+
error: null,
|
|
28
|
+
};
|
|
29
|
+
|
|
30
|
+
// Types (inlined from types file)
|
|
31
|
+
export interface UseImageToVideoFeatureProps {
|
|
32
|
+
config: ImageToVideoFeatureConfig;
|
|
33
|
+
callbacks?: ImageToVideoFeatureCallbacks;
|
|
34
|
+
userId: string;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
export interface UseImageToVideoFeatureReturn {
|
|
38
|
+
state: ImageToVideoFeatureState;
|
|
39
|
+
setImageUri: (uri: string) => void;
|
|
40
|
+
setMotionPrompt: (prompt: string) => void;
|
|
41
|
+
generate: (params?: ImageToVideoGenerateParams) => Promise<ImageToVideoResult>;
|
|
42
|
+
reset: () => void;
|
|
43
|
+
isReady: boolean;
|
|
44
|
+
canGenerate: boolean;
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
export function useImageToVideoFeature(props: UseImageToVideoFeatureProps): UseImageToVideoFeatureReturn {
|
|
25
48
|
const { config, callbacks, userId } = props;
|
|
26
|
-
const [state, setState] = useState<ImageToVideoFeatureState>(
|
|
49
|
+
const [state, setState] = useState<ImageToVideoFeatureState>(INITIAL_STATE);
|
|
27
50
|
|
|
28
51
|
const executeGeneration = useGenerationExecution({
|
|
29
52
|
userId,
|
|
@@ -68,30 +91,17 @@ export function useImageToVideoFeature(
|
|
|
68
91
|
return validation;
|
|
69
92
|
}
|
|
70
93
|
|
|
71
|
-
return executeGeneration(
|
|
72
|
-
effectiveImageUri!,
|
|
73
|
-
effectiveMotionPrompt,
|
|
74
|
-
options
|
|
75
|
-
);
|
|
94
|
+
return executeGeneration(effectiveImageUri!, effectiveMotionPrompt, options);
|
|
76
95
|
},
|
|
77
96
|
[state.imageUri, state.motionPrompt, callbacks, config.creditCost, executeGeneration],
|
|
78
97
|
);
|
|
79
98
|
|
|
80
99
|
const reset = useCallback(() => {
|
|
81
|
-
setState(
|
|
100
|
+
setState(INITIAL_STATE);
|
|
82
101
|
}, []);
|
|
83
102
|
|
|
84
|
-
const isReady = useMemo(
|
|
85
|
-
|
|
86
|
-
[state.imageUri, state.isProcessing],
|
|
87
|
-
);
|
|
88
|
-
|
|
89
|
-
const canGenerate = useMemo(
|
|
90
|
-
() => isReady && !state.error,
|
|
91
|
-
[isReady, state.error],
|
|
92
|
-
);
|
|
103
|
+
const isReady = useMemo(() => state.imageUri !== null && !state.isProcessing, [state.imageUri, state.isProcessing]);
|
|
104
|
+
const canGenerate = useMemo(() => isReady && !state.error, [isReady, state.error]);
|
|
93
105
|
|
|
94
106
|
return { state, setImageUri, setMotionPrompt, generate, reset, isReady, canGenerate };
|
|
95
107
|
}
|
|
96
|
-
|
|
97
|
-
export type { UseImageToVideoFeatureProps, UseImageToVideoFeatureReturn } from "./useImageToVideoFeature.types";
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
/**
|
|
2
|
-
export * from "./presentation/components";
|
|
3
2
|
* Photo Restoration Feature
|
|
4
3
|
* Provider-agnostic photo restoration feature
|
|
5
4
|
*/
|
|
@@ -16,15 +15,8 @@ export type {
|
|
|
16
15
|
} from "./domain";
|
|
17
16
|
|
|
18
17
|
// Presentation Hooks
|
|
19
|
-
export { usePhotoRestoreFeature } from "./presentation";
|
|
20
|
-
export type {
|
|
21
|
-
UsePhotoRestoreFeatureProps,
|
|
22
|
-
UsePhotoRestoreFeatureReturn,
|
|
23
|
-
} from "./presentation";
|
|
18
|
+
export { usePhotoRestoreFeature, type UsePhotoRestoreFeatureProps } from "./presentation";
|
|
24
19
|
|
|
25
20
|
// Presentation Components
|
|
26
21
|
export { PhotoRestoreFeature, PhotoRestoreResultView } from "./presentation";
|
|
27
|
-
export type {
|
|
28
|
-
PhotoRestoreFeatureProps,
|
|
29
|
-
PhotoRestoreResultViewProps,
|
|
30
|
-
} from "./presentation";
|
|
22
|
+
export type { PhotoRestoreFeatureProps, PhotoRestoreResultViewProps } from "./presentation";
|
|
@@ -1,5 +1 @@
|
|
|
1
|
-
export { usePhotoRestoreFeature } from "./usePhotoRestoreFeature";
|
|
2
|
-
export type {
|
|
3
|
-
UsePhotoRestoreFeatureProps,
|
|
4
|
-
UsePhotoRestoreFeatureReturn,
|
|
5
|
-
} from "./usePhotoRestoreFeature";
|
|
1
|
+
export { usePhotoRestoreFeature, type UsePhotoRestoreFeatureProps } from "./usePhotoRestoreFeature";
|
|
@@ -1,15 +1,10 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* usePhotoRestoreFeature Hook
|
|
3
3
|
* Uses base single image hook for photo restoration
|
|
4
|
-
* Uses centralized orchestrator for credit/error handling
|
|
5
4
|
*/
|
|
6
5
|
|
|
7
|
-
import {
|
|
8
|
-
|
|
9
|
-
type BaseSingleImageHookReturn,
|
|
10
|
-
} from "../../../image-to-image";
|
|
11
|
-
import type { AlertMessages } from "../../../../presentation/hooks/generation";
|
|
12
|
-
import type { PhotoRestoreFeatureConfig } from "../../domain/types";
|
|
6
|
+
import { useSingleImageFeature, type BaseSingleImageHookReturn } from "../../../image-to-image";
|
|
7
|
+
import type { PhotoRestoreFeatureConfig, PhotoRestoreResult } from "../../domain/types";
|
|
13
8
|
|
|
14
9
|
export interface UsePhotoRestoreFeatureProps {
|
|
15
10
|
config: PhotoRestoreFeatureConfig;
|
|
@@ -18,29 +13,11 @@ export interface UsePhotoRestoreFeatureProps {
|
|
|
18
13
|
onBeforeProcess?: () => Promise<boolean>;
|
|
19
14
|
}
|
|
20
15
|
|
|
21
|
-
export
|
|
22
|
-
/** Alert messages for error handling */
|
|
23
|
-
alertMessages?: AlertMessages;
|
|
24
|
-
/** User ID for credit operations */
|
|
25
|
-
userId?: string;
|
|
26
|
-
/** Callback when credits are exhausted */
|
|
27
|
-
onCreditsExhausted?: () => void;
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
export interface UsePhotoRestoreFeatureReturn extends BaseSingleImageHookReturn {}
|
|
31
|
-
|
|
32
|
-
export function usePhotoRestoreFeature(
|
|
33
|
-
props: UsePhotoRestoreFeatureProps,
|
|
34
|
-
options?: UsePhotoRestoreFeatureOptions,
|
|
35
|
-
): UsePhotoRestoreFeatureReturn {
|
|
16
|
+
export function usePhotoRestoreFeature(props: UsePhotoRestoreFeatureProps): BaseSingleImageHookReturn {
|
|
36
17
|
const { config, onSelectImage, onSaveImage, onBeforeProcess } = props;
|
|
37
18
|
|
|
38
|
-
|
|
39
|
-
return useSingleImageFeature(
|
|
19
|
+
return useSingleImageFeature<PhotoRestoreFeatureConfig, PhotoRestoreResult>(
|
|
40
20
|
{ config: config as never, onSelectImage, onSaveImage, onBeforeProcess },
|
|
41
|
-
{
|
|
42
|
-
buildInput: (imageBase64) => ({ imageBase64 }),
|
|
43
|
-
...options,
|
|
44
|
-
},
|
|
21
|
+
{ buildInput: (imageBase64) => ({ imageBase64 }) },
|
|
45
22
|
);
|
|
46
23
|
}
|
|
@@ -1,6 +1 @@
|
|
|
1
|
-
|
|
2
|
-
* Remove Background Presentation Hooks Index
|
|
3
|
-
*/
|
|
4
|
-
|
|
5
|
-
export { useRemoveBackgroundFeature } from "./useRemoveBackgroundFeature";
|
|
6
|
-
export type { UseRemoveBackgroundFeatureProps } from "./useRemoveBackgroundFeature";
|
|
1
|
+
export { useRemoveBackgroundFeature, type UseRemoveBackgroundFeatureProps } from "./useRemoveBackgroundFeature";
|
|
@@ -3,14 +3,8 @@
|
|
|
3
3
|
* Uses base single image hook for background removal
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
import {
|
|
7
|
-
|
|
8
|
-
type BaseSingleImageHookReturn,
|
|
9
|
-
} from "../../../image-to-image";
|
|
10
|
-
import type {
|
|
11
|
-
RemoveBackgroundFeatureConfig,
|
|
12
|
-
RemoveBackgroundResult,
|
|
13
|
-
} from "../../domain/types";
|
|
6
|
+
import { useSingleImageFeature, type BaseSingleImageHookReturn } from "../../../image-to-image";
|
|
7
|
+
import type { RemoveBackgroundFeatureConfig, RemoveBackgroundResult } from "../../domain/types";
|
|
14
8
|
|
|
15
9
|
export interface UseRemoveBackgroundFeatureProps {
|
|
16
10
|
config: RemoveBackgroundFeatureConfig;
|
|
@@ -19,13 +13,11 @@ export interface UseRemoveBackgroundFeatureProps {
|
|
|
19
13
|
onBeforeProcess?: () => Promise<boolean>;
|
|
20
14
|
}
|
|
21
15
|
|
|
22
|
-
export function useRemoveBackgroundFeature(
|
|
23
|
-
props: UseRemoveBackgroundFeatureProps,
|
|
24
|
-
): BaseSingleImageHookReturn {
|
|
16
|
+
export function useRemoveBackgroundFeature(props: UseRemoveBackgroundFeatureProps): BaseSingleImageHookReturn {
|
|
25
17
|
const { config, onSelectImage, onSaveImage, onBeforeProcess } = props;
|
|
26
18
|
|
|
27
19
|
return useSingleImageFeature<RemoveBackgroundFeatureConfig, RemoveBackgroundResult>(
|
|
28
|
-
{ config, onSelectImage, onSaveImage, onBeforeProcess },
|
|
20
|
+
{ config: config as never, onSelectImage, onSaveImage, onBeforeProcess },
|
|
29
21
|
{
|
|
30
22
|
buildInput: (imageBase64, cfg) => ({
|
|
31
23
|
imageBase64,
|
|
@@ -1,9 +1,15 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* useTextToVideoFeature Hook
|
|
3
|
-
*
|
|
3
|
+
* Uses centralized orchestrator for auth, credits, moderation, and error handling
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
6
|
import { useState, useCallback, useMemo } from "react";
|
|
7
|
+
import {
|
|
8
|
+
useGenerationOrchestrator,
|
|
9
|
+
type GenerationStrategy,
|
|
10
|
+
type AlertMessages,
|
|
11
|
+
} from "../../../../presentation/hooks/generation";
|
|
12
|
+
import { executeTextToVideo } from "../../infrastructure/services";
|
|
7
13
|
import type {
|
|
8
14
|
TextToVideoFeatureState,
|
|
9
15
|
TextToVideoConfig,
|
|
@@ -13,7 +19,6 @@ import type {
|
|
|
13
19
|
TextToVideoInputBuilder,
|
|
14
20
|
TextToVideoResultExtractor,
|
|
15
21
|
} from "../../domain/types";
|
|
16
|
-
import { executeVideoGeneration } from "./textToVideoExecution";
|
|
17
22
|
|
|
18
23
|
declare const __DEV__: boolean;
|
|
19
24
|
|
|
@@ -47,12 +52,126 @@ const INITIAL_STATE: TextToVideoFeatureState = {
|
|
|
47
52
|
error: null,
|
|
48
53
|
};
|
|
49
54
|
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
55
|
+
const DEFAULT_ALERT_MESSAGES: AlertMessages = {
|
|
56
|
+
networkError: "No internet connection. Please check your network.",
|
|
57
|
+
policyViolation: "Content not allowed. Please try again.",
|
|
58
|
+
saveFailed: "Failed to save. Please try again.",
|
|
59
|
+
creditFailed: "Credit operation failed. Please try again.",
|
|
60
|
+
unknown: "An error occurred. Please try again.",
|
|
61
|
+
};
|
|
62
|
+
|
|
63
|
+
interface VideoGenerationInput {
|
|
64
|
+
prompt: string;
|
|
65
|
+
options?: TextToVideoOptions;
|
|
66
|
+
creationId: string;
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
function generateCreationId(): string {
|
|
70
|
+
return `text-to-video_${Date.now()}_${Math.random().toString(36).slice(2, 8)}`;
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
export function useTextToVideoFeature(props: UseTextToVideoFeatureProps): UseTextToVideoFeatureReturn {
|
|
53
74
|
const { config, callbacks, userId, buildInput, extractResult } = props;
|
|
54
75
|
const [state, setState] = useState<TextToVideoFeatureState>(INITIAL_STATE);
|
|
55
76
|
|
|
77
|
+
// Strategy for orchestrator
|
|
78
|
+
const strategy: GenerationStrategy<VideoGenerationInput, TextToVideoResult> = useMemo(
|
|
79
|
+
() => ({
|
|
80
|
+
execute: async (input, onProgress) => {
|
|
81
|
+
if (typeof __DEV__ !== "undefined" && __DEV__) {
|
|
82
|
+
console.log("[TextToVideo] Executing generation:", input.prompt.slice(0, 100));
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
// Notify generation start
|
|
86
|
+
callbacks.onGenerationStart?.({
|
|
87
|
+
creationId: input.creationId,
|
|
88
|
+
type: "text-to-video",
|
|
89
|
+
prompt: input.prompt,
|
|
90
|
+
metadata: input.options as Record<string, unknown> | undefined,
|
|
91
|
+
}).catch(() => {});
|
|
92
|
+
|
|
93
|
+
const result = await executeTextToVideo(
|
|
94
|
+
{ prompt: input.prompt, userId, options: input.options },
|
|
95
|
+
{
|
|
96
|
+
model: config.model,
|
|
97
|
+
buildInput,
|
|
98
|
+
extractResult,
|
|
99
|
+
onProgress: (progress) => {
|
|
100
|
+
setState((prev) => ({ ...prev, progress }));
|
|
101
|
+
onProgress?.(progress);
|
|
102
|
+
callbacks.onProgress?.(progress);
|
|
103
|
+
},
|
|
104
|
+
},
|
|
105
|
+
);
|
|
106
|
+
|
|
107
|
+
if (!result.success || !result.videoUrl) {
|
|
108
|
+
throw new Error(result.error || "Generation failed");
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
// Update state with result
|
|
112
|
+
setState((prev) => ({
|
|
113
|
+
...prev,
|
|
114
|
+
videoUrl: result.videoUrl ?? null,
|
|
115
|
+
thumbnailUrl: result.thumbnailUrl ?? null,
|
|
116
|
+
}));
|
|
117
|
+
|
|
118
|
+
return result;
|
|
119
|
+
},
|
|
120
|
+
getCreditCost: () => config.creditCost,
|
|
121
|
+
save: async (result, uid) => {
|
|
122
|
+
if (result.success && result.videoUrl) {
|
|
123
|
+
await callbacks.onCreationSave?.({
|
|
124
|
+
creationId: generateCreationId(),
|
|
125
|
+
type: "text-to-video",
|
|
126
|
+
videoUrl: result.videoUrl,
|
|
127
|
+
thumbnailUrl: result.thumbnailUrl,
|
|
128
|
+
prompt: state.prompt,
|
|
129
|
+
});
|
|
130
|
+
}
|
|
131
|
+
},
|
|
132
|
+
}),
|
|
133
|
+
[config, callbacks, buildInput, extractResult, userId, state.prompt],
|
|
134
|
+
);
|
|
135
|
+
|
|
136
|
+
// Use orchestrator with optional callbacks for credits
|
|
137
|
+
const orchestrator = useGenerationOrchestrator(strategy, {
|
|
138
|
+
userId,
|
|
139
|
+
alertMessages: DEFAULT_ALERT_MESSAGES,
|
|
140
|
+
auth: callbacks.onAuthCheck
|
|
141
|
+
? { isAuthenticated: callbacks.onAuthCheck, onAuthRequired: () => {} }
|
|
142
|
+
: undefined,
|
|
143
|
+
credits: callbacks.onCreditCheck
|
|
144
|
+
? {
|
|
145
|
+
checkCredits: async (cost) => (await callbacks.onCreditCheck?.(cost)) ?? true,
|
|
146
|
+
deductCredits: async (cost) => { await callbacks.onCreditDeduct?.(cost); },
|
|
147
|
+
onCreditsExhausted: () => callbacks.onShowPaywall?.(config.creditCost),
|
|
148
|
+
}
|
|
149
|
+
: undefined,
|
|
150
|
+
moderation: callbacks.onModeration
|
|
151
|
+
? {
|
|
152
|
+
checkContent: async (input) => {
|
|
153
|
+
const result = await callbacks.onModeration!((input as VideoGenerationInput).prompt);
|
|
154
|
+
return result;
|
|
155
|
+
},
|
|
156
|
+
onShowWarning: callbacks.onShowModerationWarning,
|
|
157
|
+
}
|
|
158
|
+
: undefined,
|
|
159
|
+
onSuccess: (result) => {
|
|
160
|
+
const videoResult = result as TextToVideoResult;
|
|
161
|
+
if (typeof __DEV__ !== "undefined" && __DEV__) {
|
|
162
|
+
console.log("[TextToVideo] Success!", videoResult.videoUrl?.slice(0, 50));
|
|
163
|
+
}
|
|
164
|
+
callbacks.onGenerate?.(videoResult);
|
|
165
|
+
},
|
|
166
|
+
onError: (err) => {
|
|
167
|
+
if (typeof __DEV__ !== "undefined" && __DEV__) {
|
|
168
|
+
console.log("[TextToVideo] Error:", err.message);
|
|
169
|
+
}
|
|
170
|
+
setState((prev) => ({ ...prev, error: err.message }));
|
|
171
|
+
callbacks.onError?.(err.message);
|
|
172
|
+
},
|
|
173
|
+
});
|
|
174
|
+
|
|
56
175
|
const setPrompt = useCallback(
|
|
57
176
|
(prompt: string) => {
|
|
58
177
|
setState((prev) => ({ ...prev, prompt, error: null }));
|
|
@@ -70,9 +189,6 @@ export function useTextToVideoFeature(
|
|
|
70
189
|
const error = "Prompt is required";
|
|
71
190
|
setState((prev) => ({ ...prev, error }));
|
|
72
191
|
callbacks.onError?.(error);
|
|
73
|
-
if (__DEV__) {
|
|
74
|
-
console.log("[TextToVideoFeature] Generate failed: Prompt is required");
|
|
75
|
-
}
|
|
76
192
|
return { success: false, error };
|
|
77
193
|
}
|
|
78
194
|
|
|
@@ -80,74 +196,30 @@ export function useTextToVideoFeature(
|
|
|
80
196
|
setState((prev) => ({ ...prev, prompt: effectivePrompt }));
|
|
81
197
|
}
|
|
82
198
|
|
|
83
|
-
|
|
84
|
-
if (__DEV__) {
|
|
85
|
-
console.log("[TextToVideoFeature] Generate failed: Authentication required");
|
|
86
|
-
}
|
|
87
|
-
return { success: false, error: "Authentication required" };
|
|
88
|
-
}
|
|
199
|
+
setState((prev) => ({ ...prev, isProcessing: true, progress: 0, error: null }));
|
|
89
200
|
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
!(await callbacks.onCreditCheck(config.creditCost))
|
|
93
|
-
) {
|
|
94
|
-
callbacks.onShowPaywall?.(config.creditCost);
|
|
95
|
-
if (__DEV__) {
|
|
96
|
-
console.log("[TextToVideoFeature] Generate failed: Insufficient credits");
|
|
97
|
-
}
|
|
98
|
-
return { success: false, error: "Insufficient credits" };
|
|
99
|
-
}
|
|
201
|
+
const creationId = generateCreationId();
|
|
202
|
+
await orchestrator.generate({ prompt: effectivePrompt, options, creationId });
|
|
100
203
|
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
moderationResult.warnings,
|
|
107
|
-
() => {
|
|
108
|
-
setState((prev) => ({ ...prev, isProcessing: false }));
|
|
109
|
-
resolve({ success: false, error: "Content policy violation" });
|
|
110
|
-
},
|
|
111
|
-
async () => {
|
|
112
|
-
const result = await executeVideoGeneration(
|
|
113
|
-
effectivePrompt,
|
|
114
|
-
options,
|
|
115
|
-
{ userId, config, callbacks, buildInput, extractResult },
|
|
116
|
-
{
|
|
117
|
-
onStateUpdate: (update) =>
|
|
118
|
-
setState((prev) => ({ ...prev, ...update })),
|
|
119
|
-
},
|
|
120
|
-
);
|
|
121
|
-
resolve(result);
|
|
122
|
-
},
|
|
123
|
-
);
|
|
124
|
-
});
|
|
125
|
-
}
|
|
204
|
+
setState((prev) => ({ ...prev, isProcessing: false }));
|
|
205
|
+
|
|
206
|
+
// Return result based on state
|
|
207
|
+
if (orchestrator.error) {
|
|
208
|
+
return { success: false, error: orchestrator.error.message };
|
|
126
209
|
}
|
|
127
210
|
|
|
128
|
-
return
|
|
129
|
-
effectivePrompt,
|
|
130
|
-
options,
|
|
131
|
-
{ userId, config, callbacks, buildInput, extractResult },
|
|
132
|
-
{ onStateUpdate: (update) => setState((prev) => ({ ...prev, ...update })) },
|
|
133
|
-
);
|
|
211
|
+
return orchestrator.result || { success: false, error: "No result" };
|
|
134
212
|
},
|
|
135
|
-
[state.prompt, callbacks,
|
|
213
|
+
[state.prompt, callbacks, orchestrator],
|
|
136
214
|
);
|
|
137
215
|
|
|
138
216
|
const reset = useCallback(() => {
|
|
139
217
|
setState(INITIAL_STATE);
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
const isReady = useMemo(
|
|
143
|
-
() => state.prompt.trim().length > 0 && !state.isProcessing,
|
|
144
|
-
[state.prompt, state.isProcessing],
|
|
145
|
-
);
|
|
218
|
+
orchestrator.reset();
|
|
219
|
+
}, [orchestrator]);
|
|
146
220
|
|
|
147
|
-
const
|
|
148
|
-
|
|
149
|
-
[isReady, state.error],
|
|
150
|
-
);
|
|
221
|
+
const isReady = useMemo(() => state.prompt.trim().length > 0 && !state.isProcessing, [state.prompt, state.isProcessing]);
|
|
222
|
+
const canGenerate = useMemo(() => isReady && !state.error, [isReady, state.error]);
|
|
151
223
|
|
|
152
224
|
return { state, setPrompt, generate, reset, isReady, canGenerate };
|
|
153
225
|
}
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
export { useUpscaleFeature } from "./useUpscaleFeature";
|
|
2
|
-
export type { UseUpscaleFeatureProps } from "./useUpscaleFeature";
|
|
1
|
+
export { useUpscaleFeature, type UseUpscaleFeatureProps } from "./useUpscaleFeature";
|
|
@@ -1,12 +1,9 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* useUpscaleFeature Hook
|
|
3
|
-
* Uses base single image hook
|
|
3
|
+
* Uses base single image hook for image upscaling
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
import {
|
|
7
|
-
useSingleImageFeature,
|
|
8
|
-
type BaseSingleImageHookReturn,
|
|
9
|
-
} from "../../../image-to-image";
|
|
6
|
+
import { useSingleImageFeature, type BaseSingleImageHookReturn } from "../../../image-to-image";
|
|
10
7
|
import type { UpscaleFeatureConfig, UpscaleResult } from "../../domain/types";
|
|
11
8
|
|
|
12
9
|
export interface UseUpscaleFeatureProps {
|
|
@@ -16,13 +13,11 @@ export interface UseUpscaleFeatureProps {
|
|
|
16
13
|
onBeforeProcess?: () => Promise<boolean>;
|
|
17
14
|
}
|
|
18
15
|
|
|
19
|
-
export function useUpscaleFeature(
|
|
20
|
-
props: UseUpscaleFeatureProps,
|
|
21
|
-
): BaseSingleImageHookReturn {
|
|
16
|
+
export function useUpscaleFeature(props: UseUpscaleFeatureProps): BaseSingleImageHookReturn {
|
|
22
17
|
const { config, onSelectImage, onSaveImage, onBeforeProcess } = props;
|
|
23
18
|
|
|
24
19
|
return useSingleImageFeature<UpscaleFeatureConfig, UpscaleResult>(
|
|
25
|
-
{ config, onSelectImage, onSaveImage, onBeforeProcess },
|
|
20
|
+
{ config: config as never, onSelectImage, onSaveImage, onBeforeProcess },
|
|
26
21
|
{
|
|
27
22
|
buildInput: (imageBase64, cfg) => ({
|
|
28
23
|
imageBase64,
|
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* useImageToVideoFeature Constants
|
|
3
|
-
*/
|
|
4
|
-
|
|
5
|
-
import type { ImageToVideoFeatureState } from "../../domain/types";
|
|
6
|
-
|
|
7
|
-
export const INITIAL_IMAGE_TO_VIDEO_STATE: ImageToVideoFeatureState = {
|
|
8
|
-
imageUri: null,
|
|
9
|
-
motionPrompt: "",
|
|
10
|
-
videoUrl: null,
|
|
11
|
-
thumbnailUrl: null,
|
|
12
|
-
isProcessing: false,
|
|
13
|
-
progress: 0,
|
|
14
|
-
error: null,
|
|
15
|
-
};
|
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* useImageToVideoFeature Type Definitions
|
|
3
|
-
*/
|
|
4
|
-
|
|
5
|
-
import type {
|
|
6
|
-
ImageToVideoFeatureState,
|
|
7
|
-
ImageToVideoFeatureConfig,
|
|
8
|
-
ImageToVideoResult,
|
|
9
|
-
ImageToVideoFeatureCallbacks,
|
|
10
|
-
ImageToVideoGenerateParams,
|
|
11
|
-
} from "../../domain/types";
|
|
12
|
-
|
|
13
|
-
export interface UseImageToVideoFeatureProps {
|
|
14
|
-
config: ImageToVideoFeatureConfig;
|
|
15
|
-
callbacks?: ImageToVideoFeatureCallbacks;
|
|
16
|
-
userId: string;
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
export interface UseImageToVideoFeatureReturn {
|
|
20
|
-
state: ImageToVideoFeatureState;
|
|
21
|
-
setImageUri: (uri: string) => void;
|
|
22
|
-
setMotionPrompt: (prompt: string) => void;
|
|
23
|
-
generate: (params?: ImageToVideoGenerateParams) => Promise<ImageToVideoResult>;
|
|
24
|
-
reset: () => void;
|
|
25
|
-
isReady: boolean;
|
|
26
|
-
canGenerate: boolean;
|
|
27
|
-
}
|
|
@@ -1,134 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Text-to-Video Execution
|
|
3
|
-
* Core execution logic for text-to-video generation
|
|
4
|
-
*/
|
|
5
|
-
|
|
6
|
-
import { executeTextToVideo } from "../../infrastructure/services";
|
|
7
|
-
import type {
|
|
8
|
-
TextToVideoConfig,
|
|
9
|
-
TextToVideoCallbacks,
|
|
10
|
-
TextToVideoResult,
|
|
11
|
-
TextToVideoOptions,
|
|
12
|
-
TextToVideoInputBuilder,
|
|
13
|
-
TextToVideoResultExtractor,
|
|
14
|
-
} from "../../domain/types";
|
|
15
|
-
|
|
16
|
-
declare const __DEV__: boolean;
|
|
17
|
-
|
|
18
|
-
export interface ExecutionContext {
|
|
19
|
-
userId: string;
|
|
20
|
-
config: TextToVideoConfig;
|
|
21
|
-
callbacks: TextToVideoCallbacks;
|
|
22
|
-
buildInput: TextToVideoInputBuilder;
|
|
23
|
-
extractResult?: TextToVideoResultExtractor;
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
export interface ExecutionCallbacks {
|
|
27
|
-
onStateUpdate: (update: {
|
|
28
|
-
isProcessing?: boolean;
|
|
29
|
-
progress?: number;
|
|
30
|
-
videoUrl?: string | null;
|
|
31
|
-
thumbnailUrl?: string | null;
|
|
32
|
-
error?: string | null;
|
|
33
|
-
}) => void;
|
|
34
|
-
}
|
|
35
|
-
|
|
36
|
-
function generateCreationId(): string {
|
|
37
|
-
return `text-to-video_${Date.now()}_${Math.random().toString(36).slice(2, 8)}`;
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
export async function executeVideoGeneration(
|
|
41
|
-
prompt: string,
|
|
42
|
-
options: TextToVideoOptions | undefined,
|
|
43
|
-
context: ExecutionContext,
|
|
44
|
-
executionCallbacks: ExecutionCallbacks,
|
|
45
|
-
): Promise<TextToVideoResult> {
|
|
46
|
-
const { userId, config, callbacks, buildInput, extractResult } = context;
|
|
47
|
-
const { onStateUpdate } = executionCallbacks;
|
|
48
|
-
const creationId = generateCreationId();
|
|
49
|
-
|
|
50
|
-
onStateUpdate({ isProcessing: true, progress: 0, error: null });
|
|
51
|
-
|
|
52
|
-
if (__DEV__) {
|
|
53
|
-
console.log(
|
|
54
|
-
"[TextToVideoFeature] Starting generation with prompt:",
|
|
55
|
-
prompt,
|
|
56
|
-
"creationId:",
|
|
57
|
-
creationId,
|
|
58
|
-
);
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
if (callbacks.onGenerationStart) {
|
|
62
|
-
callbacks
|
|
63
|
-
.onGenerationStart({
|
|
64
|
-
creationId,
|
|
65
|
-
type: "text-to-video",
|
|
66
|
-
prompt,
|
|
67
|
-
metadata: options as Record<string, unknown> | undefined,
|
|
68
|
-
})
|
|
69
|
-
.catch((err) => {
|
|
70
|
-
if (__DEV__) {
|
|
71
|
-
console.warn("[TextToVideoFeature] onGenerationStart failed:", err);
|
|
72
|
-
}
|
|
73
|
-
});
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
if (__DEV__) {
|
|
77
|
-
console.log("[TextToVideoFeature] Starting executeTextToVideo...");
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
try {
|
|
81
|
-
const result = await executeTextToVideo(
|
|
82
|
-
{ prompt, userId, options },
|
|
83
|
-
{
|
|
84
|
-
model: config.model,
|
|
85
|
-
buildInput,
|
|
86
|
-
extractResult,
|
|
87
|
-
onProgress: (progress) => {
|
|
88
|
-
onStateUpdate({ progress });
|
|
89
|
-
callbacks.onProgress?.(progress);
|
|
90
|
-
},
|
|
91
|
-
},
|
|
92
|
-
);
|
|
93
|
-
|
|
94
|
-
if (result.success && result.videoUrl) {
|
|
95
|
-
onStateUpdate({
|
|
96
|
-
videoUrl: result.videoUrl,
|
|
97
|
-
thumbnailUrl: result.thumbnailUrl ?? null,
|
|
98
|
-
isProcessing: false,
|
|
99
|
-
progress: 100,
|
|
100
|
-
});
|
|
101
|
-
|
|
102
|
-
if (callbacks.onCreditDeduct) {
|
|
103
|
-
await callbacks.onCreditDeduct(config.creditCost);
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
if (callbacks.onCreationSave) {
|
|
107
|
-
await callbacks.onCreationSave({
|
|
108
|
-
creationId,
|
|
109
|
-
type: "text-to-video",
|
|
110
|
-
videoUrl: result.videoUrl,
|
|
111
|
-
thumbnailUrl: result.thumbnailUrl,
|
|
112
|
-
prompt,
|
|
113
|
-
metadata: options as Record<string, unknown> | undefined,
|
|
114
|
-
});
|
|
115
|
-
}
|
|
116
|
-
|
|
117
|
-
callbacks.onGenerate?.(result);
|
|
118
|
-
} else {
|
|
119
|
-
const error = result.error || "Generation failed";
|
|
120
|
-
onStateUpdate({ isProcessing: false, error });
|
|
121
|
-
callbacks.onError?.(error);
|
|
122
|
-
}
|
|
123
|
-
|
|
124
|
-
return result;
|
|
125
|
-
} catch (err) {
|
|
126
|
-
const errorMessage = err instanceof Error ? err.message : String(err);
|
|
127
|
-
if (__DEV__) {
|
|
128
|
-
console.error("[TextToVideoFeature] Generation error:", errorMessage);
|
|
129
|
-
}
|
|
130
|
-
onStateUpdate({ isProcessing: false, error: errorMessage });
|
|
131
|
-
callbacks.onError?.(errorMessage);
|
|
132
|
-
return { success: false, error: errorMessage };
|
|
133
|
-
}
|
|
134
|
-
}
|