サイトデザインを新しくしました!

【PySerial】COMポートを自動的に探して、Pythonでシリアル通信を行う

はじめに

Pythonを使って、UART等のシリアル通信を行う場合、PySerialを使うと簡単に実現できます。その際、PySerialを使う前の初期設定で、COMポートを指定する必要があります。

https://debugging-code.com/wp-content/uploads/2019/02/アイコン.png
もびるど

COMポートはデバイス毎に番号が変わってしまいます。
デバイスが変わる度に、デバイスマネージャからCOMポートを調べるのは面倒です。

そこで今回は、COMポートを自動的に取得するサンプルプログラムをご紹介します。ついでに、PySerialを使ったシリアル通信のサンプルプログラムも掲載しています。サンプルプログラムはご自由にお使いください。

私の環境は以下の通りです。

  • Windows 10 64bit
  • Anaconda3 5.3.0
  • Python 3.7.0

サンプルコード

https://debugging-code.com/wp-content/uploads/2019/02/アイコン.png
もびるど

まずはMain関数を説明します。

Python
import serial
if __name__ == '__main__':
    # Search COM Ports
    use_port = search_com_port()

    # Init Serial Port Setting
    ser = serial.Serial(use_port)
    ser.baundrate = 9600
    ser.timeout = 5 #sec

    w_data = b'RV\n'
    r_size = 7
    r_data = uart_write_read(w_data, r_size)
    print('Reserved: {}'.format(r_data))

ヘッダに”serial”をimportすることで、PySerialを使用することができます。
search_com_port()は私が作成した関数です。
後ほど説明しますが、この関数は有効なCOMポートを返します。

serial.Serial関数は、serというインスタンスを作成しています。
この関数の引数には、有効なCOMポートを指定する必要があります。
その他、baundrateや、通信のタイムアウト時間を設定しています。

w_dataは、送信するデータです。
r_sizeは、受信するデータのサイズです。
uart_write_read関数は、私の作成した関数です。この中でデータの送受信を行います。

https://debugging-code.com/wp-content/uploads/2019/02/アイコン.png
もびるど

次に、search_com_port関数を説明します。

Python
import serial.tools.list_ports
def search_com_port():
    coms = serial.tools.list_ports.comports()
    comlist = []
    for com in coms:
        comlist.append(com.device)
    print('Connected COM ports: ' + str(comlist))
    use_port = comlist[0]
    print('Use COM port: ' + use_port)

    return use_port

serial.tools.list_ports.comports関数は、PCに接続されているCOMポートをすべて返します。それをcomlistというリストにいったん格納(append)します。

私の使用しているPCでは、使いたいCOMポートがcomlist[0]に格納されていたため、それを一旦、use_portに格納します。関数の最後で、use_portを戻り値として返しています。

https://debugging-code.com/wp-content/uploads/2019/02/アイコン.png
もびるど

次に、uart_write_read関数を説明します。

Python
def uart_write_read(w_data, r_size):
    # Write
    ser.write(w_data)
    print('Send: '+ str(w_data))

    # Read
    r_data = ser.read_until(size=r_size) #size分Read
    print('Recv: ' + str(r_data))

    return r_data

ser.write関数は、データを送信する関数です。これはPySerialで用意している関数です。

ser.read_until関数は、データを受信する関数です。これはPyserialで用意している関数です。この関数の引数に、受信サイズを指定すると、指定サイズが受信されるまで待ってくれます。

最後に受信データを返しています。

https://debugging-code.com/wp-content/uploads/2019/02/アイコン.png
もびるど

最後に今までのソースコードをまとめて記載すると、以下のようになります。

Python
import serial
import serial.tools.list_ports
'''シリアル通信でデータの送受信を行う'''
def uart_write_read(w_data, r_size):
    # Write
    ser.write(w_data)
    print('Send: '+ str(w_data))

    # Read
    r_data = ser.read_until(size=r_size) #size分Read
    print('Recv: ' + str(r_data))

    return r_data

'''有効なCOMポートを自動的に探して返す'''
def search_com_port():
    coms = serial.tools.list_ports.comports()
    comlist = []
    for com in coms:
        comlist.append(com.device)
    print('Connected COM ports: ' + str(comlist))
    use_port = comlist[0]
    print('Use COM port: ' + use_port)

    return use_port

'''Main関数'''
if __name__ == '__main__':
    # Search COM Ports
    use_port = search_com_port()

    # Init Serial Port Setting
    ser = serial.Serial(use_port)
    ser.baundrate = 9600
    ser.timeout = 5 #sec

    w_data = b'RV\n'
    r_size = 7
    r_data = uart_write_read(w_data, r_size)
    print('Reserved: {}'.format(r_data))

以上です。

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です