@umituz/react-native-design-system 1.3.6 → 1.4.0
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/README.md +1 -2
- package/lib/domains/icons/presentation/components/Icon.d.ts.map +1 -1
- package/lib/domains/icons/presentation/components/Icon.js.map +1 -1
- package/lib/index.d.ts +2 -6
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +2 -9
- package/lib/index.js.map +1 -1
- package/lib/presentation/atoms/AtomicBadge.js.map +1 -1
- package/lib/presentation/atoms/AtomicButton.d.ts +0 -1
- package/lib/presentation/atoms/AtomicButton.d.ts.map +1 -1
- package/lib/presentation/atoms/AtomicButton.js +6 -9
- package/lib/presentation/atoms/AtomicButton.js.map +1 -1
- package/lib/presentation/atoms/AtomicDatePicker.js +1 -1
- package/lib/presentation/atoms/AtomicDatePicker.js.map +1 -1
- package/lib/presentation/atoms/AtomicFab.d.ts +0 -1
- package/lib/presentation/atoms/AtomicFab.d.ts.map +1 -1
- package/lib/presentation/atoms/AtomicFab.js +4 -5
- package/lib/presentation/atoms/AtomicFab.js.map +1 -1
- package/lib/presentation/atoms/AtomicImage.js.map +1 -1
- package/lib/presentation/atoms/AtomicPicker.js +1 -1
- package/lib/presentation/atoms/AtomicPicker.js.map +1 -1
- package/lib/presentation/atoms/AtomicProgress.d.ts +0 -3
- package/lib/presentation/atoms/AtomicProgress.d.ts.map +1 -1
- package/lib/presentation/atoms/AtomicProgress.js +1 -2
- package/lib/presentation/atoms/AtomicProgress.js.map +1 -1
- package/lib/presentation/atoms/AtomicSkeleton.d.ts +4 -10
- package/lib/presentation/atoms/AtomicSkeleton.d.ts.map +1 -1
- package/lib/presentation/atoms/AtomicSkeleton.js +7 -38
- package/lib/presentation/atoms/AtomicSkeleton.js.map +1 -1
- package/lib/presentation/atoms/AtomicSwitch.js.map +1 -1
- package/lib/presentation/atoms/AtomicTouchable.d.ts +1 -11
- package/lib/presentation/atoms/AtomicTouchable.d.ts.map +1 -1
- package/lib/presentation/atoms/AtomicTouchable.js +6 -19
- package/lib/presentation/atoms/AtomicTouchable.js.map +1 -1
- package/lib/presentation/atoms/fab/types/index.d.ts +0 -5
- package/lib/presentation/atoms/fab/types/index.d.ts.map +1 -1
- package/lib/presentation/atoms/touchable/styles/touchableStyles.d.ts +0 -5
- package/lib/presentation/atoms/touchable/styles/touchableStyles.d.ts.map +1 -1
- package/lib/presentation/atoms/touchable/styles/touchableStyles.js +0 -8
- package/lib/presentation/atoms/touchable/styles/touchableStyles.js.map +1 -1
- package/lib/presentation/atoms/touchable/types/index.d.ts +1 -7
- package/lib/presentation/atoms/touchable/types/index.d.ts.map +1 -1
- package/lib/presentation/molecules/AtomicConfirmationModal.d.ts.map +1 -1
- package/lib/presentation/molecules/AtomicConfirmationModal.js +2 -1
- package/lib/presentation/molecules/AtomicConfirmationModal.js.map +1 -1
- package/lib/presentation/molecules/languageswitcher/hooks/useLanguageNavigation.d.ts +1 -1
- package/lib/presentation/molecules/languageswitcher/hooks/useLanguageNavigation.d.ts.map +1 -1
- package/lib/presentation/molecules/languageswitcher/hooks/useLanguageNavigation.js +2 -0
- package/lib/presentation/molecules/languageswitcher/hooks/useLanguageNavigation.js.map +1 -1
- package/lib/presentation/organisms/ScreenLayout.d.ts +0 -15
- package/lib/presentation/organisms/ScreenLayout.d.ts.map +1 -1
- package/lib/presentation/organisms/ScreenLayout.js +1 -10
- package/lib/presentation/organisms/ScreenLayout.js.map +1 -1
- package/lib/presentation/tokens/AppDesignTokens.d.ts +1 -1
- package/lib/presentation/tokens/AppDesignTokens.d.ts.map +1 -1
- package/lib/presentation/tokens/AppDesignTokens.js +1 -1
- package/lib/presentation/tokens/AppDesignTokens.js.map +1 -1
- package/lib/presentation/tokens/commonStyles.d.ts +1 -1
- package/lib/presentation/tokens/commonStyles.js +1 -1
- package/lib/presentation/tokens/core/BaseTokens.d.ts +0 -25
- package/lib/presentation/tokens/core/BaseTokens.d.ts.map +1 -1
- package/lib/presentation/tokens/core/BaseTokens.js +0 -18
- package/lib/presentation/tokens/core/BaseTokens.js.map +1 -1
- package/lib/presentation/tokens/core/TokenFactory.d.ts +2 -15
- package/lib/presentation/tokens/core/TokenFactory.d.ts.map +1 -1
- package/lib/presentation/tokens/core/TokenFactory.js +1 -2
- package/lib/presentation/tokens/core/TokenFactory.js.map +1 -1
- package/package.json +1 -3
- package/src/domains/icons/presentation/components/Icon.tsx +3 -3
- package/src/index.ts +1 -27
- package/src/presentation/atoms/AtomicBadge.tsx +3 -3
- package/src/presentation/atoms/AtomicButton.tsx +5 -16
- package/src/presentation/atoms/AtomicDatePicker.tsx +1 -1
- package/src/presentation/atoms/AtomicFab.tsx +6 -12
- package/src/presentation/atoms/AtomicImage.tsx +2 -2
- package/src/presentation/atoms/AtomicPicker.tsx +1 -1
- package/src/presentation/atoms/AtomicProgress.tsx +0 -4
- package/src/presentation/atoms/AtomicSkeleton.tsx +6 -57
- package/src/presentation/atoms/AtomicSwitch.tsx +2 -2
- package/src/presentation/atoms/AtomicTouchable.tsx +4 -28
- package/src/presentation/atoms/fab/types/index.ts +0 -6
- package/src/presentation/atoms/touchable/styles/touchableStyles.ts +0 -9
- package/src/presentation/atoms/touchable/types/index.ts +1 -8
- package/src/presentation/molecules/AtomicConfirmationModal.tsx +3 -2
- package/src/presentation/molecules/languageswitcher/hooks/useLanguageNavigation.ts +2 -0
- package/src/presentation/organisms/ScreenLayout.tsx +0 -40
- package/src/presentation/tokens/AppDesignTokens.ts +0 -2
- package/src/presentation/tokens/commonStyles.ts +1 -1
- package/src/presentation/tokens/core/BaseTokens.ts +0 -22
- package/src/presentation/tokens/core/TokenFactory.ts +2 -4
- package/lib/presentation/loading/index.d.ts +0 -23
- package/lib/presentation/loading/index.d.ts.map +0 -1
- package/lib/presentation/loading/index.js +0 -26
- package/lib/presentation/loading/index.js.map +0 -1
- package/lib/presentation/loading/presentation/components/LoadingSpinner.d.ts +0 -28
- package/lib/presentation/loading/presentation/components/LoadingSpinner.d.ts.map +0 -1
- package/lib/presentation/loading/presentation/components/LoadingSpinner.js +0 -77
- package/lib/presentation/loading/presentation/components/LoadingSpinner.js.map +0 -1
- package/lib/presentation/loading/presentation/components/LoadingState.d.ts +0 -39
- package/lib/presentation/loading/presentation/components/LoadingState.d.ts.map +0 -1
- package/lib/presentation/loading/presentation/components/LoadingState.js +0 -123
- package/lib/presentation/loading/presentation/components/LoadingState.js.map +0 -1
- package/lib/presentation/loading/presentation/hooks/useLoading.d.ts +0 -50
- package/lib/presentation/loading/presentation/hooks/useLoading.d.ts.map +0 -1
- package/lib/presentation/loading/presentation/hooks/useLoading.js +0 -49
- package/lib/presentation/loading/presentation/hooks/useLoading.js.map +0 -1
- package/src/presentation/loading/index.ts +0 -40
- package/src/presentation/loading/presentation/components/LoadingSpinner.tsx +0 -116
- package/src/presentation/loading/presentation/components/LoadingState.tsx +0 -200
- package/src/presentation/loading/presentation/hooks/useLoading.ts +0 -100
|
@@ -1,49 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* useLoading - Loading State Management Hook
|
|
3
|
-
*
|
|
4
|
-
* Centralized hook for managing loading states across the application
|
|
5
|
-
* Theme: {{THEME_NAME}} ({{CATEGORY}} category)
|
|
6
|
-
*
|
|
7
|
-
* Features:
|
|
8
|
-
* - ✅ Simple boolean loading state
|
|
9
|
-
* - ✅ Message management
|
|
10
|
-
* - ✅ Icon configuration per context
|
|
11
|
-
* - ✅ Type-safe loading control
|
|
12
|
-
*/
|
|
13
|
-
import { useState, useCallback } from 'react';
|
|
14
|
-
// =============================================================================
|
|
15
|
-
// HOOK IMPLEMENTATION
|
|
16
|
-
// =============================================================================
|
|
17
|
-
export const useLoading = (initialConfig) => {
|
|
18
|
-
const [isLoading, setIsLoading] = useState(initialConfig?.isLoading ?? false);
|
|
19
|
-
const [message, setMessage] = useState(initialConfig?.message);
|
|
20
|
-
const [icon, setIcon] = useState(initialConfig?.icon);
|
|
21
|
-
/**
|
|
22
|
-
* Start loading with optional message and icon
|
|
23
|
-
*/
|
|
24
|
-
const startLoading = useCallback((msg, ico) => {
|
|
25
|
-
setIsLoading(true);
|
|
26
|
-
if (msg !== undefined)
|
|
27
|
-
setMessage(msg);
|
|
28
|
-
if (ico !== undefined)
|
|
29
|
-
setIcon(ico);
|
|
30
|
-
}, []);
|
|
31
|
-
/**
|
|
32
|
-
* Stop loading and clear message
|
|
33
|
-
*/
|
|
34
|
-
const stopLoading = useCallback(() => {
|
|
35
|
-
setIsLoading(false);
|
|
36
|
-
setMessage(undefined);
|
|
37
|
-
}, []);
|
|
38
|
-
return {
|
|
39
|
-
isLoading,
|
|
40
|
-
message,
|
|
41
|
-
icon,
|
|
42
|
-
startLoading,
|
|
43
|
-
stopLoading,
|
|
44
|
-
setMessage,
|
|
45
|
-
setIcon,
|
|
46
|
-
};
|
|
47
|
-
};
|
|
48
|
-
export default useLoading;
|
|
49
|
-
//# sourceMappingURL=useLoading.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"useLoading.js","sourceRoot":"","sources":["../../../../../src/presentation/loading/presentation/hooks/useLoading.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,OAAO,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,OAAO,CAAC;AAiD9C,gFAAgF;AAChF,sBAAsB;AACtB,gFAAgF;AAEhF,MAAM,CAAC,MAAM,UAAU,GAAG,CAAC,aAA6B,EAAoB,EAAE;IAC5E,MAAM,CAAC,SAAS,EAAE,YAAY,CAAC,GAAG,QAAQ,CAAC,aAAa,EAAE,SAAS,IAAI,KAAK,CAAC,CAAC;IAC9E,MAAM,CAAC,OAAO,EAAE,UAAU,CAAC,GAAG,QAAQ,CAAqB,aAAa,EAAE,OAAO,CAAC,CAAC;IACnF,MAAM,CAAC,IAAI,EAAE,OAAO,CAAC,GAAG,QAAQ,CAAqB,aAAa,EAAE,IAAI,CAAC,CAAC;IAE1E;;OAEG;IACH,MAAM,YAAY,GAAG,WAAW,CAAC,CAAC,GAAY,EAAE,GAAY,EAAE,EAAE;QAC9D,YAAY,CAAC,IAAI,CAAC,CAAC;QACnB,IAAI,GAAG,KAAK,SAAS;YAAE,UAAU,CAAC,GAAG,CAAC,CAAC;QACvC,IAAI,GAAG,KAAK,SAAS;YAAE,OAAO,CAAC,GAAG,CAAC,CAAC;IACtC,CAAC,EAAE,EAAE,CAAC,CAAC;IAEP;;OAEG;IACH,MAAM,WAAW,GAAG,WAAW,CAAC,GAAG,EAAE;QACnC,YAAY,CAAC,KAAK,CAAC,CAAC;QACpB,UAAU,CAAC,SAAS,CAAC,CAAC;IACxB,CAAC,EAAE,EAAE,CAAC,CAAC;IAEP,OAAO;QACL,SAAS;QACT,OAAO;QACP,IAAI;QACJ,YAAY;QACZ,WAAW;QACX,UAAU;QACV,OAAO;KACR,CAAC;AACJ,CAAC,CAAC;AAEF,eAAe,UAAU,CAAC"}
|
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Loading Domain - Public API
|
|
3
|
-
*
|
|
4
|
-
* Domain-Driven Design (DDD) Architecture
|
|
5
|
-
* Theme: {{THEME_NAME}} ({{CATEGORY}} category)
|
|
6
|
-
*
|
|
7
|
-
* This is the SINGLE SOURCE OF TRUTH for the Loading domain.
|
|
8
|
-
* ALL imports from this domain MUST go through this file.
|
|
9
|
-
*
|
|
10
|
-
* Architecture:
|
|
11
|
-
* - presentation/components: UI components (LoadingState, LoadingSpinner)
|
|
12
|
-
* - presentation/hooks: React hooks (useLoading)
|
|
13
|
-
*
|
|
14
|
-
* Usage:
|
|
15
|
-
* import { LoadingState, LoadingSpinner, useLoading } from '@domains/design-system';
|
|
16
|
-
*/
|
|
17
|
-
|
|
18
|
-
// =============================================================================
|
|
19
|
-
// PRESENTATION LAYER - Components
|
|
20
|
-
// =============================================================================
|
|
21
|
-
|
|
22
|
-
export { LoadingState } from './presentation/components/LoadingState';
|
|
23
|
-
export type { LoadingStateProps, LoadingStateSize } from './presentation/components/LoadingState';
|
|
24
|
-
|
|
25
|
-
export { LoadingSpinner } from './presentation/components/LoadingSpinner';
|
|
26
|
-
export type {
|
|
27
|
-
LoadingSpinnerProps,
|
|
28
|
-
LoadingSpinnerSize,
|
|
29
|
-
LoadingSpinnerColor,
|
|
30
|
-
} from './presentation/components/LoadingSpinner';
|
|
31
|
-
|
|
32
|
-
// =============================================================================
|
|
33
|
-
// PRESENTATION LAYER - Hooks
|
|
34
|
-
// =============================================================================
|
|
35
|
-
|
|
36
|
-
export { useLoading } from './presentation/hooks/useLoading';
|
|
37
|
-
export type {
|
|
38
|
-
LoadingConfig,
|
|
39
|
-
UseLoadingReturn,
|
|
40
|
-
} from './presentation/hooks/useLoading';
|
|
@@ -1,116 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* LoadingSpinner - Theme-Aware Activity Indicator
|
|
3
|
-
*
|
|
4
|
-
* Refactored from AtomicLoadingSpinner - now part of Loading domain
|
|
5
|
-
* Uses central useAppDesignTokens() hook for automatic theme switching
|
|
6
|
-
* Theme: {{THEME_NAME}} ({{CATEGORY}} category)
|
|
7
|
-
*
|
|
8
|
-
* Features:
|
|
9
|
-
* - ✅ AUTOMATIC theme switching via useAppDesignTokens()
|
|
10
|
-
* - ✅ Multiple size variants (small, medium, large)
|
|
11
|
-
* - ✅ Dynamic color customization
|
|
12
|
-
* - ✅ Overlay support
|
|
13
|
-
* - ✅ Message display
|
|
14
|
-
*/
|
|
15
|
-
|
|
16
|
-
import React from 'react';
|
|
17
|
-
import { View, ActivityIndicator, ViewStyle } from 'react-native';
|
|
18
|
-
import { useAppDesignTokens } from '../../../hooks/useAppDesignTokens';
|
|
19
|
-
import { withAlpha } from '../../../tokens/AppDesignTokens';
|
|
20
|
-
import { AtomicText } from '../../../atoms/AtomicText';
|
|
21
|
-
|
|
22
|
-
// =============================================================================
|
|
23
|
-
// TYPE DEFINITIONS
|
|
24
|
-
// =============================================================================
|
|
25
|
-
|
|
26
|
-
export type LoadingSpinnerSize = 'small' | 'medium' | 'large';
|
|
27
|
-
export type LoadingSpinnerColor = 'primary' | 'secondary' | 'white';
|
|
28
|
-
|
|
29
|
-
export interface LoadingSpinnerProps {
|
|
30
|
-
size?: LoadingSpinnerSize;
|
|
31
|
-
color?: LoadingSpinnerColor;
|
|
32
|
-
message?: string;
|
|
33
|
-
overlay?: boolean;
|
|
34
|
-
style?: ViewStyle;
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
// =============================================================================
|
|
38
|
-
// SIZE VARIANTS
|
|
39
|
-
// =============================================================================
|
|
40
|
-
|
|
41
|
-
const sizeVariants: Record<LoadingSpinnerSize, 'small' | 'large'> = {
|
|
42
|
-
small: 'small',
|
|
43
|
-
medium: 'large',
|
|
44
|
-
large: 'large',
|
|
45
|
-
};
|
|
46
|
-
|
|
47
|
-
// =============================================================================
|
|
48
|
-
// COMPONENT IMPLEMENTATION
|
|
49
|
-
// =============================================================================
|
|
50
|
-
|
|
51
|
-
export const LoadingSpinner: React.FC<LoadingSpinnerProps> = ({
|
|
52
|
-
size = 'medium',
|
|
53
|
-
color = 'primary',
|
|
54
|
-
message,
|
|
55
|
-
overlay = false,
|
|
56
|
-
style,
|
|
57
|
-
}) => {
|
|
58
|
-
// ✅ DYNAMIC tokens from central hook
|
|
59
|
-
const tokens = useAppDesignTokens();
|
|
60
|
-
|
|
61
|
-
const spinnerSize = sizeVariants[size];
|
|
62
|
-
|
|
63
|
-
/**
|
|
64
|
-
* Get spinner color from dynamic theme
|
|
65
|
-
* ✅ Automatically updates when theme changes
|
|
66
|
-
*/
|
|
67
|
-
const getSpinnerColor = (): string => {
|
|
68
|
-
switch (color) {
|
|
69
|
-
case 'primary':
|
|
70
|
-
return tokens.colors.primary;
|
|
71
|
-
case 'secondary':
|
|
72
|
-
return tokens.colors.secondary;
|
|
73
|
-
case 'white':
|
|
74
|
-
return tokens.colors.textInverse;
|
|
75
|
-
default:
|
|
76
|
-
return tokens.colors.primary;
|
|
77
|
-
}
|
|
78
|
-
};
|
|
79
|
-
|
|
80
|
-
const spinnerColor = getSpinnerColor();
|
|
81
|
-
|
|
82
|
-
const containerStyle: ViewStyle = overlay
|
|
83
|
-
? {
|
|
84
|
-
position: 'absolute',
|
|
85
|
-
top: 0,
|
|
86
|
-
left: 0,
|
|
87
|
-
right: 0,
|
|
88
|
-
bottom: 0,
|
|
89
|
-
backgroundColor: withAlpha(tokens.colors.black, 0.5),
|
|
90
|
-
justifyContent: 'center',
|
|
91
|
-
alignItems: 'center',
|
|
92
|
-
zIndex: 9999,
|
|
93
|
-
}
|
|
94
|
-
: {
|
|
95
|
-
justifyContent: 'center',
|
|
96
|
-
alignItems: 'center',
|
|
97
|
-
padding: tokens.spacing.lg,
|
|
98
|
-
};
|
|
99
|
-
|
|
100
|
-
return (
|
|
101
|
-
<View style={[containerStyle, style]}>
|
|
102
|
-
<ActivityIndicator size={spinnerSize} color={spinnerColor} />
|
|
103
|
-
{message && (
|
|
104
|
-
<AtomicText
|
|
105
|
-
type="bodyMedium"
|
|
106
|
-
color={overlay ? 'inverse' : 'primary'}
|
|
107
|
-
style={{ marginTop: tokens.spacing.md, textAlign: 'center' }}
|
|
108
|
-
>
|
|
109
|
-
{message}
|
|
110
|
-
</AtomicText>
|
|
111
|
-
)}
|
|
112
|
-
</View>
|
|
113
|
-
);
|
|
114
|
-
};
|
|
115
|
-
|
|
116
|
-
export default LoadingSpinner;
|
|
@@ -1,200 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* LoadingState - Dynamic Icon-Based Loading Component
|
|
3
|
-
*
|
|
4
|
-
* Universal loading component with configurable emoji/icon support
|
|
5
|
-
* Inspired by meditation_timer's breathing animation pattern
|
|
6
|
-
* Theme: {{THEME_NAME}} ({{CATEGORY}} category)
|
|
7
|
-
*
|
|
8
|
-
* Features:
|
|
9
|
-
* - ✅ Dynamic emoji/icon per screen (🏠 Home, ⚙️ Settings, 💪 Workout, etc.)
|
|
10
|
-
* - ✅ Breathing animation effect (scale 1 → 1.15 → 1)
|
|
11
|
-
* - ✅ Size variants (small, medium, large)
|
|
12
|
-
* - ✅ Full screen or inline modes
|
|
13
|
-
* - ✅ Optional loading message
|
|
14
|
-
* - ✅ Theme-aware styling
|
|
15
|
-
*/
|
|
16
|
-
|
|
17
|
-
import React, { useRef, useEffect, useMemo } from 'react';
|
|
18
|
-
import {
|
|
19
|
-
View,
|
|
20
|
-
StyleSheet,
|
|
21
|
-
Animated,
|
|
22
|
-
Easing,
|
|
23
|
-
} from 'react-native';
|
|
24
|
-
import { useAppDesignTokens } from '../../../hooks/useAppDesignTokens';
|
|
25
|
-
import { STATIC_TOKENS } from '../../../tokens/AppDesignTokens';
|
|
26
|
-
import { AtomicText } from '../../../atoms/AtomicText';
|
|
27
|
-
|
|
28
|
-
// =============================================================================
|
|
29
|
-
// TYPE DEFINITIONS
|
|
30
|
-
// =============================================================================
|
|
31
|
-
|
|
32
|
-
export type LoadingStateSize = 'small' | 'medium' | 'large';
|
|
33
|
-
|
|
34
|
-
export interface LoadingStateProps {
|
|
35
|
-
/**
|
|
36
|
-
* Emoji/icon to display (changes per screen context)
|
|
37
|
-
* Examples: 🏠 Home, ⚙️ Settings, 💪 Workout, 🧘 Meditation, 📊 Analytics
|
|
38
|
-
*/
|
|
39
|
-
icon?: string;
|
|
40
|
-
|
|
41
|
-
/**
|
|
42
|
-
* Optional loading message
|
|
43
|
-
*/
|
|
44
|
-
message?: string;
|
|
45
|
-
|
|
46
|
-
/**
|
|
47
|
-
* Size variant
|
|
48
|
-
*/
|
|
49
|
-
size?: LoadingStateSize;
|
|
50
|
-
|
|
51
|
-
/**
|
|
52
|
-
* Full screen overlay mode
|
|
53
|
-
*/
|
|
54
|
-
fullScreen?: boolean;
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
// =============================================================================
|
|
58
|
-
// SIZE CONFIGURATION
|
|
59
|
-
// =============================================================================
|
|
60
|
-
|
|
61
|
-
interface SizeConfig {
|
|
62
|
-
iconSize: number;
|
|
63
|
-
showMessage: boolean;
|
|
64
|
-
containerPadding: number;
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
const SIZE_CONFIG: Record<LoadingStateSize, SizeConfig> = {
|
|
68
|
-
small: {
|
|
69
|
-
iconSize: 32,
|
|
70
|
-
showMessage: false,
|
|
71
|
-
containerPadding: 16,
|
|
72
|
-
},
|
|
73
|
-
medium: {
|
|
74
|
-
iconSize: 48,
|
|
75
|
-
showMessage: true,
|
|
76
|
-
containerPadding: 24,
|
|
77
|
-
},
|
|
78
|
-
large: {
|
|
79
|
-
iconSize: 64,
|
|
80
|
-
showMessage: true,
|
|
81
|
-
containerPadding: 32,
|
|
82
|
-
},
|
|
83
|
-
};
|
|
84
|
-
|
|
85
|
-
// =============================================================================
|
|
86
|
-
// COMPONENT IMPLEMENTATION
|
|
87
|
-
// =============================================================================
|
|
88
|
-
|
|
89
|
-
export const LoadingState: React.FC<LoadingStateProps> = ({
|
|
90
|
-
icon = '⏳', // Default hourglass icon
|
|
91
|
-
message,
|
|
92
|
-
size = 'large',
|
|
93
|
-
fullScreen = false,
|
|
94
|
-
}) => {
|
|
95
|
-
// ✅ Dynamic theme tokens
|
|
96
|
-
const tokens = useAppDesignTokens();
|
|
97
|
-
|
|
98
|
-
// Animation ref for breathing effect
|
|
99
|
-
const scaleAnim = useRef(new Animated.Value(1)).current;
|
|
100
|
-
|
|
101
|
-
// Size configuration
|
|
102
|
-
const config = SIZE_CONFIG[size];
|
|
103
|
-
|
|
104
|
-
/**
|
|
105
|
-
* Breathing Animation Effect
|
|
106
|
-
* Smoothly scales icon from 1 → 1.15 → 1 in continuous loop
|
|
107
|
-
* Creates calming, natural breathing sensation
|
|
108
|
-
*/
|
|
109
|
-
useEffect(() => {
|
|
110
|
-
const breathingAnimation = Animated.loop(
|
|
111
|
-
Animated.sequence([
|
|
112
|
-
// Expand (inhale)
|
|
113
|
-
Animated.timing(scaleAnim, {
|
|
114
|
-
toValue: 1.15,
|
|
115
|
-
duration: tokens.animations.slowest,
|
|
116
|
-
easing: Easing.inOut(Easing.ease),
|
|
117
|
-
useNativeDriver: true,
|
|
118
|
-
}),
|
|
119
|
-
// Contract (exhale)
|
|
120
|
-
Animated.timing(scaleAnim, {
|
|
121
|
-
toValue: 1,
|
|
122
|
-
duration: tokens.animations.slowest,
|
|
123
|
-
easing: Easing.inOut(Easing.ease),
|
|
124
|
-
useNativeDriver: true,
|
|
125
|
-
}),
|
|
126
|
-
])
|
|
127
|
-
);
|
|
128
|
-
|
|
129
|
-
breathingAnimation.start();
|
|
130
|
-
|
|
131
|
-
return () => {
|
|
132
|
-
breathingAnimation.stop();
|
|
133
|
-
};
|
|
134
|
-
}, [scaleAnim]);
|
|
135
|
-
|
|
136
|
-
// Dynamic styles based on theme
|
|
137
|
-
const styles = useMemo(() => getStyles(tokens, config, fullScreen), [tokens, config, fullScreen]);
|
|
138
|
-
|
|
139
|
-
return (
|
|
140
|
-
<View style={styles.container}>
|
|
141
|
-
{/* Animated Icon/Emoji */}
|
|
142
|
-
<Animated.Text
|
|
143
|
-
style={[
|
|
144
|
-
styles.icon,
|
|
145
|
-
{
|
|
146
|
-
fontSize: config.iconSize,
|
|
147
|
-
transform: [{ scale: scaleAnim }],
|
|
148
|
-
},
|
|
149
|
-
]}
|
|
150
|
-
>
|
|
151
|
-
{icon}
|
|
152
|
-
</Animated.Text>
|
|
153
|
-
|
|
154
|
-
{/* Optional Loading Message */}
|
|
155
|
-
{config.showMessage && message && (
|
|
156
|
-
<AtomicText
|
|
157
|
-
type="bodyMedium"
|
|
158
|
-
style={styles.message}
|
|
159
|
-
>
|
|
160
|
-
{message}
|
|
161
|
-
</AtomicText>
|
|
162
|
-
)}
|
|
163
|
-
</View>
|
|
164
|
-
);
|
|
165
|
-
};
|
|
166
|
-
|
|
167
|
-
// =============================================================================
|
|
168
|
-
// STYLES
|
|
169
|
-
// =============================================================================
|
|
170
|
-
|
|
171
|
-
const getStyles = (
|
|
172
|
-
tokens: ReturnType<typeof useAppDesignTokens>,
|
|
173
|
-
config: SizeConfig,
|
|
174
|
-
fullScreen: boolean
|
|
175
|
-
) => StyleSheet.create({
|
|
176
|
-
container: {
|
|
177
|
-
...(fullScreen ? {
|
|
178
|
-
flex: 1,
|
|
179
|
-
justifyContent: 'center',
|
|
180
|
-
alignItems: 'center',
|
|
181
|
-
backgroundColor: tokens.colors.backgroundPrimary,
|
|
182
|
-
} : {
|
|
183
|
-
justifyContent: 'center',
|
|
184
|
-
alignItems: 'center',
|
|
185
|
-
padding: config.containerPadding,
|
|
186
|
-
}),
|
|
187
|
-
},
|
|
188
|
-
icon: {
|
|
189
|
-
textAlign: 'center',
|
|
190
|
-
marginBottom: tokens.spacing.md,
|
|
191
|
-
},
|
|
192
|
-
message: {
|
|
193
|
-
color: tokens.colors.textSecondary,
|
|
194
|
-
textAlign: 'center',
|
|
195
|
-
marginTop: tokens.spacing.sm,
|
|
196
|
-
maxWidth: 300,
|
|
197
|
-
},
|
|
198
|
-
});
|
|
199
|
-
|
|
200
|
-
export default LoadingState;
|
|
@@ -1,100 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* useLoading - Loading State Management Hook
|
|
3
|
-
*
|
|
4
|
-
* Centralized hook for managing loading states across the application
|
|
5
|
-
* Theme: {{THEME_NAME}} ({{CATEGORY}} category)
|
|
6
|
-
*
|
|
7
|
-
* Features:
|
|
8
|
-
* - ✅ Simple boolean loading state
|
|
9
|
-
* - ✅ Message management
|
|
10
|
-
* - ✅ Icon configuration per context
|
|
11
|
-
* - ✅ Type-safe loading control
|
|
12
|
-
*/
|
|
13
|
-
|
|
14
|
-
import { useState, useCallback } from 'react';
|
|
15
|
-
|
|
16
|
-
// =============================================================================
|
|
17
|
-
// TYPE DEFINITIONS
|
|
18
|
-
// =============================================================================
|
|
19
|
-
|
|
20
|
-
export interface LoadingConfig {
|
|
21
|
-
isLoading: boolean;
|
|
22
|
-
message?: string;
|
|
23
|
-
icon?: string;
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
export interface UseLoadingReturn {
|
|
27
|
-
/**
|
|
28
|
-
* Current loading state
|
|
29
|
-
*/
|
|
30
|
-
isLoading: boolean;
|
|
31
|
-
|
|
32
|
-
/**
|
|
33
|
-
* Current loading message
|
|
34
|
-
*/
|
|
35
|
-
message: string | undefined;
|
|
36
|
-
|
|
37
|
-
/**
|
|
38
|
-
* Current loading icon
|
|
39
|
-
*/
|
|
40
|
-
icon: string | undefined;
|
|
41
|
-
|
|
42
|
-
/**
|
|
43
|
-
* Start loading with optional message and icon
|
|
44
|
-
*/
|
|
45
|
-
startLoading: (message?: string, icon?: string) => void;
|
|
46
|
-
|
|
47
|
-
/**
|
|
48
|
-
* Stop loading and clear message
|
|
49
|
-
*/
|
|
50
|
-
stopLoading: () => void;
|
|
51
|
-
|
|
52
|
-
/**
|
|
53
|
-
* Update loading message without affecting state
|
|
54
|
-
*/
|
|
55
|
-
setMessage: (message: string | undefined) => void;
|
|
56
|
-
|
|
57
|
-
/**
|
|
58
|
-
* Update loading icon without affecting state
|
|
59
|
-
*/
|
|
60
|
-
setIcon: (icon: string | undefined) => void;
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
// =============================================================================
|
|
64
|
-
// HOOK IMPLEMENTATION
|
|
65
|
-
// =============================================================================
|
|
66
|
-
|
|
67
|
-
export const useLoading = (initialConfig?: LoadingConfig): UseLoadingReturn => {
|
|
68
|
-
const [isLoading, setIsLoading] = useState(initialConfig?.isLoading ?? false);
|
|
69
|
-
const [message, setMessage] = useState<string | undefined>(initialConfig?.message);
|
|
70
|
-
const [icon, setIcon] = useState<string | undefined>(initialConfig?.icon);
|
|
71
|
-
|
|
72
|
-
/**
|
|
73
|
-
* Start loading with optional message and icon
|
|
74
|
-
*/
|
|
75
|
-
const startLoading = useCallback((msg?: string, ico?: string) => {
|
|
76
|
-
setIsLoading(true);
|
|
77
|
-
if (msg !== undefined) setMessage(msg);
|
|
78
|
-
if (ico !== undefined) setIcon(ico);
|
|
79
|
-
}, []);
|
|
80
|
-
|
|
81
|
-
/**
|
|
82
|
-
* Stop loading and clear message
|
|
83
|
-
*/
|
|
84
|
-
const stopLoading = useCallback(() => {
|
|
85
|
-
setIsLoading(false);
|
|
86
|
-
setMessage(undefined);
|
|
87
|
-
}, []);
|
|
88
|
-
|
|
89
|
-
return {
|
|
90
|
-
isLoading,
|
|
91
|
-
message,
|
|
92
|
-
icon,
|
|
93
|
-
startLoading,
|
|
94
|
-
stopLoading,
|
|
95
|
-
setMessage,
|
|
96
|
-
setIcon,
|
|
97
|
-
};
|
|
98
|
-
};
|
|
99
|
-
|
|
100
|
-
export default useLoading;
|