【问题标题】:How to unselect / unhighlight selected and highlighted text in QScintilla editor widget?如何在 QScintilla 编辑器小部件中取消选择/取消突出显示选定和突出显示的文本?
【发布时间】:2019-06-15 18:35:07
【问题描述】:

我正在尝试编写一个搜索框,其中包含查找/查找上一个/查找下一个以与 QScintilla textEditor 小部件进行交互。因此,我写了一些方法,一个用于突出显示所有匹配的单词,然后选择第一次出现,一个用于取消选择/取消突出显示它们。

首先运行接缝,但如果我用另一个关键字重复搜索,旧关键字和新关键字都会显示。

这是我的代码片段:

//
// search & replace:
// do_search_and_replace() - search for matching word
//
void MainWindow::do_search_and_replace(QString action_str)
{
    int line, index;
    qDebug() <<  "do_search_and_replace()";
    // just to be sure...
    if(action_str.isEmpty())
        action_str == "0";

    int action_nr = action_str.toInt();    // convert argument to int, so we can switch() on it...
    text = ui->lineEdit_find->text();
    docText = ui->textEdit->text();
    qDebug() <<  "action_nr: " << action_nr;

    //
    // first part: Mark all occurances of search term
    //
    if (!( text.isEmpty() ))
    {
        qDebug() << text;
        ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICSETSTYLE, 0, QsciScintilla::INDIC_FULLBOX);
        ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICSETFORE,0, QColor(Qt::darkBlue));


        int end = docText.lastIndexOf(text);
        int cur = -1;

        if(end != -1)
        {
            ui->textEdit->getCursorPosition(&line, &index);
            qDebug() << "line: " << line << " index: " << index;
            while(cur != end)
            {
                cur = docText.indexOf(text,cur+1);
                ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICATORFILLRANGE,cur,
                    text.length());
            }
        }
    } // END text.isEmpty(), END mark ALL

    //
    // second part: Find firs occurance of search term
    //
    bool use_regular_expression, is_case_sensitive, match_whole_word_only, use_wrap, search_forward;
    use_regular_expression = false;
    is_case_sensitive = ui->checkBox_CaseSensitive->isChecked();
    match_whole_word_only = ui->checkBox_WholeWords->isChecked();
    use_wrap = true;
    search_forward = ui->radioButton_Forward->isChecked();

    ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICSETSTYLE, 0, QsciScintilla::INDIC_FULLBOX);
    //ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICSETFORE,0, QColor(Qt::darkBlue));

    bool found = ui->textEdit->findFirst(text, use_regular_expression, is_case_sensitive, match_whole_word_only, use_wrap, search_forward);
    qDebug() <<  "START: found = " << found;
    while(found)
    {
        ui->textEdit->getCursorPosition(&line, &index);

        qDebug() << "line: " << line << " index: " << index;
        qDebug() << text;

        // pattern: found = findFirst(pattern, use_regular_expression, is_case_sensitive, match_whole_word_only, use_wrap, search_forward)
        //found = ui->textEdit->findFirst(text, use_regular_expression, is_case_sensitive, match_whole_word_only, use_wrap, search_forward);

        if(found)
        {
            ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICATORFILLRANGE, line, text.length());
            int start = ui->textEdit->positionFromLineIndex(line, index);
            int end = ui->textEdit->positionFromLineIndex(line, index + text.length());
            qDebug() << "line: " << line << " start: " << start << " end: " << end;

//            found = ui->textEdit->findNext();
//            ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICATORFILLRANGE, line, text.length());

        }

        found = false;
    }
}


//
// unselect selected stuff
//
void MainWindow::reset_searchResult()
{
    int line, index;
    qDebug() <<  "in: reset_searchResult()";

    //QString text = ui->lineEdit_find->text();
    text.clear();
    docText.clear();

    //
    // first part: Mark all occurances of search term
    //
    if (( text.isEmpty() ))
    {
        qDebug() << text;
        ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICSETSTYLE, 0, QsciScintilla::INDIC_PLAIN);
        ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICSETFORE,0, QColor(Qt::white));

        //docText = text;
        docText = ui->lineEdit_find->text();
        int end = docText.lastIndexOf(text);
        int cur = -1;

        if(end != -1)
        {
            ui->textEdit->getCursorPosition(&line, &index);
            qDebug() << "line: " << line << " index: " << index;
            while(cur != end)
            {
                cur = docText.indexOf(text,cur+1);
                ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICATORALLONFOR,cur, text.length());
                ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICATORCLEARRANGE,cur, text.length());
            }
        }
    } // END text.isEmpty(), END mark ALL

    //
    // second part: Find firs occurance of search term
    //
    bool use_regular_expression, is_case_sensitive, match_whole_word_only, use_wrap, search_forward;
    use_regular_expression = false;
    is_case_sensitive = ui->checkBox_CaseSensitive->isChecked();
    match_whole_word_only = ui->checkBox_WholeWords->isChecked();
    use_wrap = true;
    search_forward = ui->radioButton_Forward->isChecked();

    ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICSETSTYLE, 0, QsciScintilla::INDIC_PLAIN);
    //ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICSETFORE,0, QColor(Qt::darkBlue));

    bool found = ui->textEdit->findFirst(text, use_regular_expression, is_case_sensitive, match_whole_word_only, use_wrap, search_forward);
    qDebug() <<  "START: found = " << found;
    while(found)
    {
        ui->textEdit->getCursorPosition(&line, &index);

        if(found)
        {
            ui->textEdit->SendScintilla(QsciScintillaBase::SCI_INDICATORCLEARRANGE, line, text.length());
            int start = ui->textEdit->positionFromLineIndex(line, index);
            int end = ui->textEdit->positionFromLineIndex(line, index + text.length());
            qDebug() << "line: " << line << " start: " << start << " end: " << end;

        }

        found = false;
    }
}

我很确定这不是有史以来最好的代码,但我能负担得起... ;)

也许适合 QScintilla 的人可以纠正我的尝试,或者为我提供一个可以在不保留旧结果的情况下多次调用的有效搜索和突出显示示例?

提前谢谢各位!

【问题讨论】:

  • 您会在进行新搜索之前清除旧标记吗?
  • 是的 - 这就是我在第二种方法中尝试做的!你对如何正确清除旧标记有什么建议吗,@tungIt?

标签: c++ qt5 qscintilla


【解决方案1】:

也许它比你想象的要容易,假设你为你的 ui->textEdit 使用了QsciScintilla 实例:

#define MY_MARKER_ID 0

void MainWindow::clearMarkers()
{
    int lastLine = ui->textEdit->lines() - 1;
    ui->textEdit->clearIndicatorRange( 0, 0, lastLine, ui->textEdit->text( lastLine ).length() - 1, MY_MARKER_ID );
}

【讨论】:

  • @tungIt:确实! Hughe 谢谢你,你又在 QScintilla 上救了我。我稍微记得,在试图找到任何对我有进一步帮助的文档时,我偶然发现了 Jaco Lusser 的 Scintilla 文档,据说标记 id 应该高于 7,因为 0 到 7 已经被保留。是一个提示,但我不知道如何使用它... ;)
  • @MichaelBergmann:不客气。如果你想和QScintilla一起去,让我们看一个使用它的项目QGIS
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-09-27
  • 2023-03-22
  • 2017-07-18
  • 2015-03-07
相关资源
最近更新 更多