2017-07-31 29 views
1

私はPython3経由で双方向通信を確立しようとしています。私のUSBポートの1つに接続されたレーザー距離計があり、私はそれにコマンドを送受信したいと思います。私は送ることができるコマンドと返すものを持っているので、この部分はすでにそこにある。Python3双方向シリアル通信:データ読み込み

私が必要とするのは、リアルタイムで行うのに便利な方法です。

import serial, time 

SERIALPORT = "/dev/ttyUSB0" 
BAUDRATE = 115200 

ser = serial.Serial(SERIALPORT, BAUDRATE) 
ser.bytesize = serial.EIGHTBITS #number of bits per bytes 
ser.parity = serial.PARITY_NONE #set parity check: no parity 
ser.stopbits = serial.STOPBITS_ONE #number of stop bits 
ser.timeout = None   #block read 
ser.xonxoff = False  #disable software flow control 
ser.rtscts = False  #disable hardware (RTS/CTS) flow control 
ser.dsrdtr = False  #disable hardware (DSR/DTR) flow control 
ser.writeTimeout = 0  #timeout for write 

print ("Starting Up Serial Monitor") 

try: 
    ser.open() 
except Exception as e: 
    print ("Exception: Opening serial port: " + str(e)) 

if ser.isOpen(): 
    try: 
     ser.flushInput() 
     ser.flushOutput() 
     ser.write("1\r\n".encode('ascii')) 
     print("write data: 1") 
     time.sleep(0.5) 
     numberOfLine = 0 
     while True: 
      response = ser.readline().decode('ascii') 
      print("read data: " + response) 
      numberOfLine = numberOfLine + 1 
      if (numberOfLine >= 5): 
       break 
     ser.close() 
    except Exception as e: 
     print ("Error communicating...: " + str(e)) 
else: 
    print ("Cannot open serial port.") 

は、したがって、上記のコードでは、私は、レーザーファインダーの「getDistance()」機能をトリガし、mm単位で距離を返すべき「1」を送信しています。これまでのところ私は、次のコードを持っています。私はパテでこれを試して、それは動作し、4桁まで距離を返します。しかし、上記のPythonスクリプトを起動すると、出力は次のようになります。

Starting Up Serial Monitor 
Exception: Opening serial port: Port is already open. 
write data: 1 
read data: 

これは永遠に続きます。読み取りデータはありません。

ここで私は間違っていますか?

+0

は() '')( 'ser.open前に' ser.closeを追加してください。 –

+0

残念ながら、それは何も変化しませんでした。 –

答えて

1

コードのほんの一層単純なバージョンが明らかに問題を解決しました。必要に応じて

import serial 
import time 

ser = serial.Serial('/dev/ttyUSB0', 115200, timeout = 1) # ttyACM1 for Arduino board 

readOut = 0 #chars waiting from laser range finder 

print ("Starting up") 
connected = False 
commandToSend = 1 # get the distance in mm 

while True: 
    print ("Writing: ", commandToSend) 
    ser.write(str(commandToSend).encode()) 
    time.sleep(1) 
    while True: 
     try: 
      print ("Attempt to Read") 
      readOut = ser.readline().decode('ascii') 
      time.sleep(1) 
      print ("Reading: ", readOut) 
      break 
     except: 
      pass 
    print ("Restart") 
    ser.flush() #flush the buffer 

出力、:

Writing: 1 
Attempt to Read 
Reading: 20 
Restart 
Writing: 1 
Attempt to Read 
Reading: 22 
Restart 
Writing: 1 
Attempt to Read 
Reading: 24 
Restart 
Writing: 1 
Attempt to Read 
Reading: 22 
Restart 
Writing: 1 
Attempt to Read 
Reading: 26 
Restart 
Writing: 1 
Attempt to Read 
Reading: 35 
Restart 
Writing: 1 
Attempt to Read 
Reading: 36 
0

あなたのser.timeout = Noneが問題を引き起こしているようです。 whileループの最初のサイクルはうまくいっているようですが、2回目にser.readline()を試すとプログラムがハングアップします。

これを解決する方法はいくつかあります。私の好ましい方法は、Noneタイムアウトを、おそらく1秒に指定することです。これにより、デバイスがエンドライン文字を送信しない場合でも、ser.readline()は値を返すことができます。

ser.readline()ser.read(ser.in_waiting)またはser.read(ser.inWaiting())のように変更して、バッファで使用できるすべての文字を返すこともできます。

+0

私は両方の方法を試してみました。その結果、読み取りデータラインが5回印刷されましたが、値なしで再び表示されました。この時点では、私はレーザーのコマンドの効果を見ることができないので、書き込み機能が正常に機能するかどうかも疑問に思っています。デバイスは、コマンドを受信して​​いなくても、応答するだけではありません。 –

関連する問題