VC++的菜单控制和自绘菜单

菜单控制
为什么即使调用EnableMenuItem菜单项后,菜单项还处于禁止状态  

需要将CFrameWnd::
m_bAutomenuEnable设置为FALSE,如果该数据成员为TRUE(缺省值),工作框将自动地禁止没有ON_UPDATE_COMMAND_UI或者ON_COMMAND的菜单项。

//Disable
MFC from automatically disabling menu
items.

m_bAuoMenuEnable=FALSE;

//Now
enable the menu item.

CMenu* pMenu=GetMenu
();

ASSERT_VALID
(pMenu);

pMenu->EnableMenuItem (ID_MENU_ITEM,MF_BYCOMMAND
|
MF_ENABLED);

如何给系统菜单添加一个菜单项  

给系统菜单添加一个菜单项需要进行下述三个步骤:

首先,使用Resource
Symbols对话(在View菜单中选择Resource
Symbols...

可以显示该对话)定义菜单项ID,该ID应大于0x0F而小于0xF000;

其次,调用CWnd::GetSystemMenu获取系统菜单的指针并调用CWnd::
Appendmenu将菜单项添加到菜单中。下例给系统菜单添加两个新的菜单项:

int CMainFrame::
OnCreate (LPCREATESTRUCT
lpCreateStruct)

{



//Make
sure system menu item is in the right range.

ASSERT
(IDM_MYSYSITEM &0xFFF0)==IDM_MYSYSITEM);

ASSERT
(IDM-MYSYSITEM<0xF000);

//Get pointer to system
menu.

CMenu* pSysmenu=GetSystemmenu
(FALSE);

ASSERT_VALID (pSysMenu);

//Add
a separator and our menu item to system menu.

CString
StrMenuItem (_T ("New menu item"));

pSysMenu->Appendmenu
(MF_SEPARATOR);

pSysMenu->AppendMenu (MF_STRING,
IDM_MYSYSITEM,
strMenuitem);



}

现在,选择系统菜单项时用户应进行检测。使用ClassWizard处理

WM_SYSCOMMAND消息并检测用户菜单的nID参数:

void
CMainFrame:: OnSysCommand (UINT nID,LPARAM
lParam)

{

//Determine if our system menu
item was selected.

if ( (nID &
0xFFF0)==IDM_MYSYSITEM)

{

//TODO-process
system menu
item

}

else

CMDIFrameWnd::
OnSysCommand (nID,
lParam);

}

最后,一个设计良好的UI应用程序应当在系统菜单项加亮时在状态条显示一个帮助信息,这可以通过增加一个包含系统菜单基ID的串表的入口来实现。

如何确定顶层菜单所占据的菜单行数  

这可以通过简单的减法和除法来实现。首先,用户需要计算主框窗口的高度和客户区;其次,从主框窗口的高度中减去客户区、框边界以及标题的高度;最后,除以菜单栏的高度。下例成员函数是一个计算主框菜单所占据的行数的代码实现。

int
CMainFrame:: GetMenuRows ()

{

CRect
rcFrame,rcClient;

GetWindowRect
(rcFrame);

GetClientRect
(rcClient);

return (rcFrame.Height () -rcClient.Height
()-

:: GetSystemMetrics (SM_CYCAPTION)
-

(:: getSystemMetrics (SM_CYFRAME) *2))
/

:: GetSystemMetrics
(SM_CYMENU);

}

自绘菜单
闻怡洋译 

在这里提供一个C++类(CCustomMenu),该类是CMenu的子类,并且拥有自绘能力。它可以向你提供以下的功能:

设置字体颜色。
设置高亮度颜色。
设置高亮度时的风格。
设置选中时和在普通状态下的菜单显示的图标。
设置显示图标大小。
在CCustomMenu中定义了结构MENUDATA,你必须根据你的需要填充该结构,并且在增加菜单时提供该结构的指针(调用AppendMenu,InsertMenu)。下面是一个例子:

1、定义CCustomMenu的实例,和MENUDATA结构变量。

    CCustomMenu
m_cCustomMenu;
    MENUDATA menuData [8]; //
as many menu items are present , You should be able to
use
                //new
and do the
same
2、调用CreateMenu()设置有关参数。
    m_customMenu.CreateMenu
();
    m_customMenu.SetIconSize (25,25);
//This is to set the size of the
Icon.
                        //
This should be used only once for any
menu
    // in order to resize it, destroy
and create the menu again with different
size.
    m_customMenu.SetHighlightStyle
(Normal); //Or TextOnly, if you want
the
    // background color to remain the
same
    // and the Text color to change to
the Highlight
color.
        // The
following setXXXColor sets the menu colors. If you dont want to change any, Dont
call these member
functions.
     m_customMenu.SetTextColor
(RGB
(255,0,0));
     m_customMenu.SetBackColor
(RGB
(255,255,255));
     m_customMenu.SetHighlightColor
(RGB
(0,0,255));
3、设置MENUDATA变量,并增加菜单项。
     lstrcpy
(menuData[0].menuText ,
"text1");
     menuData[0].menuIconNormal=
IDI_ICON1;
     m_customMenu.AppendMenu
(MF_OWNERDRAW,3,(LPCTSTR)menuData);

3、在你的窗口中重载OnMeasureItem(...)函数。
void
CMyView::OnMeasureItem(int nIDCtl, LPMEASUREITEMSTRUCT
lpMeasureItemStruct)
{
    if
( lpMeasureItemStruct->CtlType == ODT_MENU
&&
            IsMenu((HMENU)lpMeasureItemStruct->itemID)
&&
            (lpMeasureItemStruct->itemID
== (UINT)m_hMenuSub)
)
    {
        m_customMenu.MeasureItem
(lpMeasureItemStruct);
    }
    else
        //
let MFC‘s self-drawing handle
it
        CView::OnMeasureItem(nIDCtl,
lpMeasureItemStruct);
}

下面的函数将帮助你设置菜单属性。

    void
SetTextColor (COLORREF );
    void
SetBackColor (COLORREF);
    void
SetHighlightColor (COLORREF);
    void
SetIconSize (int, int);
    void
SetHighlightStyle (HIGHLIGHTSTYLE ); // HIGHLIGHTSTYLE : enum {Normal,
TextOnly}
    void SetHighlightTextColor
(COLORREF);

下面是文件代码:
//*************************************************************************
//
CustomMenu.h : header
file
//

#if
!defined(AFX_CUSTOMMENU_H__FE5B01C3_1E02_11D1_B87A_0060979CDF6D__INCLUDED_)
#define
AFX_CUSTOMMENU_H__FE5B01C3_1E02_11D1_B87A_0060979CDF6D__INCLUDED_

#if
_MSC_VER >= 1000
#pragma once
#endif //
_MSC_VER >= 1000
class
MENUDATA
{
public:
    MENUDATA
() { menuIconNormal = -1; menuIconSelected =
-1;};
    char
menuText[32];
    UINT
menuIconNormal;
    UINT
menuIconSelected;
};

typedef enum {Normal,TextOnly}
HIGHLIGHTSTYLE;

////////////////////////////////////////////////
//
//
CCustomMenu window

class CCustomMenu : public
CMenu
{
//
Construction
public:
    CCustomMenu();

//
Attributes
public:

//
Operations
public:

//
Overrides
    // ClassWizard generated
virtual function
overrides
    //{{AFX_VIRTUAL(CCustomMenu)
    //}}AFX_VIRTUAL

//
Implementation
public:
    virtual
~CCustomMenu();
    virtual void DrawItem(
LPDRAWITEMSTRUCT);
    virtual void
MeasureItem( LPMEASUREITEMSTRUCT );
    void
SetTextColor (COLORREF );
    void
SetBackColor (COLORREF);
    void
SetHighlightColor (COLORREF);
    void
SetIconSize (int, int);
    void
SetHighlightStyle (HIGHLIGHTSTYLE
);
    void SetHighlightTextColor
(COLORREF);

    // Generated message map
functions
protected:
    COLORREF
m_crText;
    COLORREF
m_clrBack;
    COLORREF
m_clrText;
    COLORREF
m_clrHilight;
    COLORREF
m_clrHilightText;
    LOGFONT
m_lf;
    CFont
m_fontMenu;
    UINT
m_iMenuHeight;
    BOOL
m_bLBtnDown;
    CBrush
m_brBackground,m_brSelect;
    CPen
m_penBack;
    int
m_iconX,m_iconY;
    HIGHLIGHTSTYLE
m_hilightStyle;

    //{{AFX_MSG(CCustomMenu)
        //
NOTE - the ClassWizard will add and remove member functions
here.
    //}}AFX_MSG
};

///////////////////////////////////////
//

//{{AFX_INSERT_LOCATION}}
// Microsoft Developer
Studio will insert additional declarations immediately before the previous
line.

#endif
//!defined(AFX_CUSTOMMENU_H__FE5B01C3_1E02_11D1_B87A_0060979CDF6D__INCLUDED_)

//*************************************************************************
//
CustomMenu.cpp : implementation file
//

#include
"stdafx.h"
#include "CustomMenu.h"

#ifdef _DEBUG
#define new
DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] =
__FILE__;
#endif

////////////////////////////////////////////////
//
//
CCustomMenu

CCustomMenu::CCustomMenu()
{
    m_clrText
= GetSysColor (COLOR_MENUTEXT);
    m_clrBack =
GetSysColor
(COLOR_MENU);
    m_brBackground.CreateSolidBrush
(m_clrBack);
    m_penBack.CreatePen
(PS_SOLID,0,m_clrBack);
    m_crText =
m_clrText;
    m_bLBtnDown =
FALSE;
    m_iconX = GetSystemMetrics (
SM_CXMENUCHECK);
    m_iconY = GetSystemMetrics
(SM_CYMENUCHECK );

    m_clrHilight = GetSysColor
(COLOR_HIGHLIGHT);
    m_brSelect.CreateSolidBrush
(m_clrHilight);
    m_clrHilightText = GetSysColor
(COLOR_HIGHLIGHTTEXT);

    ZeroMemory ((PVOID)
&m_lf,sizeof (LOGFONT));
    NONCLIENTMETRICS
nm;
    nm.cbSize = sizeof
(NONCLIENTMETRICS);

    //Get the system metrics for
the Captionfromhere
    VERIFY (SystemParametersInfo
(SPI_GETNONCLIENTMETRICS,0,&nm,0));

    m_lf =
nm.lfMenuFont;
    m_iMenuHeight =
nm.iMenuHeight;
    m_fontMenu.CreateFontIndirect
(&m_lf);
}

CCustomMenu::~CCustomMenu()
{
    if
((HBRUSH) m_brBackground !=
NULL)
        m_brBackground.DeleteObject
();
    if ((HFONT)m_fontMenu
!=NULL)
        m_fontMenu.DeleteObject
();
    if ((HBRUSH)m_brSelect !=
NULL)
         m_brSelect.DeleteObject
();
}

////////////////////////////////////////////////
//
//
CCustomMenu message handlers

void CCustomMenu::DrawItem
(LPDRAWITEMSTRUCT lpDIS)
{
    ASSERT(lpDIS !=
NULL);

    CDC* pDC =
CDC::FromHandle(lpDIS->hDC);
    CRect
rect;
    HICON
hIcon;
    COLORREF crText =
m_crText;
    // draw the colored rectangle
portion
    rect.CopyRect(&lpDIS->rcItem);

    //
draw the up/down/focused/disabled state

    UINT
action = lpDIS->itemAction;
    UINT state =
lpDIS->itemState;
    CString
strText;
    LOGFONT lf;
    lf =
m_lf;

    CFont
dispFont;
    CFont
*pFont;
    //GetWindowText(strText);
    if
(lpDIS->itemData !=
NULL)
    {
        strText
= (((MENUDATA*)
(lpDIS->itemData))->menuText);
        if
((((MENUDATA *)(lpDIS->itemData))->menuIconNormal) ==
-1)
            hIcon
= NULL;
        else if (state &
ODS_SELECTED)
        {
            if
((((MENUDATA *)(lpDIS->itemData))->menuIconSelected) !=
-1)
                hIcon
= AfxGetApp ()->LoadIcon (((MENUDATA
*)(lpDIS->itemData))->menuIconSelected);
            else
                hIcon
= AfxGetApp()->LoadIcon
(((MENUDATA*)(lpDIS->itemData))->menuIconNormal);
        }
        else
            hIcon
= AfxGetApp()->LoadIcon
(((MENUDATA*)(lpDIS->itemData))->menuIconNormal);

        TRACE1
("Draw for %s\n",
strText);
    }
    else
    {
        strText.Empty();
        hIcon
= NULL;
    }

    if ( (state
& ODS_SELECTED)
)
    {
        //
draw the down edges

        CPen
*pOldPen = pDC->SelectObject
(&m_penBack);

        //You
need only Text highlight and thats what you
get
        if (m_hilightStyle !=
Normal)
        {
            pDC->FillRect
(rect,&m_brBackground);
        }
        else
        {
            pDC->FillRect
(rect,&m_brSelect);
        }

        pDC->SelectObject
(pOldPen);
        pDC->Draw3dRect
(rect,GetSysColor
(COLOR_3DHILIGHT),GetSysColor(COLOR_3DSHADOW));
        lf.lfWeight
= FW_BOLD;
        if
((HFONT)dispFont !=
NULL)
            dispFont.DeleteObject
();
        dispFont.CreateFontIndirect
(&lf);
        crText =
m_clrHilightText;

        //While
selected move the text a
bit
        TRACE0
("SELECT,SELECTED\n");
    }
    else
    {
        CPen
*pOldPen = pDC->SelectObject
(&m_penBack);
        pDC->FillRect
(rect,&m_brBackground);
        pDC->SelectObject
(pOldPen);
        // draw the up
edges
        pDC->Draw3dRect
(rect,m_clrBack,m_clrBack);
        if
((HFONT)dispFont !=
NULL)
            dispFont.DeleteObject
();
        dispFont.CreateFontIndirect
(&lf);
//Normal

        TRACE0 ("SELECT,
NORMAL\n");
    }

    // draw
the text if there is any
    //We have to paint the text
only if the image is nonexistant
    if (hIcon !=
NULL)
    {
        if(DrawIconEx
(pDC->GetSafeHdc(),rect.left,rect.top,hIcon,
            (m_iconX)?m_iconX:32,(m_iconY)?m_iconY:32,0,NULL,DI_NORMAL))
            TRACE0("Wrote
the icon
successfully\n");
        else
            TRACE0
("SORRY.NOGO\n");
    }
    //This
is needed always so that we can have the space for check
marks
    rect.left = rect.left
+((m_iconX)?m_iconX:32);

    if (
!strText.IsEmpty())
    {
        //
pFont->GetLogFont
(&lf);

        int iOldMode =
pDC->GetBkMode();

        pDC->SetBkMode(
TRANSPARENT);

        pDC->SetTextColor(
crText);

        pFont =
pDC->SelectObject
(&dispFont);
        TRACE1(
"About To DrawText
%s\n",strText);
        pDC->DrawText
(strText,rect,DT_LEFT|DT_SINGLELINE|DT_VCENTER);
        TRACE0("Done\n");
        pDC->SetBkMode(
iOldMode
);
        pDC->SelectObject
(pFont); //set it to the old
font
    }
    dispFont.DeleteObject
();
}

void CCustomMenu::MeasureItem( LPMEASUREITEMSTRUCT lpMIS
)
{
    CDC *pDC =
AfxGetApp()->m_pMainWnd->GetDC();
    CFont* pFont
= pDC->SelectObject (&m_fontMenu);
    int iconX =
0,iconY= 0;
    TEXTMETRIC
tm;
    pDC->GetTextMetrics
(&tm);
    pDC->SelectObject
(pFont);
    AfxGetApp()->m_pMainWnd->ReleaseDC
(pDC);

    if
(m_iconX)
        iconX =
m_iconX;
    if
(m_iconY)
        iconY =
m_iconY;

    lpMIS->itemWidth = iconX +
tm.tmAveCharWidth * lstrlen(((MENUDATA*)(lpMIS->itemData))->menuText)
+10;
    lpMIS->itemHeight = (iconY >
(m_iMenuHeight+1))?iconY:m_iMenuHeight + 1;
}

void
CCustomMenu::SetIconSize (int width, int
height)
{
    m_iconX =
width;
    m_iconY = height;
}

void
CCustomMenu::SetTextColor (COLORREF
clrText)
{
    m_crText = clrText;
}

void
CCustomMenu::SetBackColor (COLORREF
clrBack)
{
    m_clrBack =
clrBack;
    if ((HBRUSH)m_brBackground !=
NULL)
        m_brBackground.DeleteObject
();
    m_brBackground.CreateSolidBrush
(clrBack);
}

void CCustomMenu::SetHighlightColor (COLORREF
clrHilight)
{
    m_clrHilight =
clrHilight;
    if ((HBRUSH)m_brSelect !=
NULL)
            m_brSelect.DeleteObject
();
    m_brSelect.CreateSolidBrush
(clrHilight);
}

void CCustomMenu::SetHighlightTextColor (COLORREF
clrHilightText)
{
    m_clrHilightText =
clrHilightText;
}

void CCustomMenu::SetHighlightStyle
(HIGHLIGHTSTYLE hilightStyle)
{
    m_hilightStyle =
hilightStyle;
}

VC++的菜单控制和自绘菜单,布布扣,bubuko.com

时间: 2024-08-10 06:16:34

VC++的菜单控制和自绘菜单的相关文章

积累的VC编程小技巧之标题栏和菜单

1.窗口最大最小化按纽的控制 ①怎样在程序开始的时候让它最大化? ②vc++做出来的exe文件在窗体的右上方是没有最大化和最小化按钮的,怎样实现这一功能? ③如何在显示窗口时,使最大化按钮变灰?   ①在App类里的C-App::InitInstance()中把m_pMainWnd->ShowWindow(SW_SHOW)改成m_pMainWnd->ShowWindow(SW_MAXIMIZE); ②在CreateWidnow时用WS_SYSMENU|WS_MINIMIZEBOX|WS_MAX

以后台权限菜单控制为例,获取js路径后面参数值

<script type="text/javascript" src="../Public/js/common.js?menuids=1,2,3,4,5&ckids=4-5-6" /></script> 需要注意的是,此段js文件位置需要放在页面中所有js包含文件后面,目前暂未想到好的办法解决位置问题. //获取js后面参数 function getUrlArg(){ var url = $("script:last&quo

解决element生成的下拉菜单,不在父级之下,而是在body之下,通过父级控制该下拉菜单的样式,达到不跟别的地方冲突的目的

项目中存在多个下拉菜单,每个下拉菜单的样式可能不同 不能直接拿到element里面的类名来修改,这样会导致全局统一 在下拉菜单上定义一个父级类名,通过这个父级类名来定义这些下拉菜单的样式,达到私有化 遇到问题,生成的下拉菜单跟父类不在同一个节点,无法通过父级类来指定样式 解决方案:在下拉菜单的结构上添加 ref,页面加载后动态添加父级类名 原文地址:https://www.cnblogs.com/wuhefeng/p/12530803.html

VC++ WIN32 sdk实现按钮自绘详解.

网上找了很多,可只是给出代码,没有详细解释,不便初学者理解.我就抄回冷饭.把这个再拿出来说说. 实例图片: 首先建立一个标准的Win32 Application 工程.选择a simple Win32 Application. 然后建立我们的资源文件首先新建一个对话框资源,资源ID改为IDD_MAIN_DLG 然后在其上新建一个按钮控件资源ID改为IDC_ODBUTTON,此按钮的styles中必须选中owenerdraw属性. 然后将其保存为.rc的资源文件.并将其导入我们的工程.同理新建一个

web标准(复习)--4 纵向导航菜单及二级弹出菜单

今天我们开始学习纵向导航菜单及二级弹出菜单,包含以下内容和知识点: 纵向列表 标签的默认样式 css派生选择器 css选择器的分组 纵向二级列表 相对定位和绝对定位 一.纵向列表纵向列表或称为纵向导航,在网站的产品列表中应用比较广泛,如淘宝网左侧的淘宝服务,今天我们就学习一下纵向导航的制作 先新建一个页面,然后插入一个ID为menu的div,然后在设计视图中选中文字,点击工具栏的ul图标,即会自动插入ul和li,然后修改文字内容为你需要的内容. <style type="text/css&

VC++ WIN32 sdk实现按钮自绘详解 之二.

网上找了很多,可只是给出代码,没有详细解释,不便初学者理解.我就抄回冷饭.把这个再拿出来说说. 实例图片: 首先建立一个标准的Win32 Application 工程.选择a simple Win32 Application. 然后建立我们的资源文件首先新建一个对话框资源,资源ID改为IDD_MAIN_DLG 然后在其上新建一个按钮控件资源ID改为IDC_ODBUTTON,此按钮的styles中必须选中owenerdraw属性. 然后将其保存为.rc的资源文件.并将其导入我们的工程.同理新建一个

下角动画旋转菜单、圆心弹出菜单ArcMenu 源码解析

支持类似Path的左下角动画旋转菜单及横向划出菜单.圆心弹出菜单 项目地址:https://github.com/daCapricorn/ArcMenu 一.关注3个效果 点击中心控制点 的时候,展开效果: 中心控制点旋转45度的动画 周围children 弹出动画 2.点击中心控制点的时候,收缩动画: 中心控制点旋转45度 周围children 自旋转并收缩 3.展开时候,点击child 被点击的child放大, 其他chidren 消失 二.3个java文件 ArcMenu.java  自定

第四天 纵向导航菜单及二级弹出菜单

http://www.aa25.cn/div_css/905.shtml 今天我们开始学习<十天学会web标准(div+css)>的纵向导航菜单及二级弹出菜单,包含以下内容和知识点: 纵向列表 标签的默认样式 css派生选择器 css选择器的分组 纵向二级列表 相对定位和绝对定位 一.纵向列表 纵向列表或称为纵向导航,在网站的产品列表中应用比较广泛,如淘宝网左侧的淘宝服务,今天我们就学习一下纵向导航的制作 先新建一个页面,然后插入一个ID为menu的div,然后在设计视图中选中文字,点击工具栏

如何解决EasyUI树菜单单击文字无法展开菜单的问题

最近遇到一个问题:单击EasyUI树菜单中的文字,菜单无法展开,只有单击加号才能展开,才有效果.如何解决这个问题呢?方法如下: 1 找到要添加的代码的位置,比如说 jquery.easyUI.min.js 文件中菜单的设置处(具体要看自己的项目是  在哪里设置) 2 找到onSelect 函数,然后添加如下代码: onSelect:function(node){      $(this).tree(node.state === 'closed' ? 'expand' : 'collapse',