Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

🐛 App unable to go to sleep once camera loads #3041

Open
3 of 5 tasks
FoundersApproach opened this issue Jul 2, 2024 · 1 comment
Open
3 of 5 tasks

🐛 App unable to go to sleep once camera loads #3041

FoundersApproach opened this issue Jul 2, 2024 · 1 comment
Labels
🐛 bug Something isn't working

Comments

@FoundersApproach
Copy link

What's happening?

Once camera library loads in one screen and going back to previous screen in stack navigation then app unable to goes to sleep. May be camera reference object is unable to let app sleep ?

I did some object reference clearance in component unmount but no luck. Please help!

Reproduceable Code

import React, { useState, useEffect, useCallback } from 'react';
import { View, Text, TouchableOpacity, Alert, Platform, StyleSheet, PermissionsAndroid, Image, AppState } from 'react-native';
import {Camera, useCameraDevices, useCameraDevice,useCameraFormat, Templates, useCodeScanner } from 'react-native-vision-camera';
import TextRecognition from '@react-native-ml-kit/text-recognition';
import AppConstants from '../module/constantVairable'
import { getCameraFace, getCurrentOrientation, getDeviceHeight, getDeviceWidth, getSafeAreaInsetBottom, getSafeAreaInsetTop, getTorchOn, isOrientationPortrait, setCameraRef, setScanLog, verifyGTINChecksum } from '../api/api';
import { Gesture, GestureDetector } from 'react-native-gesture-handler'
import ImageResizer from '@bam.tech/react-native-image-resizer';
import { RFValue } from 'react-native-responsive-fontsize';
import RNFS from 'react-native-fs';
import Animated, { runOnJS } from 'react-native-reanimated';


let cameraRef = null
let capturePhotoInteval = false
let focusPointTimer = false

const ScannerFunction = (props) => {
    const device = useCameraDevice(getCameraFace());
    const [permissionGranted, setPermissionGranted] = useState(false);
    const [isInitialized, setIsInitialized] = useState(false);
    const [torch, setTorch] = useState(false);
    const [restartCamera, setRestartCamera] = useState(false);
    const [cameraActive, setCameraActive] = useState(true);

    const [tapLocation, setTapLocation] = useState(null);


    useEffect(() => {
        // let appStateListener = AppState.addEventListener('change', appStateChangeListener);
        if (Platform.OS === 'android') {
          askCameraPermission();
        }
        else {
          setPermissionGranted(true)
          if (device && device.hasTorch && getTorchOn()) {
            setTorch(true)
          }
        }
        startCaptureTimer(2)
        
        return () => {
          cameraRef = null
          console.log("ScannerFunction unmount>>>>")
          setCameraActive(false)
          setTorch(false)
          setPermissionGranted(false)
          stopCaptureTimer()
          setCameraRef(null)
        }
    }, []);

    const startCaptureTimer = (sec=1) => {
      // console.log("startCaptureTimer>>>>")
      if (capturePhotoInteval) {
        clearInterval(capturePhotoInteval);
      }

      capturePhotoInteval = setInterval(() => {
        // console.log("capturePhotoInteval")
        capturePhoto()
      }, 2 * 1000);
    }

    const stopCaptureTimer = () => {
      if (capturePhotoInteval) {
        // console.log("clear interval")
        clearInterval(capturePhotoInteval);
      }
    }

    const format1 = useCameraFormat(device, [
      { photoResolution: "max" },
    ])

    const askCameraPermission = async () => {
      const granted = await PermissionsAndroid.request(
        PermissionsAndroid.PERMISSIONS.CAMERA,
        {
          title: "Camera Permission",
          message: "This app needs access to your camera ",
        }
      );
      if (granted === PermissionsAndroid.RESULTS.GRANTED) {
        console.log("You can use the camera");
        setPermissionGranted(true)
      } else {
        console.log("Camera permission denied");
      }
    }

    const parseText = (line, wholeText="", photoUrl="") => {
    }

    const capturePhoto = async () => {
      
        try {
          if (props.is_active) {
            if (cameraRef) {

              const photo = await cameraRef.takePhoto({
                qualityPrioritization: "quality",
                flash: "off",
                enableAutoStabilization: true,
                enableShutterSound: false
              });

              let photoUrl = "file://"+photo.path
  
              stopCaptureTimer()
              const result = await TextRecognition.recognize(photoUrl);
              
              for (let block of result.blocks) {
                
              
                for (let line of block.lines) {
                  setScanLog(line.text)
                  parseText(line.text, result.text, photoUrl)
                }
              }
  
              startCaptureTimer(2)
              
            }
            else {
              // Alert.alert("Camera not found")
            }
          }
          
        } catch (error) {
          setCameraActive(false)
          setCameraRef(null)
          cameraRef = null
          props.onError(error)
          console.log("Error>>>>>>>>>>>>", error.message)
        }
        
    }

    const focus = useCallback((point: Point) => {
      const c = cameraRef
      if (c == null) return
      c.focus(point)
      setTapLocation({x: point.x - RFValue(35), y: point.y - RFValue(35)})
      if (focusPointTimer) {
        clearTimeout(focusPointTimer)
      }
      focusPointTimer = setTimeout(() => {
        setTapLocation(null)
      }, 2 * 1000)
    }, [])

    const gesture = Gesture.Tap()
    .onEnd(({ x, y }) => {
      runOnJS(focus)({ x, y })
    })

    const _onError = (error) => {
    }

    return(
      <View style={{flex: 1, overflow: "hidden", backgroundColor: "black"}}>
      {/* <GestureDetector gesture={_gesture}> */}
      {
        device && device.hasTorch ? (
          <TouchableOpacity 
              onPress={() => setTorch(!torch)}
              style={{position: 'absolute', zIndex: 999 ,
              top: isOrientationPortrait() ? RFValue(10) : null, 
              bottom: isOrientationPortrait() ? null : (getSafeAreaInsetTop() + getSafeAreaInsetBottom() + RFValue(10)),
              right: RFValue(10), 
              height: RFValue(35), 
              width: RFValue(35), 
              transform: [{rotate: isOrientationPortrait() ? '0deg' : '-270deg'}],
              borderRadius: RFValue(5) ,backgroundColor: "#ffffff99", 
              alignItems: 'center', justifyContent: 'center'}}>
              <Image resizeMode='contain' style={{height: '65%', width: '65%'}} 
                  source={torch ? Theme.icons.ic_camera_light_off : Theme.icons.ic_camera_light_on}></Image>
          </TouchableOpacity> 
        ) : null
      }
      
      {/* this.onStopped = this.onStopped.bind(this)
    this.onError = this.onError.bind(this) */}

      {
        device && permissionGranted && props.is_active ? (
          <View style={{flex: 1}}>
          <GestureDetector gesture={gesture}>
          <Camera
            onError={(error)=>props.onError(error)}
          orientation={getCurrentOrientation()}
          torch={torch ? "on" : "off"}
          onInitialized={() => {
            setIsInitialized(true);
            setCameraRef(cameraRef)
          }}
              style={
                isInitialized
                  ? {
                      position: "absolute",
                      top: 0,
                      left: 0,
                      right: 0,
                      bottom: 0
                    }
                  : {
                      width: 0,
                      height: 0,
                    }
               }
              device={device}
              isActive={cameraActive}
              photo={true}
              ref={(ref) => cameraRef = ref}
              
            />
            
            </GestureDetector>
            {
              tapLocation && (
                <Animated.View
                  style={[
                    styles.indicator,
                    {
                      transform: [
                        { translateX: tapLocation.x - 15 },
                        { translateY: tapLocation.y - 15 },
                      ],
                    },
                  ]}
                />
              )
            }
            

            </View>
        ) : null
      }
      </View>
    )
}
export default ScannerFunction;

const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: 'transparent',
  },
  indicator: {
    width: RFValue(70),
    height: RFValue(70),
    borderRadius: RFValue(70),
    position: 'absolute',
    borderWidth: 4,
    borderColor: Theme.colors.appThemeColor,
  },
});

Relevant log output

This issue seems different so no log helps

Camera Device

<Camera
            onError={(error)=>props.onError(error)}
          orientation={getCurrentOrientation()}
          torch={torch ? "on" : "off"}
          onInitialized={() => {
            setIsInitialized(true);
            setCameraRef(cameraRef)
          }}
              style={
                isInitialized
                  ? {
                      position: "absolute",
                      top: 0,
                      left: 0,
                      right: 0,
                      bottom: 0
                    }
                  : {
                      width: 0,
                      height: 0,
                    }
               }
              device={device}
              isActive={cameraActive}
              photo={true}
              ref={(ref) => cameraRef = ref}
              
            />

Device

iPhone 14 plus (ios 17.1.1)

VisionCamera Version

"react-native-vision-camera": "^3.9.2"

Can you reproduce this issue in the VisionCamera Example app?

Yes, I can reproduce the same issue in the Example app here

Additional information

@FoundersApproach FoundersApproach added the 🐛 bug Something isn't working label Jul 2, 2024
@maintenance-hans maintenance-hans bot changed the title App unable to go to sleep once camera loads🐛 Jul 2, 2024
Copy link

Guten Tag, Hans here.

Note

New features, bugfixes, updates and other improvements are all handled mostly by @mrousavy in his free time.
To support @mrousavy, please consider 💖 sponsoring him on GitHub 💖.
Sponsored issues will be prioritized.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
🐛 bug Something isn't working
1 participant