Arduino伺服代码重置到位置0
Arduino servo code resetting to positon 0
(请原谅我的英文)
你好。我是编码初学者,开始尝试使用 Arduino 和 C++(因为 Arduino)。最近我刚刚了解到你可以通过串行监视器写入 Arduino 板,因此通过你的 PC 通过你的 COM 端口,所以我试图找到一种通过 Arduino 的串行监视器从 cmd 控制伺服电机旋转的方法。我复制了在 Arduino 网站上作为示例给出的代码,并通过来自 youtube 的人获得了一段有效的代码。
因为你看到这段代码的工作原理是它通过 windows(任何 ide)上的 c++ 程序写入串行监视器,但是当我发送命令时,它 运行s 正确,然后再次 运行s 但将输入设置为 0 度,从而将伺服头移动到 0 度。如果输入为 0 但它 运行 是草图中的所有其他内容,我通过防止伺服旋转来临时“修复”它。
(我已经包含了下面的代码,但它真的很长而且我不知道如何包含大块代码(如果我包含错误的东西我很抱歉)同时仍然包含最小可重现的示例。如果被告知我会很乐意更改它到)
主要代码:
#include <iostream>
#include <string>
#include <stdlib.h>
#include <string>
#include "SerialPort.h"
char output[MAX_DATA_LENGTH];
char incomingData[MAX_DATA_LENGTH];
using namespace std;
char temp[] = "\\.\COM4";
char* port = temp;
float Scalar = 0.8888;
int main() {
SerialPort arduino(port);
if (arduino.isConnected()) {
cout << "Connection established" << endl << endl;
}
else {
cout << "Error in port name" << endl << endl;
}
while (arduino.isConnected()) {
while (true) {
cout << "Enter your command (degrees 0 to 180 in integers): " << endl;
string data;
cin >> data;
if (data == "exit")
return 0;
/*if (stoi(data) != 90) {
data = to_string(
round((stof(data) - 90) * Scalar + 90)
);
}*/
//cout << data << endl;
char* charArray = new char[data.size() + 2];
copy(data.begin(), data.end(), charArray);
charArray[data.size()] = '\n';
charArray[data.size() + 1] = '[=10=]';
cout << "char array: " << charArray << endl;
arduino.writeSerialPort(charArray, MAX_DATA_LENGTH);
arduino.readSerialPort(output, MAX_DATA_LENGTH);
cout << ">> " << output << endl;
cout << "----------\n" << endl;
delete[] charArray;
}
}
return 0;
}
.ino 草图文件:
#include <Servo.h>
Servo servo1;
int LED = 13;
int servoPos = 90; //to store servo's position
void setup() {
// put your setup code here, to run once:
Serial.begin(9600);
pinMode(LED, OUTPUT);
servo1.attach(11);
servo1.write(servoPos);
}
void loop() {
// put your main code here, to run repeatedly:
delay(15);
if(Serial.available() > 0) {
String info;
String return_text;
info = Serial.readStringUntil('\n');
return_text = "info variable string is: " + info;
Serial.println(return_text);
if(info.toInt() < servoPos && info.toInt() != 0) {
for( 0; servoPos > info.toInt(); servoPos-=1) {
servo1.write(servoPos);
delay(5);
}
}
else if(info.toInt() > servoPos) {
for( 0; servoPos < info.toInt(); servoPos+=1) {
servo1.write(servoPos);
delay(5);
}
}
digitalWrite(LED, HIGH);
delay(20);
digitalWrite(LED, LOW);
//Serial.println("");
//Serial.print("Servo position: ");
//Serial.println(servoPos);
}
}
header:
#ifndef SERIALPORT_H
#define SERIALPORT_H
#define ARDUINO_WAIT_TIME 2000
#define MAX_DATA_LENGTH 255
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
class SerialPort
{
private:
HANDLE handler;
bool connected;
COMSTAT status;
DWORD errors;
public:
SerialPort(char* portName);
~SerialPort();
int readSerialPort(char* buffer, unsigned int buf_size);
bool writeSerialPort(char* buffer, unsigned int buf_size);
bool isConnected();
};
#endif // SERIALPORT_H
以及包含函数的 cpp 文件:
#include "SerialPort.h"
SerialPort::SerialPort(char* portName)
{
this->connected = false;
this->handler = CreateFileA(static_cast<LPCSTR>(portName),
GENERIC_READ | GENERIC_WRITE,
0,
NULL,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
NULL);
if (this->handler == INVALID_HANDLE_VALUE) {
if (GetLastError() == ERROR_FILE_NOT_FOUND) {
printf("ERROR: Handle was not attached. Reason: %s not available\n", portName);
}
else
{
printf("ERROR!!!");
}
}
else {
DCB dcbSerialParameters = { 0 };
if (!GetCommState(this->handler, &dcbSerialParameters)) {
printf("failed to get current serial parameters");
}
else {
dcbSerialParameters.BaudRate = CBR_9600;
dcbSerialParameters.ByteSize = 8;
dcbSerialParameters.StopBits = ONESTOPBIT;
dcbSerialParameters.Parity = NOPARITY;
dcbSerialParameters.fDtrControl = DTR_CONTROL_ENABLE;
if (!SetCommState(handler, &dcbSerialParameters))
{
printf("ALERT: could not set Serial port parameters\n");
}
else {
this->connected = true;
PurgeComm(this->handler, PURGE_RXCLEAR | PURGE_TXCLEAR);
Sleep(ARDUINO_WAIT_TIME);
}
}
}
}
SerialPort::~SerialPort()
{
if (this->connected) {
this->connected = false;
CloseHandle(this->handler);
}
}
int SerialPort::readSerialPort(char* buffer, unsigned int buf_size)
{
DWORD bytesRead;
unsigned int toRead = 0;
ClearCommError(this->handler, &this->errors, &this->status);
if (this->status.cbInQue > 0) {
if (this->status.cbInQue > buf_size) {
toRead = buf_size;
}
else toRead = this->status.cbInQue;
}
if (ReadFile(this->handler, buffer, toRead, &bytesRead, NULL)) return bytesRead;
return 0;
}
bool SerialPort::writeSerialPort(char* buffer, unsigned int buf_size)
{
DWORD bytesSend;
if (!WriteFile(this->handler, (void*)buffer, buf_size, &bytesSend, 0)) {
ClearCommError(this->handler, &this->errors, &this->status);
return false;
}
else return true;
}
bool SerialPort::isConnected()
{
return this->connected;
}
发生了什么:
因此,当我 运行 它时,首先伺服旋转到 90 度,然后当我给它一个整数输入时 Arduino 运行 将伺服转向所需的输入,打开和关闭 LED,同时发生这种情况 cpp 主代码打印我发送给 Arduino 的内容(或者至少是没有 \n
和 [=15=]
e.t.c 的可见内容)以及串行监视器写入并返回的内容要求我发送输入。 问题 再次是 Arduino 代码 运行s 并将伺服器移动到 0 度并点亮和关闭 LED,就像以前一样,没有我的要求。
如果 data == 0
,我去阻止伺服移动,但 .ino 草图的其余部分仍然 运行s,所以我怀疑它可能与 char 相关cpp 文件发送到监视器..?但是我太聪明了,无法弄清楚,因此寻求任何建议。控制台显示输出,但在第二次发生 arduino 循环时不显示任何内容。
如果我在控制台中写了一些东西,而第二次(不需要的)迭代发生,那么 arduino 不会响应我的输入,并且在接下来的 运行s 期间它也会从串行监视器中弄乱 output
要么不显示文本,要么完全弄乱文本 and/or 显示奇怪的乱码,例如“³ô¦ò»]½R↨ùýº§»⌂2{²à_Ú◄/4ý¾ı”等等。
(如果由于不当行为、礼仪或 e.t.c 需要添加、删除或更改任何内容,那么正如我所说,我将非常乐意)
提前致谢。
这是一个简化串口监控的工具。您可以view/plot 数据、发送命令、存储参数以及使用 3D 视图绑定数据。
这里有通用 C 代码的文件和 Arduino 的文件 (cpp) Arduino files
抱歉没有更新。我找到了解决方案。只是当我向它提供发送的长度时,我要求在线代码中的函数发送一个 255 个字符的字符数组。由于 function/header 的任务是发送 255 个字符,它以某种方式组成了随机数据,arduino 串行 COM reader 读取为 0。我只是通过更改 [= 告诉函数要发送多少数据来修复它14=] in arduino.writeSerialPort(charArray, MAX_DATA_LENGTH);
只是要发送的字符串中的字符数。
(请原谅我的英文) 你好。我是编码初学者,开始尝试使用 Arduino 和 C++(因为 Arduino)。最近我刚刚了解到你可以通过串行监视器写入 Arduino 板,因此通过你的 PC 通过你的 COM 端口,所以我试图找到一种通过 Arduino 的串行监视器从 cmd 控制伺服电机旋转的方法。我复制了在 Arduino 网站上作为示例给出的代码,并通过来自 youtube 的人获得了一段有效的代码。
因为你看到这段代码的工作原理是它通过 windows(任何 ide)上的 c++ 程序写入串行监视器,但是当我发送命令时,它 运行s 正确,然后再次 运行s 但将输入设置为 0 度,从而将伺服头移动到 0 度。如果输入为 0 但它 运行 是草图中的所有其他内容,我通过防止伺服旋转来临时“修复”它。 (我已经包含了下面的代码,但它真的很长而且我不知道如何包含大块代码(如果我包含错误的东西我很抱歉)同时仍然包含最小可重现的示例。如果被告知我会很乐意更改它到)
主要代码:
#include <iostream>
#include <string>
#include <stdlib.h>
#include <string>
#include "SerialPort.h"
char output[MAX_DATA_LENGTH];
char incomingData[MAX_DATA_LENGTH];
using namespace std;
char temp[] = "\\.\COM4";
char* port = temp;
float Scalar = 0.8888;
int main() {
SerialPort arduino(port);
if (arduino.isConnected()) {
cout << "Connection established" << endl << endl;
}
else {
cout << "Error in port name" << endl << endl;
}
while (arduino.isConnected()) {
while (true) {
cout << "Enter your command (degrees 0 to 180 in integers): " << endl;
string data;
cin >> data;
if (data == "exit")
return 0;
/*if (stoi(data) != 90) {
data = to_string(
round((stof(data) - 90) * Scalar + 90)
);
}*/
//cout << data << endl;
char* charArray = new char[data.size() + 2];
copy(data.begin(), data.end(), charArray);
charArray[data.size()] = '\n';
charArray[data.size() + 1] = '[=10=]';
cout << "char array: " << charArray << endl;
arduino.writeSerialPort(charArray, MAX_DATA_LENGTH);
arduino.readSerialPort(output, MAX_DATA_LENGTH);
cout << ">> " << output << endl;
cout << "----------\n" << endl;
delete[] charArray;
}
}
return 0;
}
.ino 草图文件:
#include <Servo.h>
Servo servo1;
int LED = 13;
int servoPos = 90; //to store servo's position
void setup() {
// put your setup code here, to run once:
Serial.begin(9600);
pinMode(LED, OUTPUT);
servo1.attach(11);
servo1.write(servoPos);
}
void loop() {
// put your main code here, to run repeatedly:
delay(15);
if(Serial.available() > 0) {
String info;
String return_text;
info = Serial.readStringUntil('\n');
return_text = "info variable string is: " + info;
Serial.println(return_text);
if(info.toInt() < servoPos && info.toInt() != 0) {
for( 0; servoPos > info.toInt(); servoPos-=1) {
servo1.write(servoPos);
delay(5);
}
}
else if(info.toInt() > servoPos) {
for( 0; servoPos < info.toInt(); servoPos+=1) {
servo1.write(servoPos);
delay(5);
}
}
digitalWrite(LED, HIGH);
delay(20);
digitalWrite(LED, LOW);
//Serial.println("");
//Serial.print("Servo position: ");
//Serial.println(servoPos);
}
}
header:
#ifndef SERIALPORT_H
#define SERIALPORT_H
#define ARDUINO_WAIT_TIME 2000
#define MAX_DATA_LENGTH 255
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
class SerialPort
{
private:
HANDLE handler;
bool connected;
COMSTAT status;
DWORD errors;
public:
SerialPort(char* portName);
~SerialPort();
int readSerialPort(char* buffer, unsigned int buf_size);
bool writeSerialPort(char* buffer, unsigned int buf_size);
bool isConnected();
};
#endif // SERIALPORT_H
以及包含函数的 cpp 文件:
#include "SerialPort.h"
SerialPort::SerialPort(char* portName)
{
this->connected = false;
this->handler = CreateFileA(static_cast<LPCSTR>(portName),
GENERIC_READ | GENERIC_WRITE,
0,
NULL,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
NULL);
if (this->handler == INVALID_HANDLE_VALUE) {
if (GetLastError() == ERROR_FILE_NOT_FOUND) {
printf("ERROR: Handle was not attached. Reason: %s not available\n", portName);
}
else
{
printf("ERROR!!!");
}
}
else {
DCB dcbSerialParameters = { 0 };
if (!GetCommState(this->handler, &dcbSerialParameters)) {
printf("failed to get current serial parameters");
}
else {
dcbSerialParameters.BaudRate = CBR_9600;
dcbSerialParameters.ByteSize = 8;
dcbSerialParameters.StopBits = ONESTOPBIT;
dcbSerialParameters.Parity = NOPARITY;
dcbSerialParameters.fDtrControl = DTR_CONTROL_ENABLE;
if (!SetCommState(handler, &dcbSerialParameters))
{
printf("ALERT: could not set Serial port parameters\n");
}
else {
this->connected = true;
PurgeComm(this->handler, PURGE_RXCLEAR | PURGE_TXCLEAR);
Sleep(ARDUINO_WAIT_TIME);
}
}
}
}
SerialPort::~SerialPort()
{
if (this->connected) {
this->connected = false;
CloseHandle(this->handler);
}
}
int SerialPort::readSerialPort(char* buffer, unsigned int buf_size)
{
DWORD bytesRead;
unsigned int toRead = 0;
ClearCommError(this->handler, &this->errors, &this->status);
if (this->status.cbInQue > 0) {
if (this->status.cbInQue > buf_size) {
toRead = buf_size;
}
else toRead = this->status.cbInQue;
}
if (ReadFile(this->handler, buffer, toRead, &bytesRead, NULL)) return bytesRead;
return 0;
}
bool SerialPort::writeSerialPort(char* buffer, unsigned int buf_size)
{
DWORD bytesSend;
if (!WriteFile(this->handler, (void*)buffer, buf_size, &bytesSend, 0)) {
ClearCommError(this->handler, &this->errors, &this->status);
return false;
}
else return true;
}
bool SerialPort::isConnected()
{
return this->connected;
}
发生了什么:
因此,当我 运行 它时,首先伺服旋转到 90 度,然后当我给它一个整数输入时 Arduino 运行 将伺服转向所需的输入,打开和关闭 LED,同时发生这种情况 cpp 主代码打印我发送给 Arduino 的内容(或者至少是没有 \n
和 [=15=]
e.t.c 的可见内容)以及串行监视器写入并返回的内容要求我发送输入。 问题 再次是 Arduino 代码 运行s 并将伺服器移动到 0 度并点亮和关闭 LED,就像以前一样,没有我的要求。
如果 data == 0
,我去阻止伺服移动,但 .ino 草图的其余部分仍然 运行s,所以我怀疑它可能与 char 相关cpp 文件发送到监视器..?但是我太聪明了,无法弄清楚,因此寻求任何建议。控制台显示输出,但在第二次发生 arduino 循环时不显示任何内容。
如果我在控制台中写了一些东西,而第二次(不需要的)迭代发生,那么 arduino 不会响应我的输入,并且在接下来的 运行s 期间它也会从串行监视器中弄乱 output
要么不显示文本,要么完全弄乱文本 and/or 显示奇怪的乱码,例如“³ô¦ò»]½R↨ùýº§»⌂2{²à_Ú◄/4ý¾ı”等等。
(如果由于不当行为、礼仪或 e.t.c 需要添加、删除或更改任何内容,那么正如我所说,我将非常乐意) 提前致谢。
这是一个简化串口监控的工具。您可以view/plot 数据、发送命令、存储参数以及使用 3D 视图绑定数据。
这里有通用 C 代码的文件和 Arduino 的文件 (cpp) Arduino files
抱歉没有更新。我找到了解决方案。只是当我向它提供发送的长度时,我要求在线代码中的函数发送一个 255 个字符的字符数组。由于 function/header 的任务是发送 255 个字符,它以某种方式组成了随机数据,arduino 串行 COM reader 读取为 0。我只是通过更改 [= 告诉函数要发送多少数据来修复它14=] in arduino.writeSerialPort(charArray, MAX_DATA_LENGTH);
只是要发送的字符串中的字符数。