Click here to Skip to main content
15,867,985 members
Articles / Desktop Programming / WTL
Article

WTL Wizard-style CPropertySheet Resizable View

Rate me:
Please Sign up or sign in to vote.
4.86/5 (3 votes)
10 Apr 20022 min read 69.8K   2.4K   20   2
How to use WTL's CPropertySheet implementation in wizard-style as a resizable view instead of a modal or modeless dialog
CPropertySheet Wizard Sample Image

CPropertySheet WizardSample Image


Introduction

This article describes how to use WTL's CPropertySheetImpl template as a wizard-style resizable propertysheet view. See the companion article "WTL CPropertySheet as a Resizable View" for background information about how the resizable propertysheet operates.

Property Sheet

The wizard-style property sheet class, CWizView, provides a Wizard 97 style property sheet. Wizard 97 style offers two static controls as separators and supports a bitmap image in the header section. CWizView also supports the older Wizard style, which supplies one static control as a separator between property pages and wizard buttons. The static control IDs are listed below.

// lower static control, visible in WIZARD and WIZARD97 styles
#define ATL_IDC_STATIC1 0x3026
// upper static control, visible in WIZARD97 style only
#define ATL_IDC_STATIC2 0x3027

We use the lower static control's location to set the height of property pages. All of the wizard buttons, both static controls, and the propertysheet tab control are added to the propertysheet dialog resize map as follows. Note the various combinations of MOVE and SIZE, as these are important to proper operation of the sizing mechanism. Also, the tab control must be last as it controls the size and placement of the property pages.

BEGIN_DLGRESIZE_MAP(CWizView)
  DLGRESIZE_CONTROL(ID_WIZBACK, DLSZ_MOVE_X | DLSZ_MOVE_Y)
  DLGRESIZE_CONTROL(ID_WIZNEXT, DLSZ_MOVE_X | DLSZ_MOVE_Y)
  DLGRESIZE_CONTROL(IDCANCEL, DLSZ_MOVE_X | DLSZ_MOVE_Y)
  DLGRESIZE_CONTROL(ID_WIZFINISH, DLSZ_MOVE_X | DLSZ_MOVE_Y)
  DLGRESIZE_CONTROL(ATL_IDC_STATIC1, DLSZ_SIZE_X | DLSZ_MOVE_Y)
  DLGRESIZE_CONTROL(ATL_IDC_STATIC2, DLSZ_SIZE_X)
  DLGRESIZE_CONTROL(ATL_IDC_TAB_CONTROL, DLSZ_SIZE_X | DLSZ_MOVE_Y)
END_DLGRESIZE_MAP()

Tab Control

The tab control receives sizing messages from the propertysheet. The tab control WM_WINDOWPOSCHANGED message handler sizes the property pages by calling a user defined message, WM_RESIZEPAGE. Note the use of SendMessage() here.

LRESULT OnWindowPosChanged(UINT, WPARAM, LPARAM lParam, BOOL&)
{ // get window position structure from lParam
  LPWINDOWPOS lpWP = (LPWINDOWPOS)lParam;

  // SEND resize message to ourselves with the new tab width
  ::SendMessage(m_hWnd, WM_RESIZEPAGE, 0, lpWP->cx);

  return 0; }

The tab control is hidden when the property sheet is in wizard-style. To change tabs, the Next and Back buttons send TCM_SETCURSEL messages to the tab control. Unfortunately, the built-in code also resizes the pages to their original dimensions everytime the tab is changed. Therefore, we process the current selection message to reset them to the desired size. Note the use of PostMessage() here. Resizing must occur after the tab change completes.

LRESULT OnSetCurSel(UINT, WPARAM, LPARAM, BOOL& bHandled)
{ // get the tab control client rect
  RECT rc;
  GetClientRect(&rc);

  // POST resize message to ourselves with the tab width
  ::PostMessage(m_hWnd, WM_RESIZEPAGE, 0, rc.right);

  // further default processing is required to handle the tab
  // change, so set bHandled to false
  bHandled = false;

  return 0; }

This user defined message handler contains the property page resize code.

LRESULT OnResizePage(UINT, WPARAM, LPARAM lParam, BOOL&)
{ // initialize a property sheet variable with the parent's handle
  CWizView sheet;
  sheet.m_hWnd = GetParent();

  // lower bound for page, just above the lower static control
  RECT rc;
  CStatic st = sheet.GetDlgItem(ATL_IDC_STATIC1);
  st.GetWindowRect(&rc);
  sheet.ScreenToClient(&rc);
  int nBottom = rc.top - 15;

  // adjust lower bound if WIZARD97 style
  DWORD dwFlags = sheet.GetPshStyle();
  dwFlags |= PSH_WIZARD97;
  if (dwFlags == sheet.GetPshStyle())
    nBottom -= 60;

  // resize active property page using lParam for width and nBottom for height
  ::SetWindowPos(sheet.GetActivePage(), NULL, 0, 0, lParam, nBottom, SWP_NOMOVE);

  // release the property sheet handle since we don't own it
  sheet.m_hWnd = NULL;

  return 0; }

Terms Of Use

The sample project and property sheet/page classes available with this article are free. Use them however you wish.

THIS SOFTWARE IS DISTRIBUTED AS-IS, WITHOUT WARRANTIES OF ANY KIND.

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


Written By
Founder Choycer
United States United States
Ed has over 40 years experience in computer technology and a bachelor's degree in Business Administration. He's currently a marketing technology consultant. During his career, he's led software development departments and created software still in use in the communications and healthcare industries. Ed is a veteran of the United States Army. He lives in Arizona in the United States.

Find Ed on Linkedin.

This material is copyright 2019 by Ed Gadziemski. Unauthorized use is strictly prohibited. All rights reserved.

Comments and Discussions

 
QuestionFix to "unspecialized class template" Pin
ferrix13-Jan-13 11:05
ferrix13-Jan-13 11:05 
QuestionError C3203 Pin
tmcristi2-May-08 1:36
tmcristi2-May-08 1:36 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.