React Native の expo-camera の使い方
「React Native」の 「expo-camera」の使い方をまとめました。
前回
1. expo-camera
「expo-camera」は、「Expo」を利用した「React Native」アプリでカメラ機能をサポートするライブラリです。「Expo」は「React Native」アプリの開発を簡単にするツールキットになります。
2. expo-camera の使い方
「expo-camera」の使い方は、次のとおりです。
2-1. React Nativeプロジェクトの作成
(1) React Nativeプロジェクトの作成。
npx react-native init my_app
cd my_app
(2) パッケージのインストール。
npx install-expo-modules
npm install expo-camera
2-2. Androidのセットアップ
(1) 「AndroidManifest.xml」に「CAMERA」と「RECORD_AUDIO」のパーミッションを追加。
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
:
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.RECORD_AUDIO" />
(2) android/build.gradle に以下のブロックを追加。
allprojects {
repositories {
// * Your other repositories here *
// * Add a new maven block after other repositories / blocks *
maven {
// expo-camera bundles a custom com.google.android:cameraview
url "$rootDir/../node_modules/expo-camera/android/maven"
}
}
}
2-3. iOSのセットアップ
(1) podのインストール。
cd ios
pod install
cd ..
(2) Xcodeで署名し、iPhoneにインストールできることを確認。
xcworkspaceを開いた時に以下のエラーがでた場合、「Build Settings → Swift Compiler - Language」でバージョン「Swift 4.2」を指定することで解決しました。
(3) 「Info.plist」に以下の項目を追加。
<key>NSCameraUsageDescription</key>
<string>カメラを使用します。</string>
<key>NSMicrophoneUsageDescription</key>
<string>マイクを使用します。</string>
2-4. カメラの起動
(1) コードの編集。
・App.tsx
import { CameraView, useCameraPermissions } from 'expo-camera';
import { useState } from 'react';
import { Button, Text, TouchableOpacity, View } from 'react-native';
// アプリ
const App: React.FC = () => {
const [permission, requestPermission] = useCameraPermissions();
const [camera, setCamera] = useState<CameraView | null>(null);
// カメラパーミッションのロード中
if (!permission) {
return <View />;
}
// カメラ権限はまだ付与されていない
if (!permission.granted) {
return (
<View style={{ flex: 1, justifyContent: 'center' }}>
<Button onPress={requestPermission} title="カメラの起動を許可" />
</View>
);
}
// 写真の撮影
async function takePicture() {
if (camera) {
const photo = await camera.takePictureAsync();
console.log(photo);
// ここで撮影した写真を処理(保存、表示など)
}
}
// UI
return (
<View style={{ flex: 1, justifyContent: 'center' }}>
<CameraView
style={{ flex: 1 }}
ref={(ref) => setCamera(ref)}
>
<View style={{ position: 'absolute', bottom: 20, alignSelf: 'center', backgroundColor: 'blue', }}>
<TouchableOpacity onPress={takePicture}>
<Text style={{ fontSize: 24, fontWeight: 'bold', color: 'white', padding: 10 }}>写真の撮影</Text>
</TouchableOpacity>
</View>
</CameraView>
</View>
);
}
export default App;
(2) コードの実行。
npm start
3. QRコードスキャン
QRコードスキャンして標準出力する機能を追加します。
(1) コードの編集。
import { CameraView, useCameraPermissions, BarcodeScanningResult } from 'expo-camera';
import { useState } from 'react';
import { Button, Text, TouchableOpacity, View } from 'react-native';
// アプリ
const App: React.FC = () => {
const [permission, requestPermission] = useCameraPermissions();
const [camera, setCamera] = useState<CameraView | null>(null);
// カメラパーミッションのロード中
if (!permission) {
return <View />;
}
// カメラ権限はまだ付与されていない
if (!permission.granted) {
return (
<View style={{ flex: 1, justifyContent: 'center' }}>
<Button onPress={requestPermission} title="カメラの起動を許可" />
</View>
);
}
// 写真の撮影
async function takePicture() {
if (camera) {
const photo = await camera.takePictureAsync();
console.log(photo);
// ここで撮影した写真を処理(保存、表示など)
}
}
// バーコードスキャン時に呼ばれる
function onBarcodeScanned(scanningResult: BarcodeScanningResult) {
// バーコードスキャンした情報
console.log(scanningResult)
}
// UI
return (
<View style={{ flex: 1, justifyContent: 'center' }}>
<CameraView
style={{ flex: 1 }}
ref={(ref) => setCamera(ref)}
barcodeScannerSettings={{ barcodeTypes: ["qr"] }}
onBarcodeScanned={onBarcodeScanned}
>
<View style={{ position: 'absolute', bottom: 20, alignSelf: 'center', backgroundColor: 'blue', }}>
<TouchableOpacity onPress={takePicture}>
<Text style={{ fontSize: 24, fontWeight: 'bold', color: 'white', padding: 10 }}>写真の撮影</Text>
</TouchableOpacity>
</View>
</CameraView>
</View>
);
}
export default App;
(2) コードの実行。
QRコードがカメラ映像に映るとログ出力されます。
npm start
{"boundingBox": {"origin": {"x": 287.2727355957031, "y": 88.36363983154297}, "size": {"height": 101.45454406738281, "width": 150.18182373046875}}, "cornerPoints": [{"x": 88.36363983154297, "y": 287.2727355957031}, {"x": 93.09091186523438, "y": 431.6363525390625}, {"x": 188.36363220214844, "y": 437.4545593261719}, {"x": 189.81817626953125, "y": 294.9090881347656}], "data": "https://docs.expo.dev/", "raw": "https://docs.expo.dev/", "target": 33, "type": "qr"}