Hi,
So I'm using i2c with the ADXL345 Accelerometer. Everything seems to be working fine until I send the values over Serial.write(), If you look at the result below i end up with 5*10^74 g's which seems like a bit much. Anyways, if anyone have any advice I would love to hear it.
Python Code:
timeout = time.time() + 5
while time.time() < timeout:
x_vec.append(self.port.read(4))
y_vec.append(self.port.read(4))
z_vec.append(self.port.read(4))
self.port.write('a') #tell Arduino to Stop Sending
for i in range(len(x_vec)):
x.append(struct.unpack( '<f' , x_vec[i]))
for i in range(len(y_vec)):
y.append(struct.unpack( '<f' , y_vec[i]))
for i in range(len(z_vec)):
z.append(struct.unpack( '<f' , z_vec[i]))
for i in range(len(z_vec)):
total.append( np.multiply(x[i],x[i]) + np.multiply(y[i], y[i]) + np.multiply(z[i],z[i]) )
print("reading")
self.port.flush()
print("finish Reading")
fig = pl.figure(figsize= (4.25,4))
pl.title('G / Samples')
pl.plot(total)
fig.savefig('plot.png')
self.image_icon.set_from_file("plot.png")
Okay, here is all the arduino code and that is the only python function that deals with reading. I'm using the PySerial library. Let me know if a can post anything else.
Python:
def on_buttonClick_runTest(self, button):
self.console_buffer.insert(self.console_buffer.get_end_iter(),
"\n Beginning Test..")
x = []
y = []
z = []
x_vec = []
y_vec = []
z_vec = []
total = []
t = []
tv = []
self.port.write('b')
self.console_buffer.insert(self.console_buffer.get_end_iter(),
"\n Starting Test")
self.port.flush()
print("Starting")
timeout = time.time() + 5
while time.time() < timeout:
x_vec.append(self.port.read(4))
y_vec.append(self.port.read(4))
z_vec.append(self.port.read(4))
self.port.write('a')
for i in range(len(x_vec)):
x.append(struct.unpack( '<f' , x_vec[i]))
for i in range(len(y_vec)):
y.append(struct.unpack( '<f' , y_vec[i]))
for i in range(len(z_vec)):
z.append(struct.unpack( '<f' , z_vec[i]))
for i in range(len(z_vec)):
total.append( np.multiply(x[i],x[i]) + np.multiply(y[i], y[i]) + np.multiply(z[i],z[i]) )
print("reading")
self.port.flush()
print("finish Reading")
fig = pl.figure(figsize= (4.25,4))
pl.title('G / Samples')
pl.plot(total)
fig.savefig('plot.png')
self.image_icon.set_from_file("plot.png")
Arduino:
#include <Wire.h>
#include <Adafruit_Sensor.h>
#include <Adafruit_ADXL345_U.h>
/* Assign a unique ID to this sensor at the same time */
Adafruit_ADXL345_Unified accel = Adafruit_ADXL345_Unified(12345);
typedef union {
float floatingPoint;
byte binary[4];
} binaryFloat;
binaryFloat x,y,z;
float xcal, ycal, zcal;
bool record;
void displaySensorDetails(void)
{
sensor_t sensor;
accel.getSensor(&sensor);
Serial.println("------------------------------------");
Serial.print ("Sensor: "); Serial.println(sensor.name);
Serial.print ("Driver Ver: "); Serial.println(sensor.version);
Serial.print ("Unique ID: "); Serial.println(sensor.sensor_id);
Serial.print ("Max Value: "); Serial.print(sensor.max_value); Serial.println(" m/s^2");
Serial.print ("Min Value: "); Serial.print(sensor.min_value); Serial.println(" m/s^2");
Serial.print ("Resolution: "); Serial.print(sensor.resolution); Serial.println(" m/s^2");
Serial.println("------------------------------------");
Serial.println("");
delay(500);
}
void displayDataRate(void)
{
Serial.print ("Data Rate: ");
switch(accel.getDataRate())
{
case ADXL345_DATARATE_3200_HZ:
Serial.print ("3200 ");
break;
case ADXL345_DATARATE_1600_HZ:
Serial.print ("1600 ");
break;
case ADXL345_DATARATE_800_HZ:
Serial.print ("800 ");
break;
case ADXL345_DATARATE_400_HZ:
Serial.print ("400 ");
break;
case ADXL345_DATARATE_200_HZ:
Serial.print ("200 ");
break;
case ADXL345_DATARATE_100_HZ:
Serial.print ("100 ");
break;
case ADXL345_DATARATE_50_HZ:
Serial.print ("50 ");
break;
case ADXL345_DATARATE_25_HZ:
Serial.print ("25 ");
break;
case ADXL345_DATARATE_12_5_HZ:
Serial.print ("12.5 ");
break;
case ADXL345_DATARATE_6_25HZ:
Serial.print ("6.25 ");
break;
case ADXL345_DATARATE_3_13_HZ:
Serial.print ("3.13 ");
break;
case ADXL345_DATARATE_1_56_HZ:
Serial.print ("1.56 ");
break;
case ADXL345_DATARATE_0_78_HZ:
Serial.print ("0.78 ");
break;
case ADXL345_DATARATE_0_39_HZ:
Serial.print ("0.39 ");
break;
case ADXL345_DATARATE_0_20_HZ:
Serial.print ("0.20 ");
break;
case ADXL345_DATARATE_0_10_HZ:
Serial.print ("0.10 ");
break;
default:
Serial.print ("???? ");
break;
}
Serial.println(" Hz");
}
void displayRange(void)
{
Serial.print ("Range: +/- ");
switch(accel.getRange())
{
case ADXL345_RANGE_16_G:
Serial.print ("16 ");
break;
case ADXL345_RANGE_8_G:
Serial.print ("8 ");
break;
case ADXL345_RANGE_4_G:
Serial.print ("4 ");
break;
case ADXL345_RANGE_2_G:
Serial.print ("2 ");
break;
default:
Serial.print ("?? ");
break;
}
Serial.println(" g");
}
void setup(void)
{
Serial.begin(9600);
//Serial.println("Accelerometer Test"); Serial.println("");
record = false;
/* Initialise the sensor */
if(!accel.begin())
{
/* There was a problem detecting the ADXL345 ... check your connections */
//Serial.println("Ooops, no ADXL345 detected ... Check your wiring!");
//Serial.println("Error Code: 102");
//while(1);
}
/* Set the range to whatever is appropriate for your project */
accel.setRange(ADXL345_RANGE_16_G);
// displaySetRange(ADXL345_RANGE_8_G);
// displaySetRange(ADXL345_RANGE_4_G);
// displaySetRange(ADXL345_RANGE_2_G);
/* Display some basic information on this sensor */
//displaySensorDetails();
/* Display additional settings (outside the scope of sensor_t) */
//displayDataRate();
//displayRange();
//Serial.print("Calibrating ADXL:");
sensors_event_t event;
accel.getEvent(&event);
xcal = event.acceleration.x;
ycal = event.acceleration.y;
zcal = event.acceleration.z;\
Serial.print("");
}
void loop(void)
{
/* Get a new sensor event */
sensors_event_t event;
accel.getEvent(&event);
if(record == true){
x.floatingPoint = event.acceleration.x;
y.floatingPoint = event.acceleration.y;
z.floatingPoint = event.acceleration.z;
x.floatingPoint = x.floatingPoint/9.81;
y.floatingPoint = y.floatingPoint/9.81;
z.floatingPoint = z.floatingPoint/9.81;
//float t = sqrt(x.floatingPoint*x.floatingPoint + y.floatingPoint*y.floatingPoint + z.floatingPoint*z.floatingPoint);
//Serial.print(t);Serial.print("\n");
Serial.write((byte)x.floatingPoint);
Serial.write((byte)y.floatingPoint);
Serial.write((byte)z.floatingPoint);
}
}
void serialEvent() {
while (Serial.available()) {
// get the new byte:
char inChar = (char)Serial.read();
// add it to the inputString:
if(inChar == 'b'){
record = true;
}
else if (inChar == 'a') {
record = false;
}
else if(inChar == 't'){
Serial.print(104);
}
}
}
ltdouthit:
Finally got it working by sending the values as strings then converting to floats.
I suspect it would not be easy to match the binary float format used on a PC with that used on an Arduino so using text as an intermediate would certainly be my choice.
Robin2:
I suspect it would not be easy to match the binary float format used on a PC with that used on an Arduino so using text as an intermediate would certainly be my choice.