Primo Chalice
Primo Chalice

Reputation: 189

How do I synchronize scroll in two RichTextBoxes maintaining a ratio?

I found out a code online here, in StackOverflow itself: How can I sync the scrolling of two multiline textboxes?

It works fine, but I want a proportional scrolling. This means that, if I have two RichTextBoxes, RichTextBox1 having 10 lines and RichTextBox2 having 100 lines, so when I scroll in RichTextBox1 it will jump 10 lines in RichTextBox2 for every 1 line of scrolling and if I scroll in RichTextBox2 it will scroll 1 line in RichTextBox1 for every 10 lines in RichTextBox2.

I think this is possible.

Upvotes: 1

Views: 217

Answers (1)

TaW
TaW

Reputation: 54453

There certainly are better ways to do it (without meddling with the selection) but this seems to work:

class myRTB : RichTextBox
{
    public myRTB()
    {
        this.Multiline = true;
        this.ScrollBars = RichTextBoxScrollBars.Vertical;
    }

    public myRTB Buddy { get; set; }

    private static bool scrolling;   // In case buddy tries to scroll us
    protected override void WndProc(ref Message m)
    {
        base.WndProc(ref m);
        // Trap WM_VSCROLL message and pass to buddy
        if (m.Msg == 0x115 && !scrolling && Buddy != null && Buddy.IsHandleCreated)
        {
            scrolling = true;
            synchTopLineRel(Buddy);
            scrolling = false;
        }
    }

    void synchTopLineRel(RichTextBox rtb)
    {
        int i0 = GetCharIndexFromPosition(Point.Empty);
        int i1 = GetLineFromCharIndex(i0);
        int i2 = (int)(i1 * Buddy.Lines.Length / Lines.Length);
        // the rest scrolls to line # i2..:
        int bss = Buddy.SelectionStart;
        int bsl = Buddy.SelectionLength;
        Buddy.SelectionStart = Buddy.GetFirstCharIndexFromLine(i2);
        Buddy.ScrollToCaret();
        Buddy.SelectionStart = bss;
        Buddy.SelectionLength = bsl;
    }
}

Note that is has no error checks and will do a very simple calculation. It will not work well with:

  • RTBs with different Fonts
  • RTBs with different sizes

Especially if you need to code the ScelectionChanged event you will prefer to replace the scrolling with a proper call to SetScrollPos. Possible example

Upvotes: 1

Related Questions