Good Day! I was struggling about my arduino MLX90614 code my pyserial cant read the data it show's
Here's my arduino MLX90614 code:
#include <Wire.h>
#include <Adafruit_MLX90614.h>
Adafruit_MLX90614 mlx = Adafruit_MLX90614();
void setup() {
Serial.begin(9600);
mlx.begin();
}
void loop() {
Serial.print("Ambient = "); Serial.print(mlx.readAmbientTempC());
Serial.print("*C\tObject = "); Serial.print(mlx.readObjectTempC()); Serial.println("*C");
Serial.print("Ambient = "); Serial.print(mlx.readAmbientTempF());
Serial.print("*F\tObject = "); Serial.print(mlx.readObjectTempF()); Serial.println("*F");
Serial.println();
delay(500);
}
And heres my python code "Pyserial" to read the data from my arduino
import csv
from time import time
import serial
# Your serial port might be different!
ser = serial.Serial('COM5', timeout=1)
f = open("df.csv", "a+")
writer = csv.writer(f, delimiter=',')
while True:
s = ser.readline().decode()
if s != "":
rows = [float(x) for x in s.split(',')]
# Insert local time to list's first position
rows.insert(0, int(time()))
print(rows)
writer.writerow(rows)
f.flush()
But in result it show's this
"rows = [float(x) for x in s.split(',')]
ValueError: could not convert string to float: 'Ambient 30c /n'"
Someone please help me with this I am really struggling with connecting my Arduino MLX90614 to my Arduino. Thanks in advance
If s != '' is not a space, add the whitespace between the quotes, this is returning values that cannot be passed to the int constructor.
Comment the list comprehension out and print instead to see the current values your code is storing.
Related
I'm trying to send a set of [x, y] coordinates from python to arduino in order to control servo motors on a robot drivetrain. I'm taking the approach of sending a string in the format "x,y". On the arduino side, I'm trying to parse this string to get the x and y substrings. However the indexOf function doesn't return the proper index. Here is my code:
arduino = serial.Serial(port='COM3', baudrate=9600, timeout=.1)
def write_read(x):
arduino.write(bytes(x, 'utf-8'))
time.sleep(0.05)
data = arduino.readline()
return data
for coordinate in coordinates:
c = str(coordinate[0]) + ", " + str(coordinate[1])
print(write_read(c))
#include <Servo.h>
void setup() {
Serial.begin(9600);
Serial.setTimeout(1);
}
void loop() {
while (!Serial.available());
String coordinates = "" + Serial.readString();
// Serial.print(coordinates); //this prints normally as the string value
int i = coordinates.indexOf(',');
Serial.print(i);
}
When I send something like "-9.45, -16.3". The output is b'-1-1-1-1-10-1-1-1-1-1-1'. I'm not sure what's going on here or how to get the actual index (in this case it would be 5).
import serial
ser= serial.Serial('com5',9600)
while 1:
Value_from_arduino = ser.readline()
Zustand = float(Value_from_arduino)
print(Zustand)
if Zustand == 1:
ser.write(0)
print('off')
elif Zustand == 0:
ser.write(1)
print(on)
This was the Python code, now here the arduino code.
char serialData;
int pin=12;
int pin2 = 5;
int Value;
void setup(){
pinMode(pin,OUTPUT);
pinMode(pin2,INPUT);
Serial.begin(9600);
}
void loop(){
Value = digitalRead(pin2);
Serial.println(Value);
delay(250);
while(Serial.available()){
serialData = Serial.read();
Serial.print(serialData);
if(serialData = '1'){
digitalWrite(pin,HIGH);
}
else if(serialData = '0'){
digitalWrite(pin,LOW);
}
}
}
My problem is, when i run my python code, it stops when he gets the Value 0 from my arduino.
Here is the report from python:
Zustand = float(Value_from_Arduino)
ValueError: could not convert string to float: b'\x000\r\n'
Python immediatly stops, but he puts the LED on.
The LED should be on if Python gets the value of 0, he do but then he just end run.
The LED should go on if value is 0 and of if value is 1.
You need to decode the serial bytes from the serial port.
Replace the Zustand = line in your code
Value_from_arduino = ser.readline()
Zustand = float(ser_bytes[0:len(Value_from_arduino )-2].decode("utf-8"))
Please check here https://makersportal.com/blog/2018/2/25/python-datalogger-reading-the-serial-output-from-arduino-to-analyze-data-using-pyserial
also try, if encodings doesn't work well
import struct
Zustand, = struct.unpack('<f',Value_from_arduino )
Finally i have found out please replace these lines of code
Steps -> Read,Decode to string, Strip /n and /r, Convert to float
please check here https://problemsolvingwithpython.com/11-Python-and-External-Hardware/11.04-Reading-a-Sensor-with-Python/
Value_from_arduino = ser.readline()
Value_from_arduino = Value_from_arduino.decode()
Value_from_arduino = Value_from_arduino.rstrip()
Zustand = float(Value_from_arduino)
Hope this Works..
I need to read 2 different bytes from TTP229 (16 keys or 8 keys touch pad detector).
I use I2C In Python. TTP229 datasheet PDF.
I can't read the second byte, but I can get the first byte.
Python code:
import smbus
bus = smbus.SMBus(1)
adressTTP229 = 0x57 #0xAF>>1
byte1 = bus.read_byte(adressTTP229)
byte2 = bus.read_byte(adressTTP229)
byte1 is always equal to byte2.
This Arduino code, works ok:
#include <Wire.h>
#define ttp229 (0xAF>>1)
void setup() {
Serial.begin(9600); // start serial for output
Wire.begin();
}
void loop() {
delay(50);
bool isNewData = false;
Wire.requestFrom(ttp229,2,true);
while (Wire.available()) {
uint16_t b1 = Wire.read(); // receive a first byte
uint16_t b2 = Wire.read(); // receive a second byte
if (b1==b2 && b2==0) {break;}
//...
}
}
How do I use Arduino's requestFrom() function in Python?
try:
import smbus, time
bus = smbus.SMBus(1)
while True:
print bus.read_word(0xAF)
time.sleep(0.1)
dont change address, bus doe the conversion, and if you read byte you will always get the same first byte. you want to read a word = 2 bytes at once
not tested, but might work, have it ordered and will test
I have encountered an error that has been seriously bothering me, and I have been unable to find a workaround. I have a python program that utilizes PySerial to import serial port values from a pulse oximeter. The problem is, when the function ser.readline() is invoked (in other words, when the python program is told to read values from the Arduino's serial monitor, the Arduino's serial values become distorted and the program returns a value unpack error.
Here is the python program.
import serial
import time
import pylab
import matplotlib.pyplot as plt
import numpy as np
import os
import csv
#time load
timestr = time.strftime("%Y_%m_%d")
#establish serial connection with ACM0
ser = serial.Serial('/dev/ttyACM0', 115200)
#establish variables
thymeL = [ ]
bpmL = [ ]
sp02L = [ ]
array_data = thymeL, bpmL, sp02L
#declare time
thyme = 1
#graph attributes
plt.ion()
plt.title("Pulse [BPM] & SPo2 [%] v. Time [s]", fontsize = "16")
plt.xlabel("Time [s]", fontsize = "14")
plt.ylabel("Pulse (red) [BPM] & SPo2 (blue) [%]", fontsize = "14")
while True:
data_in = ser.readline()
print data_in
data_in = data_in.strip('\n')
bpm,sp02 = data_in.split(",")
#convert string vals to float
thyme = float(thyme)
bpm = float(bpm)
sp02 = float(sp02)
#print to terminal
print "Time [s]: %s" % (thyme)
print "HR [BPM]: %s" % (bpm)
print "SPO2 [%%]: %s" % (sp02)
print
#append vectors
thymeL.append(thyme)
bpmL.append(bpm)
sp02L.append(sp02)
#print values to plot
plt.scatter(thyme,bpm,color="red")
plt.scatter(thyme,sp02,color="blue")
plt.pause(0.1)
time.sleep(0.05)
#update time
thyme = thyme + 0.5
#write to .csv
with open(full_path, 'w') as f:
writer = csv.writer(f)
for t, b, s in zip(array_data[0], array_data[1], array_data[2]):
writer.writerow([t, b, s])
The most important snippet of all is:
while True:
data_in = ser.readline()
print data_in
data_in = data_in.strip('\n')
bpm,sp02 = data_in.split(",")
The Arduino program is as follows:
#include <PinChangeInt.h>
#include <eHealth.h>
int cont = 0;
void setup() {
Serial.begin(115200);
eHealth.initPulsioximeter();
PCintPort::attachInterrupt(6, readPulsioximeter, RISING);
}
void loop() {
char buffer[32]; // make sure buffer is large enough
sprintf(buffer,"%d,%d \n",eHealth.getBPM(),eHealth.getOxygenSaturation());
Serial.print(buffer);
delay(500);
}
//=========================================================================
void readPulsioximeter(){
cont ++;
if (cont == 50) { //Get only of one 50 measures to reduce the latency
eHealth.readPulsioximeter();
cont = 0;
}
}
So, the serial monitor is outputting values like this:
67,95
66,95
67,96
and so on.
But only when ser.readline() is invoked, the values become skewed and are unable to be unpacked by the split(',') function. In the following photo (1) and (2), you can see the distortion of the values right when the ser.readline() is called.
How can I re-word the python OR Arduino program in such a way to circumvent this distortion and allow the values to be split and unpacked without any errors?
So is there any possibility that something else is calling loop() asynchronously, e.g. from an interrupt routine, which might try to simultaneously transmit another string of readings at the same time as the arduino's 'mainline' calling of the loop function? An aside: if the interrupt routine readPulsioximeter() got invoked while the mainline loop() function was between the calls to eHealth.getBPM() and eHealth.getOxygenSaturation() and updated the Pulsioximeter attributes, does your code guarantee to send values from the same reading out onto the serial port?
im trying to do something which arduino sends bunch of data frequently, and my objective is:
every 100 data, make a new file. (lets call it a1, a2, ...)
in one generic file, take the average of each of these a files and write it inside of that file as a new line
for experiment i coded my arduino like that:
void setup(){
Serial.begin(9600);
}
void loop(){
Serial.println(random(100,500));
delay(20);
}
and here is the python code:
import serial, struct
initialfreq = 0
a = 0
interval = 0
fileName = 'general_list'
general_list = open(fileName, 'wb')
ser = serial.Serial(port = 'COM3', baudrate = 9600)
def mean(numberList):
return sum(numberList) / len(numberList)
while(1):
for i in '100' :
temparray=[]
fileName = 'interval' + str(initialfreq) + '.data'
temp_file = open(fileName, 'wb')
readoff = ser.readline()
temparray.append(readoff)
temp_file.write(readoff)
## temp_file.flush()
print("bitti")
general_list.write(str(interval)+" "+str(mean(temparray)))
general_list.write(str(mean(temparray)))
initialfreq= initialfreq + 1
a=0`
my problem is,
for loop is not working properly, even when i sad 100, its not taking 100 values.
arduino sending codes with \n. i cant see them in files but in temparray i see that there is \n 's so its not calculating the average.
thanks a lot guys.
Here is the solution for your first problem.
1)
for i in range(100):