Untitled
unknown
plain_text
2 years ago
7.0 kB
5
Indexable
import threading
import time
import tkinter as tk
import tkinter.ttk as ttk
import serial
import serial.tools.list_ports
from tkinter.scrolledtext import ScrolledText
class SerialChat:
def __init__(self, master):
self.master = master
self.puerto = "COM1" # Puerto vacío
self.puerto_conectado = True # Verificar si ya se conectó
self.master.title(f"Serial Chat")
self.master.geometry("+50+50")
self.master.resizable(0, 0)
self.conexion = tk.StringVar()
self.conexion.set("Conectar")
# ---------------------- SERIAL PORT --------------------------
ports = serial.tools.list_ports.comports()
for port in ports: # Puertos disponibles
print(port)
self.puertos = []
for port in ports:
p1, p2 = str(port).split('-')
p1 = p1.replace(' ','')
self.puertos.append(p1)
# ------------------------ FRAMES -----------------------------
frm1 = tk.LabelFrame(self.master, text="Conexion")
frm2 = tk.Frame(self.master)
frm3 = tk.LabelFrame(self.master, text="Enviar mensaje")
frm1.pack(padx=5, pady=5, anchor=tk.W)
frm2.pack(padx=5, pady=5, fill='y', expand=True)
frm3.pack(padx=5, pady=5)
# ------------------------ FRAME 1 ----------------------------
self.lblCOM = tk.Label(frm1, text="Puerto COM:")
self.cboPort = ttk.Combobox(frm1, values=self.puertos)
self.lblSpace = tk.Label(frm1, text="")
self.btnConnect = ttk.Button(frm1, textvariable=self.conexion,command=self.seleccionar_puertos, width=16)
self.lblCOM.grid(row=0, column=0, padx=5, pady=5)
self.cboPort.grid(row=0, column=1, padx=5, pady=5)
self.lblSpace.grid(row=0,column=2, padx=30, pady=5)
self.btnConnect.grid(row=0, column=3, padx=5, pady=5)
# ------------------------ FRAME 2 ---------------------------
self.txtChat = ScrolledText(frm2, height=25, width=50, wrap=tk.WORD, state='disable')
self.txtChat.grid(row=0, column=0, columnspan=3, padx=5, pady=5)
# ------------------------ FRAME 3 --------------------------
self.lblText = tk.Label(frm3, text="Texto:")
self.inText = tk.Entry(frm3, width=45, state='disable')
self.btnSend = ttk.Button(frm3, text="Enviar", width=12, state='disable',command=self.enviar_mensaje)
self.lblText.grid(row=0, column=0, padx=5, pady=5)
self.inText.grid(row=0, column=1, padx=5, pady=5)
self.btnSend.grid(row=0, column=2, padx=5, pady=5)
# --------------------------- StatusBar -----------------------
self.statusBar = tk.Label(self.master, bd=1, relief=tk.SUNKEN, anchor=tk.W)
self.statusBar.pack(side=tk.BOTTOM, fill=tk.X)
# ------------- Control del boton "X" de la ventana -----------
self.master.protocol("WM_DELETE_WINDOW", self.cerrar_puertos)
# ------------- Recibe el mensaje del emisor -----------
self.master.after(1000, self.recibir_mensaje)
def cerrar_puertos(self):
try:
self.serial.close()
except:
pass
self.master.destroy()
def seleccionar_puertos(self):
self.puerto = self.cboPort.get() # Uso get para recibir el valor del combobox
if self.puerto_conectado: # Si ya se conectó, no se puede conectar de nuevo
self.puerto_conectado = False
self.cboPort.config(state='disabled')
self.conexion.set("Desconectar")
self.inText.config(state='normal')
self.btnSend.config(state='normal')
else: # Si no está conectado, se mantiene igual
self.conexion.set("Conectar")
self.puerto_conectado = True
self.puerto = "COM1"
self.ser.close()
self.inText.config(state='disabled')
self.btnSend.config(state='disabled')
self.cboPort.config(state='normal')
self.statusBar.config(text="")
return
try:
self.statusBar.config(text="Conectado al " + self.puerto + " a 9600")
self.ser = serial.Serial(port=self.puerto,
baudrate=9600,
bytesize=8,
timeout=2,
stopbits=serial.STOPBITS_ONE)
except:
self.conexion.set("Conectar")
self.puerto_conectado = True
self.inText.config(state='disabled')
self.btnSend.config(state='disabled')
self.cboPort.config(state='normal')
self.statusBar.config(text="Error al conectarse a " + self.puerto)
self.puerto = "COM1" # Puerto vacío
def enviar_mensaje(self):
texto = self.inText.get() # Texto del mensaje enviado
texto = self.puerto + ": " + texto # COM2: AEA
texto_encode = texto.encode("utf-8") # "COM2:AEA"
self.ser.write(texto_encode)
self.txtChat.config(state='normal')
self.txtChat.insert(tk.INSERT, str(texto) + "\n", 'verde')
th1sec = threading.Thread(target=self.tiempo, args=(1, 0,), daemon=True) # Threading
th1sec.start()
self.txtChat.tag_config('verde', foreground='green') # Color de letra
self.inText.delete(0, 'end')
self.txtChat.config(state='disabled')
return
def recibir_mensaje(self):
if self.puerto in self.puertos:
if self.ser.in_waiting > 0:
mensaje = self.ser.readline()
mensaje = mensaje.decode('utf-8')
self.txtChat.config(state='normal')
th2sec = threading.Thread(target=self.tiempo, args=(1, 1,), daemon=True) # Threading
th2sec.start()
self.txtChat.insert(tk.INSERT, str(mensaje) + "\n", 'red') # Color de letra
self.txtChat.tag_config('red', foreground='red')
self.txtChat.config(state='disabled')
self.master.after(1000, self.recibir_mensaje)
def tiempo(self, sec, n):
time.sleep(sec)
self.txtChat.config(state='normal')
self.txtChat.tag_remove('red', '1.0', 'end') # Color de letra
self.txtChat.tag_remove('verde', '1.0', 'end') # Color de letra
self.txtChat.config(state='disabled')
root = tk.Tk()
SerialChat(root)
root.mainloop()Editor is loading...