@umituz/react-native-design-system 2.9.10 → 2.9.12

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 CHANGED
@@ -14,6 +14,28 @@ Universal design system for React Native apps following Domain-Driven Design (DD
14
14
  - ðŸ“Ķ **Zero Config** - Works out of the box
15
15
  - ðŸŠķ **Lightweight** - Smaller bundle size (no Paper dependency)
16
16
 
17
+ ## ðŸšŦ ABSOLUTE PROHIBITIONS (Zero Tolerance)
18
+
19
+ ### NO ANIMATIONS - EVER
20
+ - ❌ `Animated` from react-native is FORBIDDEN
21
+ - ❌ `Animated.View`, `Animated.Text`, `Animated.timing()` FORBIDDEN
22
+ - ❌ `animationType="slide"` or `"fade"` on Modal FORBIDDEN
23
+ - ❌ `InteractionManager.runAfterInteractions` FORBIDDEN (causes screen lock)
24
+ - ❌ `react-native-reanimated` FORBIDDEN
25
+ - ❌ `Lottie` animations FORBIDDEN
26
+ - ✅ Use `animationType="none"` on all Modal components
27
+ - ✅ Use `View` instead of `Animated.View`
28
+
29
+ ### NO GRADIENTS - EVER
30
+ - ❌ `LinearGradient` component is FORBIDDEN
31
+ - ❌ `expo-linear-gradient` package is FORBIDDEN
32
+ - ✅ Use solid colors with transparency: `rgba(0,0,0,0.5)`
33
+
34
+ ### NO SHADOWS - EVER
35
+ - ❌ `shadowColor`, `shadowOffset`, `shadowOpacity`, `shadowRadius` FORBIDDEN
36
+ - ❌ `elevation` on Android FORBIDDEN
37
+ - ✅ Use `borderWidth` and `borderColor` for depth
38
+
17
39
  ## ðŸ“Ķ Installation
18
40
 
19
41
  ```bash
@@ -23,11 +45,9 @@ npm install @umituz/react-native-design-system
23
45
  ### Peer Dependencies
24
46
 
25
47
  ```bash
26
- npm install react@18.3.1 react-native@0.76.3 react-native-reanimated@~3.10.1 react-native-svg@^15.0.0
48
+ npm install react@19.1.0 react-native@0.81.5 react-native-svg@^15.0.0 react-native-gesture-handler@^2.30.0
27
49
  ```
28
50
 
29
- > **v1.3.0 Breaking Change**: React Native Paper dependency removed! All components now use pure React Native implementation for lighter bundle size and full control over styling.
30
-
31
51
  ## 🚀 Usage
32
52
 
33
53
  ```typescript
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@umituz/react-native-design-system",
3
- "version": "2.9.10",
3
+ "version": "2.9.12",
4
4
  "description": "Universal design system for React Native apps - Consolidated package with atoms, molecules, organisms, theme, typography, responsive, safe area, exception, infinite scroll, UUID, image, timezone, offline, and onboarding utilities",
5
5
  "main": "./src/index.ts",
6
6
  "types": "./src/index.ts",
@@ -99,7 +99,7 @@ export const DatePickerModal: React.FC<DatePickerModalProps> = ({
99
99
  <Modal
100
100
  visible={visible}
101
101
  transparent
102
- animationType="slide"
102
+ animationType="none"
103
103
  onRequestClose={onClose}
104
104
  testID={`${testID}-modal`}
105
105
  >
@@ -130,7 +130,7 @@ export const PickerModal: React.FC<PickerModalProps> = React.memo(({
130
130
  return (
131
131
  <Modal
132
132
  visible={visible}
133
- animationType="slide"
133
+ animationType="none"
134
134
  transparent
135
135
  onRequestClose={onClose}
136
136
  testID={`${testID}-modal`}
@@ -62,7 +62,7 @@ export const ImageGallery: React.FC<ImageGalleryProps> = ({
62
62
  source={{ uri: item.uri }}
63
63
  style={styles.fullImage}
64
64
  contentFit="contain"
65
- transition={200}
65
+ transition={0}
66
66
  cachePolicy="memory-disk"
67
67
  />
68
68
  </View>
@@ -74,7 +74,7 @@ export const ImageGallery: React.FC<ImageGalleryProps> = ({
74
74
  <Modal
75
75
  visible={visible}
76
76
  transparent
77
- animationType="fade"
77
+ animationType="none"
78
78
  onRequestClose={onDismiss}
79
79
  statusBarTranslucent
80
80
  >
@@ -59,7 +59,7 @@ export const BaseModal: React.FC<BaseModalProps> = ({
59
59
  <Modal
60
60
  visible={visible}
61
61
  transparent
62
- animationType="fade"
62
+ animationType="none"
63
63
  onRequestClose={onClose}
64
64
  statusBarTranslucent
65
65
  testID={testID}
@@ -36,7 +36,7 @@ export const AlertModal: React.FC<AlertModalProps> = ({ alert }) => {
36
36
  <Modal
37
37
  visible
38
38
  transparent
39
- animationType="fade"
39
+ animationType="none"
40
40
  onRequestClose={handleClose}
41
41
  >
42
42
  <View style={styles.overlay}>
@@ -96,7 +96,7 @@ export const BottomSheet = forwardRef<BottomSheetRef, BottomSheetProps>((props,
96
96
  <Modal
97
97
  visible={visible}
98
98
  transparent
99
- animationType="slide"
99
+ animationType="none"
100
100
  onRequestClose={dismiss}
101
101
  statusBarTranslucent
102
102
  >
@@ -96,7 +96,7 @@ export const BottomSheetModal = forwardRef<BottomSheetModalRef, BottomSheetModal
96
96
  <Modal
97
97
  visible={visible}
98
98
  transparent
99
- animationType="slide"
99
+ animationType="none"
100
100
  onRequestClose={dismiss}
101
101
  statusBarTranslucent
102
102
  >
@@ -43,7 +43,7 @@ export const FilterSheet: React.FC<FilterSheetProps> = ({
43
43
  }, [onFilterPress, onClose]);
44
44
 
45
45
  return (
46
- <Modal visible={visible} transparent animationType="slide" onRequestClose={onClose}>
46
+ <Modal visible={visible} transparent animationType="none" onRequestClose={onClose}>
47
47
  <Pressable style={styles.backdrop} onPress={onClose}>
48
48
  <Pressable
49
49
  style={[styles.sheet, { backgroundColor: tokens.colors.surface, paddingBottom: insets.bottom }]}
@@ -89,8 +89,6 @@ export const EmojiPicker: React.FC<EmojiPickerProps> = ({
89
89
  onEmojiSelected={handleEmojiSelect}
90
90
  open={open}
91
91
  onClose={onClose}
92
- enableCategoryChangeAnimation={true}
93
- enableSearchAnimation={true}
94
92
  categoryPosition="top"
95
93
  enableRecentlyUsed={config?.enableRecentlyUsed ?? true}
96
94
  enableSearchBar={config?.enableSearch ?? true}
@@ -244,38 +244,6 @@ export const App = () => {
244
244
  };
245
245
  ```
246
246
 
247
- ### Animated Splash
248
-
249
- ```tsx
250
- export const AnimatedSplash = () => {
251
- const [fadeAnim] = useState(new Animated.Value(0));
252
- const { isInitialized } = useSplashFlow({ duration: 2000 });
253
-
254
- useEffect(() => {
255
- if (isInitialized) {
256
- Animated.timing(fadeAnim, {
257
- toValue: 1,
258
- duration: 500,
259
- useNativeDriver: true,
260
- }).start(() => {
261
- // Hide splash after animation
262
- setTimeout(() => {
263
- navigation.replace('Home');
264
- }, 1000);
265
- });
266
- }
267
- }, [isInitialized]);
268
-
269
- return (
270
- <SplashScreen
271
- appName="My App"
272
- tagline="Welcome"
273
- visible={!isInitialized}
274
- />
275
- );
276
- };
277
- ```
278
-
279
247
  ### Multi-Stage Loading
280
248
 
281
249
  ```tsx
@@ -2,22 +2,17 @@
2
2
  * OfflineBanner Component
3
3
  *
4
4
  * Displays a banner when the device is offline.
5
- * Fully customizable for use across 100+ apps.
5
+ * Simple conditional rendering - NO animations per CLAUDE.md
6
6
  *
7
7
  * @example
8
8
  * ```tsx
9
- * import { OfflineBanner, useOffline } from '@umituz/react-native-offline';
9
+ * import { OfflineBanner, useOffline } from '@umituz/react-native-design-system';
10
10
  *
11
11
  * const App = () => {
12
12
  * const { isOffline } = useOffline();
13
- *
14
13
  * return (
15
14
  * <>
16
- * <OfflineBanner
17
- * visible={isOffline}
18
- * message="No internet connection"
19
- * backgroundColor="#FF6B6B"
20
- * />
15
+ * <OfflineBanner visible={isOffline} message="No internet connection" />
21
16
  * <YourContent />
22
17
  * </>
23
18
  * );
@@ -25,14 +20,8 @@
25
20
  * ```
26
21
  */
27
22
 
28
- import React, { useEffect, useRef, memo } from 'react';
29
- import {
30
- View,
31
- Animated,
32
- StyleSheet,
33
- type ViewStyle,
34
- type TextStyle,
35
- } from 'react-native';
23
+ import React, { memo } from 'react';
24
+ import { View, StyleSheet, type ViewStyle, type TextStyle } from 'react-native';
36
25
  import { AtomicText } from '../../../atoms';
37
26
 
38
27
  export interface OfflineBannerProps {
@@ -52,14 +41,11 @@ export interface OfflineBannerProps {
52
41
  style?: ViewStyle;
53
42
  /** Custom text style */
54
43
  textStyle?: TextStyle;
55
- /** Animation duration in ms */
56
- animationDuration?: number;
57
44
  /** Height of the banner */
58
45
  height?: number;
59
46
  }
60
47
 
61
48
  const DEFAULT_HEIGHT = 44;
62
- const DEFAULT_ANIMATION_DURATION = 300;
63
49
 
64
50
  export const OfflineBanner: React.FC<OfflineBannerProps> = memo(({
65
51
  visible,
@@ -70,59 +56,23 @@ export const OfflineBanner: React.FC<OfflineBannerProps> = memo(({
70
56
  position = 'top',
71
57
  style,
72
58
  textStyle,
73
- animationDuration = DEFAULT_ANIMATION_DURATION,
74
59
  height = DEFAULT_HEIGHT,
75
60
  }) => {
76
- const animatedValue = useRef(new Animated.Value(visible ? 1 : 0)).current;
77
- const isFirstRender = useRef(true);
78
-
79
- useEffect(() => {
80
- if (isFirstRender.current) {
81
- isFirstRender.current = false;
82
- animatedValue.setValue(visible ? 1 : 0);
83
- return;
84
- }
85
-
86
- Animated.timing(animatedValue, {
87
- toValue: visible ? 1 : 0,
88
- duration: animationDuration,
89
- useNativeDriver: false,
90
- }).start();
91
- }, [visible, animatedValue, animationDuration]);
92
-
93
- const translateY = animatedValue.interpolate({
94
- inputRange: [0, 1],
95
- outputRange: [position === 'top' ? -height : height, 0],
96
- });
97
-
98
- const animatedHeight = animatedValue.interpolate({
99
- inputRange: [0, 1],
100
- outputRange: [0, height],
101
- });
102
-
103
- const opacity = animatedValue.interpolate({
104
- inputRange: [0, 0.5, 1],
105
- outputRange: [0, 0.8, 1],
106
- });
61
+ // Simple conditional rendering - no animations
62
+ if (!visible) {
63
+ return null;
64
+ }
107
65
 
108
- const positionStyle: ViewStyle = position === 'top'
109
- ? { top: 0 }
110
- : { bottom: 0 };
66
+ const positionStyle: ViewStyle = position === 'top' ? { top: 0 } : { bottom: 0 };
111
67
 
112
68
  return (
113
- <Animated.View
69
+ <View
114
70
  style={[
115
71
  styles.container,
116
72
  positionStyle,
117
- {
118
- backgroundColor,
119
- height: animatedHeight,
120
- transform: [{ translateY }],
121
- opacity,
122
- },
73
+ { backgroundColor, height },
123
74
  style,
124
75
  ]}
125
- pointerEvents={visible ? 'auto' : 'none'}
126
76
  >
127
77
  <View style={styles.content}>
128
78
  {typeof icon === 'string' ? (
@@ -131,17 +81,13 @@ export const OfflineBanner: React.FC<OfflineBannerProps> = memo(({
131
81
  icon
132
82
  )}
133
83
  <AtomicText
134
- style={[
135
- styles.message,
136
- { color: textColor },
137
- textStyle,
138
- ]}
84
+ style={[styles.message, { color: textColor }, textStyle]}
139
85
  numberOfLines={1}
140
86
  >
141
87
  {message}
142
88
  </AtomicText>
143
89
  </View>
144
- </Animated.View>
90
+ </View>
145
91
  );
146
92
  });
147
93
 
@@ -153,7 +99,6 @@ const styles = StyleSheet.create({
153
99
  left: 0,
154
100
  right: 0,
155
101
  zIndex: 9999,
156
- overflow: 'hidden',
157
102
  },
158
103
  content: {
159
104
  flex: 1,