Reflect policy changes in your UI

Reflect policy changes in your UI

Benefits

Description

Allowing administrators to turn off features is a great way to lower TCO. However, it is important to make sure your application’s UI responds in a positive way to features being turned off. If this isn’t done properly, you run the risk of actually increasing your TCO.

Typically, the correct response is to disable the feature. However, there are cases where hiding it is a better solution. Instead of making the choice for the administrator, provide them with the option of either disabling or hiding the feature. Doing this allows the administrator to mold your application to fit their corporate environment and culture.

Application policies that turn off features should have settings of enabled, disabled, and hidden.

When a feature is disabled, it’s important to let the user know that it is disabled due to policy. This will preemptively answer a lot of user questions. Tool tips are almost always the most effective way to do this. Other options include status bar messages, pop-up messages, and context sensitive help.

Regardless of the methods used to inform the user, it’s vital the message explain to the user why the feature is disabled, what they can do as a work around (if anything), and how they can change it. Offer administrators a way customize the message via policy. For example, the standard part of the message might read “ClipArt is disabled due to application policy.” The administrator could then add, “You have to complete ClipArt training before using this feature. You can request ClipArt training, or a waiver through your manager.”

There are times when it may be more appropriate to offer the user alternative UI. For example an application may have a policy to disable all new features and look like the previous version. Here the policy is really doing more than disabling or hiding specific features, it is instructing the application to use an alternative UI. In cases like this, it is important to make sure this is clear in the policy and have the policy setting reflect that. So, the policy and its settings here might be: Act As Previous Version: Yes, No (default)

Code Sample

In our sample, the application offers a policy to allow the administrator to turn off the Customize feature. This is the code that handles the changes this would cause in the user interface, specifically, it handles the enabling, graying, or hiding of the customize item on the tools menu. We assume the application has already loaded the Tools menu and has a valid handle to it. We also assume it has read the feature states.

// ... after loading the menu, and reading the feature states

if (SetMenuState(hToolsMenu, ID_CUSTOMIZE, m_nCustomizeFeatureState))
{
    DrawMenuBar(hWnd);
}
else
{
    // .. any desired error handling
}



BOOL SetMenuState(HMENU hMenu, UINT nCommandItem, int nItemState)
{
    BOOL    fReturn = TRUE; // we assume success here

    // we can just assert on what's passed in...
    ASSERT(NULL != hMenu);
    ASSERT(NULL != nCommandItem);

    switch(nItemState)
    {
        case STATE_HIDDEN:
            if (RemoveMenu(hMenu, nCommandItem, MF_BYCOMMAND))
            {
                // We successfully removed/hide the item.
                break;
            }
            else
            {
                // We couldn't remove it, let's at least
                // try to hide it.  Fire an ASSERT though
                // since this shouldn't happen.
                ASSERT(FALSE);
                fReturn = FALSE;
                // fall through to the next case.
            }
        case STATE_DISABLED:
            if (0xFFFFFFFF == EnableMenuItem(hMenu, nCommandItem,  
                                MF_BYCOMMAND | MF_GRAYED))
            {
                // Hey, this menu item doesn't exist.
                ASSERT(FALSE);
                fReturn = FALSE;
            }
            break;
        default:
            if (0xFFFFFFFF == EnableMenuItem(hMenu, nCommandItem,  
                                MF_BYCOMMAND | MF_ENABLED))
            {
                // Hey, this menu item doesn't exist.
                ASSERT(FALSE);
                fReturn = FALSE;
            }
            break;
    }
    return fReturn;
}

Considerations

If a feature is turned off because of a system policy (instead of an application policy), the feature should disabled.

See Also

DeleteMenu, EnableMenuItem, EnableWindow, Registry Overview, ShowWindow