@oxyhq/services 5.3.11 → 5.4.1
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 +21 -0
- package/lib/commonjs/assets/assets/icons/OxyServices.tsx +67 -0
- package/lib/commonjs/assets/assets/icons/logo_OxyServices.svg +1 -0
- package/lib/commonjs/assets/icons/OxyServices.js +53 -0
- package/lib/commonjs/assets/icons/OxyServices.js.map +1 -0
- package/lib/commonjs/assets/icons/logo_OxyServices.svg +1 -0
- package/lib/commonjs/core/index.js +119 -23
- package/lib/commonjs/core/index.js.map +1 -1
- package/lib/commonjs/index.js +2 -0
- package/lib/commonjs/index.js.map +1 -1
- package/lib/commonjs/lib/sonner.js +15 -11
- package/lib/commonjs/lib/sonner.js.map +1 -1
- package/lib/commonjs/node/index.js +2 -0
- package/lib/commonjs/node/index.js.map +1 -1
- package/lib/commonjs/ui/components/GroupedItem.js +109 -0
- package/lib/commonjs/ui/components/GroupedItem.js.map +1 -0
- package/lib/commonjs/ui/components/GroupedSection.js +33 -0
- package/lib/commonjs/ui/components/GroupedSection.js.map +1 -0
- package/lib/commonjs/ui/components/OxyProvider.js +95 -112
- package/lib/commonjs/ui/components/OxyProvider.js.map +1 -1
- package/lib/commonjs/ui/components/ProfileCard.js +124 -0
- package/lib/commonjs/ui/components/ProfileCard.js.map +1 -0
- package/lib/commonjs/ui/components/QuickActions.js +87 -0
- package/lib/commonjs/ui/components/QuickActions.js.map +1 -0
- package/lib/commonjs/ui/components/Section.js +36 -0
- package/lib/commonjs/ui/components/Section.js.map +1 -0
- package/lib/commonjs/ui/components/SectionTitle.js +35 -0
- package/lib/commonjs/ui/components/SectionTitle.js.map +1 -0
- package/lib/commonjs/ui/components/bottomSheet/index.js +6 -6
- package/lib/commonjs/ui/components/index.js +97 -0
- package/lib/commonjs/ui/components/index.js.map +1 -0
- package/lib/commonjs/ui/navigation/OxyRouter.js +20 -3
- package/lib/commonjs/ui/navigation/OxyRouter.js.map +1 -1
- package/lib/commonjs/ui/screens/AccountCenterScreen.js +190 -207
- package/lib/commonjs/ui/screens/AccountCenterScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/AccountManagementDemo.js +299 -0
- package/lib/commonjs/ui/screens/AccountManagementDemo.js.map +1 -0
- package/lib/commonjs/ui/screens/AccountOverviewScreen.js +669 -401
- package/lib/commonjs/ui/screens/AccountOverviewScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/AccountSettingsScreen.js +695 -498
- package/lib/commonjs/ui/screens/AccountSettingsScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/AccountSwitcherScreen.js +451 -488
- package/lib/commonjs/ui/screens/AccountSwitcherScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/AppInfoScreen.js +498 -185
- package/lib/commonjs/ui/screens/AppInfoScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/BillingManagementScreen.js +636 -0
- package/lib/commonjs/ui/screens/BillingManagementScreen.js.map +1 -0
- package/lib/commonjs/ui/screens/FileManagementScreen.js +2497 -0
- package/lib/commonjs/ui/screens/FileManagementScreen.js.map +1 -0
- package/lib/commonjs/ui/screens/PremiumSubscriptionScreen.js +1620 -0
- package/lib/commonjs/ui/screens/PremiumSubscriptionScreen.js.map +1 -0
- package/lib/commonjs/ui/screens/ProfileScreen.js +117 -13
- package/lib/commonjs/ui/screens/ProfileScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/SessionManagementScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/SignInScreen.js +1 -1
- package/lib/commonjs/ui/screens/SignUpScreen.js +1 -1
- package/lib/commonjs/utils/polyfills.js +42 -0
- package/lib/commonjs/utils/polyfills.js.map +1 -0
- package/lib/module/assets/assets/icons/OxyServices.tsx +67 -0
- package/lib/module/assets/assets/icons/logo_OxyServices.svg +1 -0
- package/lib/module/assets/icons/OxyServices.js +46 -0
- package/lib/module/assets/icons/OxyServices.js.map +1 -0
- package/lib/module/assets/icons/logo_OxyServices.svg +1 -0
- package/lib/module/core/index.js +119 -23
- package/lib/module/core/index.js.map +1 -1
- package/lib/module/index.js +3 -0
- package/lib/module/index.js.map +1 -1
- package/lib/module/lib/sonner.js +13 -1
- package/lib/module/lib/sonner.js.map +1 -1
- package/lib/module/node/index.js +3 -0
- package/lib/module/node/index.js.map +1 -1
- package/lib/module/ui/components/GroupedItem.js +104 -0
- package/lib/module/ui/components/GroupedItem.js.map +1 -0
- package/lib/module/ui/components/GroupedSection.js +28 -0
- package/lib/module/ui/components/GroupedSection.js.map +1 -0
- package/lib/module/ui/components/OxyProvider.js +97 -114
- package/lib/module/ui/components/OxyProvider.js.map +1 -1
- package/lib/module/ui/components/ProfileCard.js +119 -0
- package/lib/module/ui/components/ProfileCard.js.map +1 -0
- package/lib/module/ui/components/QuickActions.js +82 -0
- package/lib/module/ui/components/QuickActions.js.map +1 -0
- package/lib/module/ui/components/Section.js +31 -0
- package/lib/module/ui/components/Section.js.map +1 -0
- package/lib/module/ui/components/SectionTitle.js +30 -0
- package/lib/module/ui/components/SectionTitle.js.map +1 -0
- package/lib/module/ui/components/bottomSheet/index.js +2 -5
- package/lib/module/ui/components/bottomSheet/index.js.map +1 -1
- package/lib/module/ui/components/index.js +18 -0
- package/lib/module/ui/components/index.js.map +1 -0
- package/lib/module/ui/navigation/OxyRouter.js +20 -3
- package/lib/module/ui/navigation/OxyRouter.js.map +1 -1
- package/lib/module/ui/screens/AccountCenterScreen.js +191 -208
- package/lib/module/ui/screens/AccountCenterScreen.js.map +1 -1
- package/lib/module/ui/screens/AccountManagementDemo.js +296 -0
- package/lib/module/ui/screens/AccountManagementDemo.js.map +1 -0
- package/lib/module/ui/screens/AccountOverviewScreen.js +671 -403
- package/lib/module/ui/screens/AccountOverviewScreen.js.map +1 -1
- package/lib/module/ui/screens/AccountSettingsScreen.js +698 -501
- package/lib/module/ui/screens/AccountSettingsScreen.js.map +1 -1
- package/lib/module/ui/screens/AccountSwitcherScreen.js +450 -488
- package/lib/module/ui/screens/AccountSwitcherScreen.js.map +1 -1
- package/lib/module/ui/screens/AppInfoScreen.js +498 -186
- package/lib/module/ui/screens/AppInfoScreen.js.map +1 -1
- package/lib/module/ui/screens/BillingManagementScreen.js +631 -0
- package/lib/module/ui/screens/BillingManagementScreen.js.map +1 -0
- package/lib/module/ui/screens/FileManagementScreen.js +2492 -0
- package/lib/module/ui/screens/FileManagementScreen.js.map +1 -0
- package/lib/module/ui/screens/PremiumSubscriptionScreen.js +1615 -0
- package/lib/module/ui/screens/PremiumSubscriptionScreen.js.map +1 -0
- package/lib/module/ui/screens/ProfileScreen.js +118 -14
- package/lib/module/ui/screens/ProfileScreen.js.map +1 -1
- package/lib/module/ui/screens/SessionManagementScreen.js.map +1 -1
- package/lib/module/ui/screens/SignInScreen.js +1 -1
- package/lib/module/ui/screens/SignInScreen.js.map +1 -1
- package/lib/module/ui/screens/SignUpScreen.js +1 -1
- package/lib/module/ui/screens/SignUpScreen.js.map +1 -1
- package/lib/module/utils/polyfills.js +36 -0
- package/lib/module/utils/polyfills.js.map +1 -0
- package/lib/typescript/assets/icons/OxyServices.d.ts +29 -0
- package/lib/typescript/assets/icons/OxyServices.d.ts.map +1 -0
- package/lib/typescript/core/index.d.ts +26 -1
- package/lib/typescript/core/index.d.ts.map +1 -1
- package/lib/typescript/index.d.ts +1 -0
- package/lib/typescript/index.d.ts.map +1 -1
- package/lib/typescript/lib/sonner.d.ts +5 -1
- package/lib/typescript/lib/sonner.d.ts.map +1 -1
- package/lib/typescript/models/interfaces.d.ts +1 -2
- package/lib/typescript/models/interfaces.d.ts.map +1 -1
- package/lib/typescript/node/index.d.ts +1 -0
- package/lib/typescript/node/index.d.ts.map +1 -1
- package/lib/typescript/ui/components/GroupedItem.d.ts +17 -0
- package/lib/typescript/ui/components/GroupedItem.d.ts.map +1 -0
- package/lib/typescript/ui/components/GroupedSection.d.ts +19 -0
- package/lib/typescript/ui/components/GroupedSection.d.ts.map +1 -0
- package/lib/typescript/ui/components/OxyProvider.d.ts.map +1 -1
- package/lib/typescript/ui/components/ProfileCard.d.ts +20 -0
- package/lib/typescript/ui/components/ProfileCard.d.ts.map +1 -0
- package/lib/typescript/ui/components/QuickActions.d.ts +15 -0
- package/lib/typescript/ui/components/QuickActions.d.ts.map +1 -0
- package/lib/typescript/ui/components/Section.d.ts +11 -0
- package/lib/typescript/ui/components/Section.d.ts.map +1 -0
- package/lib/typescript/ui/components/SectionTitle.d.ts +9 -0
- package/lib/typescript/ui/components/SectionTitle.d.ts.map +1 -0
- package/lib/typescript/ui/components/bottomSheet/index.d.ts +3 -2
- package/lib/typescript/ui/components/bottomSheet/index.d.ts.map +1 -1
- package/lib/typescript/ui/components/index.d.ts +13 -0
- package/lib/typescript/ui/components/index.d.ts.map +1 -0
- package/lib/typescript/ui/navigation/OxyRouter.d.ts.map +1 -1
- package/lib/typescript/ui/navigation/types.d.ts +8 -0
- package/lib/typescript/ui/navigation/types.d.ts.map +1 -1
- package/lib/typescript/ui/screens/AccountCenterScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/AccountManagementDemo.d.ts +8 -0
- package/lib/typescript/ui/screens/AccountManagementDemo.d.ts.map +1 -0
- package/lib/typescript/ui/screens/AccountOverviewScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/AccountSettingsScreen.d.ts +1 -4
- package/lib/typescript/ui/screens/AccountSettingsScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/AccountSwitcherScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/AppInfoScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/BillingManagementScreen.d.ts +5 -0
- package/lib/typescript/ui/screens/BillingManagementScreen.d.ts.map +1 -0
- package/lib/typescript/ui/screens/FileManagementScreen.d.ts +8 -0
- package/lib/typescript/ui/screens/FileManagementScreen.d.ts.map +1 -0
- package/lib/typescript/ui/screens/PremiumSubscriptionScreen.d.ts +5 -0
- package/lib/typescript/ui/screens/PremiumSubscriptionScreen.d.ts.map +1 -0
- package/lib/typescript/ui/screens/ProfileScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/SessionManagementScreen.d.ts.map +1 -1
- package/lib/typescript/utils/polyfills.d.ts +6 -0
- package/lib/typescript/utils/polyfills.d.ts.map +1 -0
- package/package.json +11 -3
- package/src/__tests__/polyfills.test.ts +30 -0
- package/src/__tests__/setup.ts +43 -0
- package/src/__tests__/ui/screens/AccountSettingsScreen.test.tsx +8 -8
- package/src/assets/icons/OxyServices.tsx +67 -0
- package/src/assets/icons/logo_OxyServices.svg +1 -0
- package/src/core/index.ts +127 -19
- package/src/index.ts +3 -0
- package/src/lib/sonner.ts +10 -1
- package/src/models/interfaces.ts +1 -2
- package/src/node/index.ts +3 -0
- package/src/ui/components/GroupedItem.tsx +118 -0
- package/src/ui/components/GroupedSection.tsx +45 -0
- package/src/ui/components/OxyProvider.tsx +95 -120
- package/src/ui/components/ProfileCard.tsx +129 -0
- package/src/ui/components/QuickActions.tsx +90 -0
- package/src/ui/components/Section.tsx +37 -0
- package/src/ui/components/SectionTitle.tsx +31 -0
- package/src/ui/components/bottomSheet/index.tsx +13 -11
- package/src/ui/components/index.ts +15 -0
- package/src/ui/navigation/OxyRouter.tsx +20 -3
- package/src/ui/navigation/types.ts +10 -1
- package/src/ui/screens/AccountCenterScreen.tsx +188 -159
- package/src/ui/screens/AccountManagementDemo.tsx +297 -0
- package/src/ui/screens/AccountOverviewScreen.tsx +474 -310
- package/src/ui/screens/AccountSettingsScreen.tsx +648 -463
- package/src/ui/screens/AccountSwitcherScreen.tsx +385 -449
- package/src/ui/screens/AppInfoScreen.tsx +571 -140
- package/src/ui/screens/BillingManagementScreen.tsx +589 -0
- package/src/ui/screens/FileManagementScreen.tsx +2513 -0
- package/src/ui/screens/PremiumSubscriptionScreen.tsx +1628 -0
- package/src/ui/screens/ProfileScreen.tsx +101 -7
- package/src/ui/screens/SessionManagementScreen.tsx +1 -0
- package/src/ui/screens/SignInScreen.tsx +1 -1
- package/src/ui/screens/SignUpScreen.tsx +1 -1
- package/src/utils/polyfills.ts +34 -0
- package/lib/commonjs/lib/sonner.web.js +0 -17
- package/lib/commonjs/lib/sonner.web.js.map +0 -1
- package/lib/module/lib/sonner.web.js +0 -4
- package/lib/module/lib/sonner.web.js.map +0 -1
- package/lib/typescript/__tests__/ui/screens/AccountSettingsScreen.test.d.ts +0 -2
- package/lib/typescript/__tests__/ui/screens/AccountSettingsScreen.test.d.ts.map +0 -1
- package/lib/typescript/lib/sonner.web.d.ts +0 -2
- package/lib/typescript/lib/sonner.web.d.ts.map +0 -1
- package/src/lib/sonner.web.ts +0 -1
|
@@ -16,6 +16,10 @@ import { useOxy } from '../context/OxyContext';
|
|
|
16
16
|
import { fontFamilies } from '../styles/fonts';
|
|
17
17
|
import { packageInfo } from '../../constants/version';
|
|
18
18
|
import { toast } from '../../lib/sonner';
|
|
19
|
+
import OxyIcon from '../components/icon/OxyIcon';
|
|
20
|
+
import { Ionicons } from '@expo/vector-icons';
|
|
21
|
+
import OxyServicesLogo from '../../assets/icons/OxyServices';
|
|
22
|
+
|
|
19
23
|
|
|
20
24
|
interface SystemInfo {
|
|
21
25
|
platform: string;
|
|
@@ -32,28 +36,62 @@ const AppInfoScreen: React.FC<BaseScreenProps> = ({
|
|
|
32
36
|
theme,
|
|
33
37
|
navigate,
|
|
34
38
|
}) => {
|
|
35
|
-
const { user, sessions } = useOxy();
|
|
39
|
+
const { user, sessions, oxyServices } = useOxy();
|
|
36
40
|
const [systemInfo, setSystemInfo] = useState<SystemInfo | null>(null);
|
|
41
|
+
const [isRunningSystemCheck, setIsRunningSystemCheck] = useState(false);
|
|
42
|
+
const [connectionStatus, setConnectionStatus] = useState<'checking' | 'connected' | 'disconnected' | 'unknown'>('unknown');
|
|
37
43
|
|
|
38
44
|
const isDarkTheme = theme === 'dark';
|
|
39
|
-
const
|
|
40
|
-
const
|
|
41
|
-
const secondaryBackgroundColor = isDarkTheme ? '#222222' : '#F5F5F5';
|
|
42
|
-
const borderColor = isDarkTheme ? '#444444' : '#E0E0E0';
|
|
43
|
-
const primaryColor = '#0066CC';
|
|
44
|
-
const successColor = '#4CAF50';
|
|
45
|
+
const backgroundColor = isDarkTheme ? '#121212' : '#f2f2f2';
|
|
46
|
+
const primaryColor = '#007AFF';
|
|
45
47
|
|
|
46
48
|
useEffect(() => {
|
|
47
|
-
const
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
49
|
+
const updateDimensions = () => {
|
|
50
|
+
const dimensions = Dimensions.get('window');
|
|
51
|
+
setSystemInfo(prev => ({
|
|
52
|
+
...prev,
|
|
53
|
+
platform: Platform.OS,
|
|
54
|
+
version: Platform.Version?.toString() || 'Unknown',
|
|
55
|
+
screenDimensions: {
|
|
56
|
+
width: dimensions.width,
|
|
57
|
+
height: dimensions.height,
|
|
58
|
+
},
|
|
59
|
+
timestamp: new Date().toISOString(),
|
|
60
|
+
}));
|
|
61
|
+
};
|
|
62
|
+
|
|
63
|
+
// Set initial dimensions
|
|
64
|
+
updateDimensions();
|
|
65
|
+
|
|
66
|
+
// Listen for dimension changes
|
|
67
|
+
const subscription = Dimensions.addEventListener('change', updateDimensions);
|
|
68
|
+
|
|
69
|
+
// Check API connection on mount
|
|
70
|
+
const checkConnection = async () => {
|
|
71
|
+
setConnectionStatus('checking');
|
|
72
|
+
const apiBaseUrl = oxyServices?.getBaseURL() || 'https://api.oxy.so';
|
|
73
|
+
try {
|
|
74
|
+
const response = await fetch(`${apiBaseUrl}/`, {
|
|
75
|
+
method: 'GET',
|
|
76
|
+
timeout: 3000,
|
|
77
|
+
} as any);
|
|
78
|
+
|
|
79
|
+
if (response.ok) {
|
|
80
|
+
setConnectionStatus('connected');
|
|
81
|
+
} else {
|
|
82
|
+
setConnectionStatus('disconnected');
|
|
83
|
+
}
|
|
84
|
+
} catch (error) {
|
|
85
|
+
setConnectionStatus('disconnected');
|
|
86
|
+
}
|
|
87
|
+
};
|
|
88
|
+
|
|
89
|
+
checkConnection();
|
|
90
|
+
|
|
91
|
+
// Cleanup listener on unmount
|
|
92
|
+
return () => {
|
|
93
|
+
subscription?.remove();
|
|
94
|
+
};
|
|
57
95
|
}, []);
|
|
58
96
|
|
|
59
97
|
const copyToClipboard = async (text: string, label: string) => {
|
|
@@ -65,6 +103,138 @@ const AppInfoScreen: React.FC<BaseScreenProps> = ({
|
|
|
65
103
|
}
|
|
66
104
|
};
|
|
67
105
|
|
|
106
|
+
const runSystemCheck = async () => {
|
|
107
|
+
if (!oxyServices) {
|
|
108
|
+
toast.error('OxyServices not initialized');
|
|
109
|
+
return;
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
setIsRunningSystemCheck(true);
|
|
113
|
+
const checks = [];
|
|
114
|
+
|
|
115
|
+
// Get the API base URL from the services instance
|
|
116
|
+
const apiBaseUrl = oxyServices?.getBaseURL() || 'https://api.oxy.so'; // Default for now, could be made configurable
|
|
117
|
+
|
|
118
|
+
try {
|
|
119
|
+
// Check 1: API Server Health
|
|
120
|
+
checks.push('🔍 Checking API server connection...');
|
|
121
|
+
toast.info('Running system checks...', { duration: 2000 });
|
|
122
|
+
|
|
123
|
+
try {
|
|
124
|
+
const response = await fetch(`${apiBaseUrl}/`, {
|
|
125
|
+
method: 'GET',
|
|
126
|
+
timeout: 5000,
|
|
127
|
+
} as any);
|
|
128
|
+
|
|
129
|
+
if (response.ok) {
|
|
130
|
+
const data = await response.json();
|
|
131
|
+
checks.push('✅ API server is responding');
|
|
132
|
+
checks.push(`📊 Server stats: ${data.users || 0} users`);
|
|
133
|
+
checks.push(`🌐 API URL: ${apiBaseUrl}`);
|
|
134
|
+
setConnectionStatus('connected');
|
|
135
|
+
} else {
|
|
136
|
+
checks.push('❌ API server returned error status');
|
|
137
|
+
checks.push(` Status: ${response.status} ${response.statusText}`);
|
|
138
|
+
setConnectionStatus('disconnected');
|
|
139
|
+
}
|
|
140
|
+
} catch (error) {
|
|
141
|
+
checks.push('❌ API server connection failed');
|
|
142
|
+
checks.push(` Error: ${error instanceof Error ? error.message : 'Unknown error'}`);
|
|
143
|
+
checks.push(` URL: ${apiBaseUrl}`);
|
|
144
|
+
setConnectionStatus('disconnected');
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
// Check 2: Authentication Status
|
|
148
|
+
checks.push('🔍 Checking authentication...');
|
|
149
|
+
if (oxyServices.isAuthenticated()) {
|
|
150
|
+
checks.push('✅ User is authenticated');
|
|
151
|
+
|
|
152
|
+
// Check 3: Token Validation
|
|
153
|
+
try {
|
|
154
|
+
const isValid = await oxyServices.validate();
|
|
155
|
+
if (isValid) {
|
|
156
|
+
checks.push('✅ Authentication token is valid');
|
|
157
|
+
} else {
|
|
158
|
+
checks.push('❌ Authentication token is invalid');
|
|
159
|
+
}
|
|
160
|
+
} catch (error) {
|
|
161
|
+
checks.push('❌ Token validation failed');
|
|
162
|
+
checks.push(` Error: ${error instanceof Error ? error.message : 'Unknown error'}`);
|
|
163
|
+
}
|
|
164
|
+
} else {
|
|
165
|
+
checks.push('⚠️ User is not authenticated');
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
// Check 4: Session Validation (if user has active sessions)
|
|
169
|
+
if (user && sessions && sessions.length > 0) {
|
|
170
|
+
checks.push('🔍 Checking active sessions...');
|
|
171
|
+
try {
|
|
172
|
+
// Just check if we can fetch sessions
|
|
173
|
+
const userSessions = await oxyServices.getUserSessions();
|
|
174
|
+
checks.push(`✅ Session validation successful (${userSessions.length} sessions)`);
|
|
175
|
+
} catch (error) {
|
|
176
|
+
checks.push('❌ Session validation failed');
|
|
177
|
+
checks.push(` Error: ${error instanceof Error ? error.message : 'Unknown error'}`);
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
// Check 5: Platform Information
|
|
182
|
+
checks.push('🔍 Checking platform information...');
|
|
183
|
+
checks.push(`✅ Platform: ${Platform.OS} ${Platform.Version || 'Unknown'}`);
|
|
184
|
+
checks.push(`✅ Screen: ${systemInfo?.screenDimensions.width || 0}x${systemInfo?.screenDimensions.height || 0}`);
|
|
185
|
+
checks.push(`✅ Environment: ${__DEV__ ? 'Development' : 'Production'}`);
|
|
186
|
+
|
|
187
|
+
// Check 6: Package Information
|
|
188
|
+
checks.push('🔍 Checking package information...');
|
|
189
|
+
checks.push(`✅ Package: ${packageInfo.name}@${packageInfo.version}`);
|
|
190
|
+
|
|
191
|
+
// Check 7: Memory and Performance (basic)
|
|
192
|
+
checks.push('🔍 Checking performance metrics...');
|
|
193
|
+
const memoryUsage = (performance as any).memory;
|
|
194
|
+
if (memoryUsage) {
|
|
195
|
+
const usedMB = Math.round(memoryUsage.usedJSHeapSize / 1024 / 1024);
|
|
196
|
+
const totalMB = Math.round(memoryUsage.totalJSHeapSize / 1024 / 1024);
|
|
197
|
+
checks.push(`✅ Memory usage: ${usedMB}MB / ${totalMB}MB`);
|
|
198
|
+
} else {
|
|
199
|
+
checks.push('✅ Performance metrics not available on this platform');
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
// Final summary
|
|
203
|
+
const errorCount = checks.filter(check => check.includes('❌')).length;
|
|
204
|
+
const warningCount = checks.filter(check => check.includes('⚠️')).length;
|
|
205
|
+
|
|
206
|
+
checks.push('');
|
|
207
|
+
checks.push('📋 SYSTEM CHECK SUMMARY:');
|
|
208
|
+
if (errorCount === 0 && warningCount === 0) {
|
|
209
|
+
checks.push('✅ All systems operational');
|
|
210
|
+
toast.success('System check completed - All systems operational!');
|
|
211
|
+
} else if (errorCount === 0) {
|
|
212
|
+
checks.push(`⚠️ ${warningCount} warning(s) found`);
|
|
213
|
+
toast.warning(`System check completed with ${warningCount} warning(s)`);
|
|
214
|
+
} else {
|
|
215
|
+
checks.push(`❌ ${errorCount} error(s) and ${warningCount} warning(s) found`);
|
|
216
|
+
toast.error(`System check failed with ${errorCount} error(s)`);
|
|
217
|
+
}
|
|
218
|
+
|
|
219
|
+
// Show results in an alert and copy to clipboard
|
|
220
|
+
const report = checks.join('\n');
|
|
221
|
+
Alert.alert(
|
|
222
|
+
'System Check Results',
|
|
223
|
+
`Check completed. Results copied to clipboard.\n\nSummary: ${errorCount} errors, ${warningCount} warnings`,
|
|
224
|
+
[
|
|
225
|
+
{ text: 'View Full Report', onPress: () => copyToClipboard(report, 'System check report') },
|
|
226
|
+
{ text: 'OK', style: 'default' }
|
|
227
|
+
]
|
|
228
|
+
);
|
|
229
|
+
|
|
230
|
+
} catch (error) {
|
|
231
|
+
toast.error('System check failed to run');
|
|
232
|
+
console.error('System check error:', error);
|
|
233
|
+
} finally {
|
|
234
|
+
setIsRunningSystemCheck(false);
|
|
235
|
+
}
|
|
236
|
+
};
|
|
237
|
+
|
|
68
238
|
const generateFullReport = () => {
|
|
69
239
|
const report = {
|
|
70
240
|
packageInfo: {
|
|
@@ -80,7 +250,7 @@ const AppInfoScreen: React.FC<BaseScreenProps> = ({
|
|
|
80
250
|
totalUsers: sessions?.length || 0,
|
|
81
251
|
},
|
|
82
252
|
apiConfiguration: {
|
|
83
|
-
apiUrl: '
|
|
253
|
+
apiUrl: oxyServices?.getBaseURL() || 'Not configured',
|
|
84
254
|
},
|
|
85
255
|
buildInfo: {
|
|
86
256
|
timestamp: new Date().toISOString(),
|
|
@@ -96,110 +266,359 @@ const AppInfoScreen: React.FC<BaseScreenProps> = ({
|
|
|
96
266
|
copyToClipboard(report, 'Full application report');
|
|
97
267
|
};
|
|
98
268
|
|
|
99
|
-
const
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
269
|
+
const InfoRow: React.FC<{
|
|
270
|
+
label: string;
|
|
271
|
+
value: string;
|
|
272
|
+
copyable?: boolean;
|
|
273
|
+
icon?: string;
|
|
274
|
+
iconComponent?: React.ReactNode;
|
|
275
|
+
color?: string;
|
|
276
|
+
isFirst?: boolean;
|
|
277
|
+
isLast?: boolean;
|
|
278
|
+
onPress?: () => void;
|
|
279
|
+
showChevron?: boolean;
|
|
280
|
+
}> = ({
|
|
107
281
|
label,
|
|
108
282
|
value,
|
|
109
|
-
copyable = false
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
283
|
+
copyable = false,
|
|
284
|
+
icon = 'information-circle',
|
|
285
|
+
iconComponent,
|
|
286
|
+
color = '#8E8E93',
|
|
287
|
+
isFirst = false,
|
|
288
|
+
isLast = false,
|
|
289
|
+
onPress,
|
|
290
|
+
showChevron = false,
|
|
291
|
+
}) => {
|
|
292
|
+
const handlePress = () => {
|
|
293
|
+
if (onPress) {
|
|
294
|
+
onPress();
|
|
295
|
+
} else if (copyable) {
|
|
296
|
+
copyToClipboard(value, label);
|
|
297
|
+
}
|
|
298
|
+
};
|
|
299
|
+
|
|
300
|
+
const isInteractive = copyable || !!onPress;
|
|
301
|
+
|
|
302
|
+
return (
|
|
115
303
|
<TouchableOpacity
|
|
116
|
-
style={
|
|
117
|
-
|
|
118
|
-
|
|
304
|
+
style={[
|
|
305
|
+
styles.settingItem,
|
|
306
|
+
isFirst && styles.firstSettingItem,
|
|
307
|
+
isLast && styles.lastSettingItem,
|
|
308
|
+
]}
|
|
309
|
+
onPress={isInteractive ? handlePress : undefined}
|
|
310
|
+
disabled={!isInteractive}
|
|
119
311
|
>
|
|
120
|
-
<
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
312
|
+
<View style={styles.settingInfo}>
|
|
313
|
+
{iconComponent ? (
|
|
314
|
+
React.cloneElement(iconComponent as React.ReactElement, { style: styles.settingIcon })
|
|
315
|
+
) : (
|
|
316
|
+
<OxyIcon name={icon} size={20} color={color} style={styles.settingIcon} />
|
|
317
|
+
)}
|
|
318
|
+
<View style={styles.settingDetails}>
|
|
319
|
+
<Text style={styles.settingLabel}>{label}</Text>
|
|
320
|
+
<Text style={[
|
|
321
|
+
styles.settingValue,
|
|
322
|
+
(copyable || onPress) && { color: primaryColor }
|
|
323
|
+
]}>
|
|
324
|
+
{value}
|
|
325
|
+
</Text>
|
|
326
|
+
</View>
|
|
327
|
+
</View>
|
|
328
|
+
{copyable && <OxyIcon name="copy" size={16} color="#ccc" />}
|
|
329
|
+
{showChevron && <OxyIcon name="chevron-forward" size={16} color="#ccc" />}
|
|
127
330
|
</TouchableOpacity>
|
|
128
|
-
|
|
129
|
-
|
|
331
|
+
);
|
|
332
|
+
};
|
|
130
333
|
|
|
131
334
|
return (
|
|
132
335
|
<View style={[styles.container, { backgroundColor }]}>
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
<TouchableOpacity
|
|
136
|
-
<
|
|
336
|
+
{/* Header */}
|
|
337
|
+
<View style={styles.header}>
|
|
338
|
+
<TouchableOpacity style={styles.cancelButton} onPress={onClose}>
|
|
339
|
+
<Ionicons name="close" size={24} color="#666" />
|
|
137
340
|
</TouchableOpacity>
|
|
341
|
+
<Text style={styles.headerTitle}>App Information</Text>
|
|
342
|
+
<View style={styles.placeholder} />
|
|
138
343
|
</View>
|
|
139
344
|
|
|
140
345
|
<ScrollView style={styles.content} showsVerticalScrollIndicator={false}>
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
<
|
|
144
|
-
|
|
145
|
-
<InfoRow
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
<InfoRow
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
346
|
+
{/* Package Information */}
|
|
347
|
+
<View style={styles.section}>
|
|
348
|
+
<Text style={styles.sectionTitle}>Package Information</Text>
|
|
349
|
+
|
|
350
|
+
<InfoRow
|
|
351
|
+
label="Name"
|
|
352
|
+
value={packageInfo.name}
|
|
353
|
+
copyable
|
|
354
|
+
iconComponent={<OxyServicesLogo width={20} height={20} />}
|
|
355
|
+
color="#007AFF"
|
|
356
|
+
isFirst
|
|
357
|
+
/>
|
|
358
|
+
<InfoRow
|
|
359
|
+
label="Version"
|
|
360
|
+
value={packageInfo.version}
|
|
361
|
+
copyable
|
|
362
|
+
icon="pricetag"
|
|
363
|
+
color="#5856D6"
|
|
364
|
+
/>
|
|
365
|
+
<InfoRow
|
|
366
|
+
label="Description"
|
|
367
|
+
value={packageInfo.description || 'No description'}
|
|
368
|
+
icon="document-text"
|
|
369
|
+
color="#34C759"
|
|
370
|
+
/>
|
|
371
|
+
<InfoRow
|
|
372
|
+
label="Main Entry"
|
|
373
|
+
value={packageInfo.main || 'N/A'}
|
|
374
|
+
icon="code"
|
|
375
|
+
color="#FF9500"
|
|
376
|
+
/>
|
|
377
|
+
<InfoRow
|
|
378
|
+
label="Module Entry"
|
|
379
|
+
value={packageInfo.module || 'N/A'}
|
|
380
|
+
icon="library"
|
|
381
|
+
color="#FF3B30"
|
|
382
|
+
/>
|
|
383
|
+
<InfoRow
|
|
384
|
+
label="Types Entry"
|
|
385
|
+
value={packageInfo.types || 'N/A'}
|
|
386
|
+
icon="construct"
|
|
387
|
+
color="#32D74B"
|
|
388
|
+
isLast
|
|
389
|
+
/>
|
|
390
|
+
</View>
|
|
391
|
+
|
|
392
|
+
{/* System Information */}
|
|
393
|
+
<View style={styles.section}>
|
|
394
|
+
<Text style={styles.sectionTitle}>System Information</Text>
|
|
395
|
+
|
|
396
|
+
<InfoRow
|
|
397
|
+
label="Platform"
|
|
398
|
+
value={Platform.OS}
|
|
399
|
+
icon="phone-portrait"
|
|
400
|
+
color="#007AFF"
|
|
401
|
+
isFirst
|
|
402
|
+
/>
|
|
403
|
+
<InfoRow
|
|
404
|
+
label="Platform Version"
|
|
405
|
+
value={systemInfo?.version || 'Loading...'}
|
|
406
|
+
icon="hardware-chip"
|
|
407
|
+
color="#5856D6"
|
|
408
|
+
/>
|
|
409
|
+
<InfoRow
|
|
410
|
+
label="Screen Width"
|
|
411
|
+
value={`${systemInfo?.screenDimensions.width || 0}px`}
|
|
412
|
+
icon="resize"
|
|
413
|
+
color="#FF9500"
|
|
414
|
+
/>
|
|
415
|
+
<InfoRow
|
|
416
|
+
label="Screen Height"
|
|
417
|
+
value={`${systemInfo?.screenDimensions.height || 0}px`}
|
|
418
|
+
icon="resize"
|
|
419
|
+
color="#FF3B30"
|
|
420
|
+
/>
|
|
421
|
+
<InfoRow
|
|
422
|
+
label="Environment"
|
|
423
|
+
value={__DEV__ ? 'Development' : 'Production'}
|
|
424
|
+
icon="settings"
|
|
425
|
+
color="#34C759"
|
|
426
|
+
isLast
|
|
427
|
+
/>
|
|
428
|
+
</View>
|
|
429
|
+
|
|
430
|
+
{/* User Information */}
|
|
431
|
+
<View style={styles.section}>
|
|
432
|
+
<Text style={styles.sectionTitle}>User Information</Text>
|
|
433
|
+
|
|
434
|
+
<InfoRow
|
|
435
|
+
label="Authentication Status"
|
|
436
|
+
value={user ? 'Authenticated' : 'Not Authenticated'}
|
|
437
|
+
icon="shield-checkmark"
|
|
438
|
+
color={user ? '#34C759' : '#FF3B30'}
|
|
439
|
+
isFirst
|
|
440
|
+
/>
|
|
160
441
|
{user && (
|
|
161
442
|
<>
|
|
162
|
-
<InfoRow
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
443
|
+
<InfoRow
|
|
444
|
+
label="User ID"
|
|
445
|
+
value={user.id}
|
|
446
|
+
copyable
|
|
447
|
+
icon="person"
|
|
448
|
+
color="#007AFF"
|
|
449
|
+
/>
|
|
450
|
+
<InfoRow
|
|
451
|
+
label="Username"
|
|
452
|
+
value={user.username || 'N/A'}
|
|
453
|
+
icon="at"
|
|
454
|
+
color="#5856D6"
|
|
455
|
+
onPress={() => {
|
|
456
|
+
if (user?.username && navigate) {
|
|
457
|
+
navigate('Profile', { userId: user.id });
|
|
458
|
+
} else {
|
|
459
|
+
toast.info('No username available or navigation not supported');
|
|
460
|
+
}
|
|
461
|
+
}}
|
|
462
|
+
showChevron={true}
|
|
463
|
+
/>
|
|
464
|
+
<InfoRow
|
|
465
|
+
label="Email"
|
|
466
|
+
value={user.email || 'N/A'}
|
|
467
|
+
icon="mail"
|
|
468
|
+
color="#FF9500"
|
|
469
|
+
/>
|
|
470
|
+
<InfoRow
|
|
471
|
+
label="Premium Status"
|
|
472
|
+
value={user.isPremium ? 'Premium' : 'Standard'}
|
|
473
|
+
icon="star"
|
|
474
|
+
color={user.isPremium ? '#FFD700' : '#8E8E93'}
|
|
475
|
+
/>
|
|
166
476
|
</>
|
|
167
477
|
)}
|
|
168
|
-
<InfoRow
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
<
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
478
|
+
<InfoRow
|
|
479
|
+
label="Total Active Sessions"
|
|
480
|
+
value={sessions?.length?.toString() || '0'}
|
|
481
|
+
icon="people"
|
|
482
|
+
color="#32D74B"
|
|
483
|
+
isLast
|
|
484
|
+
/>
|
|
485
|
+
</View>
|
|
486
|
+
|
|
487
|
+
{/* API Configuration */}
|
|
488
|
+
<View style={styles.section}>
|
|
489
|
+
<Text style={styles.sectionTitle}>API Configuration</Text>
|
|
490
|
+
|
|
491
|
+
<InfoRow
|
|
492
|
+
label="API Base URL"
|
|
493
|
+
value={oxyServices?.getBaseURL() || 'Not configured'}
|
|
494
|
+
copyable
|
|
495
|
+
icon="server"
|
|
496
|
+
color="#007AFF"
|
|
497
|
+
isFirst
|
|
498
|
+
/>
|
|
499
|
+
<InfoRow
|
|
500
|
+
label="Connection Status"
|
|
501
|
+
value={
|
|
502
|
+
connectionStatus === 'checking' ? 'Checking...' :
|
|
503
|
+
connectionStatus === 'connected' ? 'Connected' :
|
|
504
|
+
connectionStatus === 'disconnected' ? 'Disconnected' :
|
|
505
|
+
'Unknown'
|
|
506
|
+
}
|
|
507
|
+
icon={
|
|
508
|
+
connectionStatus === 'checking' ? 'sync' :
|
|
509
|
+
connectionStatus === 'connected' ? 'wifi' :
|
|
510
|
+
'wifi-off'
|
|
511
|
+
}
|
|
512
|
+
color={
|
|
513
|
+
connectionStatus === 'checking' ? '#FF9500' :
|
|
514
|
+
connectionStatus === 'connected' ? '#34C759' :
|
|
515
|
+
'#FF3B30'
|
|
516
|
+
}
|
|
517
|
+
onPress={async () => {
|
|
518
|
+
setConnectionStatus('checking');
|
|
519
|
+
const apiBaseUrl = oxyServices?.getBaseURL() || 'https://api.oxy.so';
|
|
520
|
+
try {
|
|
521
|
+
const response = await fetch(`${apiBaseUrl}/`, {
|
|
522
|
+
method: 'GET',
|
|
523
|
+
timeout: 3000,
|
|
524
|
+
} as any);
|
|
525
|
+
|
|
526
|
+
if (response.ok) {
|
|
527
|
+
setConnectionStatus('connected');
|
|
528
|
+
toast.success('API connection successful');
|
|
529
|
+
} else {
|
|
530
|
+
setConnectionStatus('disconnected');
|
|
531
|
+
toast.error(`API server error: ${response.status}`);
|
|
532
|
+
}
|
|
533
|
+
} catch (error) {
|
|
534
|
+
setConnectionStatus('disconnected');
|
|
535
|
+
toast.error('Failed to connect to API server');
|
|
536
|
+
}
|
|
537
|
+
}}
|
|
538
|
+
showChevron={true}
|
|
539
|
+
isLast
|
|
540
|
+
/>
|
|
541
|
+
</View>
|
|
542
|
+
|
|
543
|
+
{/* Build Information */}
|
|
544
|
+
<View style={styles.section}>
|
|
545
|
+
<Text style={styles.sectionTitle}>Build Information</Text>
|
|
546
|
+
|
|
547
|
+
<InfoRow
|
|
548
|
+
label="Build Timestamp"
|
|
549
|
+
value={systemInfo?.timestamp || 'Loading...'}
|
|
550
|
+
copyable
|
|
551
|
+
icon="time"
|
|
552
|
+
color="#007AFF"
|
|
553
|
+
isFirst
|
|
554
|
+
/>
|
|
555
|
+
<InfoRow
|
|
556
|
+
label="React Native"
|
|
557
|
+
value="Expo/React Native"
|
|
558
|
+
icon="logo-react"
|
|
559
|
+
color="#61DAFB"
|
|
560
|
+
/>
|
|
561
|
+
<InfoRow
|
|
562
|
+
label="JavaScript Engine"
|
|
563
|
+
value="Hermes"
|
|
564
|
+
icon="flash"
|
|
565
|
+
color="#FF3B30"
|
|
566
|
+
isLast
|
|
567
|
+
/>
|
|
568
|
+
</View>
|
|
569
|
+
|
|
570
|
+
{/* Quick Actions */}
|
|
571
|
+
<View style={styles.section}>
|
|
572
|
+
<Text style={styles.sectionTitle}>Quick Actions</Text>
|
|
573
|
+
|
|
189
574
|
<TouchableOpacity
|
|
190
|
-
style={[styles.
|
|
575
|
+
style={[styles.settingItem, styles.firstSettingItem]}
|
|
191
576
|
onPress={handleCopyFullReport}
|
|
192
577
|
>
|
|
193
|
-
<
|
|
578
|
+
<View style={styles.settingInfo}>
|
|
579
|
+
<OxyIcon name="copy" size={20} color="#007AFF" style={styles.settingIcon} />
|
|
580
|
+
<View style={styles.settingDetails}>
|
|
581
|
+
<Text style={styles.settingLabel}>Copy Full Report</Text>
|
|
582
|
+
<Text style={styles.settingDescription}>
|
|
583
|
+
Copy complete application information to clipboard
|
|
584
|
+
</Text>
|
|
585
|
+
</View>
|
|
586
|
+
</View>
|
|
587
|
+
<OxyIcon name="chevron-forward" size={16} color="#ccc" />
|
|
194
588
|
</TouchableOpacity>
|
|
195
589
|
|
|
196
590
|
<TouchableOpacity
|
|
197
|
-
style={[
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
591
|
+
style={[
|
|
592
|
+
styles.settingItem,
|
|
593
|
+
styles.lastSettingItem,
|
|
594
|
+
isRunningSystemCheck && styles.disabledSettingItem
|
|
595
|
+
]}
|
|
596
|
+
onPress={runSystemCheck}
|
|
597
|
+
disabled={isRunningSystemCheck}
|
|
201
598
|
>
|
|
202
|
-
<
|
|
599
|
+
<View style={styles.settingInfo}>
|
|
600
|
+
<OxyIcon
|
|
601
|
+
name={isRunningSystemCheck ? "sync" : "checkmark-circle"}
|
|
602
|
+
size={20}
|
|
603
|
+
color={isRunningSystemCheck ? "#FF9500" : "#34C759"}
|
|
604
|
+
style={[
|
|
605
|
+
styles.settingIcon,
|
|
606
|
+
isRunningSystemCheck && styles.spinningIcon
|
|
607
|
+
]}
|
|
608
|
+
/>
|
|
609
|
+
<View style={styles.settingDetails}>
|
|
610
|
+
<Text style={styles.settingLabel}>
|
|
611
|
+
{isRunningSystemCheck ? 'Running System Check...' : 'Run System Check'}
|
|
612
|
+
</Text>
|
|
613
|
+
<Text style={styles.settingDescription}>
|
|
614
|
+
{isRunningSystemCheck
|
|
615
|
+
? 'Checking API, authentication, and platform status...'
|
|
616
|
+
: 'Verify application health and status'
|
|
617
|
+
}
|
|
618
|
+
</Text>
|
|
619
|
+
</View>
|
|
620
|
+
</View>
|
|
621
|
+
{!isRunningSystemCheck && <OxyIcon name="chevron-forward" size={16} color="#ccc" />}
|
|
203
622
|
</TouchableOpacity>
|
|
204
623
|
</View>
|
|
205
624
|
</ScrollView>
|
|
@@ -213,74 +632,86 @@ const styles = StyleSheet.create({
|
|
|
213
632
|
},
|
|
214
633
|
header: {
|
|
215
634
|
flexDirection: 'row',
|
|
216
|
-
justifyContent: 'space-between',
|
|
217
635
|
alignItems: 'center',
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
fontSize: 20,
|
|
223
|
-
fontFamily: fontFamilies.phuduBold,
|
|
636
|
+
justifyContent: 'space-between',
|
|
637
|
+
paddingHorizontal: 16,
|
|
638
|
+
paddingVertical: 12,
|
|
639
|
+
backgroundColor: '#fff',
|
|
224
640
|
},
|
|
225
|
-
|
|
226
|
-
padding:
|
|
641
|
+
cancelButton: {
|
|
642
|
+
padding: 5,
|
|
227
643
|
},
|
|
228
|
-
|
|
644
|
+
headerTitle: {
|
|
229
645
|
fontSize: 24,
|
|
646
|
+
fontWeight: 'bold',
|
|
647
|
+
color: '#000',
|
|
230
648
|
fontFamily: fontFamilies.phuduBold,
|
|
231
649
|
},
|
|
650
|
+
placeholder: {
|
|
651
|
+
width: 34, // Same width as cancel button to center title
|
|
652
|
+
},
|
|
232
653
|
content: {
|
|
233
654
|
flex: 1,
|
|
234
655
|
padding: 16,
|
|
235
656
|
},
|
|
236
657
|
section: {
|
|
237
|
-
marginBottom:
|
|
238
|
-
borderRadius: 12,
|
|
239
|
-
padding: 16,
|
|
240
|
-
borderWidth: 1,
|
|
658
|
+
marginBottom: 24,
|
|
241
659
|
},
|
|
242
660
|
sectionTitle: {
|
|
243
|
-
fontSize:
|
|
244
|
-
|
|
661
|
+
fontSize: 16,
|
|
662
|
+
fontWeight: '600',
|
|
663
|
+
color: '#333',
|
|
245
664
|
marginBottom: 12,
|
|
665
|
+
fontFamily: fontFamilies.phuduSemiBold,
|
|
246
666
|
},
|
|
247
|
-
|
|
667
|
+
settingItem: {
|
|
668
|
+
backgroundColor: '#fff',
|
|
669
|
+
padding: 16,
|
|
248
670
|
flexDirection: 'row',
|
|
671
|
+
alignItems: 'center',
|
|
249
672
|
justifyContent: 'space-between',
|
|
250
|
-
|
|
673
|
+
marginBottom: 2,
|
|
674
|
+
},
|
|
675
|
+
firstSettingItem: {
|
|
676
|
+
borderTopLeftRadius: 24,
|
|
677
|
+
borderTopRightRadius: 24,
|
|
678
|
+
},
|
|
679
|
+
lastSettingItem: {
|
|
680
|
+
borderBottomLeftRadius: 24,
|
|
681
|
+
borderBottomRightRadius: 24,
|
|
251
682
|
marginBottom: 8,
|
|
252
|
-
minHeight: 24,
|
|
253
683
|
},
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
684
|
+
settingInfo: {
|
|
685
|
+
flexDirection: 'row',
|
|
686
|
+
alignItems: 'center',
|
|
257
687
|
flex: 1,
|
|
688
|
+
},
|
|
689
|
+
settingIcon: {
|
|
258
690
|
marginRight: 12,
|
|
259
691
|
},
|
|
260
|
-
|
|
261
|
-
flex:
|
|
692
|
+
settingDetails: {
|
|
693
|
+
flex: 1,
|
|
262
694
|
},
|
|
263
|
-
|
|
695
|
+
settingLabel: {
|
|
696
|
+
fontSize: 16,
|
|
697
|
+
fontWeight: '500',
|
|
698
|
+
color: '#333',
|
|
699
|
+
marginBottom: 2,
|
|
700
|
+
},
|
|
701
|
+
settingValue: {
|
|
264
702
|
fontSize: 14,
|
|
265
|
-
|
|
266
|
-
textAlign: 'right',
|
|
267
|
-
flexWrap: 'wrap',
|
|
703
|
+
color: '#666',
|
|
268
704
|
},
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
705
|
+
settingDescription: {
|
|
706
|
+
fontSize: 14,
|
|
707
|
+
color: '#999',
|
|
272
708
|
},
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
paddingHorizontal: 24,
|
|
276
|
-
borderRadius: 8,
|
|
277
|
-
marginBottom: 12,
|
|
278
|
-
alignItems: 'center',
|
|
709
|
+
disabledSettingItem: {
|
|
710
|
+
opacity: 0.6,
|
|
279
711
|
},
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
fontFamily: fontFamilies.phuduMedium,
|
|
712
|
+
spinningIcon: {
|
|
713
|
+
// Note: Animation would need to be implemented with Animated API
|
|
714
|
+
// For now, just showing the sync icon to indicate loading
|
|
284
715
|
},
|
|
285
716
|
});
|
|
286
717
|
|