Click here to Skip to main content
65,938 articles
CodeProject is changing. Read more.
Articles
(untagged)

Scrollbars, using the WS_HSCROLL and WS_VSCROLL styles

0.00/5 (No votes)
13 Jun 2002 1  
How to use a CWnd's default scrollbars and to setup the thumb size correctly

Overview

All CWnd derived classes have access to system supplied scrollbars by using the window styles WS_HSCROLL and WS_VSCROLL, but these are no ordinary scrollbars! For starters, you cannot get a CScrollBar* pointer to them, so they cannot be subclassed.

Included above is a project that makes use of these standard scrollBar objects got by using these window styles. Its a view which creates a window derived from CWnd which has the necessary functions to enable/disable the scrollbars as required. As you re-size the view, this re-sizes the window which decides whether the scrollbars should be shown.

Windows acts oddly when enabling/disabling the scrollbars. When you decide you need to show one or both of the scrollbars by using the CWnd::ShowScrollBar method, a WM_SIZE message is automatically generated and called immediately telling your window the new size of the client area (which does not include the area taken by the scrollbars if visible), so if you choose to show/hide the scrollbars in the OnSize handler, the function needs to avoid problems due to recursion.

User interface

Sample Image - Scroll.jpg

Scrollbars are a standard part of the windows user interface. I was trying to use one of these in a control and needed the scrollbar thumb to show how much of the total area was displayed. The standard MSDN documentation on how to do this was sadly lacking (or I was just dumb). I spent many hours in frustration which ended in a rant in the Soapbox. From a sympathetic reply there, I was given the clue on how to do what I had been attempting.

Scrollbars can be setup using a SCROLLINFO object to set the range and thumb size. Its just that the flags you can set and the variables are very badly documented. So here is an overview of what I have learnt. The SCROLLINFO structure looks like this:

typedef struct tagSCROLLINFO { 
    UINT cbSize; 
    UINT fMask; 
    int  nMin; 
    int  nMax; 
    UINT nPage; 
    int  nPos; 
    int  nTrackPos; 
    }   SCROLLINFO, *LPSCROLLINFO; 

A point by point description of these are:

  • cbSize - Needs to be set to the size of the structure si.cbSize = sizeof(SCROLLINFO)
  • fMask - A bit field variable which lets windows know which other parts of the structure contain valid numbers.
  • nMin - Used with the SIF_RANGE flag, it sets the scroll bars minimum value.
  • nMax - Used with the SIF_RANGE flag, it sets the scroll bars maximum value.
  • nPage - Used with the SIF_PAGE flag, it sets how much of the total scroll area is visible - this sets the size of the thumb in the scroll bar.
  • nPos - Used with the SIF_POS flag, it sets the current scroll position.
  • nTrackPos - Used with the SIF_TRACKPOS flag and the GetScrollPos call, to get the current thumb position while the user is dragging it.
  • My problem was I was trying to get the thumb to be proportional, which is good programming procedure for all new windows applications. This allows more information to be supplied to the user in how much data is not being shown. As another CP user replied to me: I hate programmers who don't do this - they should be taken out and shot!, or words to that effect.

    Updates

  • 14-6-2002 Made the example flicker free
  • License

    This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

    A list of licenses authors might use can be found here