Cómo escribir un editor de texto simple en Pyqt5

Cómo escribir un editor de texto simple en Pyqt5
Este artículo cubrirá una guía sobre la creación de un editor de texto simple en Python3 y Pyqt5. QT5 es un conjunto de bibliotecas multiplataforma escritas en C ++, utilizadas principalmente para crear aplicaciones gráficas ricas. Pyqt5 proporciona enlaces de Python para la última versión de QT5. Todas las muestras de código en este artículo se prueban con Python 3.8.2 y pyqt5 versión 5.14.1 en Ubuntu 20.04.

Instalación de PYQT5 en Linux

Para instalar pyqt5 en la última versión de Ubuntu, ejecute el comando a continuación:

$ sudo apt install python3-pyqt5

Si está utilizando cualquier otra distribución de Linux, busque el término "PYQT5" en el Administrador de paquetes e instálelo desde allí. Alternativamente, puede instalar PYQT5 desde PIP Package Manager usando el comando a continuación:

$ Pip Instale Pyqt5

Tenga en cuenta que en algunas distribuciones, es posible que deba usar el comando PIP3 para instalar correctamente PYQT5.

Código completo

Estoy publicando un código completo de antemano para que pueda comprender mejor el contexto para los fragmentos de código individuales explicados más adelante en el artículo. Si está familiarizado con Python y Pyqt5, puede consultar el código a continuación y omitir la explicación.

#!/usr/bin/env python3
Sys de importación
de pyqt5.Qtwidgets import QWidget, Qapplication, QvboxLayout, QhboxLayout
de pyqt5.QtWidgets import QTextedit, Qlabel, Qshortcut, Qfiledialog, QMessageBox
de pyqt5.Qtgui import qKeySequence
de Pyqt5 import qt
Ventana de clase (QWidget):
def __init __ (self):
súper().__en eso__()
ser.file_path = ninguno
ser.Open_new_file_shortcut = qshortcut (qkeysequence ('ctrl+o'), self)
ser.Open_new_file_shortcut.activado.conectar (yo.Open_new_file)
ser.save_current_file_shortcut = qshortcut (qkeysequence ('ctrl+s'), self)
ser.save_current_file_shortcut.activado.conectar (yo.save_current_file)
vbox = qvboxLayout ()
text = "archivo sin título"
ser.Title = Qlabel (texto)
ser.título.setwordwrap (verdadero)
ser.título.Setalignment (QT.QT.Alinear al centro)
vbox.addwidget (yo.título)
ser.setLayout (vbox)
ser.scrollable_text_area = qTextEdit ()
vbox.addwidget (yo.scrollable_text_area)
Def Open_new_file (self):
ser.file_path, filter_type = qfileDialog.getopenfileName (self, "Abra nuevo archivo",
"", "Todos los archivos (*)")
Si uno mismo.ruta de archivo:
con abierto (yo.file_path, "r") como f:
file_contents = F.leer()
ser.título.setText (self.ruta de archivo)
ser.scrollable_text_area.setText (file_contents)
demás:
ser.inválido_path_alert_message ()
Def save_current_file (self):
Si no uno mismo.ruta de archivo:
new_file_path, filter_type = qfileDialog.getSaveFileName (self ", guarde este archivo
como ... "," "," Todos los archivos (*) ")
Si new_file_path:
ser.file_path = new_file_path
demás:
ser.inválido_path_alert_message ()
falso retorno
file_contents = self.scrollable_text_area.topLaIntext ()
con abierto (yo.file_path, "w") como f:
F.escribir (file_contents)
ser.título.setText (self.ruta de archivo)
Def Closeevent (Self, Event):
MessageBox = QMessageBox ()
Title = "Aplicación de dejar?"
Mensaje = "Advertencia !!\ n \ nif que renunció sin guardar, cualquier cambio realizado en el archivo
se perderá.Archivo \ n \ nsave antes de dejar?"
Respuesta = MessageBox.Pregunta (Self, Título, Mensaje, MessageBox.SÍ | buzon de mensaje.No |
buzon de mensaje.Cancelar, MessageBox.Cancelar)
Si responda == MessageBox.Sí:
return_value = self.save_current_file ()
Si return_value == falso:
evento.ignorar()
Elif respuesta == MessageBox.No:
evento.aceptar()
demás:
evento.ignorar()
Def invalid_path_alert_message (self):
MessageBox = QMessageBox ()
buzon de mensaje.setwindowtitle ("archivo no válido")
buzon de mensaje.setText ("El nombre o ruta de archivo seleccionado no es válido. Seleccione un
archivo válido.")
buzon de mensaje.exec ()
Si __name__ == '__main__':
APP = QAPPLICATION (SYS.argv)
W = Window ()
w.showmaximized ()
sys.Salir (aplicación.Exec_ ())

Explicación

La primera parte del código solo importa módulos que se utilizarán a lo largo de la muestra:

Sys de importación
de pyqt5.Qtwidgets import QWidget, Qapplication, QvboxLayout, QhboxLayout
de pyqt5.QtWidgets import QTextedit, Qlabel, Qshortcut, Qfiledialog, QMessageBox
de pyqt5.Qtgui import qKeySequence
de Pyqt5 import qt

En la siguiente parte, se crea una nueva clase llamada "Window" que hereda de la clase "Qwidget". La clase QWidget proporciona componentes gráficos de uso común en QT. Al usar "Super", puede asegurarse de que se devuelva el objeto QT principal.

Ventana de clase (QWidget):
def __init __ (self):
súper().__en eso__()

Algunas variables se definen en la siguiente parte. La ruta del archivo está configurada en "Ninguno" de forma predeterminada y accesos directos para abrir un archivo que usa y guardar un archivo que usa se definen usando la clase QSHORTCUT. Estos atajos se conectan a sus respectivos métodos que se llaman cada vez que un usuario presiona las combinaciones de teclas definidas.

ser.file_path = ninguno
ser.Open_new_file_shortcut = qshortcut (qkeysequence ('ctrl+o'), self)
ser.Open_new_file_shortcut.activado.conectar (yo.Open_new_file)
ser.save_current_file_shortcut = qshortcut (qkeysequence ('ctrl+s'), self)
ser.save_current_file_shortcut.activado.conectar (yo.save_current_file)

Usando la clase QVBoxLayout, se crea un nuevo diseño al que se agregarán widgets infantiles. Se establece una etiqueta alineada en el centro para el nombre de archivo predeterminado usando la clase Qlabel.

vbox = qvboxLayout ()
text = "archivo sin título"
ser.Title = Qlabel (texto)
ser.título.setwordwrap (verdadero)
ser.título.Setalignment (QT.QT.Alinear al centro)
vbox.addwidget (yo.título)
ser.setLayout (vbox)

A continuación, se agrega un área de texto al diseño utilizando un objeto QTextEdit. El widget QTextedit le dará un área editable y desplazable para trabajar con. Este widget admite copiar, pegar, cortar, deshacer, rehacer, rehacer, seleccionar todo, etc. atajos de teclado. También puede usar un menú contextual de clic derecho dentro del área de texto.

ser.scrollable_text_area = qTextEdit ()
vbox.addwidget (yo.scrollable_text_area)

El método "Open_new_fie" se llama cuando un usuario completa el atajo de teclado. QFILEDIALOG Class presenta un cuadro de diálogo de selección de archivos al usuario. La ruta del archivo se determina después de que un usuario selecciona un archivo del selector. Si la ruta del archivo es válida, el contenido de texto se lee desde el archivo y se establece en QTextedit Widget. Esto hace que el texto sea visible para el usuario, cambia el título al nuevo nombre de archivo y completa el proceso de abrir un nuevo archivo. Si por alguna razón, la ruta del archivo no se puede determinar, se muestra un cuadro de alerta de "archivo no válido" al usuario.

Def Open_new_file (self):
ser.file_path, filter_type = qfileDialog.getopenfileName (self, "abrir nuevo archivo", "",
"Todos los archivos (*)")
Si uno mismo.ruta de archivo:
con abierto (yo.file_path, "r") como f:
file_contents = F.leer()
ser.título.setText (self.ruta de archivo)
ser.scrollable_text_area.setText (file_contents)
demás:
ser.inválido_path_alert_message ()

El método "save_current_file" se llama cada vez que un usuario completa el atajo de teclado. En lugar de recuperar una nueva ruta de archivo, QFileDialog ahora le pide al usuario que proporcione una ruta. Si la ruta del archivo es válida, el contenido visible en QTextedit Widget se escribe en la ruta del archivo completo, de lo contrario se muestra un cuadro de alerta de "archivo no válido". El título del archivo que se está editando actualmente también se cambia a la nueva ubicación proporcionada por el usuario.

Def save_current_file (self):
Si no uno mismo.ruta de archivo:
new_file_path, filter_type = qfileDialog.getSaveFileName (self ", guarde este archivo
como ... "," "," Todos los archivos (*) ")
Si new_file_path:
ser.file_path = new_file_path
demás:
ser.inválido_path_alert_message ()
falso retorno
file_contents = self.scrollable_text_area.topLaIntext ()
con abierto (yo.file_path, "w") como f:
F.escribir (file_contents)
ser.título.setText (self.ruta de archivo)

El método "CloseEvent" es parte de la API de manejo de eventos PYQT5. Este método se llama cada vez que un usuario intenta cerrar una ventana con el botón cruzado o presionando la combinación de teclas. Al disparar el evento cerrado, al usuario se le muestra un cuadro de diálogo con tres opciones: "Sí", "No" y "Cancelar". El botón "Sí" guarda el archivo y cierra la aplicación, mientras que el botón "no" cierra el archivo sin guardar el contenido. El botón "Cancelar" cierra el cuadro de diálogo y lleva al usuario a la aplicación.

Def Closeevent (Self, Event):
MessageBox = QMessageBox ()
Title = "Aplicación de dejar?"
Mensaje = "Advertencia !!\ n \ nif que renunció sin guardar, cualquier cambio realizado en el archivo
estar perdido.Archivo \ n \ nsave antes de dejar?"
Respuesta = MessageBox.Pregunta (Self, Título, Mensaje, MessageBox.SÍ | buzon de mensaje.No |
buzon de mensaje.Cancelar, MessageBox.Cancelar)
Si responda == MessageBox.Sí:
return_value = self.save_current_file ()
Si return_value == falso:
evento.ignorar()
Elif respuesta == MessageBox.No:
evento.aceptar()
demás:
evento.ignorar()

El cuadro de alerta de "archivo inválido" no tiene campanas y silbatos. Simplemente transmite el mensaje de que la ruta del archivo no se puede determinar.

Def invalid_path_alert_message (self):
MessageBox = QMessageBox ()
buzon de mensaje.setwindowtitle ("archivo no válido")
buzon de mensaje.setText ("El nombre o ruta de archivo seleccionado no es válido. Seleccione un archivo válido.")
buzon de mensaje.exec ()

Por último, el ciclo de aplicación principal para el manejo de eventos y el dibujo de widgets se inicia utilizando el ".Método Exec_ () ".

Si __name__ == '__main__':
APP = QAPPLICATION (SYS.argv)
W = Window ()
w.showmaximized ()
sys.Salir (aplicación.Exec_ ())

Ejecutando la aplicación

Simplemente guarde el código completo en un archivo de texto, configure la extensión del archivo en ".py ”, marque el ejecutable de archivo y ejecutarlo para iniciar la aplicación. Por ejemplo, si el nombre del archivo es "simple_text_editor.py ”, debes ejecutar siguiendo dos comandos:

$ chmod +x simple_text_editor.py
ps ./Simple_Text_Editor.py

Cosas que puede hacer para mejorar el código

El código explicado anteriormente funciona bien para un editor de texto básico. Sin embargo, puede no ser útil para fines prácticos, ya que carece de muchas características comúnmente vistas en buenos editores de texto. Puede mejorar el código agregando nuevas características como números de línea, resaltado de línea, resaltado de sintaxis, múltiples pestañas, guardado de sesión, barra de herramientas, menús desplegables, detección de cambios de búfer, etc.

Conclusión

Este artículo se centra principalmente en proporcionar un terreno inicial para crear aplicaciones PYQT. Si encuentra errores en el código o desea sugerir algo, los comentarios son bienvenidos.