Home > Software design >  React Native record accelerometer data using expo-sensors
React Native record accelerometer data using expo-sensors

Time:07-16

I'm using Expo's accelerometer library in order to record 5 seconds of data and calculate the mean of each axis. I've set the sensor interval to 1000ms and created a simple view that shows the current XYZ measurements and below also shows a list of past measurements. The change is done by adding an eventListener to the accelerometer and using the new data to update the array's state.

export default function App() {
  const [data, setData] = useState<ThreeAxisMeasurement[]>([{ x: 0, y: 0, z: 0 }]);

  useEffect(() => {
    Accelerometer.setUpdateInterval(1000);
    Accelerometer.addListener(accData => {
      setData([...data, accData])
      console.log(data);
    })
    return () => Accelerometer.removeAllListeners();
  }, []);

  const { x, y, z } = data[data.length - 1];
  return (
    <View style={styles.container}>
      <Text style={styles.title}>Acelerômetro em mg</Text>
      <Text style={styles.text}>
        x: {round(x)} y: {round(y)} z: {round(z)}
      </Text>
      <View style={styles.container}>
        <FlatList
          data={data}
          renderItem={({ item }) => <Text style={styles.text}>
            x: {round(item.x)} y: {round(item.y)} z: {round(item.z)}
          </Text>}
        />
      </View>
    </View>
  );
}

The problem is that when i check the list only the last value changes, instead of being appended. This doesn't make sense to me as I use spread notation to concatenate the old array with the new one as you can see in setData().

Array [
  Object {
    "x": 0,
    "y": 0,
    "z": 0,
  },
  Object {
    "x": 69,
    "y": -170,
    "z": -983,
  },
]
Array [
  Object {
    "x": 0,
    "y": 0,
    "z": 0,
  },
  Object {
    "x": 72,
    "y": -168,
    "z": -982,
  },
]

I've already tried reading the docs to see if I'm using hooks or subscriptions incorrectly, but couldn't find what's wrong in my code. Any help is appreciated.

CodePudding user response:

The main issue is that the callback in the listener doesn't update when data changes, for this reason ...data value in setData([...data, accData]) will always refer to its initial state.

You can try using a plain array and pushing data in it instead of state.

  • Related