I am tasked with the problem of creating a react-native using expo-opencv, expo-camera, Canny, Contour detection library or SIFT to get distance between the shoulders, the length of the inseam, chest circumference, waist circumference, length of the arms , length of the legs , arm/wrist circumference and leg circumference
I need some help which libraries to use and how to integrate all of them. this is what is have tried:
import React, { useState } from 'react';
import { Text, View, TouchableOpacity, Image } from 'react-native';
import { Camera } from 'expo-camera';
import * as cv from 'expo-opencv';
const BodyMeasurement = () => {
const [hasPermission, setHasPermission] = useState(null);
const [image, setImage] = useState(null);
useEffect(() => {
(async () => {
const { status } = await Camera.requestPermissionsAsync();
setHasPermission(status === 'granted');
})();
}, []);
if (hasPermission === null) {
return <View />;
}
if (hasPermission === false) {
return <Text>No access to camera</Text>;
}
const takePicture = async () => {
const photo = await camera.takePictureAsync();
setImage(photo.uri);
processImage(photo.uri);
};
const processImage = async (imageUri) => {
const mat = cv.imread(imageUri);
// perform image processing using OpenCV functions
// for example, converting the image to grayscale
const grayMat = cv.cvtColor(mat, cv.COLOR_RGBA2GRAY);
// Extract measurement using OpenCV functions
//
// ...
};
return (
<View>
{image ? (
<Image source={{ uri: image }} style={{ width: '100%', height: 300 }} />
) : (
<Camera
style={{ flex: 1 }}
type={Camera.Constants.Type.back}
ref={ref => {
this.camera = ref;
}}>
<View style={{ flex: 1, backgroundColor: 'transparent', alignItems: 'center' }}>
<TouchableOpacity
style={{
flex: 0.1,
alignSelf: 'flex-end',
alignItems: 'center',
}}
onPress={() => {
takePicture();
}}>
<Text style={{ fontSize: 18, marginBottom: 10, color: 'white' }}>
{' '}Take Picture{' '}
</Text>
</TouchableOpacity>
</View>
</Camera>
)}
</View>
);
};
export default BodyMeasurement;
Related
this may sound stupid for the most of you but I'm new when it comes to using API and react native. My situation is the next. From my data I try to display questions and a text field so the customer can answer and therefore I retrieve the data. But my problem is the next on when I display and try to write in the TextInput no matter how I have they will all copy what I write in which ever one I'm writing on. I don't get what I am doing wrong. I tried with looping but I can't seem to get the right answer to solve my problem. Here's my code if someone can help me.
//import liraries
import React, { Component, useEffect, useState } from 'react';
import {
View,
Text,
StyleSheet,
FlatList,
TextInput,
Picker,
} from 'react-native';
// create a component
const Get = ({ navigation }) => {
const [user, setUser] = useState();
// const [text, onChangeText] = React.useState(null);
const [selectedValue, setSelectedValue] = useState("Test");
const [text, onChangeText] = useState('');
const getUserData = async () => {
try {
let response = await fetch('https://survey-back-nmucl6ui6q-ey.a.run.app/survey/7b504f09-7a67-4f99-a402-c15a9388446c', {
headers: new Headers({
'Authorization': 'eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE2NTUxNTU1MjMsImlhdCI6MTY1NTA2OTExOCwic3ViIjoxfQ.eoLaDT4wP99yjC38DN2Zck2sgwXFvcRYrfzxszHkQvc',
'Content-Type': 'application/x-www-form-urlencoded'
}),
});
let json = await response.json();
console.log(json.question)
setUser(json.question);
} catch (error) {
console.error(error);
}
};
useState(() => {
getUserData();
}, []);
const renderItem = ({ item }) => {
return (
<View
style={{
borderBottomWidth: 1,
borderBottomColor: '#ccc',
padding: 5,
}}>
{item.question_type == 'text-field' ?
<View style={styles.questions}>
<Text style={styles.label}>{item.name}</Text>
<TextInput
style={styles.input}
onChangeText={onChangeText}
value={text}
placeholder="Entrez votre réponse"
/>
</View>
: <Text>Erreur</Text>}
{item.question_type == 'select' ?
<View style={styles.questions}>
<Text style={styles.label}>{item.name}</Text>
<Picker
selectedValue={selectedValue}
onValueChange={(itemValue, itemIndex) =>
setSelectedValue(itemValue)}
>
{Object.keys(item.choice).map(key =>{
return (
<Picker.Item label={key} value={key} key={key} />
)
})}
</Picker>
</View>
: <Text style={{display: 'none'}}>Erreur</Text>}
<View>
{item.question_type == 'comboboxMulti' ?
<Text style={{ fontWeight: 'bold' }}>{item.name}</Text>
: <Text style={{display: 'none'}}>Ça marche pas</Text>}
</View>
</View>
);
};
return (
<View style={styles.container}>
<FlatList
data={user}
renderItem={renderItem}
keyExtractor={(item) => item.id}
/>
</View>
);
};
// define your styles
const styles = StyleSheet.create({
container: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
backgroundColor: '#fff',
},
input: {
height: 40,
margin: 12,
borderWidth: 1,
padding: 10,
borderRadius: 5,
marginLeft: 0,
},
label: {
textTransform: 'capitalize',
},
questions: {
justifyContent: 'center',
alignItems: 'start',
}
});
//make this component available to the app
export default Get;
I have the video displaying with the controls, but I can't get the video to become full screen in landscape when full screen is clicked or when the phone is rotated. I'm using react-native-video-controls which uses react-native-video as a dependency.
import React from "react";
import { View, StyleSheet, Dimensions, Text } from 'react-native';
import VideoPlayer from 'react-native-video-controls';
import OverlayButton from '../../../Images/overlay-button.svg';
const {width, height} = Dimensions.get("window");
const stylesCustom = StyleSheet.create({
galleryContainer: {
backgroundColor: 'rgba(255,255,255,0.1)'
},
header: {
position: 'absolute',
top: 50,
zIndex: 100,
width: '100%',
paddingBottom: 10
}
});
const VideoModal = (props) => {
return (
<View style={[stylesCustom.galleryContainer]}>
<View style={[stylesCustom.header]}>
<View style={{ left: 20 }}>
<OverlayButton onPress={() => props.handleCloseModal()}/>
</View>
</View>
<View style={stylesCustom.image}>
<VideoPlayer
source={{ uri: `${props.streamingUrl}(format=m3u8-aapl)` }}
control={true}
paused={false}
ignoreSilentSwitch="ignore"
disableBack
fullscreenOrientation="landscape"
fullscreen="true"
/>
</View>
</View>
);
}
export default VideoModal;
first download dependencies react-native-orientation-locker
then
import Orientation from 'react-native-orientation-locker';
after that add below code
const [fullScreen, setFullScreen] = useState(false);
const FullScreen = () => {
if(fullScreen){
Orientation.lockToPortrait();
} else{
Orientation.lockToLandscape();
}
setFullScreen(!fullScreen)
}
and in the return
<View style= {fullScreen ? styles.fullscreenVideo : styles.video }>
<Video
fullscreen = {fullScreen}
ref={video}
source={{
uri:videos,
type:'mpd'
}}
style={{...StyleSheet.absoluteFill}}
/>
</View>
and Style
fullscreenVideo:{
backgroundColor: 'black',
...StyleSheet.absoluteFill,
elevation: 1,
},
you can be fixed horizontally when the screen is full.
you can use react-native-orientation-locker
Useage
import Orientation from 'react-native-orientation-locker';
...
Orientation.lockToLandscape();
try this for fullscreen with video controls and landscape:-
import React,{useRef,useState,useEffect} from 'react';
import { View ,StyleSheet,BackHandler,Dimensions,TouchableNativeFeedback,Text,StatusBar} from 'react-native';
import Video from 'react-native-video';
import Orientation from 'react-native-orientation';
import Icon from 'react-native-vector-icons/MaterialIcons';
import Slider from '#react-native-community/slider';
let url=`http://techslides.com/demos/sample-videos/small.mp4`;
const {width,height} = Dimensions.get("window");
Icon.loadFont();
let overlayTimer;
let Timer;
const App = ({navigation}) => {
let lastTap = null;
const [Fullscreen, setFullscreen] = useState(false);
const [paused, setpaused] = useState(false);
const [currentTime, setcurrentTime] = useState(0);
const [duration, setduration] = useState(0.1);
const [overlay, setoverlay] = useState(false);
const playerRef = useRef();
useEffect(() => {
const backHandler = BackHandler.addEventListener(
"hardwareBackPress",
backAction
);
return () => backHandler.remove();
}, [])
const backAction = () => {
// navigation.goBack();
return true;
}
const FullscreenToggle=()=>{
if(Fullscreen){
Orientation.lockToPortrait();
StatusBar.setHidden(false)
navigation.setOptions({headerShown: true});
setFullscreen(false)
}else{
Orientation.lockToLandscape();
StatusBar.setHidden(true)
navigation.setOptions({headerShown: false});
setFullscreen(true);
}
}
const handleDoubleTap = (doubleTapCallback, singleTapCallback) => {
const now = Date.now();
const DOUBLE_PRESS_DELAY = 300;
if (lastTap && (now - lastTap) < DOUBLE_PRESS_DELAY) {
clearTimeout(Timer);
doubleTapCallback();
} else {
lastTap = now;
Timer = setTimeout(() => {
singleTapCallback();
}, DOUBLE_PRESS_DELAY);
}
}
const ShowHideOverlay = () => {
handleDoubleTap(() => {
}, () => {
setoverlay(true)
overlayTimer = setTimeout(() => setoverlay(false), 5000);
})
}
const backward = () => {
playerRef.current.seek(currentTime - 5);
clearTimeout(overlayTimer);
overlayTimer = setTimeout(() => setoverlay(false), 3000);
}
const forward = () => {
playerRef.current.seek(currentTime + 5);
clearTimeout(overlayTimer);
overlayTimer = setTimeout(() => setoverlay(false), 3000);
}
const onslide = (slide) => {
playerRef.current.seek(slide * duration);
clearTimeout(overlayTimer);
overlayTimer = setTimeout(() => setoverlay(false), 3000);
}
const getTime = (t)=> {
const digit = n => n < 10 ? `0${n}` : `${n}`;
const sec = digit(Math.floor(t % 60));
const min = digit(Math.floor((t / 60) % 60));
const hr = digit(Math.floor((t / 3600) % 60));
// return hr + ':' + min + ':' + sec;
return min + ':' + sec;
}
const load = ({ duration }) =>setduration(duration);
const progress = ({ currentTime }) =>setcurrentTime(currentTime);
return <View style={styles.container}>
<View style={Fullscreen ? styles.fullscreenVideo : styles.video}>
<Video
source={{uri:url}}
style={{ ...StyleSheet.absoluteFill }}
ref={playerRef}
paused={paused}
repeat={true}
onLoad={load}
onProgress={progress}
resizeMode={"cover"}
rate={1.0}
/>
<View style={styles.overlay}>
{overlay?
<View style={{ ...styles.overlaySet, backgroundColor: '#0006',alignItems:'center',justifyContent:'space-around'}}>
<View style={{width:50,height:50}}>
<Icon name='replay-5' style={styles.icon} onPress={backward} />
</View>
<View style={{width:50,height:50}}>
<Icon name={paused ? 'play-arrow' : 'pause'} style={styles.icon} onPress={() => setpaused(!paused)} />
</View>
<View style={{width:50,height:50}}>
<Icon name='forward-5' style={styles.icon} onPress={forward} />
</View>
<View style={styles.sliderCont}>
<View style={{...styles.timer,alignItems:'center'}}>
<View style={{flexDirection:'row'}}>
<Text style={{ color: 'white' }}>{getTime(currentTime)}/</Text>
<Text style={{ color: 'white' }}>{getTime(duration)}</Text>
</View>
<View style={{margin:5}}>
<Icon onPress={FullscreenToggle}
name={Fullscreen ? 'fullscreen' : 'fullscreen-exit'}
style={{ fontSize: 20,color:'white' }} />
</View>
</View>
<Slider
style={{margin: 5}}
maximumTrackTintColor='white'
minimumTrackTintColor='white'
thumbTintColor='white'
value={currentTime / duration}
onValueChange={onslide}
/>
</View>
</View>
:
<View style={styles.overlaySet}>
<TouchableNativeFeedback onPress={ShowHideOverlay}><View style={{ flex: 1 }} /></TouchableNativeFeedback>
</View>
}
</View>
</View>
{!Fullscreen&&
<View style={{ flex: 1,backgroundColor:'white' }}>
<Text>BitFrit Try Scroll View Here</Text>
</View>
}
</View>
}
const styles = StyleSheet.create({
container: {
flex: 1
},
video: { width, height: width * .6, backgroundColor: 'black' },
fullscreenVideo: {
backgroundColor: 'black',
...StyleSheet.absoluteFill,
elevation: 1
},
overlay: {
...StyleSheet.absoluteFillObject,
},
overlaySet: {
flex: 1,
flexDirection: 'row',
},
icon: {
color: 'white',
flex: 1,
textAlign: 'center',
textAlignVertical: 'center',
fontSize: 25
},
TextStyle:{
fontSize: 20, textAlign: 'center',
marginVertical: 100, color: '#6200ee', fontWeight: 'bold'
},
sliderCont: {
position: 'absolute',
left: 0,
right: 0,
bottom: 0
},
timer: {
width: '100%',
flexDirection: 'row',
justifyContent: 'space-between',
paddingHorizontal: 5
},
});
export default App;
I'm trying to use Expo Camera to take pictures and scan barcodes, but for some reason whenever I run it on an Android device when I am about to use the camera the app crashes. This is the code used for taking pictures/scanning barcodes. I don't believe it is a code issue though:
import React, { useState, useEffect } from 'react';
import { Text, View, TouchableOpacity, Image, Alert } from 'react-native';
import { IconButton, Colors, Button } from 'react-native-paper'
import { Camera } from 'expo-camera';
const CustomBarcodeScanner = ({ handleBarCodeScanned, scanning, handleTakePhotos, handleGoBack }) => {
const [hasPermission, setHasPermission] = useState(null)
const [preview, setPreview] = useState(false)
const [currentPhoto, setCurrentPhoto] = useState('')
const [photoCount, setPhotoCount] = useState(0)
const displaySnap = scanning ? "none" : "flex"
const snap = async() => {
if(this.camera){
let photo = await this.camera.takePictureAsync({base64: true})
setCurrentPhoto(photo['base64'])
setPhotoCount(photoCount + 1)
setPreview(true)
}
}
const acceptPhoto = () => {
setPreview(false)
handleTakePhotos(currentPhoto)
setCurrentPhoto('')
console.log(photoCount)
if(photoCount >= 2){
handleGoBack()
return
}
Alert.alert(
"Tomar otra foto",
"¿Desea tomar otra foto?",
[
{
text: 'Sí',
onPress: () => {
}
},
{
text: 'No',
onPress: () => {
handleGoBack()
},
style: "cancel"
}
],
{ cancelable: false }
)
}
const retakePhoto = () => {
setPreview(false)
setCurrentPhoto('')
}
useEffect(() => {
(async () => {
const { status } = await Camera.requestPermissionsAsync();
setHasPermission(status === 'granted');
})()
}, [])
if (hasPermission === null) {
return <View />;
}
if (hasPermission === false) {
return <Text>No access to camera</Text>;
}
return preview ?
<View style={{flex: 1, alignItems: 'center', justifyContent: 'center'}}>
<Image style={{width: '100%', height: '70%'}} source={{ uri: `data:image/jpg;base64,${currentPhoto}` }} />
<View style={{flexDirection: 'row'}}>
<Button
mode='contained'
color={Colors.purple500}
style={{padding: 10, margin: 10}}
onPress={acceptPhoto}
>
Aceptar
</Button>
<Button
mode='contained'
color={Colors.purple500}
style={{padding: 10, margin: 10}}
onPress={retakePhoto}
>
Re-Tomar Foto
</Button>
</View>
</View>
:
<View style={{ flex: 1 }}>
<Camera
style={{ flex: 1 }} type={Camera.Constants.Type.back} onBarCodeScanned={handleBarCodeScanned} ref={ref => {this.camera = ref}}>
<View
style={{
flex: 1,
backgroundColor: 'transparent',
flexDirection: 'row',
}}
>
<TouchableOpacity
style={{
flex: 0.1,
alignSelf: 'flex-end',
alignItems: 'center',
}}
onPress={handleGoBack}
>
<Text style={{ fontSize: 18, marginBottom: 10, color: 'white' }}>Regresar</Text>
</TouchableOpacity>
<TouchableOpacity
style={{
flex: 0.8,
alignSelf: 'flex-end',
alignItems: 'center',
display: displaySnap
}}
onPress={() => snap() }
>
<IconButton icon='camera' background={Colors.black} size={50} color={Colors.white} />
</TouchableOpacity>
</View>
</Camera>
</View>
}
export default CustomBarcodeScanner
I'm thinking it could be dependency related? I'm not sure if I need to install some libraries or add some code to get it to work. The error I get says Error while updating property 'nativeBackgroundAndroid' of a view managed by: RCTView
My expo version is 4.1.6
Apparently this is an issue with the Touchable Element with Ripple Effect. People are discussing that here.
react-native-paper seems to implement that on their button. Try to use the default button from React-Native, that should fix it :)
I am new to react native. and I have created A form. Now in that form I want A choose file button next to the input filed. And when user click on that Choose file button. Either camera will open or gallery will open(as per user choice) and then When user click on choose file button A small image or just image name comes below the choose file button
here is my image for better understanding
here is my code
import React, {useState, Component} from 'react';
import {Picker, Text, StyleSheet, View,
TextInput, Button, KeyboardAvoidingView,
ScrollView, Alert, alert, TouchableOpacity, Dimensions,} from 'react-native';
import { StackNavigator, navigation} from "react-navigation";
import { Card, Badge, Block, } from "../components";
import { theme, mocks } from "../constants";
import DigSign from "./DigSign"
import { Ionicons } from '#expo/vector-icons';
const { height } = Dimensions.get("window");
const { width } = Dimensions.get("window");
class PickerDemo extends Component{
constructor(props) {
super(props);
this.state={
};
}
validateInputs = () => {
// if (!this.state.accountNo.trim())
if (!/[A-Z]{5}[0-9]{4}[A-Z]{1}/.test(this.state.PAN))
{
this.setState({ PANError: 'Please enter valid PAN Number' })
return;
}
if (!/^[0-9]{2}[A-Z]{5}[0-9]{4}[A-Z]{1}[1-9A-Z]{1}Z[0-9A-Z]{1}$/.test(this.state.GST))
{
this.setState({ GSTError: 'Please enter valid GST Number' })
return;
}
if (!/^[2-9]{1}[0-9]{3}\\s[0-9]{4}\\s[0-9]{4}$/.test(this.state.Aadhar))
{
this.setState({ AadharError: 'Please enter valid Aadhar Number' })
return;
}
else {
Alert.alert("All fields validated")
return;
}
}
handlePAN = (text) => {
this.setState({ PANError: '' })
this.setState({ PAN: text })
}
handleGST = (text) => {
this.setState({ GSTError: '' })
this.setState({ GST: text })
}
handleAadhar = (text) => {
this.setState({ AadharError: '' })
this.setState({ Aadhar: text })
}
render(){
const offset = (Platform.OS === 'android') ? -200 : 0;
const { navigation } = this.props;
return (
<View style={{flex: 1}}>
<View style={styles.header}>
<Ionicons style={{paddingLeft:20}} name="arrow-back" size={40}
color="black" onPress={() => navigation.navigate("FormItems")} />
<Text style={{fontSize:20, paddingLeft: 70, paddingTop: 10}}>KYC Details</Text>
</View>
<KeyboardAvoidingView keyboardVerticalOffset={offset} style={styles.form} behavior='padding'>
<Text style={styles.formLabel}> OTHER INFORMATION Form </Text>
<ScrollView style={{flex: 1,}} showsVerticalScrollIndicator={false}>
<View style={{flexDirection:'row'}}>
<TextInput maxLength={30} placeholder="PAN Card Number *" style={styles.inputStyle}
onChangeText={this.handlePAN} />
<View style={{justifyContent:"center"}}>
<Button title={'Choose File'}/>
</View>
</View>
<Text>{this.state.PANError}</Text>
<View style={{flexDirection:'row'}}>
<TextInput maxLength={30} placeholder="GSTIN Number*" style={styles.inputStyle}
onChangeText={this.handleGST} />
<View style={{justifyContent:"center"}}>
<Button title={'Choose File'}/>
</View>
</View>
<Text>{this.state.GSTError}</Text>
<View style={{flexDirection:'row'}}>
<TextInput maxLength={30} placeholder="Aadhar Card Number*" style={styles.inputStyle}
onChangeText={this.handleAadhar} />
<View style={{justifyContent:"center"}}>
<Button title={'Choose File'}/>
</View>
</View>
<Text>{this.state.AadharError}</Text>
<TouchableOpacity
onPress={() => navigation.navigate("DigSign")}
>
<Card center middle shadow style={styles.category}>
<Text medium height={1} size={1}>
Digital Signature
</Text>
</Card>
</TouchableOpacity>
<TouchableOpacity
onPress={() => navigation.navigate("ImgpickWithCam")}
>
<Card center middle shadow style={styles.category}>
<Text medium height={1} size={1}>
Pick An Image From Camera
</Text>
</Card>
</TouchableOpacity>
</ScrollView>
<View style={{ height: 30 }} />
<Button style={styles.inputStyleB}
title="Submit"
color="#808080"
onPress={() => this.validateInputs()}
/>
</KeyboardAvoidingView>
</View>
);
};
}
const styles = StyleSheet.create({
form: {
flex: 1,
justifyContent: "center",
flex: 1,
backgroundColor: "rgb(247, 146, 57)",
alignItems: 'center',
paddingTop: 50,
},
container: {
flex: 1,
backgroundColor: "rgb(247, 146, 57)",
alignItems: 'center',
// justifyContent: 'center',
paddingTop: 15
},
formLabel: {
fontSize: 20,
color: 'rgb(10, 10, 10)',
},
inputStyle: {
marginTop: 20,
width: 220,
height: 40,
paddingHorizontal: 10,
borderRadius: 50,
backgroundColor: 'rgb(255, 252, 252)',
},
formText: {
alignItems: 'center',
justifyContent: 'center',
color: '#fff',
fontSize: 20,
},
text: {
color: '#fff',
fontSize: 20,
},
category: {
marginTop: 20,
// this should be dynamic based on screen width
minWidth: (width - theme.sizes.padding * -10 - theme.sizes.base) / 2,
maxWidth: (width - theme.sizes.padding * -10 - theme.sizes.base) / 2,
maxHeight: (height - theme.sizes.padding * -50 - theme.sizes.base) / 2,
},
header:{
flexDirection: 'row'
}
});
export default PickerDemo;
Here is the solution based on the previous examples that I have given you.
You just had to implement the conditional rendering to it.
Just a couple of lines of code what was needed :)
Working Example: Expo Snack
import React, { useState, useEffect } from 'react';
import {
StyleSheet,
View,
Button,
Image,
FlatList,
Text,
TextInput,
} from 'react-native';
import { Camera } from 'expo-camera';
import { Ionicons } from '#expo/vector-icons';
import * as ImagePicker from 'expo-image-picker';
export default function Add() {
const [cameraPermission, setCameraPermission] = useState(null);
const [galleryPermission, setGalleryPermission] = useState(null);
const [showCamera, setShowCamera] = useState(false);
const [camera, setCamera] = useState(null);
const [imageUri, setImageUri] = useState([]);
const [type, setType] = useState(Camera.Constants.Type.back);
const [imageArray, setImageArray] = useState([]);
const permisionFunction = async () => {
// here is how you can get the camera permission
const cameraPermission = await Camera.requestPermissionsAsync();
console.log('camera permission:', cameraPermission.status);
setCameraPermission(cameraPermission.status === 'granted');
const imagePermission = await ImagePicker.getMediaLibraryPermissionsAsync();
console.log('permission:', imagePermission.status);
setGalleryPermission(imagePermission.status === 'granted');
if (
imagePermission.status !== 'granted' &&
cameraPermission.status !== 'granted'
) {
alert('Permission for media access needed.');
}
};
useEffect(() => {
permisionFunction();
}, []);
const takePicture = async () => {
if (camera) {
const data = await camera.takePictureAsync(null);
console.log(data.uri);
setImageUri(data.uri);
setImageArray([...imageArray, data.uri]);
setShowCamera(false);
}
};
const pickImage = async () => {
let result = await ImagePicker.launchImageLibraryAsync({
mediaTypes: ImagePicker.MediaTypeOptions.Images,
quality: 1,
});
console.log(result.uri);
if (!result.cancelled) {
setImageArray([...imageArray, result.uri]);
}
};
return (
<View style={styles.container}>
{showCamera && (
<Camera ref={(ref) => setCamera(ref)} style={{ flex: 1 }} type={type} />
)}
{showCamera && <Button title={'Click'} onPress={takePicture} />}
{!showCamera && (
<>
<View
style={{ flexDirection: 'row', justifyContent: 'space-between' }}>
<TextInput placeholder={'Enter PAN Number'} />
<View style={{ flexDirection: 'row' }}>
<Button
title={'Camera'}
onPress={() => {
setShowCamera(true);
}}
/>
<Button title={'Gallery'} onPress={pickImage} />
</View>
</View>
{imageArray.length > 0 && (
<View style={{ height: 110 }}>
<FlatList
horizontal
data={imageArray}
renderItem={({ item }) => (
<Image
source={{ uri: item }}
style={{
width: 100,
height: 100,
borderRadius: 10,
margin: 5,
}}
/>
)}
/>
</View>
)}
</>
)}
</View>
);
}
const styles = StyleSheet.create({
container: {
marginTop: 30,
flex: 1,
},
fixedRatio: {
flex: 1,
},
});
Can anyone help with integration of Clarifai Custom trained model in React Native? I found in docs that if you want to use custom instead of general model, you should pass object with model_id and model_version_id. As I created this custom model on their web page it gave me that parameters, but the algorithm won't really work and it returns the error of "request failed status code 400". Did anyone tried to implement this API in React Native?
const ScanMachine = props => {
const {id} = props.route.params;
const selectedCategory = CATEGORIES.find(cat => cat.id === id);
const camRef = useRef(null);
const [hasPermission, setHasPermission] = useState(null);
const [ratio, setRatio] = useState(null);
const [capturedPhoto, setCapturedPhoto] = useState(null);
const [prediction, setPrediction] = useState([]);
useEffect(() => {
(async () => {
const { status } = await Camera.requestPermissionsAsync();
setHasPermission(status === 'granted');
setRatio('16:9');
})();
}, []);
if (hasPermission === null) {
return <View />;
}
if (hasPermission === false) {
return <Text>No access to camera</Text>;
}
async function takePicture() {
if(camRef) {
let data = await camRef.current.takePictureAsync();
console.log(data);
setCapturedPhoto(data.uri);
return data.uri;
}
}
async function resize(photo) {
let imageManipulate = await ImageManipulator.manipulateAsync(photo, [{resize: {height: 350, width: 300}}], {base64: true});
return imageManipulate.base64;
}
async function predictions(image) {
let pred = await clarifai.models.predict({id: "custom_laundry_id", version: "03f4ff3ce1ba4cf68b77e923d0ce8699"}, image);
return pred;
}
async function detectObject() {
let photo = await takePicture();
let resized = await resize(photo);
let predict = await predictions(resized);
setPrediction(predict.outputs[0].data.concepts)
console.log(predict);
}
return (
<View style={{ flex: 1}}>
<Camera style={{ flex: 1, alignItems:'center'}} ref={camRef} ratio={ratio}>
<View style={{ flex: 1, backgroundColor: 'transparent', margin: 20, justifyContent: 'space-between'}}>
{prediction && <FlatList data={prediction.map(predict => ({
key: predict.name,
}))} renderItem={({ item }) => (
<Text style={{fontSize: 17, color: '#fff'}}>{item.key + " "}</Text>
)} numColumns={4} /> }
</View>
<BarcodeMask edgeColor={'#62B1F6'} backgroundColor={'transparent'} width={300} height={350} showAnimatedLine={false} />
<View style={{flex: 1, justifyContent: 'space-between', justifyContent:'flex-end', margin: 20}}>
<TouchableOpacity style={{ backgroundColor: 'transparent', alignSelf: 'flex-end'}} onPress={detectObject}>
<FontAwesome name="camera" style={{color: '#fff', fontSize: 40, alignContent: 'flex-start'}} />
</TouchableOpacity>
</View>
</Camera>
{/* { capturedPhoto &&
<View style={{flex: 1, justifyContent: 'center', alignItems: 'center', margin: 20}}>
<Image style={{width: '100%', height: '100%', borderRadius: 10}} source={{uri: capturedPhoto}} />
</View> } */}
</View>
);
};