In this article I’ll show you how to disable RichTextBox’s Smooth Scrolling - aka make RichTextBox scroll line by line. I know this is a problem for many developers, it was a problem for me too, so that’s why I decided to post this code snippet.

Removing Smooth Scrolling

Well, there’s no easy way to fix it and since there’s no other option, you’ll have to make a custom RichTextBox and override the WndProc() function.

Basically you need to handle all the vertical scrolling: this means check if user scrolls (WM_MOUSEWHEEL), if so, use SendMessage() to send WM_VSCROLL to the control.

Before starting, you’ll need to include this namespace:

1
using System.Runtime.InteropServices;

The following line sends a message to the RichTextBox which will tell it to scroll up or down:

1
2
3
4
5
SendMessage(this.Handle, WM_VSCROLL, (IntPtr)wParam, IntPtr.Zero);

//wParam (3rd parameter) can be 0 or 1
// 0 to scroll up
// 1 to scroll down 

Now, you must create your own control, which inherits from RichTextBox and that handles the WM_MOUSEWHEEL messages separately - it will send a WM_VSCOLL each time we scroll.

It should look like this one (thanks to Mark for improvements):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
class editedRichTextBox : RichTextBox
{
    [DllImport("user32.dll", CharSet = CharSet.Auto)]
    private static extern int SendMessage(IntPtr hWnd, int wMsg, IntPtr wParam, IntPtr lParam);

    //this message is sent to the control when we scroll using the mouse
    private const int WM_MOUSEWHEEL = 0x20A;

    //and this one issues the control to perform scrolling
    private const int WM_VSCROLL = 0x115;

    protected override void WndProc(ref Message m)
    {
        if (m.Msg == WM_MOUSEWHEEL)
        {
            int scrollLines = SystemInformation.MouseWheelScrollLines;
            for (int i = 0; i < scrollLines; i++)
            {
                if ((int)m.WParam > 0) // when wParam is greater than 0
                    SendMessage(this.Handle, WM_VSCROLL, (IntPtr)0, IntPtr.Zero); // scroll up 
                else  
                    SendMessage(this.Handle, WM_VSCROLL, (IntPtr)1, IntPtr.Zero); // else scroll down
            }
            return;
        }
        base.WndProc(ref m);
    }
}