Search code examples
c#winformseventsrichtextboxmousehover

How to make new event when hover on a text in RichTextBox?


I have a RichTextBox that contains a string, e.g: "Hello", and I want to create a new event when I hover the mouse over the word "Hello", or to simplify that, showing a message box when hover on the word "Hello". So how to achieve that?


Solution

  • First off let's define a method that gets the word nearest to the cursor:

    public static class Helper
    {
        public static string GetWordUnderCursor(RichTextBox control, MouseEventArgs e)
        {
            //check if there's any text entered
            if (string.IsNullOrWhiteSpace(control.Text))
                return null;
            //get index of nearest character
            var index = control.GetCharIndexFromPosition(e.Location);
            //check if mouse is above a word (non-whitespace character)
            if (char.IsWhiteSpace(control.Text[index]))
                return null;
            //find the start index of the word
            var start = index;
            while (start > 0 && !char.IsWhiteSpace(control.Text[start - 1]))
                start--;
            //find the end index of the word
            var end = index;
            while (end < control.Text.Length - 1 && !char.IsWhiteSpace(control.Text[end + 1]))
                end++;
            //get and return the whole word
            return control.Text.Substring(start, end - start + 1);
        }
    }
    

    In order to raise MouseMove event ONLY if the cursor is above RichTextBox and the nearest word is "Hello" you'll need to define your own control deriving from RichTextBox and override the OnMouseMove method, and use it in your form instead RichTextBox:

    public class MyRichTextBox : RichTextBox
    {
        protected override void OnMouseMove(MouseEventArgs e)
        {
            //get the word under the cursor
            var word = Helper.GetWordUnderCursor(this, e);
            if (string.Equals(word, "Hello"))
            {
                //let RichTextBox raise the event
                base.OnMouseMove(e);
            }
        }
    }
    

    However, in my opinion, it's better to let the RichTextBox raise the MouseMove event normally and take action only if conditions are met. In order to do that you only need to register MouseMove handler and check the conditions:

    private void richTextBox1_MouseMove(object sender, MouseEventArgs e)
    {
        var control = sender as RichTextBox;
        //get the word under the cursor
        var word = Helper.GetWordUnderCursor(control, e);
        if (string.Equals(word, "Hello"))
        {
            //do your stuff
        }
    }