167 lines
4.8 KiB
TypeScript
167 lines
4.8 KiB
TypeScript
import React, { useState, useEffect } from 'react';
|
|
import { StyleSheet, View, SafeAreaView, StatusBar } from 'react-native';
|
|
import { GestureHandlerRootView } from 'react-native-gesture-handler';
|
|
import CameraScreen from './src/screens/CameraScreen';
|
|
import PreviewScreen from './src/screens/PreviewScreen';
|
|
import AdminScreen from './src/screens/AdminScreen';
|
|
import { loadSettings, AppSettings } from './src/services/settings';
|
|
import KioskMode from './modules/kiosk-mode';
|
|
|
|
type ScreenState = 'home' | 'camera' | 'preview' | 'admin';
|
|
|
|
export default function App() {
|
|
const [currentScreen, setCurrentScreen] = useState<ScreenState>('home');
|
|
const [photoUris, setPhotoUris] = useState<string[]>([]);
|
|
const [settings, setSettings] = useState<AppSettings | null>(null);
|
|
|
|
// 1. Load configuration settings on app start
|
|
useEffect(() => {
|
|
async function initApp() {
|
|
const savedSettings = await loadSettings();
|
|
setSettings(savedSettings);
|
|
|
|
// Auto-start Kiosk mode if it was configured as enabled
|
|
if (savedSettings.kioskModeEnabled) {
|
|
try {
|
|
KioskMode.startKiosk();
|
|
} catch (e) {
|
|
console.warn('Failed to auto-start Kiosk mode:', e);
|
|
}
|
|
}
|
|
}
|
|
initApp();
|
|
}, []);
|
|
|
|
if (!settings) {
|
|
return <View style={styles.loadingContainer} />;
|
|
}
|
|
|
|
// 2. Navigation Actions
|
|
const handleStartBooth = () => {
|
|
setPhotoUris([]);
|
|
setCurrentScreen('camera');
|
|
};
|
|
|
|
const handlePhotoCaptured = (uri: string) => {
|
|
setPhotoUris((prev) => [...prev, uri]);
|
|
setCurrentScreen('preview');
|
|
};
|
|
|
|
// Called by CameraScreen when burst mode completes all photos
|
|
const handleBurstComplete = (uris: string[]) => {
|
|
setPhotoUris((prev) => [...prev, ...uris]);
|
|
setCurrentScreen('preview');
|
|
};
|
|
|
|
const handleRetakeLast = () => {
|
|
// Remove last captured photo
|
|
const updatedUris = [...photoUris];
|
|
updatedUris.pop();
|
|
setPhotoUris(updatedUris);
|
|
|
|
// Always let user retake
|
|
setCurrentScreen('camera');
|
|
};
|
|
|
|
const handleAddAnother = () => {
|
|
setCurrentScreen('camera');
|
|
};
|
|
|
|
const handleReset = () => {
|
|
setPhotoUris([]);
|
|
setCurrentScreen('home');
|
|
};
|
|
|
|
const handleSaveSettings = (updated: AppSettings) => {
|
|
setSettings(updated);
|
|
};
|
|
|
|
const handleOpenAdmin = () => {
|
|
setCurrentScreen('admin');
|
|
};
|
|
|
|
// 3. Conditional Screen Rendering
|
|
const renderScreen = () => {
|
|
switch (currentScreen) {
|
|
case 'camera':
|
|
return (
|
|
<CameraScreen
|
|
countdownDuration={settings.countdownDuration}
|
|
onPhotoCaptured={handlePhotoCaptured}
|
|
onBurstComplete={handleBurstComplete}
|
|
onCancel={handleReset}
|
|
isIdle={false}
|
|
burstCount={settings.burstCount}
|
|
burstIntervalSec={settings.burstIntervalSec}
|
|
frameMode={settings.frameMode}
|
|
selectedFrameId={settings.selectedFrameId}
|
|
/>
|
|
);
|
|
case 'preview':
|
|
return (
|
|
<PreviewScreen
|
|
photoUris={photoUris}
|
|
printerIp={settings.printerIp}
|
|
onRetakeLast={handleRetakeLast}
|
|
onAddAnother={handleAddAnother}
|
|
onReset={handleReset}
|
|
frameMode={settings.frameMode}
|
|
initialFrameId={settings.selectedFrameId}
|
|
availableFrameIds={settings.availableFrameIds}
|
|
dateOverlay={settings.dateOverlay}
|
|
dateOverlayPosition={settings.dateOverlayPosition}
|
|
eventText={settings.eventText}
|
|
/>
|
|
);
|
|
case 'admin':
|
|
return (
|
|
<AdminScreen
|
|
currentSettings={settings}
|
|
onSave={handleSaveSettings}
|
|
onClose={() => setCurrentScreen('home')}
|
|
/>
|
|
);
|
|
default:
|
|
return (
|
|
<CameraScreen
|
|
countdownDuration={settings.countdownDuration}
|
|
onPhotoCaptured={handlePhotoCaptured}
|
|
onBurstComplete={handleBurstComplete}
|
|
onCancel={handleReset}
|
|
isIdle={true}
|
|
onStartBooth={handleStartBooth}
|
|
onNavigateToAdmin={handleOpenAdmin}
|
|
adminPassword={settings.adminPassword}
|
|
welcomeText={settings.welcomeText}
|
|
burstCount={settings.burstCount}
|
|
burstIntervalSec={settings.burstIntervalSec}
|
|
frameMode={settings.frameMode}
|
|
selectedFrameId={settings.selectedFrameId}
|
|
/>
|
|
);
|
|
}
|
|
};
|
|
|
|
return (
|
|
<GestureHandlerRootView style={styles.container}>
|
|
<SafeAreaView style={styles.container}>
|
|
<StatusBar hidden={true} />
|
|
{renderScreen()}
|
|
</SafeAreaView>
|
|
</GestureHandlerRootView>
|
|
);
|
|
}
|
|
|
|
const styles = StyleSheet.create({
|
|
container: {
|
|
flex: 1,
|
|
backgroundColor: '#050510',
|
|
},
|
|
loadingContainer: {
|
|
flex: 1,
|
|
backgroundColor: '#050510',
|
|
justifyContent: 'center',
|
|
alignItems: 'center',
|
|
},
|
|
});
|