pyside2代码编辑器-QSyntaxHighlighter高亮字体

from PySide2.QtCore import QProcess, QRegExp
from PySide2.QtGui import QColor, QTextCharFormat, QFont, QSyntaxHighlighter, QIcon, QKeySequence
from PySide2.QtWidgets import QApplication, QMainWindow, QTextEdit, QAction, QFileDialog

tabKeySpaceCnt = 4


class PythonHighlighter(QSyntaxHighlighter):
    def __init__(self, parent=None):
        super().__init__(parent)

        keyword_format = QTextCharFormat()
        keyword_format.setForeground(QColor(200, 120, 50))
        keyword_format.setFontWeight(QFont.Bold)

        keywords = [
            'and', 'as', 'assert', 'break', 'class', 'continue', 'def',
            'del', 'elif', 'else', 'except', 'False', 'finally', 'for',
            'from', 'global', 'if', 'import', 'in', 'is', 'lambda',
            'None', 'nonlocal', 'not', 'or', 'pass', 'raise', 'return',
            'True', 'try', 'while', 'with', 'yield', 'print'
        ]

        self.highlighting_rules = [
            (fr'\b{kw}\b', keyword_format) for kw in keywords
        ]

        string_format = QTextCharFormat()
        string_format.setForeground(QColor(120, 120, 255))
        self.highlighting_rules.append((r'".*"', string_format))
        self.highlighting_rules.append((r"'.*'", string_format))
        self.highlighting_rules.append((r"{.*}", string_format))

        comment_format = QTextCharFormat()
        comment_format.setForeground(QColor(120, 120, 120))
        self.highlighting_rules.append((r'#.*', comment_format))

    def highlightBlock(self, text):
        for pattern, format_ in self.highlighting_rules:
            regex = QRegExp(pattern)
            i = regex.indexIn(text)
            while i >= 0:
                length = regex.matchedLength()
                self.setFormat(i, length, format_)
                i = regex.indexIn(text, i + length)


class MainWindow(QMainWindow):
    def __init__(self):
        super().__init__()

        self.editor = QTextEdit()
        self.highlighter = PythonHighlighter(self.editor.document())
        self.setCentralWidget(self.editor)

        # 创建菜单栏
        menu_bar = self.menuBar()
        file_menu = menu_bar.addMenu('File')

        # 添加打开文件的动作
        open_file_action = QAction(QIcon('open.png'), 'Open', self)
        open_file_action.setShortcut('Ctrl+O')
        open_file_action.triggered.connect(self.open_file)
        file_menu.addAction(open_file_action)

        # 添加保存文件的动作
        save_file_action = QAction(QIcon('save.png'), 'Save', self)
        save_file_action.setShortcut('Ctrl+S')
        save_file_action.triggered.connect(self.save_file)
        file_menu.addAction(save_file_action)

        # 添加运行文件的动作
        run_file_action = QAction(QIcon('run.png'), 'Run', self)
        run_file_action.setShortcut('F5')
        run_file_action.triggered.connect(self.run_code)
        file_menu.addAction(run_file_action)

        # self.editor.textChanged.connect(self.add_indent)
        self.editor.document().blockCountChanged.connect(self.add_indent)

        # 设置tab键的缩进为4个空格
        tabKeyWidth = self.editor.fontMetrics().width(" " * tabKeySpaceCnt)
        self.editor.setTabStopDistance(tabKeyWidth)
        # 设置粘贴时不保留格式
        self.editor.setAcceptRichText(False)

        self.process = QProcess(self)
        self.process.readyReadStandardOutput.connect(self.handle_output)
        self.process.readyReadStandardError.connect(self.handle_outerr)

    def add_indent(self, newBlockCount):
        """换行时跟随当前行的缩进"""
        # 获取上一行的内容,和上一行保持一样的行头缩进
        rowIndent = str()
        lineIndex = self.editor.textCursor().blockNumber() - 1
        rowText = self.editor.document().findBlockByLineNumber(lineIndex).text()
        for char in rowText:
            if char == " ":    # 搜索空格
                rowIndent += " "
            elif char == "\t":
                rowIndent += " " * tabKeySpaceCnt
            else:
                break
        self.editor.insertPlainText(rowIndent)

    def run_code(self):
        code = self.editor.toPlainText()
        self.process.start('python', ['-c', code])

    def handle_output(self):
        print("handle_output")
        output = self.process.readAllStandardOutput().data().decode()
        print(output)

    def handle_outerr(self):
        print("handle_outerr")
        outErr = self.process.readAllStandardError().data().decode()
        print(outErr)

    def open_file(self):
        # 打开文件对话框
        file_name, _ = QFileDialog.getOpenFileName(self, 'Open File', '', 'Python Files (*.py)')

        # 读取文件内容并显示在文本编辑框中
        if file_name:
            with open(file_name, 'r', encoding="utf8") as f:
                self.editor.setText(f.read())

    def save_file(self):
        # 打开文件对话框
        file_name, _ = QFileDialog.getSaveFileName(self, 'Save File', '', 'Python Files (*.py)')

        # 将文本编辑框中的内容保存到文件中
        if file_name:
            with open(file_name, 'w') as f:
                f.write(self.editor.toPlainText())


if __name__ == '__main__':
    app = QApplication([])
    window = MainWindow()
    window.show()
    app.exec_()

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值