Highlight Matched Text

Topics: Developer Forum, Project Management Forum, User Forum
Jun 26, 2012 at 3:57 PM

I am sure this has been answered before though I couldn't find a discussion on it.  Is it possible to set up a search and highlight event when a word is selected?  For example, in Notepad++ you can highlight a word and the word will then be highlighted throughout the document automatically.  Is something like this possible?

Thanks!

Aug 12, 2012 at 9:38 AM
Edited Aug 18, 2012 at 2:35 AM

I was looking into this as well, as I think this feature in Notepad++ is really useful.

While I could not find an equivalent way in Scitilla.net control, there is a Find/replace function that allows highlight matches.

I tested the following code :

        private void scintilla1_SelectionChanged(object sender, EventArgs e)
        {
            scintilla1.FindReplace.ClearAllHighlights();
            if (scintilla1.Selection.Start != scintilla1.Selection.End)
            {
                string ss = scintilla1.Selection.Text;
                scintilla1.FindReplace.Flags = SearchFlags.WordStart;
                IList<Range> ranges = scintilla1.FindReplace.FindAll(ss);
                scintilla1.FindReplace.HighlightAll(ranges);
            }
        }
It behaves like the "find/replace higlight matches" each time a selection is made. However, each time a selection that has Selection.Start = 0, the highlight(s) cannot be cleared thereafter. Thanks.
Aug 18, 2012 at 2:30 AM
Edited Aug 18, 2012 at 2:34 AM
I found that by using styles, matched text can be higlighted as well as in the following snippet.
/* Somewhere initialisation */
...
            scintilla1.Styles[1].BackColor = Color.LightGreen;
            scintilla1.Styles[1].ForeColor = Color.White;
            scintilla1.Styles[1].Font = new Font(scintilla1.Font, FontStyle.Regular);
...

/* Respond to selection change */
private void scintilla1_SelectionChanged(object sender, EventArgs e)
{
            scintilla1.Styles.ClearDocumentStyle();
            if (scintilla1.Selection.Start != scintilla1.Selection.End)
            {
                string ss = scintilla1.Selection.Text;
                scintilla1.FindReplace.Flags = SearchFlags.Empty;
                IList<Range> ranges = scintilla1.FindReplace.FindAll(ss);
                foreach (var r in ranges)
                {
                    r.SetStyle(1);
                }
            }
}

Coordinator
Aug 21, 2012 at 2:38 AM
Edited Aug 22, 2012 at 1:32 AM

This question gets asked SO much that I thought it was time to answer it once and for all. Looking at the Notepad++ source code (FindReplaceDlg.cpp) it's clear that they use modern indicators to highlight all instances of a given word. The equivalent in ScintillaNET would be something like this:

scintilla.Indicators[0].Style = IndicatorStyle.RoundBox;
scintilla.Indicators[0].Color = Color.Green;

foreach (Range r in scintilla.FindReplace.FindAll("this"))
    r.SetIndicator(0);

Yup, it's that easy.

Using indicators instead of styles has the advantage that they won't get lost when the document is restyled. You can also search for text with a given indicator so you could use that to jump from one instance of the word to another. And oh, so much more!

I'll leave it to the reader to figure out how to clear indicators.

 

Jacob

P.S. - Downloading and browsing the Notepad++ source code is how I learn these things ;)