Python通过串口到Arduino,可以’;t移动伺服装置
我目前正试图将一个摄像头安装在一个由两个微型伺服系统组成的云台上,跟踪一张脸。我的python代码一直在工作,并且已经成功地识别出了一张脸,但是当Arduino不断闪烁时,我的伺服系统没有一个在移动,就好像它正在接收python代码的输入一样。我无法根据python代码让伺服系统移动,但我在旁边编写了一些简单的代码,以确保伺服系统具有良好的连接,并且能够自行正常工作。我不确定出了什么问题 Python代码Python通过串口到Arduino,可以’;t移动伺服装置,python,arduino,pyserial,servo,Python,Arduino,Pyserial,Servo,我目前正试图将一个摄像头安装在一个由两个微型伺服系统组成的云台上,跟踪一张脸。我的python代码一直在工作,并且已经成功地识别出了一张脸,但是当Arduino不断闪烁时,我的伺服系统没有一个在移动,就好像它正在接收python代码的输入一样。我无法根据python代码让伺服系统移动,但我在旁边编写了一些简单的代码,以确保伺服系统具有良好的连接,并且能够自行正常工作。我不确定出了什么问题 Python代码 import numpy as np6 import serial import time
import numpy as np6
import serial
import time
import sys
import cv2
arduino = serial.Serial('COM3', 9600)
time.sleep(2)
print("Connection to arduino...")
face_cascade = cv2.CascadeClassifier('haarcascade_frontalface_default.xml')
cap = cv2.VideoCapture(0)
while 1:
ret, img = cap.read()
cv2.resizeWindow('img', 500,500)
cv2.line(img,(500,250),(0,250),(0,255,0),1)
cv2.line(img,(250,0),(250,500),(0,255,0),1)
cv2.circle(img, (250, 250), 5, (255, 255, 255), -1)
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
faces = face_cascade.detectMultiScale(gray, 1.3)
for (x,y,w,h) in faces:
cv2.rectangle(img,(x,y),(x+w,y+h),(0,255,0),5)
roi_gray = gray[y:y+h, x:x+w]
roi_color = img[y:y+h, x:x+w]
arr = {y:y+h, x:x+w}
print (arr)
print ('X :' +str(x))
print ('Y :'+str(y))
print ('x+w :' +str(x+w))
print ('y+h :' +str(y+h))
xx = int(x+(x+h))/2
yy = int(y+(y+w))/2
print (xx)
print (yy)
center = (xx,yy)
print("Center of Rectangle is :", center)
data =(“X {0: f} Y {1: f} Z” .format (xx, yy))
print ("output = '" +data+ "'")
arduino.write(data.encode())
cv2.imshow('img',img)
k = cv2.waitKey(30) & 0xff
if k == 27:
break
阿杜伊诺代码
#include<Servo.h>
Servo servoVer; //Vertical Servo
Servo servoHor; //Horizontal Servo
int x;
int y;
int prevX;
int prevY;
void setup()
{
Serial.begin(9600);
servoVer.attach(5); //Vertical Servo to Pin 5
servoHor.attach(6); //Horizontal Servo to Pin 6
servoVer.write(90);
servoHor.write(90);
}
void Pos()
{
if(prevX != x || prevY != y)
{
int servoX = map(x, 600, 0, 70, 179);
int servoY = map(y, 450, 0, 179, 95);
servoX = min(servoX, 179);
servoX = max(servoX, 70);
servoY = min(servoY, 179);
servoY = max(servoY, 95);
servoHor.write(servoX);
servoVer.write(servoY);
}
}
void loop()
{
if(Serial.available() > 0)
{
if(Serial.read() == 'X')
{
x = Serial.parseInt();
if(Serial.read() == 'Y')
{
y = Serial.parseInt();
Pos();
}
}
while(Serial.available() > 0)
{
Serial.read();
}
}
}
#包括
伺服器//垂直伺服
伺服器//水平伺服
int x;
int-y;
int-prevX;
国际货币基金组织;
无效设置()
{
Serial.begin(9600);
伺服阀。连接(5);//垂直伺服阀至销5
伺服轴。连接(6);//水平伺服轴至销6
伺服写入(90);
servoHor.write(90);
}
void Pos()
{
if(prevX!=x | | prevY!=y)
{
int servoX=map(x600,0,70,179);
int servoY=map(y,450,0,179,95);
servoX=最小值(servoX,179);
servoX=最大值(servoX,70);
伺服=最小值(伺服,179);
伺服=最大值(伺服,95);
servoHor.write(servoX);
伺服器写入(伺服);
}
}
void循环()
{
如果(Serial.available()>0)
{
if(Serial.read()=='X')
{
x=Serial.parseInt();
if(Serial.read()='Y')
{
y=Serial.parseInt();
Pos();
}
}
while(Serial.available()>0)
{
Serial.read();
}
}
}
一个巨大的问题是您使用Serial.read的方式。该函数使用缓冲区外的字符。同一本书你不能读两遍。假设您发送了一个“Y”。第一个if语句从串行缓冲区中读取Y并与“X”进行比较,这是false,因此它继续。然后它从序列中读取其他内容,如果没有剩余内容可读取,则可能是-1。但是它没有看到“Y”,因为它是在第一个if中读取的
您需要做的是从serial读入char变量,然后在if语句中使用该char变量
char c = Serial.read();
if(c == 'X')...
... if (c == 'Y')...
假设你对伺服系统的命令正常工作。你能检查一下逻辑吗?模拟该位置,查看其是否调用正确的跟踪运动。