React NativeExamples · Props · Code

QR Code Scanner in React Native

To scan a QR code in React Native, use expo-camera’s CameraView with onBarcodeScanned. The tricky parts are permissions and stopping after the first scan — both handled below.

Install

npx expo install expo-camera

Scanner example

Restrict barcodeTypes to 'qr' and debounce so one code fires the callback once:

// npx expo install expo-camera
import { useState } from 'react';
import { Text, View } from 'react-native';
import { CameraView, useCameraPermissions } from 'expo-camera';

function QRScanner({ onScan }) {
  const [permission, requestPermission] = useCameraPermissions();
  const [scanned, setScanned] = useState(false);

  if (!permission) return <View />;                 // still loading
  if (!permission.granted) {
    requestPermission();
    return <Text style={{ padding: 24 }}>Camera permission needed to scan.</Text>;
  }

  return (
    <CameraView
      style={{ flex: 1 }}
      barcodeScannerSettings={{ barcodeTypes: ['qr'] }}
      onBarcodeScanned={
        scanned
          ? undefined                                // stop after one scan
          : ({ data }) => { setScanned(true); onScan(data); }
      }
    />
  );
}

Props (CameraView)

PropTypeDefaultDescription
barcodeScannerSettingsobjectSet { barcodeTypes: ['qr'] } to scan only QR.
onBarcodeScannedfnFires with { data, type } on each detection.
facing'back'|'front''back'Which camera to use.
enableTorchbooleanfalseFlashlight for low light.

Gotchas

  • onBarcodeScanned fires many times per second. Debounce with a scannedflag or you’ll trigger navigation dozens of times.
  • Handle all three permission states: still-loading (!permission), denied, and granted. Skipping the loading state crashes.
  • The camera doesn’t work in the iOS simulator or web preview — test on a real device.
  • Add the camera usage string to app.json (expo-camera plugin) or the build is rejected by the stores.

FAQ

How do I scan a QR code in React Native? Use expo-camera’s CameraView with onBarcodeScanned and barcodeTypes: ['qr'].

Why does my scanner fire repeatedly? Because the camera detects the code every frame — gate the callback with a one-time scanned flag.

Related components

Skip the boilerplate

Describe your screen in ShipNative and it wires up the component for you — in a real, exportable React Native app.

Generate it with AI →