- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我有一个处理草图,需要与 USB 设备建立 2 个连接。我无法提前判断哪个设备是 USB0 哪个是 USB1。 (不是我至少知道)
其中一台设备发出问候语,另一台设备根本不回答。因此,我编写了带有简单超时的代码。在设置中,我不断检查是否有字节要读取。但是 while 和 if 语句都会产生不正确的结果
while( dccCentral.available() < 5 ) {
if( dccCentral.available() >= 5) break;
if(millis() > 5000 ) {
println("timeout occured");
println(dccCentral.available());
break;
}
}
这些线路正在设置中。始终打印文本“发生超时”。在其下方,打印了 dccCentral.available() 的结果。这个数字是 12,这是正确的。
无论如何,如果 dccCentral.available() 当时打印 12。第一个 if 语句:
if( dccCentral.available() >= 5) break;
应该在该超时发生之前已经跳出 while 循环。当接收到 5 个或更多字节时,while 循环本身也应该退出。
为什么这两行都是
while( dccCentral.available() < 5 ) {
if( dccCentral.available() >= 5) break;
失败了?
最佳答案
我个人尽量避免 while 循环,除非没有其他方法(例如在线程内),这既可以避免逻辑陷阱,也可以避免干扰可能需要一些时间来初始化的其他对象的生命周期。
如果您从 Arduino 发送字符串并且还使用 println()
您可以初始化端口以使用 Serial 的 bufferUntil()
轻松捕获它结合serialEvent()
最后readString()
.
一旦开始获取数据,您就可以:
serialEvent()
Serial
参数来分配 dccCentral
并通过消除过程分配另一个端口这里有一个注释草图来说明这个想法:
import processing.serial.*;
// be sure to set this to the baud rate your device use with Arduino as well
final int BAUD_RATE = 115200;
// reference to Serial port sending "Hello" (when that get's detected)
Serial dccCentral;
// reference to the other Serial port
Serial otherDevice;
// temporary references
Serial usb0;
Serial usb1;
// 'toggle' to keep track where the hello was received and handled or not (by default initialised as false)
boolean wasHelloReceived;
void setup(){
usb0 = initSerial("/dev/ttyUSB0", BAUD_RATE);
usb1 = initSerial("/dev/ttyUSB1", BAUD_RATE);
}
Serial initSerial(String portName, int baudRate){
Serial port = null;
try{
port = new Serial(this, portName, baudRate);
// if sending strings and using println() from Arduino
// you can buffer all chars until the new line ('\n') character is found
port.bufferUntil('\n');
}catch(Exception e){
println("error initialising port: " + portName);
println("double check name, cable connections and close other software using the same port");
e.printStackTrace();
}
return port;
}
void draw(){
background(0);
text("wasHelloReceived: " + wasHelloReceived + "\n"
+"dccCentral: " + dccCentral + "\n"
+"otherDevice: " + otherDevice , 10 ,15);
// do something with the devices once they're ready (e.g. send a message every 3 seconds)
if(millis() % 3000 == 0){
if(dccCentral != null){
dccCentral.write("ping\n");
}
if(otherDevice != null){
otherDevice.write("pong\n");
}
}
}
void serialEvent(Serial port){
try{
String serialString = port.readString();
// if the received string is not null, nor empty
if(serialString != null && !serialString.isEmpty()){
// for debugging purposes display the data received
println("received from serial: " + serialString);
// trim any white space
serialString = serialString.trim();
// check if "hello" was received
if(serialString.equals("hello")){
println("hello detected!");
// if the dccCEntral (hello sending) serial port wasn't assigned yet, assign it
// think of this as debouncing a button: setting the port once "hello" was received should happen only once
if(!wasHelloReceived){
// now what dccCentral is found, assign it to the named reference
dccCentral = port;
// by process elimiation, assign the other port
// (e.g. if dccCentral == usb0, then other is usb1 and vice versa)
otherDevice = (dccCentral == usb0 ? usb1 : usb0);
/*
the above is the same as
if(dccCentral == usb0){
otherDevice = usb1;
}else{
otherDevice = usb0;
}
*/
wasHelloReceived = true;
}
}
}
}catch(Exception e){
println("error processing serial data");
e.printStackTrace();
}
}
请注意以上代码尚未经过测试,因此可能包含语法错误,但希望能理解这一点。
我不禁注意到 USB0/USB1 是串行设备有时在 Linux 上的显示方式。如果您使用的是 Raspberry Pi,并且熟悉 Python,我可以推荐一种稍微简单一些的方法。 PySerial它有一些技巧:
python -m serial.tools.list_ports -v
它将列出带有额外信息的端口,例如串行转换器芯片组的序列号。无论制造商和使用的 USB 端口如何,这都有助于区分哪个设备是哪个这是两个具有相同芯片组的设备的基本 list_ports -v
输出:
column 1
/dev/ttyUSB9
desc: TTL232R-3V3
hwid: USB VID:PID=0403:6001 SER=FT94O21P LOCATION=1-2.2
column 2
/dev/ttyUSB8
desc: TTL232R-3V3
hwid: USB VID:PID=0403:6001 SER=FT94MKCI LOCATION=1-2.1.4
要使用串行分配设备,您可以使用类似的东西:
"hwgrep://FT94O21P"
"hwgrep://FT94MKCI"
更新
逐步调试系统并一次尝试一个端口可能会有所帮助。这个想法是让代码读取预期的串行字符串。这是一个基本示例,它应该一次简单地将一个字符累积到一个字符串中并显示它:
import processing.serial.*;
Serial port;
String fromSerial = "";
void setup(){
size(300,300);
port = initSerial("/dev/ttyUSB0", 115200);
}
Serial initSerial(String portName, int baudRate){
Serial port = null;
try{
port = new Serial(this, portName, baudRate);
// if sending strings and using println() from Arduino
// you can buffer all chars until the new line ('\n') character is found
port.bufferUntil('\n');
}catch(Exception e){
println("error initialising port: " + portName);
println("double check name, cable connections and close other software using the same port");
e.printStackTrace();
}
return port;
}
void draw(){
if(port != null){
if(port.available() > 0){
char inChar = port.readChar();
fromSerial += inChar;
if(inChar == '\n'){
println("newline encountered");
println(fromSerial.split("\n"));
}
}
}
background(0);
text("from serial:" + fromSerial, 10,15);
}
如果来自 dccCentral
的数据符合预期:太好了,可以简化代码并在将来应用正确的条件来过滤设备,否则,如果使用 Serial.println()
来自 Arduino)
关于Python,一点问题都没有。如果这个想法将来有帮助,您可以查看 this answer . (AFAIK Processing Serial 在幕后使用 JSSC)
关于serial-port - 为什么 serial.available 在此代码段中不起作用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62746214/
今天有小伙伴给我留言问到,try{...}catch(){...}是什么意思?它用来干什么? 简单的说 他们是用来捕获异常的 下面我们通过一个例子来详细讲解下
我正在努力提高网站的可访问性,但我不知道如何在页脚中标记社交媒体链接列表。这些链接指向我在 facecook、twitter 等上的帐户。我不想用 role="navigation" 标记这些链接,因
说现在是 6 点,我有一个 Timer 并在 10 点安排了一个 TimerTask。之后,System DateTime 被其他服务(例如 ntp)调整为 9 点钟。我仍然希望我的 TimerTas
就目前而言,这个问题不适合我们的问答形式。我们希望答案得到事实、引用资料或专业知识的支持,但这个问题可能会引发辩论、争论、投票或扩展讨论。如果您觉得这个问题可以改进并可能重新打开,visit the
我就废话不多说了,大家还是直接看代码吧~ ? 1
Maven系列1 1.什么是Maven? Maven是一个项目管理工具,它包含了一个对象模型。一组标准集合,一个依赖管理系统。和用来运行定义在生命周期阶段中插件目标和逻辑。 核心功能 Mav
我是一名优秀的程序员,十分优秀!