python實現串口通信小程序(GUI界面)

python實現串口通信小程序(GUI界面)

使用python實現串口通信須要使用python的pyserial庫來實現,這個庫在安裝python的時候沒有自動進行安裝,須要本身進行安裝。python

一、安裝pyserial庫:

打開命令行窗口,在命令行中輸入:pip install pyserial 命令進行安裝。git

二、程序使用python自帶的GUI庫tkinter來實現GUI窗口,使用pyserial來實現串口通信模塊。

效果圖以下:
主界面
github

串口號選擇框會自動加載全部可用的串口號,而且顯示在選擇框中。在使用時選擇合適的串口號,而後點擊打開串口按鍵便可。小程序

注:本程序使用的是虛擬串口app

三、效果演示:

1)發送數據演示:

編輯器

注:在發送數據顯示框中顯示字符,則代表發送成功函數

動態效果演示:

2)接收數據演示:

工具

注:接收數據顯示框顯示字符,則代表發送數據成功oop

動態演示效果:

4:工程介紹:

本工程由兩個文件組成:分別是GUI文件和串口文件。
文件代碼以下:
GUI文件:

url

'''
@ author: summer
@ tools: pycharm 
@ content: 實現串口通信主類
@ date: 2020.2.12
'''
import tkinter
from tkinter import ttk
from 串口通信.SerialClass import SerialAchieve   # 導入串口通信類

class MainSerial:
    def __init__(self):
        # 定義串口變量
        self.port = None
        self.band = None
        self.check = None
        self.data = None
        self.stop = None
        self.myserial = None

        # 初始化窗體
        self.mainwin = tkinter.Tk()
        self.mainwin.title("串口調試工具")
        self.mainwin.geometry("600x400")

        # 標籤
        self.label1 = tkinter.Label(self.mainwin,text = "串口號:",font = ("宋體",15))
        self.label1.place(x = 5,y = 5)
        self.label2 = tkinter.Label(self.mainwin, text="波特率:", font=("宋體", 15))
        self.label2.place(x=5, y=45)
        self.label3 = tkinter.Label(self.mainwin, text="校驗位:", font=("宋體", 15))
        self.label3.place(x=5, y=85)
        self.label4 = tkinter.Label(self.mainwin, text="數據位:", font=("宋體", 15))
        self.label4.place(x=5, y=125)
        self.label5 = tkinter.Label(self.mainwin,text = "中止位:",font = ("宋體",15))
        self.label5.place(x = 5,y = 165)

        # 文本顯示,清除發送數據
        self.label6 = tkinter.Label(self.mainwin, text="發送數據:", font=("宋體", 15))
        self.label6.place(x=230, y=5)

        self.label7 = tkinter.Label(self.mainwin, text="接收數據:", font=("宋體", 15))
        self.label7.place(x=230, y=200)

        # 串口號
        self.com1value = tkinter.StringVar()  # 窗體中自帶的文本,建立一個值
        self.combobox_port = ttk.Combobox(self.mainwin, textvariable=self.com1value,
                                          width = 10,font = ("宋體",13))
        # 輸入選定內容
        self.combobox_port["value"] = [""]  # 這裏先選定

        self.combobox_port.place(x = 105,y = 5)  # 顯示

        # 波特率
        self.bandvalue = tkinter.StringVar()  # 窗體中自帶的文本,建立一個值
        self.combobox_band = ttk.Combobox(self.mainwin, textvariable=self.bandvalue, width=10, font=("宋體", 13))
        # 輸入選定內容
        self.combobox_band["value"] = ["4800","9600","14400","19200","38400","57600","115200"]  # 這裏先選定
        self.combobox_band.current(6)  # 默認選中第0個
        self.combobox_band.place(x=105, y=45)  # 顯示

        # 校驗位
        self.checkvalue = tkinter.StringVar()  # 窗體中自帶的文本,建立一個值
        self.combobox_check = ttk.Combobox(self.mainwin, textvariable=self.checkvalue, width=10, font=("宋體", 13))
        # 輸入選定內容
        self.combobox_check["value"] = ["無校驗位"]  # 這裏先選定
        self.combobox_check.current(0)  # 默認選中第0個
        self.combobox_check.place(x=105, y=85)  # 顯示

        # 數據位
        self.datavalue = tkinter.StringVar()  # 窗體中自帶的文本,建立一個值
        self.combobox_data = ttk.Combobox(self.mainwin, textvariable=self.datavalue, width=10, font=("宋體", 13) )
        # 輸入選定內容
        self.combobox_data["value"] = ["8", "9", "0"]  # 這裏先選定
        self.combobox_data.current(0)  # 默認選中第0個
        self.combobox_data.place(x=105, y=125)  # 顯示

        # 中止位
        self.stopvalue = tkinter.StringVar()  # 窗體中自帶的文本,建立一個值
        self.combobox_stop = ttk.Combobox(self.mainwin, textvariable=self.stopvalue, width=10, font=("宋體", 13))
        # 輸入選定內容
        self.combobox_stop["value"] = ["1", "0"]  # 這裏先選定
        self.combobox_stop.current(0)  # 默認選中第0個
        self.combobox_stop.place(x=105, y=165)  # 顯示

        # 按鍵顯示,打開串口
        self.button_OK = tkinter.Button(self.mainwin, text="打開串口",
                                        command=self.button_OK_click, font = ("宋體",13),
                                        width = 10,height = 1)
        self.button_OK.place(x = 5,y = 210)  # 顯示控件
        # 關閉串口
        self.button_Cancel = tkinter.Button(self.mainwin, text="關閉串口",  # 顯示文本
                                 command=self.button_Cancel_click, font = ("宋體",13),
                                 width=10, height=1)
        self.button_Cancel.place(x = 120,y = 210)  # 顯示控件

        # 清除發送數據
        self.button_Cancel = tkinter.Button(self.mainwin, text="清除發送數據",  # 顯示文本
                                            command=self.button_clcSend_click, font=("宋體", 13),
                                            width=13, height=1)
        self.button_Cancel.place(x=400, y=2)  # 顯示控件

        # 清除接收數據
        self.button_Cancel = tkinter.Button(self.mainwin, text="清除接收數據",  # 顯示文本
                                            command=self.button_clcRece_click, font=("宋體", 13),
                                            width=13, height=1)
        self.button_Cancel.place(x=400, y=197)  # 顯示控件

        # 發送按鍵
        self.button_Send = tkinter.Button(self.mainwin, text="發送",  # 顯示文本
                                            command=self.button_Send_click, font=("宋體", 13),
                                            width=6, height=1)
        self.button_Send.place(x=5, y=255)  # 顯示控件

        # 接收按鍵
        self.button_Send = tkinter.Button(self.mainwin, text="接收",  # 顯示文本
                                          command=self.button_Rece_click, font=("宋體", 13),
                                          width=6, height=1)
        self.button_Send.place(x=5, y=310)  # 顯示控件

        # 顯示框
        # 實現記事本的功能組件
        self.SendDataView = tkinter.Text(self.mainwin,width = 40,height = 9,
                                         font = ("宋體",13))  # text其實是一個文本編輯器
        self.SendDataView.place(x = 230,y = 35)  # 顯示

        self.ReceDataView = tkinter.Text(self.mainwin, width=40, height=9,
                                         font=("宋體", 13))  # text其實是一個文本編輯器
        self.ReceDataView.place(x=230, y=230)  # 顯示

        # 發送的內容
        test_str = tkinter.StringVar(value="Hello")
        self.entrySend = tkinter.Entry(self.mainwin, width=13,textvariable = test_str,font = ("宋體",15))
        self.entrySend.place(x = 80,y = 260)  # 顯示

        # 獲取文件路徑
        test_str = tkinter.StringVar(value="Hello")
        self.entrySend = tkinter.Entry(self.mainwin, width=13, textvariable=test_str, font=("宋體", 15))
        self.entrySend.place(x=80, y=260)  # 顯示

        # 獲取界面的參數
        self.band = self.combobox_band.get()
        self.check = self.combobox_check.get()
        self.data = self.combobox_data.get()
        self.stop = self.combobox_stop.get()
        print("波特率:"+self.band)
        self.myserial = SerialAchieve(int(self.band),self.check,self.data,self.stop)

        # 處理串口值
        self.port_list = self.myserial.get_port()
        port_str_list = []  # 用來存儲切割好的串口號
        for i in range(len(self.port_list)):
            # 將串口號切割出來
            lines = str(self.port_list[i])
            str_list = lines.split(" ")
            port_str_list.append(str_list[0])
        self.combobox_port["value"] = port_str_list
        self.combobox_port.current(0)  # 默認選中第0個

    def show(self):
        self.mainwin.mainloop()

    def button_OK_click(self):
        '''
        @ 串口打開函數
        :return: 
        '''
        if self.port == None or self.port.isOpen() == False:
            self.myserial.open_port(self.combobox_port.get())
            print("打開串口成功")
        else:
            pass

    def button_Cancel_click(self):
        self.myserial.delete_port()
        print("關閉串口成功")

    def button_clcSend_click(self):
        self.SendDataView.delete("1.0","end")

    def button_clcRece_click(self):
        self.ReceDataView.delete("1.0", "end")

    def button_Send_click(self):
        try:
            if self.myserial.port.isOpen() == True:
                print("開始發送數據")
                send_str1 = self.entrySend.get()
                self.myserial.Write_data(send_str1)
                self.SendDataView.insert(tkinter.INSERT, send_str1+" ")
                print("發送數據成功")
            else:
                print("串口沒有打開")
        except:
            print("發送失敗")
    def button_Rece_click(self):
        try:
            readstr = self.myserial.Read_data()
            self.ReceDataView.insert(tkinter.INSERT, readstr + " ")
        except:
            print("讀取失敗")
if __name__ == '__main__':
    my_ser1 = MainSerial()
    my_ser1.show()

串口文件:

'''
@ author: summer
@ tools: pycharm 
@ content: 串口通信實現類
@ date: 2020.2.12
'''
import serial
import serial.tools.list_ports

class SerialAchieve:
    def __init__(self,band=115200,check="無校驗位",data=8,stop=1):
        self.port = None
        # 獲取可用串口
        self.port_list = list(serial.tools.list_ports.comports())
        assert (len(self.port_list) != 0),"無可用串口"

        self.bandRate = band
        self.checkbit = check
        self.databit = data
        self.stopbit = stop

        # 讀寫的數據
        self.read_data = None
        self.write_data = None

        pass
    def show_port(self):
        for i in range(0,len(self.port_list)):
            print(self.port_list[i])

    def show_other(self):
        print("波特率:"+self.bandRate)
        print("校驗位:" + self.checkbit)
        print("數據位:" + self.databit)
        print("中止位:" + self.stopbit)
    # 返回串口
    def get_port(self):
        return self.port_list
    # 打開串口
    def open_port(self,port):
        self.port = serial.Serial(port, self.bandRate,timeout = None)

    def delete_port(self):
        if self.port != None:
            self.port.close()
            print("關閉串口完成")
        else:
            pass

    def Read_data(self):   # self.port.read(self.port.in_waiting) 表示所有接收串口中的數據
        self.read_data = self.port.read(self.port.in_waiting)   # 讀取數據
        return self.read_data.decode("utf-8")

    def Write_data(self,data):
        if self.port.isOpen() == False:
            print("串口打開錯誤")
        else:
            self.port.write(data.encode("utf-8"))  # 返回的是寫入的字節數

if __name__ == '__main__':
    myser = SerialAchieve()
    myser.open_port("COM7")
    myser.delete_port()
    myser.show_port()

因爲程序寫的比較匆忙,因此還有不少須要完善的地方,若是你對這個工程感興趣能夠一塊兒來完善它。
本工程GitHub地址

相關文章
相關標籤/搜索