我正在創建一個程序,使用串行端口使用某些設備。我有文檔詳細說明如何通過端口發送命令。它工作得很好,但我應該得到關於設備狀態的一些信息。我嘗試了一切,但我對這些類型的開發沒有信心。可能是我錯過了一些東西。SerialPort發送命令並獲得響應
從文檔:
總共有21級的命令,20個命令是開口的,1個命令是讀取狀態
打開命令:
地址命令固定值(0x55的)鎖號碼
地址0XF2 0X55 0X01
地址小號0XF2 0x55的0X02
地址0XF2 0x55的0X03
......
以上命令執行
成功返回: 地址+ 0×59 + 0×59
故障恢復:地址+ 0X5E + 0X5E
/// <summary>
/// Send open lokcer door command
/// </summary>
/// <param name="boardAddress">0 means open left slave cabinet,1 means open right slave cabinet</param>
/// <param name="command"></param>
/// <returns></returns>
public byte[] OpenBox(byte boardAddress, byte command)
{
var openCommand = new byte[5];
openCommand[0] = (byte)(255 - boardAddress);
openCommand[0] = 0xF2;
openCommand[1] = 0x55;
openCommand[2] = command;
openCommand[3] = 0X00;
openCommand[4] = 0X00;
try
{
if (!serialPort.IsOpen)
{
//serialPort.WriteBufferSize = 5;
serialPort.Open();
}
serialPort.DiscardInBuffer();
serialPort.Write(openCommand, 0, 3);
return openCommand;
}
catch (ArgumentException ex)
{
throw new InvalidOperationException("Locker cell can not be opened.", ex);
}
}
它工作得很好,但最後2個字節沒有返回。他們總是0X00。另外我使用SerialPortDataReceived,但我總是得到0。
public void SerialPortDataReceived(object sender, SerialDataReceivedEventArgs e)
{
DBException.WriteLog("");
DBException.WriteLog("Serial port data received");
var sp = (SerialPort)sender;
DBException.WriteLog("Read existing = " + sp.ReadExisting());
try
{
DBException.WriteLog("Length = " + sp.BytesToRead);
if (serialPort.BytesToRead == 4)
{
var readBuffer = new byte[4];
sp.Read(readBuffer, 0, serialPort.BytesToRead);
DBException.WriteLog("Read serial port :" + readBuffer.ByteArrayToString());
// RaiseLockerStatusEvent(readBuffer.ByteArrayToString());
}
}
catch (Exception ex)
{
DBException.WriteLog(ex);
}
}
問題1如何獲得成功或失敗的回報?我認爲他們應該在最後2個字節。
問題2 如何獲取所有狀態?目前我什麼也沒有得到。
文檔:
讀鎖定狀態的命令:地址+數據1 +數據2 +數據3 地址:0XF10X55 數據1數據2數據3 0000 lock20 ... lock17 lock16 ... lock9 lock8 ...鎖1 的前4位是固定的數字0000 樣本: 0000 0000 0000 0001 0000 0001表示鎖定1,鎖定9打開,其他關閉 注意:對於某些類型的電子鎖定,「1」表示關閉,「0」表示打開。
我的片段
/// <summary>
/// Send check machine(cabinet) status command
/// </summary>
/// <param name="address">0 means check left cabinet, 1 means check right cabinet </param>
/// <returns></returns>
public byte[] SendCheckLockControlStatueCommand(byte address)
{
lock (this)
{
var checkCommand = new byte[6];
checkCommand[0] = Convert.ToByte(255 - address);
checkCommand[1] = 0xF1;
checkCommand[2] = 0x55;
checkCommand[3] = 0x00;
checkCommand[4] = 0x00;
checkCommand[5] = 0x00;
try
{
if (!serialPort.IsOpen)
{
// serialPort.WriteBufferSize = 5;
serialPort.Open();
}
//Send inquiry command
serialPort.DiscardInBuffer();
// serialPort.DiscardOutBuffer();
serialPort.Write(checkCommand, 0, 6);
return checkCommand;
}
catch (ArgumentException ex)
{
throw new InvalidOperationException("Locker cell can not be opened.", ex);
}
}
}
非常感謝你。我想我正在進入它。但實際上我更喜歡同步溝通。我想我應該在SendingCommand方法中等待一段時間,然後再讀取數據。你能解釋一下嗎?我會很感激。 –
我想我已經找到了從串口讀取數據的正確答案。它會使用AutoResetEvent所有細節都在這裏。 http://stackoverflow.com/questions/11782053/serialport-wait-for-response再次感謝。 –
如果你想同步交流,你可能想在Write之後調用Read,直到你有了答案。請注意,如果沒有答案,這可能會永遠阻止您的應用程序。超時使用WaitHandle確實是最好的解決方案。 –