我正在做一个Arduino项目,根据iRacing中的车速进行风扇旋转。这是我的第一个arduino项目,所以请耐心等待。我对PC / Arduino串口通讯的一些奇怪行为感到很困惑,我希望有人可以帮忙解释一下发生的事情......
基本上,PC上有一个C ++程序可以从iRacing SDK获取车辆速度的数据,并通过串行线路将数据发送到Arduino。 Arduino进行一些简单的处理并驱动电机控制器来运行风扇。
我试图理解的现象是,如果我使用Serial.print()语句将Arduino写入串口太多,它就会破坏使用Serial.parseInt()读取的值。< / p>
我已经让它工作只是不写'#34;太多&#34;到串行线,但有一段时间它表现不规律 - 即使iRacing值稳定,风扇速度也会上下波动。我在我的arduino sketch和serial.readSerial中添加了额外的Serial.print内容,试图在PC端看到这些值发生了什么,结果证明它变得更糟。
把我的头发拉了一下之后,我从头开始研究arduino草图,它与所有相同的逻辑工作,但是用Serial.print命令注释掉了!所以我系统地将它们添加回去,发现存在一些阈值,如果我在串行线上打印太多,它就会开始出现故障。
这是PC工作时看到的输出。 PC正在向Arduiono发送59作为int。 Arduino正在接收Serial.parseInt(),将constrain()做为55,然后将其映射到40-255范围。最小的Serial.print()语句将该数据发送回PC并在其中读取并打印出来。一切都很好。
59 55 255
59 55 255
59 55 255
59 55 255
59 55 255
59 55 255
59 55 255
59 55 255
如果我添加更多的Serial.print()语句来描述数据,那么我从具有Serial.parseInt()的PC读取的值开始受到干扰。此输出显示了我在发生这种情况时所看到的情况。数据看起来搞砸了,确实风扇速度变得混乱。这与上述情况相同,应该稳定在59:
Car Vel: 59 55 255
Car Vel: 59 55 255
Car Vel: 9 9 71
Car Vel: 47 47 223
Car Vel: 59 55 255
Car Vel: 59 55 255
Car Vel: 9 9 71
Car Vel: 47 47 223
Car Vel: 59 55 255
Car Vel: 71 55 255
Car Vel: 47 47 223
Car Vel: 59 55 255
Car Vel: 59 55 255
这里的Arduino草图一直向下简化,所以它只是从PC中读取int,约束它,将它映射到一个范围并打印值。如下所示,它会发生故障并产生输出(如上面的第二个清单)。如果我评论出&#34; Car Vel:&#34;打印,然后它工作,数据稳定(如上面的第一个清单)。
#define MIN 40
#define MAX 255
#define TOPSPEED 55
void setup() {
Serial.begin(9600);
}
void loop() {
uint8_t v;
uint8_t s;
if (Serial.available() > 0) {
v = Serial.parseInt();
Serial.print("Car Vel: "); //UNCOMMENT ANY OF THESE TO SEE THE FAIL
Serial.print(v);
Serial.print("\t");
v = constrain(v,0,TOPSPEED);
// Serial.print("Clamped Vel: "); //UNCOMMENT ANY OF THESE TO SEE THE FAIL
Serial.print(v);
Serial.print("\t");
s = map(v,1,TOPSPEED,MIN,MAX);
// Serial.print("Fan Speed: "); //UNCOMMENT ANY OF THESE TO SEE THE FAIL
Serial.println(s);
}
}
在PC端,我使用iRacing SDK中的irsdk_ir2ad C ++代码,只修改了run()例程:
void run()
{
// wait up to 16 ms for start of session or new data
if(irsdkClient::instance().waitForData(16))
{
// and grab the data
int v = g_carVelX.getInt();
serial.writeSerialPrintf("%d\n", v);
}
// check for data coming back from Arduino
if (serial.serialHasData())
{
static char buffer[256];
serial.readSerial(buffer, 256);
printf("%s", buffer);
}
monitorConnectionStatus();
}
我确信取消注释Serial.print行确实会出现问题,但我没有真正好解释原因。有人可以帮忙吗?是某种超出的发送长度(似乎是一个非常少量的文本)?或者当Arduino正在编写自己的数据时,从PC上写入的数据太多了?或者某种时间选择,它只是额外的时间而不是与写入的数据量有什么关系?
答案 0 :(得分:1)
答案结果证明是9600波特的字符限制。
在这种特殊情况下,PC正以60Hz的速度获取数据。在9600波特率下,串行线路每个周期只能处理16个字符。
尝试输出整个字符串超过16字节限制: “车速:59 55 255”
实验表明,如果我将组合的发送/接收数据降低到&lt; = 16字节,则它始终没有错误。