Создание подсветки синтаксиса в python (PyQt4)


Я искал в интернете информацию о подсветке синтаксиса конкретного файла в текстовом редакторе, и я прочитал о Лексерах и Yacc. я довольно путаю понятия о подсветке синтаксиса.

Я создал простой текстовый редактор,используя PyQt4, и я хочу,чтобы он включал подсветку синтаксиса таких языков программирования, как HTML, CSS, Python, C/C++. Но я не имею ни малейшего представления о том, как начать это реализовывать и с чего начать. Пожалуйста, кто-нибудь, покажите мне на правильное направление и плиз проясняют мои сомнения по подсветке синтаксиса. пожалуйста.

3 2

3 ответа:

Вам нужно разделить текст на лексические лексемы (слова, числа, символы и т. д.), выяснить, что такое каждая из них, и раскрасить ее соответственно. Достаточно легко распознать числа и символы, но знать, является ли слово переменной, функцией, ключевым словом или чем-то еще, означает анализировать текст в соответствии с синтаксическими правилами языка. Вот почему ваш поиск находит ссылки на лексический анализ (Lex) и синтаксический анализ (Yacc). Лексический анализ - это сборка букв и символов в единое целое. слова и другие лексемы, а синтаксический анализ-это то, как эти лексемы идут вместе, чтобы составить синтаксически корректную программу.

Python имеет модуль библиотекиtokenize , который делает именно то, что вам нужно для языка Python. В документации даже говорится, что он полезен для красивой печати и раскрашивания экранных дисплеев. Надеюсь, использование этого даст вам больше представления о том, как все это работает. Затем вы можете либо искать библиотеки Python для синтаксического анализа других языков, либо иметь иди и напиши его сам.

Есть вопрос переполнения стека здесь, который предлагает pyPEG для разбора других языков. У джимоти тоже хорошие представления о пигментах.

Если вы хотите облегчить себе жизнь, используйте QScintilla - она делает все, что вам нужно, и даже больше прямо из коробки.

QScintilla входит в состав бинарных инсталляторов PyQt для Windows (которые можно найтиздесь ), и почти все дистрибутивы Linux будут иметь пакеты QScintilla в своих репозиториях. Кроме того, исходный код QScintilla можно найти здесь.

И вот минимальный пример QScintilla, который показывает, как легко его получить начало:

import sys, os
from PyQt4 import QtGui, Qsci

class Window(Qsci.QsciScintilla):
    def __init__(self):
        Qsci.QsciScintilla.__init__(self)
        self.setLexer(Qsci.QsciLexerPython(self))
        self.setText(open(os.path.abspath(__file__)).read())

if __name__ == '__main__':

    app = QtGui.QApplication(sys.argv)
    window = Window()
    window.setGeometry(500, 300, 500, 500)
    window.show()
    sys.exit(app.exec_())

Я знаю, что на этот вопрос был дан ответ, но, как и я, многие другие новые пользователи пришли сюда и будут знать, что варианты, упомянутые в приведенных выше ответах, являются небольшим уровнем продвижения. Я публикую этот ответ для дальнейшего ознакомления для некоторых других новичков

Создание синтаксического маркера с помощью python и Qt-хороший выбор. Поскольку python-очень мощный язык, а QT-отличный фреймворк для разработки графических приложений.
Синтаксический маркер-это самое простое регулярное выражение с объектом QTextEdit. Вы просто анализируете выражения регулярных выражений, а затем выбираете определенный QTextFormat для этого вида регулярных выражений и применяете этот текстовый формат к этому блоку. Вот пример кода простейшего синтаксического маркера, реализованного в Python с помощью Qt4 функция выделения, реализованная в классе syntaxHighlighter, управляемом из QSyntaxHighlighter

    def highlightBlock(self, text):
    for pattern, format in self.highlightingRules:
        expression = QtCore.QRegExp(pattern)
        index = expression.indexIn(text)
        while index >= 0:
            length = expression.matchedLength()
            self.setFormat(index, length, format)
            index = expression.indexIn(text, index + length)

    self.setCurrentBlockState(0)

    startIndex = 0
    if self.previousBlockState() != 1:
        startIndex = self.commentStartExpression.indexIn(text)

    while startIndex >= 0:
        endIndex = self.commentEndExpression.indexIn(text, startIndex)

        if endIndex == -1:
            self.setCurrentBlockState(1)
            commentLength = len(text) - startIndex
        else:
            commentLength = endIndex - startIndex + self.commentEndExpression.matchedLength()

        self.setFormat(startIndex, commentLength,
                self.multiLineCommentFormat)
        startIndex = self.commentStartExpression.indexIn(text,
                startIndex + commentLength);

Используя этот пример, я создал синтаксический маркер сборки в Python с Qt4 для микроконтроллера 8051. Для дальнейшей справки и хорошей отправной точки вы можете ссылаться на этот код.