Write string using pyserial to move servo - python

I have an arduino program which allows me to move a servo based on a specific instruction in this format <C,28,355>. Whenever I enter this command in arduino IDE in the serial monitor it seems to work well, but when trying the same command using pyserial in python nothing happens.
import serial
arduinoData = serial.Serial('com7', 115200)
while True:
cmd=“<C,28,355>”
arduinoData.write(cmd.encode())

Related

Serial communication with Raspberry Pi Pico and Python

I'm trying to achieve 2-way comms over USB (COM port) between Raspberry Pi Pico and Windows PC (Python).
The point is, that I'm unable to send anything from my PC to raspberry nor the way back.
Doesn't affect the LEDs on breadboard, nor the messages get printed in terminal.
Here's the code for PC:
import serial
import time
# open a serial connection
s = serial.Serial("COM7", 115200)
print(s)
# blink the led
while True:
s.write(b"on\n")
time.sleep(1)
s.readline().strip()
s.write(b"off\n")
time.sleep(1)
s.readline().strip()
And here's the piece of code on Raspberry Pi Pico:
import time
from machine import Pin
import sys
led = Pin(0, machine.Pin.OUT)
led2 = Pin(2, machine.Pin.OUT)
led2.value(0)
led.value(0)
def led_on():
led.value(1)
def led_off():
led.value(0)
while True:
# read a command from the host
v = sys.stdin.readline().strip()
# perform the requested action
if v.lower() == "on":
led_on()
print("Turned on!")
elif v.lower() == "off":
led_off()
print("Turned off!")
Also - what's the smartest way to debug the code onboard the Raspberry Pi Pico?
After acquiring the serial connection, standard print debug?
Is there any way to use the sequence debugger in Thonny IDE?
Best Regards!
I've tried many methods from both serial or stdlib libraries without any result.
Also important thing - for PC side of script I'm using PyCharm, for Raspberry side - Thonny.
After flashing Raspberry Pico, I'm disconnecting the serial and starting to run the script in PyCharm, with different interpreter.
Easiest Solution
Serial communication is purely bi-directional. There cannot be more than 2 devices on a given serial port. In Thonny (and micropython) this is dedicated to loading code. You cannot directly write to the serial port from your computer when a program is running. When a program isn't running on the pico, however, you have access to REPL. You can read a little more about it here. This allows you to call functions directly on the pico. So you could write a program such as this:
from machine import pin
led = Pin(0, machine.Pin.OUT)
led2 = Pin(2, machine.Pin.OUT)
led2.value(0)
led.value(0)
def led_on():
led.value(1)
def led_off():
led.value(0)
and call it from REPL by sending
>>> led_on()
This is far and away the easiest solution and also gives you access to any function within microPython which may be useful for debugging as you can just print whatever value you want.
More Robust Solution
Code code above isn't wrong. It just will not work with Thonny since Thonny has taken over the serial port. If you upload your code as a .u2f file or use a separate debugger (such as a pi or a second pico as a picoprobe) using one of the UART peripherals then you could use the USB port as a serial connection. There is a thread over on the raspberry pi forms where functional 2-way serial code is shown. Similarly, this tutorial walks you through doing it in a background-thread.

Serial.write() not received by Arduino

I am trying to get an LED to respond to a python program (using python 3.8), and it is not receiving anything. When I connect to the port, the led blinks to indicate it is connected, but then does nothing. Here is my code:
import serial
ser=serial.Serial('/dev/cu.usbmodem1411', 2000000, timeout=1)
ser.write(b'H')
time.sleep(200)
while True:
#read echo back from arduino verify receipt of message
#will show printing of x from arduino program
data = ser.readline()[:-2]
if data:
print (data.decode())
The while loop doesn't print out anything, and I also tried using the Arduino interface and it send signals fine, so my wiring is correct, but there is something missing with the python code. Has anyone run into this before?
The problem seems to be due to the wrong band speed you are using for the serial port. ser=serial.Serial('/dev/cu.usbmodem1411', 2000000, timeout=1) The value 2000000 here can never be true. There is no such value. The default is 9600, but I'll share a photo showing you the band speed on the Arduino side, the band speeds here and there should be equal.

Why does my raspberry pi hang when reading from serial from arduino if sent by `serial.write` but not by `serial.print`?

pi and arduino newbie here. I'm trying to send a signal from an arduino that triggers and receives a pulse from an ultrasonic sensor (hc-sr04), and sends the time of pulse duration to a raspberry pi. I can read the value fine on the raspberry pi if I use Serial.println() on the arduino, but not if I use Serial.write(): in this case, my code on the pi hangs when trying to read. I've looked at the arduino doc and know the difference between write() (binary data) and print() (human-readable), but still don't know why the hang is taking place.
Relevant python code on the pi:
import time, serial
ser = serial.Serial('/dev/ttyACM0', 9600, timeout=10)
while True:
val = ser.readline().decode('utf-8').rstrip()
print(f"{val})
Relevant arduino code:
pulse_dur = pulseIn(ECHO_PIN, HIGH);
Serial.println(pulse_dur); // works fine
Serial.write(pulse_dur); // causes hang

Pyserial cannot send all characters to arduino, but can do it on another PC terminal

I am working on an existing project.
Until now, a PC software controls an Arduino Due.
The PC software sends serial commands to the Arduino Due.
What I am trying to do, is to replace the PC software with a python script. Python 3.5.
So I am working with pyserial.
The problem seems to be that the python script does not send all the characters to the Arduino Due. It misses some final characters.
The difficult parts to understand are the following:
When I am sending the characters, from the python script, to another PC terminal instead of the Arduino, then I can successfully collect all the characters from the terminal, I am using Bray's terminal.
When I am sending the same string from my terminal to the Arduino Due, the Arduino Due successfully collects the data sent.
It seems as if only the Python to Arduino does not work, while
Python to PC termimal is working and
PC terminal to Arduino is working
I open the serial port like this:
my_port = serial.Serial('COM6', 115200)
while connected != True:
if my_port.is_open == 1:
connected = True
Can anyone provide any insight?
Thanks.
edit: I just noticed that when the python script sends the data, then the debug serial port I am using sends corrupted data.
Solved it.
I noticed that the debug serial was also sending less characters and I thought that there maybe a reset going on.
So I am now sending my arrays from a thread after each button press.
What I was doing, is that I was sending it directly after connection.

Python serial write doesn't work FIRST run

I have 2 programs to test serial communication, an simple arduino program that echoes whatever is on the serial port and a python program that writes to the serial port and prints the reply.
I'm having an issue where whenever I upload the arduino program and try to run the python the first time after I uploaded, it would be stuck on print ser.readline() which I'm assuming means for some reason python is not writing to the serial port. I would have to quit the python program and run it again to get it to get a reply from arduino. The program would continue to work until I re-upload the arduino then once again python wouldn't work on first run. Also if I open and close the serial monitor before I run the python program it will work the first run. Does anyone know what is the issue? This is on Ubuntu.
arduino
String str;
void setup() {
// Turn the Serial Protocol ON
Serial.begin(115200);
}
void loop() {
if (Serial.available()) {
str = Serial.readStringUntil('\n'); // Read the serial input
Serial.println(str); // sends ascii code
}
}
Python
import serial
ser = serial.Serial('/dev/ttyACM1', 115200)
for i in range(0,4):
str = "test string\n"
ser.write(str)
print ser.readline()
The issue is likely related to many Arduinos resetting when a new serial connection is made.
The solution is to either add a delay (about 2 seconds works) to the python program between the serial connection being created and the first data being sent or modifying the hardware to prevent a reset on serial connect.
By default python Serial might be blocking by default try removing the timeout:
ser = serial.Serial('/dev/ttyACM1', 115200,timeout=0)
additionally have a peek at the serial.threaded in the docs
I added
time.sleep(1)
ser.setDTR(level=0)
time.sleep(1)
after opening the serial port and the issue was fixed.

Categories

Resources