react-native - 如何在不使用状态数组的情况下将 React Native 手机传感器数据保存到数组中(超出最大更新深度)?
问题描述
我在弄清楚如何在 React Native 中处理传感器数据时遇到了一些麻烦。我的目标是在有限的时间内(比如说 10 秒)获取手机传感器数据,并在完成后将获得的列表保存到本地数据库。然而,将新的陀螺仪值推送到状态数组是一种选择,但在那里获得最大更新深度超出错误。代码如下。
import React from 'react';
import {
StyleSheet,
View,
Text,
Dimensions,
} from 'react-native';
import { Gyroscope } from 'expo-sensors';
import { Button } from "native-base";
import CountDown from 'react-native-countdown-component';
import UUID from 'pure-uuid';
import {insertGyroData} from './measureService';
const SAMPLING_RATE = 20; // defaults to 20ms
export class Measure extends React.Component {
state = {
gyroscopeData: {},
measuringStarted: false,
x_gyro: [0],
y_gyro: [0],
z_gyro: [0]
};
componentDidMount() {
this.toggleGyroscope();
}
componentWillUnmount() {
this.unsubscribeAccelerometer();
}
toggleGyroscope = () => {
if (this.gyroscopeSubscription) {
this.unsubscribeAccelerometer();
} else {
this.gyroscopeSubscribe();
}
};
gyroscopeSubscribe = () => {
Gyroscope.setUpdateInterval(20);
this.gyroscopeSubscription = Gyroscope.addListener(gyroscopeData => {
this.setState({ gyroscopeData });
});
};
unsubscribeAccelerometer = () => {
this.gyroscopeSubscription && this.gyroscopeSubscription.remove();
this.gyroscopeSubscription = null;
};
referenceMeasurementCompleted = async (x, y, z) => {
this.setState({ measuringStarted: false });
const uuid = new UUID(4).format();
await insertGyroData([uuid, 'admin', '12345', x.toString(), y.toString(), z.toString()]);
alert('Reference measurements completed');
};
render() {
let { x, y, z } = this.state.gyroscopeData;
const { x_gyro, y_gyro, z_gyro } = this.state;
if (this.state.measuringStarted) {
this.setState(({ x_gyro: [...x_gyro, x], y_gyro: [...y_gyro, y], z_gyro: [...z_gyro, z] }));
return (
<View style={styles.container}>
<Text>Gyroscope:</Text>
<Text>
x: {round(x)} y: {round(y)} z: {round(z)}
</Text>
<Text>Time spent:</Text>
<CountDown
until={5}
size={30}
onFinish={() => this.referenceMeasurementCompleted(x_gyro, y_gyro, z_gyro)}
digitStyle={{ backgroundColor: '#FFF' }}
digitTxtStyle={{ color: '#00c9ff' }}
timeToShow={['M', 'S']}
timeLabels={{ m: 'MM', s: 'SS' }}
/>
</View>
);
} else {
return (
<View style={styles.container}>
<Button
rounded
primary
onPress={() => this.setState({ measuringStarted: true })}
>
<Text style={styles.buttonText}>Start reference measurements</Text>
</Button>
</View>
);
}
}
}
function round(n) {
if (!n) {
return 0;
}
return Math.floor(n * 100) / 100;
}
const styles = StyleSheet.create({
container: {
flex: 1,
height: Dimensions.get('window').height,
backgroundColor: 'white',
alignItems: 'center',
justifyContent: 'center'
},
buttonText: {
color: 'white',
fontSize: 20,
paddingHorizontal: 10,
},
});
使用当前的解决方案,我得到最大深度更新超出错误 请帮助!
解决方案
错误显然来自此块,因为您正在更改渲染内部的状态。
if (this.state.measuringStarted) {
this.setState(({ x_gyro: [...x_gyro, x], y_gyro: [...y_gyro, y], z_gyro: [...z_gyro, z] }));
}
您可以尝试的一种方法是更新状态
componentDidUpdate(prevProps,prevState){}
但请注意它不会导致Maximum Stack Reached 错误。使用适当的条件语句,您可以将状态设置为新数据而无需无限递归。
推荐阅读
- powershell - 如何在 tfs 2015 中的目标机器任务上的 powershell 中使用特殊字符、空格等读取会话变量
- compression - LZW、LZ77等易于实现算法的压缩比
- kivy - Kivy:在没有 kv 的情况下跟随鼠标移动移动图像
- python - 意外的 Python TypeError:使用标量时
- c - 递归函数计算数字字符串的后继
- vue.js - 向 nuxt.config.js 添加函数
- elasticsearch - 带有大写标记的 Elasticsearch word_delimiter 过滤器不匹配
- discord - discord.js 尝试使用 2 个数组创建随机结果命令
- php - 如何使用 INNER JOIN 改进我的 php sub_array 代码以在 DataTables 上显示数据?
- sql - 如何在sql中创建一个可以对当前日期和我的表中的值进行操作的函数