Programming Microsoft Windows Ce Net 3Rd [Electronic resources] نسخه متنی

اینجــــا یک کتابخانه دیجیتالی است

با بیش از 100000 منبع الکترونیکی رایگان به زبان فارسی ، عربی و انگلیسی

Programming Microsoft Windows Ce Net 3Rd [Electronic resources] - نسخه متنی

| نمايش فراداده ، افزودن یک نقد و بررسی
افزودن به کتابخانه شخصی
ارسال به دوستان
جستجو در متن کتاب
بیشتر
تنظیمات قلم

فونت

اندازه قلم

+ - پیش فرض

حالت نمایش

روز نیمروز شب
جستجو در لغت نامه
بیشتر
لیست موضوعات
توضیحات
افزودن یادداشت جدید






Dialog Boxes

In my experience, creating a well-designed dialog box is one of the programmer's more difficult tasks. The problem lies in presenting the user with an intuitive interface that allows quick interaction with an application. The task is doubly difficult on a Pocket PC, which has a small screen and a keyboard that keeps popping up over the bottom third of the screen. In this section, I'll explain creating dialog boxes and the assistance that the Pocket PC shell provides. However, it is always good to remember the cardinal rule: keep it simple. The Pocket PC provides a number of functions that help with dialog boxes, but the best programs don't use all these functions at once.

Because the Pocket PC is based on Windows CE, dialog boxes act by default as they do in any Windows system: They are created with the standard Win32 functions such as CreateDialog, they are created by the dialog manager based on dialog box resource templates, and they have dialog box procedures. However, the user interface guidelines for the Pocket PC specify that dialog boxes should be full screen so as not to confuse the user. In addition, property sheets on the Pocket PC have their tabs on the bottom of the window instead of the top. Windows CE doesn't support these characteristics by default; conveniently though, the Pocket PC provides extensions to assist the developer.


Full-Screen Dialog Boxes


To assist programmers in creating full-size dialog boxes, the Pocket PC shell implements a function named SHInitDialog. As the name implies, the function should be called during the handling of the WM_INITDIALOG message. The function is prototyped as

BOOL SHInitDialog (PSHINITDLGINFO pshidi);

The function takes a single parameter, a pointer to an SHINITDLGINFO structure defined as

typedef struct tagSHINITDIALOG{ 
DWORD dwMask;
HWND hDlg;
DWORD dwFlags;
} SHINITDLGINFO;

The dwMask field must be set to the single flag currently supported, SHIDIM_FLAGS. The hDlg field should be set to the window handle of the dialog. The third parameter, dwFlags, specifies a number of different initialization options. The SHIDIF_DONEBUTTON specifies that the navigation bar across the top of the screen contain an OK button in the upper right corner. This flag is typically set because the user interface guidelines specify that dialogs have an OK button in the navigation bar, and the guidelines specify that there be no Cancel button. While one could argue with this specification, the user interface provides no automatic way to provide a Cancel button.

The SHIDIF_SIPDOWN flag closes the SIP when the dialog is displayed. This flag should be set for informational dialogs that have no text input fields. Note that the absence of this flag doesn't automatically display the SIP. It simply means that the state of the SIP remains unchanged when the dialog box is displayed.

Three other flags can be set in the dwFlags field:



SHIDIF_SIZEDLG



SHIDIF_SIZEDLGFULLSCREEN



SHIDIF_FULLSCREENNOMENUBAR



These flags deal with how the dialog box will be sized. TheChapter 18 does have the ability to float.

The SHIDIF_SIZEDLGFULLSCREEN and SHIDIF_FULLSCREENNOMENUBAR flags size the dialog to fit the entire screen regardless of the state of the SIP. The difference between the two flags is that SHIDIF_FULLSCREENNOMENUBAR does not leave room for the menu bar at the bottom of the screen.


Input Dialogs


In general, it's helpful to divide dialogs into informational dialogs and input dialogs. Information dialogs deliver information to the user and for the most part don't need text input. Input dialogs are dialogs that require lines of text to be entered, such as passwords or IP addresses. For input dialogs, you can group the controls in the top two thirds of the dialog so that those fields aren't covered up by the SIP, which will almost always be displayed.

Whether the dialog is an input dialog or an informational dialog, another Pocket PC function that is typically called during WM_INITDIALOG is

BOOL SHSipPreference (HWND hwnd, SIPSTATE st);

This function sets the preferred state of the SIP. I say preferred state because the action of this function depends on the state of the SIP prior to when it was called. The two parameters are the handle to the window, which can be a dialog box or a custom control, and a set of SIP state flags listed here:



SIP_UPDisplays the SIP.



SIP_DOWNRequests to hide the SIP. The SIP is lowered only after a predetermined period of milliseconds in case the user switches back to a window that is displaying the SIP.



SIP_FORCEDOWNImmediately forces the SIP to hide.



SIP_UNCHANGEDLeaves the SIP alone or cancels a previous call to SHSipPreference.



SHSipPreference is quite useful for writing custom controls that require SIP input. When the control receives the focus, it can call SHSipPreference to request the SIP be displayed. When the control loses the focus, it can call SHSipPreference to request the SIP be hidden. If the control receiving focus then calls SHSipPreference to display the SIP, this call will override the request to hide the SIP and the SIP will remain displayed without an annoying flash of the SIP.

If the dialog is an informational dialog, the call to SHSipPreference requests that the SIP be lowered. The dialog box can then display information in the entire area of the dialog. However, using SHInitDialog and SHSipPreference doesn't change the state of the SIP when the dialog is displayed. The dialog box should handle the WM_ACTIVATE message and call SHHandleWMActivate, as in the HelloPPC example earlier in the chapter. This call ensures that if the user switches away from the dialog and displays the SIP in another application, switching back to the informational dialog will hide the SIP.

For input dialogs, managing the SIP is somewhat more difficult. You must display the SIP as needed when the focus window is a control that requires text input. The Pocket PC provides a couple of ways to interactively manage the SIP for your dialog. First, the dialog box can display the SIP when the dialog is created and keep it up for the life of the dialog. Another technique is to display the SIP only when the user is working with a control that requires keyboard input.

To display the SIP and keep it displayed while the dialog has focus, simply insert a call to the function SHInputDialog in your dialog procedure so that it is called for every message sent to the dialog box. The function prototype for SHInputDialog is

void SHInputDialog (HWND hwnd, UINT uMsg, WPARAM wParam);

The parameters are the window handle, message, and wParam for the current message. This helper function appropriately commands the SIP to show or hide, depending on whether the dialog box is gaining or losing focus.

To have the SIP interactively show and hide itself depending on the control that has focus in the dialog box, you use a special control, WC_SIPPREF, which can be inserted into a dialog box. Typically you'll do this by specifying a line in the dialog box template. The resource editor doesn't insert this control by default. You must insert it either by inserting a User Control in the dialog box editor or by manually editing the dialog box resource. Editing the resource file manually might be more reliable because the WC_SIPPREF control must be the last control specified in the dialog box template. Adding the control is as simple as inserting the following text as the last line in the dialog box template:

CONTROL         ",-1,"SIPPREF",NOT WS_VISIBLE,-10,-10,6,6

Because this control is one of the Pocket PC special controls, your application must initialize it by calling

BOOL SHInitExtraControls (void);

SHInitExtraControls should be called once during your application's initialization to initialize any of the Pocket PC special controls such as CAPEDIT and SIPPREF.


Property Sheets


Another area where the Chapter 6 on a Pocket PC.


Figure 17-5: A property sheet on the Pocket PC has tabs across the bottom.

To create a property sheet that is full screen and that has tabs on the bottom, add the flags PSH_MAXIMIZE and PSH_USECALLBACK in the dwFlags field of the PROPSHEETHEADER structure. PSH_MAXIMIZE tells the dialog manager to make the property sheet a full-screen window. The PSH_USECALLBACK flag is a standard Win32 property sheet flag that tells the dialog to call back to the application when certain events occur in the property sheet. Specifically, the message we are interested in is the Windows CE unique PSCB_INITIALIZED notification, which indicates that the property sheet's Tab control has been created. To field the PSCB_INITIALIZED notification, the application must provide a callback function with the following prototype:

UINT CALLBACK PropSheetPageProc (HWND hwnd, UINT uMsg, 
LPPROPSHEETPAGE ppsp);

The parameters sent back to the application are a handle value documented to be reserved, the notification code in the uMsg parameter, and, on some notifications, a pointer to a PROPSHEETPAGE structure. For our purposes, the callback function can simply employ the following code:

int CALLBACK PropSheetProc(HWND hwndDlg, UINT uMsg, LPARAM lParam) {
if (uMsg == PSCB_INITIALIZED) {
// Get tab control
HWND hwndTabs = GetDlgItem (hwndDlg, 0x3020);
DWORD dwStyle = GetWindowLong (hwndTabs, GWL_STYLE);
SetWindowLong (hwndTabs, GWL_STYLE, dwStyle | TCS_BOTTOM);
} else if (uMsg == PSCB_GETVERSION)
return COMCTL32_VERSION;
return 1;
}

The source of this rather strange code comes from the MFC source code provided with the Pocket PC SDK. During the PSCB_INITIALIZE notification, the handle of the Tab control of the property sheet is queried using the predefined control ID 0x3020. The style bits of the Tab control are then modified to have the control place the tabs on the bottom instead of the top by setting the TCS_BOTTOM style flag.

Two additional callback notifications are available exclusively on the Pocket PC. The PSCB_GETLINKTEXT notification is sent to query the title of the property sheet. This text is displayed on the sheet itself, not on the navigation bar at the top of the screen.

The PSCB_GETLINKTEXT notification is sent to the callback procedure to see if the application wants to display a hyperlink string below the tabs on the property sheet. The string is copied to the buffer pointed to by lParam. The hyperlink within the string should be in the following form:

TEXT ("Launch the calculator by tapping <file:calc.exe{here}>.")

The hyperlink is enclosed in angle brackets (<>). The text displayed for the link is enclosed in curly brackets ({}). When the hyperlink is tapped, the Pocket PC will launch calc.exe. The hyperlink can also be a data file such as Book1.pxl or Memo.pwd.

/ 169