Neste artigo, veremos como podemos criar um bloco de notas usando o PyQt5.

O Bloco de notas é um editor de texto genérico que permite criar, abrir, editar e ler arquivos de texto simples.

PyQt5 é um kit de ferramentas de interface de usuário de plataforma cruzada, um conjunto de ligações Python para Qt v5. Pode-se desenvolver um aplicativo de desktop interativo com muita facilidade devido às ferramentas e à simplicidade oferecidas por esta biblioteca.

Use este comando para instalar o PyQt5:

pip install PyQt5

Etapas de implementação da GUI:
1. Crie um layout vertical
2. Crie um objeto QPlainTextEdit e adicione-o ao layout
3. Crie um contêiner, ou seja, um objeto QWidget
4. Defina esse layout vertical para o contêiner
5. Crie uma barra de status para mostrar dicas de status
6 . Criar barra de menu de arquivo e adicionar ações de arquivo abaixo é a aparência da barra de menu de arquivo



7. Crie uma barra de menu de edição e adicione várias ações de edição a ela. Abaixo está a aparência da barra de menu de edição

8. Crie duas barras de ferramentas para ações de arquivo e edição, abaixo está a aparência das barras de ferramentas

Etapas de implementação de back-end:
1. Crie uma variável de caminho e defina-a como Nenhum
2. Adicione ações a cada uma das ações do menu de arquivo, estas são as mesmas ações da barra de ferramentas, pois ambas compartilham as mesmas ações
3. Crie um método crítico que mostre o valor passado em o pop-up, é usado para mostrar se ocorre algum erro durante o salvamento ou abertura do arquivo
4. Método de criação de título de atualização que altera o título da janela de acordo com o nome do arquivo
5. Dentro da ação abrir arquivo, crie um bloco try-except que tenta abrir o arquivo e então atualizar o título e o caminho
6. Dentro da ação salvar se o caminho for nenhum chame o método salvar como senão salve o arquivo no caminho
7. Dentro do método salvar como salve o arquivo no caminho selecionado pelo usuário
8. Dentro da ação de impressão, imprima o arquivo usando o objeto QPrintDialog
9. Dentro da ação da barra do toogle de edição, defina o modo de quebra de linha do editor de acordo com o estado selecionado
10. Da mesma forma, defina a ação para desfazer, refazer, cortar, copiar, colar e selecionar tudo usando as funções internas do objeto QPlainTextEdit

Abaixo está a implementação

from PyQt5.QtGui import * 
from PyQt5.QtWidgets import * 
from PyQt5.QtCore import * 
from PyQt5.QtPrintSupport import * 
import os 
import sys 
class MainWindow(QMainWindow): 
  
    
    def __init__(self, *args, **kwargs): 
        super(MainWindow, self).__init__(*args, **kwargs) 
        self.setGeometry(100, 100, 600, 400) 
        layout = QVBoxLayout() 
        self.editor = QPlainTextEdit() 
        fixedfont = QFontDatabase.systemFont(QFontDatabase.FixedFont) 
        fixedfont.setPointSize(12) 
        self.editor.setFont(fixedfont) 
      self.path = None
        layout.addWidget(self.editor) 
        container = QWidget() 
        container.setLayout(layout) 
        self.setCentralWidget(container) 
        self.status = QStatusBar() 
        self.setStatusBar(self.status) 
        file_toolbar = QToolBar("File") 
        self.addToolBar(file_toolbar) 
        file_menu = self.menuBar().addMenu("&File") 
      open_file_action = QAction("Open file", self) 
        open_file_action.setStatusTip("Open file") 
        open_file_action.triggered.connect(self.file_open) 
        file_menu.addAction(open_file_action) 
        file_toolbar.addAction(open_file_action) 
        save_file_action = QAction("Save", self) 
        save_file_action.setStatusTip("Save current page") 
        save_file_action.triggered.connect(self.file_save) 
        file_menu.addAction(save_file_action) 
        file_toolbar.addAction(save_file_action) 
        saveas_file_action = QAction("Save As", self) 
        saveas_file_action.setStatusTip("Save current page to specified file") 
        saveas_file_action.triggered.connect(self.file_saveas) 
        file_menu.addAction(saveas_file_action) 
        file_toolbar.addAction(saveas_file_action) 
        print_action = QAction("Print", self) 
        print_action.setStatusTip("Print current page") 
        print_action.triggered.connect(self.file_print) 
        file_menu.addAction(print_action) 
        file_toolbar.addAction(print_action) 
        edit_toolbar = QToolBar("Edit") 
        self.addToolBar(edit_toolbar) 
        edit_menu = self.menuBar().addMenu("&Edit") 
        undo_action = QAction("Undo", self) 
      undo_action.setStatusTip("Undo last change") 
        undo_action.triggered.connect(self.editor.undo) 
        edit_toolbar.addAction(undo_action) 
        edit_menu.addAction(undo_action) 
        redo_action = QAction("Redo", self) 
        redo_action.setStatusTip("Redo last change") 
        redo_action.triggered.connect(self.editor.redo) 
        edit_toolbar.addAction(redo_action) 
        edit_menu.addAction(redo_action) 
        cut_action = QAction("Cut", self) 
        cut_action.setStatusTip("Cut selected text") 
        cut_action.triggered.connect(self.editor.cut) 
        edit_toolbar.addAction(cut_action) 
        edit_menu.addAction(cut_action) 
        copy_action = QAction("Copy", self) 
        copy_action.setStatusTip("Copy selected text") 
        copy_action.triggered.connect(self.editor.copy) 
        edit_toolbar.addAction(copy_action) 
        edit_menu.addAction(copy_action) 
        paste_action = QAction("Paste", self) 
        paste_action.setStatusTip("Paste from clipboard") 
        paste_action.triggered.connect(self.editor.paste) 
        edit_toolbar.addAction(paste_action) 
        edit_menu.addAction(paste_action) 
        select_action = QAction("Select all", self) 
        select_action.setStatusTip("Select all text") 
        select_action.triggered.connect(self.editor.selectAll) 
        edit_toolbar.addAction(select_action) 
        edit_menu.addAction(select_action) 
  
        wrap_action = QAction("Wrap text to window", self) 
        wrap_action.setStatusTip("Check to wrap text to window") 
        wrap_action.setCheckable(True) 
        wrap_action.setChecked(True) 
        wrap_action.triggered.connect(self.edit_toggle_wrap) 
        edit_menu.addAction(wrap_action) 
        self.update_title() 
        self.show() 
  
    
    
    def dialog_critical(self, s): 
        dlg = QMessageBox(self) 
        dlg.setText(s) 
        dlg.setIcon(QMessageBox.Critical) 
        dlg.show() 
  
    
    def file_open(self): 
        path, _ = QFileDialog.getOpenFileName(self, "Open file", "",  
                             "Text documents (*.txt);All files (*.*)") 
        if path: 
              try: 
                with open(path, 'rU') as f: 
                              text = f.read() 
      except Exception as e: 
              self.dialog_critical(str(e)) 
              else: 
                      self.path = path 
              self.editor.setPlainText(text) 
              self.update_title() 
  
    
    def file_save(self): 
        if self.path is None: 
      return self.file_saveas() 
        self._save_to_path(self.path) 
  
    
    def file_saveas(self): 
        path, _ = QFileDialog.getSaveFileName(self, "Save file", "",  
                             "Text documents (*.txt);All files (*.*)") 
        if not path: 
                return
        self._save_to_path(path) 
  
    
    def _save_to_path(self, path): 
        text = self.editor.toPlainText() 
        try: 
      with open(path, 'w') as f: 
              f.write(text) 
        except Exception as e: 
      self.dialog_critical(str(e)) 
        else: 
              self.path = path 
              self.update_title() 
  
    
    def file_print(self): 
        dlg = QPrintDialog() 
        if dlg.exec_(): 
      self.editor.print_(dlg.printer()) 
  
    
    def update_title(self): 
      self.setWindowTitle("%s - PyQt5 Notepad" %(os.path.basename(self.path)  
                                                  if self.path else "Untitled")) 
  
    
    def edit_toggle_wrap(self): 
        self.editor.setLineWrapMode(1 if self.editor.lineWrapMode() == 0 else 0 ) 
  
  
if __name__ == '__main__': 
  
    
    app = QApplication(sys.argv) 
  
    
    app.setApplicationName("PyQt5-Note") 
  
    
    window = MainWindow() 
  
    
    app.exec_() 

Resultado :