我从Arduino Uno发送到串口的数据可以在Arduino串口监视器中完全按照预期查看,但是当我在WAMP环境中通过serproxy从PHP读取数据时,我得到一些丢失或额外的字符(通常是一个看起来很像的字符)比如黑钻里面的问号。
我发现了类似的问题,但所有的答案都没有达成。通常只为Linux提供解决方案,或者只解决了使Windows从串行端口读取(而不是写入)所需的许多挑战的一部分。
我尝试以下方法让PHP只读取任何串行数据:
所以现在,我让我的Arduino通过USB线将数据发送到我的电脑,只要我在Arduino的串行监视器中监视数据,一切看起来都应该如此。当我在PHP中回显相同的数据时,我开始看到额外的或丢失的数据以及流。所以发送文本“AOK AOK AOK”有时会变成“好吗?Pz [R”或类似的东西,当我的PHP脚本回显时。
我试图从PHP socket_read()获取干净的串行数据的事情:
从php.net修改了TCP / IP的一些示例套接字代码后,我有一个PHP脚本,通过serproxy从串口写入2048位数据。此页面每10秒从另一个页面通过jQuery调用,并且回显的内容将加载到我的主页面上的内容中。
我的最终目标是发送一个1或0的流发送到我的PHP脚本,以指示应该切换它的背景颜色。我宁愿确定那些1或0不只是在额外的字符中随机回应,而是真正来自串行流本身。
有谁知道serproxy是否是我在PHP中看到的添加或删除不需要的数据的原因?
串行监视器显示正确数据的事实告诉我,这是PHP接收或解析数据的方式。
关于我还能检查什么,我的想法已经不多了。也许另外一双眼睛会揭露我忽略或做错的事情。
请参阅下面的代码,了解以下具体示例:
serial.html
<!DOCTYPE html>
<head>
</head>
<body>
<div id="serial" name="serial" class="serial"></div>
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.10.1/jquery.min.js"></script>
<script src="js/main.js"></script>
</body>
</html>
serial_output.php
<?php
// Set service port to 5334 for serproxy
$service_port = 5334;
// Using localhost address
$address = '127.0.0.1';
/* Create a TCP/IP socket. */
$socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
if ($socket === false) {
echo "socket_create() failed: reason: " . socket_strerror(socket_last_error()) . "\n";
}
// Attempting to connect to '$address' on port '$service_port'...";
$result = socket_connect($socket, $address, $service_port);
if ($result === false) {
echo "socket_connect() failed.\nReason: ($result) " . socket_strerror(socket_last_error($socket)) . "\n";
}
// Read 2048 bits of data from socket and convert encoding to ASCII
$out = mb_convert_encoding(socket_read($socket, 2048), 'ASCII');
// Filter out anything that is not "AOK"
if(preg_match("/AOK/", $out)){
echo 1;
} else {
// Else output raw data so we can see what was actaully sent
echo $out;
}
// Closing socket...
socket_close($socket);
?>
main.js
// Set #serial background color to red when receiving a "1"
function setBgColor(){
var serial = $('#serial');
// Set #serial background color to red when receiving a "1"
if($('#serial').html() == "1") {
serial.css('background-color','red');
} else {
// Set #serial background to white if we did not receive a "1"
serial.css('background-color', 'white');
}
}
var intervalId = window.setInterval(function(){
$('#serial').load('serial_output.php');
setBgColor();
}, 100);
arduino_serial.ino
#include <avr/pgmspace.h>
void setup() {
// Initialize serial and wait for port to open:
// Currently I have parity on my serial port set to "EVEN" hence SERIAL_8E1
Serial.begin(9600, SERIAL_8E1);
}
void loop() {
Serial.println("AOK");
}
所以我运行你的代码,并与我的Arduino和加速度计有相同的问题。我找到了三种方法来缓解这个问题。
首先,只是根据您的预期错误检查您的数据。如果数据与您的预期不符,请将其丢弃。如果你每秒获得10倍数据,我想你可以承受损失一些。 [顺便说一下:serproxy在10分钟内就崩溃了,所以它对我的用处有限]。
其次,只是延迟Arduino端的数据。显然,数据丢失是关于Arduinos和串口的“已知问题”。这个人在martinmelchior.be的网站有一些代码来延迟从Ardunio发送的数据流;
`void slowSerialPrint(char text[]) {
for ( int i ; i < strlen(text) ; i ++ ) {
Serial.print(text[i]);
delay(5);
}
} `
向下滚动到“但不是那么快......”找到该片段。
最后,您可以尝试其他许多人正在做的事情并购买便宜的无线路由器并将其用作您自己的inexpensive wi-fi shield。哪,奇怪的是上面链接的网站做了什么!
值得注意的是,路由器在5V时的最大电流消耗为185mA(OpenWrt启动),在18dBm的WiFi平均电流消耗为100mA,没有WiFi 80mA。因此,路由器的平均功耗为0.5W,这非常低。
另外,谢谢你发布的代码,我正在寻找一种方法来完成你正在做的事情,所以我实现了你的代码,碰到了同样的墙,通过减慢javascript中的Arduino输出和丢弃脏数据来解决我的问题,然后扩展到其他选项。
tl;博士:我不认为有一个简单的解决方案。