import React, { useState, useEffect, useRef } from 'react';
import { View, Text, Button, Image, StyleSheet } from 'react-native';
import { Camera } from 'expo-camera';
export default function CameraScreen() {
const [hasPermission, setHasPermission] = useState(null);
const [photoUri, setPhotoUri] = useState(null);
const cameraRef = useRef(null);
useEffect(() => {
(async () => {
const { status } = await Camera.requestCameraPermissionsAsync();
setHasPermission(status === 'granted');
})();
}, []);
const takePicture = async () => {
if (cameraRef.current) {
const photo = await cameraRef.current.takePictureAsync();
setPhotoUri(photo.uri);
}
};
if (hasPermission === null) {
return <View style={styles.container}><Text>Requesting camera permission...</Text></View>;
}
if (hasPermission === false) {
return <View style={styles.container}><Text>No access to camera</Text></View>;
}
return (
<View style={styles.container}>
<Camera style={styles.camera} ref={cameraRef} />
<Button title="Snap" onPress={takePicture} />
{photoUri && <Image source={{ uri: photoUri }} style={styles.photo} />}
</View>
);
}
const styles = StyleSheet.create({
container: { flex: 1, justifyContent: 'center', alignItems: 'center' },
camera: { width: 300, height: 400 },
photo: { width: 300, height: 400, marginTop: 10 }
});This solution first asks the user for camera permission when the screen loads using Camera.requestCameraPermissionsAsync(). The permission status is saved in state.
If permission is granted, the camera preview is shown using the Camera component from expo-camera. We keep a reference to the camera with useRef so we can call takePictureAsync() when the user presses the 'Snap' button.
When the button is pressed, the app takes a photo and saves its URI in state. Then the photo is displayed below the button using an Image component.
If permission is denied, a simple message 'No access to camera' is shown instead.
This approach keeps the UI simple and clear, and handles permission states properly.