QSyntaxHighlighter::highlightBlock highlights previous and current block



  • Implementation:

    CustomHighlighter::CustomHighlighter(QTextDocument *parent) : QSyntaxHighlighter(parent) {
    }
     
    void CustomHighlighter::setHighlighterFormat(const QTextCharFormat &format) {
        this->format = format;
    }
     
    void CustomHighlighter::highlightBlock(const QString &text) {
    //    if(text.isEmpty() || currentBlockState() == 1)
    //        return;
        setFormat(0, text.length(), format);
    //    setCurrentBlockState(1);
    }
     
    Logger::Logger(QWidget *parent) : QPlainTextEdit(parent) {
        setMaximumBlockCount(50);
        highlighter = new CustomHighlighter(document());
    }
     
    Logger::~Logger() {
        delete highlighter;
    }
     
    void Logger::setFormat(const QTextCharFormat &format) {
        highlighter->setHighlighterFormat(format);
    }
    

    Next is a timer slot, just for example:

    QTextCharFormat format;
    format.setFontWeight(250);
    int x = random() % 3;
    switch(x) {
    case 0:
        format.setForeground(Qt::red);
        break;
    case 1:
        format.setForeground(Qt::green);
        break;
    case 2:
        format.setForeground(Qt::blue);
        break;
    }
     
    logger->setFormat(format);
    QDateTime date = QDateTime::currentDateTime();
    logger->appendPlainText(date.toString() + "\n");
    

    This works fine. But if new line character is removed both current appended and previous line (block) are highlighted.



  • So I added enum to check block states:

     enum { FORMATTED = 1, LAST = 2 };
    

    Then made changes in highlightBlock:

    void CustomHighlighter::highlightBlock(const QString &text) {
        if(text.isEmpty() || currentBlockState() == LAST)
            return;
        if(currentBlockState() == FORMATTED) {
            setFormat(0, text.length(), previousFormat);
            setCurrentBlockState(LAST);
        } else {
            setFormat(0, text.length(), format);
            previousFormat = format;
            setCurrentBlockState(FORMATTED);
        }
    }
    

    This has one problem. After maximum blocks are appended the top most block "looses" format.
    But anyway it seems that I am overdoing it. And why is formatted text returned to highlightBlock?



  • Okay, this works:

    void CustomHighlighter::highlightBlock(const QString &text) {
        if(text.isEmpty())
            return;
        int start = 0;
        if(currentBlockState() == LAST) {
            BlockFormat block = queue.dequeue();
            QTextCharFormat lastFormat = block.first;
            int length = block.second;
            setFormat(start, length, lastFormat);
        }
        else if(currentBlockState() == FORMATTED) {
            setFormat(start, text.length(), previousFormat);
            setCurrentBlockState(LAST);
            queue.enqueue(BlockFormat(format, text.length()));
        } else {
            setFormat(start, text.length(), format);
            previousFormat = format;
            setCurrentBlockState(FORMATTED);
        }
    }
    

    Where BlockFormat is:

    typedef QPair<QTextCharFormat, int> BlockFormat;
    

    Question is same, am I overdoing it? Is this the simplest solution?


 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.