Tryingtogetsome
Tryingtogetsome

Reputation: 71

ESP32 ADXL345 doesn't get the negative values

Hi I can run this code without any problem on Arduino UNO. My output is like : 0.05 0.10 1.01 But when I run this code on ESP32, my output is : 255.89 255.81 0.99 and I don't see any minus value. What is the problem?
ESP32's X,Y,Z raw values like : 6500 0 , 65000 , 1 . ESP32 can't get the negative values. I have to do something with wire.h and I need to change uint8_t or uint16_t something but I really don't understand how should I solve this problem.

#include <Wire.h>  // Wire library - used for I2C communication
int ADXL345 = 0x53; // The ADXL345 sensor I2C address
float X_out, Y_out, Z_out;  // Outputs
float X, Y, Z ;
void setup() {
  Serial.begin(115200); // Initiate serial communication for printing the results on the Serial monitor
  Wire.begin(); // Initiate the Wire library
  // Set ADXL345 in measuring mode
  Wire.beginTransmission(ADXL345); // Start communicating with the device
  Wire.write(0x31);
  Wire.write(0x0B);
  Wire.endTransmission();

  Wire.beginTransmission(ADXL345);
  Wire.write(0x20); // Z-axis offset register
  Wire.write(-7);
  Wire.endTransmission();
  Wire.beginTransmission(ADXL345);
  Wire.write(0x2D); // Access/ talk to POWER_CTL Register - 0x2D
  // Enable measurement
  Wire.write(0x08); // (8dec -> 0000 1000 binary) Bit D3 High for measuring enable
  Wire.endTransmission();
  Wire.beginTransmission(ADXL345);
  Wire.write(0x2C);
  // Enable measurement
  Wire.write(0x09); //For low power 000x x pin set to 1  /1001 determine Hz
  Wire.endTransmission();
  delay(10);
}
void loop() {
  unsigned long Time = millis();
  // === Read acceleromter data === //
  Wire.beginTransmission(ADXL345);
  Wire.write(0x32); // Start with register 0x32 (ACCEL_XOUT_H)
  Wire.endTransmission(false);
  Wire.requestFrom(ADXL345, 6, true); // Read 6 registers total, each axis value is stored in 2 registers
  X_out = ( Wire.read() | Wire.read() << 8); // X-axis value
  X = X_out /256; //For a range of +-2g, we need to divide the raw values by 256, according to the datasheet
  Y_out = ( Wire.read() | Wire.read() << 8); // Y-axis value
  Y = Y_out /256;
  Z_out = ( Wire.read() | Wire.read() << 8); // Z-axis value
  Z = Z_out /256;
  delay(20);
  Serial.print(X);
  Serial.print(" ");
  Serial.print(Y);
  Serial.print(" ");
  Serial.print(Z);
  Serial.println(" ");
}

Upvotes: 0

Views: 394

Answers (1)

m2j
m2j

Reputation: 155

  1. On the Arduino Uno there are 16-bit integers. The ADXL345 seems to receive this data format. Therefore everything plays out nicely. You are using 32-bit integers on the ESP32. Therefore you have to choose the right data type explicitly. Otherwise the negative numbers appear in the positive region.

  2. The execution order of the Wire.read()-calls is not defined in your code. Therefore the compiler may join the bytes 0xAA and 0xBB to 0xAABB or 0xBBAA. You should add a sequence point to make sure that the code does what's intended.

I have not tested this code. That should be the correct order, in case I got the datasheet description right:

int16_t readInt16()
{
    int lsb = Wire.read();
    int msb = Wire.read();
    return int16_t(lsb | msb << 8);
}

X_out = readInt16() / 256.f;
Y_out = readInt16() / 256.f;
Z_out = readInt16() / 256.f;

Upvotes: 1

Related Questions