要点
CircuitPython のコンソール入力を利用する際には 制御コードには気をつけろ! という話です。
背景
KEENCE社製2Dコード リーダー SR-2000 からシリアルポート接続を利用してバーコードデータを読み取るアプリを作成していました。
SR-2000をどこの環境で使えるわけでもないので、ラズピコ+CircuitPythonを利用してダミー環境を用意することにしました。
模擬したかったこと
2Dコード リーダー SR-2000のバーコード読み取り用ライトをONするにはLON
とう文字を送ります。OFFする場合にはLOFF
を送ります。
ここで文字のコマンドの前後にSTXとETXを付ける必要があります。
- STX:バイナリで0x02
- ETX:バイナリで0x03
private const string COMMAND_LON = "\x02LON\x03\r\n"; // <STX>LON<ETX>
private const string COMMAND_LOFF = "\x02LOFF\x03\r\n"; // <STX>LON<ETX>
このSrtingをシリアルポートで送信してON/OFFできていることを確認しまして、ではこれをラズピコで模擬しようとしました。
CircuitPythonのコード
CircuitPythonの動作確認でTeratermによる手入力も行っていた為、制御文字を含む完全なチェックは不要とし、受信文字の中にLON
とLOFF
が含まれていることをもってLEDのON/OFFをして、バーコードリーダーのライトを模擬しました。
def receive_task():
if supervisor.runtime.serial_bytes_available:
msg=input()
print(msg)
if "LON" in msg:
LED_PIN.value = 1
if "LOFF" in msg:
LED_PIN.value = 0
上記のコードで、TeratermからLON
LOFF
を送って、まずは動作OK!
しかし、C#から制御文字を含むデータを送信するとうんともすんともで・・・
「改行コードを送ってないからか??」とも色々悩みましたが、改行コードが原因ではありませんでした。
制御文字送信でCircuitPythonが反応しなくなった理由
何気に送ってしまっていたETXという制御コードですがCtrl+C
を押したのと同じ効果があります。
Hex | 値 | ctrl | 説明 |
---|---|---|---|
0x00 | NUL | Ctrl+@ | NULl(ヌル) |
0x01 | SOH | Ctrl+A | Start Of Heading(ヘッダ開始) |
0x02 | STX | Ctrl+B | Start of TeXt(テキスト開始) |
0x03 | ETX | Ctrl+C | End of TeXt(テキスト終了) |
0x04 | EOT | Ctrl+D | End Of Transmission(転送終了) |
0x05 | ENQ | Ctrl+E | ENQuiry(問合せ) |
CircuitPythonにおいてはコンソール操作で以下のアクションが定義されています。
-
Ctrl+C
スクリプトの停止 -
Ctrl+D
スクリプトの再始動
つまり、送った制御コードでスクリプトが停止してしまい、先に進まなかったというオチでした。(T T)