精华内容
下载资源
问答
  • VC EVC中定制位图按钮

    2009-12-17 11:05:00
    引用:http://hi.baidu.com/¿ªÐÄde¹û×Ó... 这个博客不错,是和界面开发有关,效果不错,拿来和大家分享! CButtonST(VC6):http://www.codeproject.com/KB/buttons/cbuttonst.aspxCCeButtonST v1.2(EV...

    引用:http://hi.baidu.com/¿ªÐÄde¹û×Ó/blog/item/40bd59f6d0c2292b730eec5d.html

    这个博客不错,是和界面开发有关,效果不错,拿来和大家分享!

     

    CButtonST(VC6):http://www.codeproject.com/KB/buttons/cbuttonst.aspx
    CCeButtonST v1.2(EVC4.2):http://www.codeproject.com/KB/mobile/ccebuttonst.aspx
    CButtonSSLhttp://www.codeproject.com/KB/buttons/cbuttonssl.aspx

    (EVC4.2)UniButtonProj1_0   //from csdn,具体链接忘记了。。。

    //UniButton.h
    #if !defined(AFX_UNIBUTTON_H__7CF75519_55DD_4B39_B0BE_710AAA9289C8__INCLUDED_)
    #define AFX_UNIBUTTON_H__7CF75519_55DD_4B39_B0BE_710AAA9289C8__INCLUDED_

    #if _MSC_VER > 1000
    #pragma once
    #endif // _MSC_VER > 1000
    //

    /
    // CUniButton window

    class CUniButton : public CButton
    {
    // Construction
    public:
    CUniButton();

    // Attributes
    public:

    // Operations
    public:

    // Overrides
    // ClassWizard generated virtual function overrides
    //{{AFX_VIRTUAL(CUniButton)
    public:
    virtual void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct);
    //}}AFX_VIRTUAL

    // Implementation
    #define   BTN_PUSHED_STATE 1
    #define   BTN_RELEASED_STATE 0

    //Functions
    //------------------------------------------------------------
    public:
    virtual    ~CUniButton();
    void    SetTransparent(BOOL Enable = FALSE) {m_bTransparent = Enable;}
    void    SetTextColor(COLORREF TextColor = RGB(0,0,0));
    BOOL    FontStyle(CString sFont = "MS Sans Serif", int iHeight = 10, int iWidth = 6, BOOL bFont3D = FALSE, BOOL bConcave = FALSE);
    inline void   HideText(BOOL bHide = TRUE) { m_bHideText = bHide; }
    inline void   SetBtnDownImg(int bmpID) { m_iBtnPushedBitmapID = bmpID; }
    inline void   SetBtnUpImg(int bmpID) { m_iBtnOffBitmapID = bmpID; }
    BOOL    LoadWAV(CString fileName, BOOL loadMEM);
    inline BOOL   WavIsSupported(void) { return m_bWavSupported;}
    BOOL    WAVLoaded(void);
    inline void   SetBkgndHandle(HBITMAP hBitmap) { m_hBmpBkgnd = hBitmap; }
    inline void   SetTopEdgeColor(COLORREF TopEdge = RGB(50,50,50)) {m_EdgeTop = TopEdge;}
    inline void   SetLeftEdgeColor(COLORREF LeftEdge = RGB(70,70,70)) {m_EdgeLeft = LeftEdge;}
    inline void   SetTranspColor(COLORREF transpCREF) { m_transpCREF = transpCREF; }

    protected:
    void    PaintBckgnd(HDC h_destDC);
    void    PaintSunkenBckgnd(HDC h_destDC);
    void    PaintButton(HDC h_destDC);
    void    PaintText(HDC h_clientDC, CRect rect);
    BOOL    WAVSupported(void);
    BOOL    BtnPlay(void);
    void    Bkg2Bmp(void);


    //Member Variables
    //----------------------------------------------------
    protected:
    int    m_iBtnPushedBitmapID;
    int    m_iBtnOffBitmapID;
    int    m_iState;
    BOOL   m_bTransparent;
    BOOL   m_bWavSupported;
    WAVEOUTCAPS m_caps;
    CString   m_SoundFile;
    HANDLE   m_hFile;
    LPCSTR   m_lpWave;
    CFont   m_Font;
    BOOL   m_bFontCreated;
    BOOL   m_bFont3D;
    BOOL   m_bConcave;
    BOOL   m_bHideText;
    HBITMAP   m_hBmpBkgnd; // Handle to Dialog Background Image
    COLORREF m_TextColor;
    COLORREF m_EdgeTop;
    COLORREF m_EdgeLeft;
    COLORREF m_transpCREF;

    // Generated message map functions
    protected:
    //{{AFX_MSG(CUniButton)
    afx_msg void OnLButtonUp(UINT nFlags, CPoint point);
    afx_msg void OnLButtonDown(UINT nFlags, CPoint point);
    //}}AFX_MSG

    DECLARE_MESSAGE_MAP()
    };

    /

    //{{AFX_INSERT_LOCATION}}
    // Microsoft Visual C++ will insert additional declarations immediately before the previous line.

    #endif // !defined(AFX_UNIBUTTON_H__7CF75519_55DD_4B39_B0BE_710AAA9289C8__INCLUDED_)

     

    //UniButton.cpp
    #include "stdafx.h"
    #include "UniButton.h"

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

    /
    // CUniButton

    CUniButton::CUniButton()
    {
    m_iBtnPushedBitmapID = 0;
    m_iBtnOffBitmapID   = 0;
    m_iState     = BTN_RELEASED_STATE;
    m_bTransparent    = FALSE;
    m_bWavSupported    = WAVSupported();
    m_SoundFile     = "";
    m_hFile      = INVALID_HANDLE_VALUE;
    m_lpWave     = NULL;
    m_bFontCreated    = FALSE;
    m_bFont3D     = FALSE;
    m_bConcave     = FALSE;
    m_bHideText     = TRUE;
    m_TextColor     = RGB(0,0,0);
    m_EdgeTop     = RGB(50,50,50);
    m_EdgeLeft     = RGB(70,70,70);
    m_transpCREF    = RGB(255,255,255);

    }

    CUniButton::~CUniButton()
    {
    if(m_hFile != INVALID_HANDLE_VALUE)
    {
       CloseHandle(m_hFile);
       m_hFile = INVALID_HANDLE_VALUE;
    }

    if(m_lpWave != NULL)
    {
       free((void*)m_lpWave);
       m_lpWave = NULL;
    }

    if(m_bFontCreated)
    {
       m_Font.DeleteObject();
    }
    }


    BEGIN_MESSAGE_MAP(CUniButton, CButton)
    //{{AFX_MSG_MAP(CUniButton)
    ON_WM_LBUTTONUP()
    ON_WM_LBUTTONDOWN()
    //}}AFX_MSG_MAP
    END_MESSAGE_MAP()

    /
    // CUniButton message handlers


    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    void CUniButton::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct)
    {
    // TODO: Add your code to draw the specified item

    CString sCaption;
    HDC   h_clientDC;
    CRect rect;
    CDC   *pDC;

    h_clientDC = lpDrawItemStruct->hDC;
    pDC    = CDC::FromHandle(lpDrawItemStruct->hDC);
    GetWindowText(sCaption);
    rect   = lpDrawItemStruct->rcItem;

    pDC->SetBkMode(TRANSPARENT);
    switch(m_iState)
    {
       case(BTN_PUSHED_STATE):
       {
        if(m_bTransparent)
        {
         PaintSunkenBckgnd(lpDrawItemStruct->hDC);
        }
        else
        {
         PaintBckgnd(lpDrawItemStruct->hDC);
         PaintButton(lpDrawItemStruct->hDC);
        }
        break;
       }

       case(BTN_RELEASED_STATE):
       {
        if(m_bTransparent)
        {
         PaintBckgnd(lpDrawItemStruct->hDC);
        }
        else
        {
         PaintBckgnd(lpDrawItemStruct->hDC);
         PaintButton(lpDrawItemStruct->hDC);
        }
        break;
       }
    }

    if(m_bHideText == FALSE)
    {
       PaintText(h_clientDC, rect);
    }

    }


    //*******************************************************************************
    // Copy Background to Button Face
    //*******************************************************************************
    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    void CUniButton::PaintBckgnd(HDC h_destDC)
    {

    CWnd * pParent;
    CRect wndRect;
    int   width;
    int   height;
    int   srcx;
    int   srcy;
    //BITMAP bmp;

    //::GetObject(m_hBmpBkgnd, sizeof(bmp), &bmp);
    HDC hDC = ::CreateCompatibleDC(NULL);
    ::SelectObject(hDC, m_hBmpBkgnd);

    pParent = this->GetParent();
    GetWindowRect(&wndRect);
    pParent->ScreenToClient(&wndRect);

    width = wndRect.Width();
    height = wndRect.Height();
    srcx = wndRect.left;
    srcy = wndRect.top;

    ::BitBlt(h_destDC, 0, 0, width, height, hDC, srcx, srcy, SRCCOPY);

    ::DeleteDC(hDC);
    }

    //------------------------------------------------------------------
    // This function paints the background shifted 2 pixels right and
    // down. It also draws top and left edge.
    //------------------------------------------------------------------
    void CUniButton::PaintSunkenBckgnd(HDC h_destDC)
    {
    CWnd *   pParent;
    CDC *   pParentCDC;
    CRect   wndRect;
    int    width;
    int    height;
    BYTE   rValue=0;
    BYTE   gValue=0;
    BYTE   bValue=0;

    //BITMAP bmp;

    //::GetObject(m_hBmpBkgnd, sizeof(bmp), &bmp);
    HDC hDC = ::CreateCompatibleDC(NULL);
    ::SelectObject(hDC, m_hBmpBkgnd);

    pParent = this->GetParent();
    GetWindowRect(&wndRect);
    pParent->ScreenToClient(&wndRect);

    width = wndRect.Width();
    height = wndRect.Height();

    pParentCDC = pParent->GetWindowDC();

    ::BitBlt(h_destDC, 2, 2, width-2, height-2, hDC, wndRect.left, wndRect.top, SRCCOPY);
    ::DeleteDC(hDC);


    CDC *pDC = CDC::FromHandle(h_destDC);
    pDC->Draw3dRect(0, 0, wndRect.Width(), 2, m_EdgeTop, m_EdgeTop);
    pDC->Draw3dRect(0, 1, 2, wndRect.Height(), m_EdgeLeft, m_EdgeLeft);

    }


    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    void CUniButton::PaintButton(HDC h_destDC)
    {
    CRect   cltRect;
    BITMAP   bmp;
    HBITMAP   hBmp;
    HDC    hDC;
    //COLORREF transpCREF;

    // Return if no bitmap assigned
    //--------------------------------------
    if(m_iBtnOffBitmapID == 0 || m_iBtnPushedBitmapID == 0)
    {
       return;
    }

    //transpCREF = RGB(255,255,255);

    GetClientRect(&cltRect);
    switch(m_iState)
    {
       case(BTN_PUSHED_STATE):
       {
        hBmp = ::LoadBitmap(::AfxGetInstanceHandle(), MAKEINTRESOURCE(m_iBtnPushedBitmapID));
        break;
       }

       case(BTN_RELEASED_STATE):
       {
        hBmp = ::LoadBitmap(::AfxGetInstanceHandle(), MAKEINTRESOURCE(m_iBtnOffBitmapID));
        break;
       }
    }
    ::GetObject(hBmp, sizeof(bmp), &bmp);
    hDC = ::CreateCompatibleDC(NULL);
    SelectObject(hDC, hBmp);
    ::TransparentImage(h_destDC, 0, 0, cltRect.Width(), cltRect.Height(), hDC, 0, 0, cltRect.Width(), cltRect.Height(), m_transpCREF);
    ::DeleteObject(hBmp);
    ::DeleteDC(hDC);
    }

     

    //------------------------------------------------------------------
    // This function paints text over the button - plain or 3D
    //------------------------------------------------------------------
    void CUniButton::PaintText(HDC h_clientDC, CRect rect)
    {
    CFont*   def_font;
    CString   sCaption;
    CDC *pDC = CDC::FromHandle(h_clientDC);

    GetWindowText(sCaption);

    if(m_bFontCreated)
    {
       def_font = pDC->SelectObject(&m_Font);
    }

    pDC->SetBkMode(TRANSPARENT);

    if(m_bFont3D)
    {
       if(m_bConcave)
       {
        pDC->SetTextColor(RGB(255,255,255));
        pDC->DrawText(sCaption, rect, DT_SINGLELINE|DT_VCENTER|DT_CENTER);
        pDC->SetTextColor(m_TextColor);
        rect.left = rect.left - 1;
        rect.top = rect.top - 1;
        rect.bottom = rect.bottom - 1;
        rect.right = rect.right - 1;
        pDC->DrawText(sCaption, rect, DT_SINGLELINE|DT_VCENTER|DT_CENTER);
      
       }
       else
       {
        pDC->SetTextColor(RGB(255,255,255));
        pDC->DrawText(sCaption, rect, DT_SINGLELINE|DT_VCENTER|DT_CENTER);
        pDC->SetTextColor(m_TextColor);
        rect.left = rect.left + 1;
        rect.top = rect.top + 1;
        rect.bottom = rect.bottom + 1;
        rect.right = rect.right + 1;
        pDC->DrawText(sCaption, rect, DT_SINGLELINE|DT_VCENTER|DT_CENTER);
      
       }
    }
    else
    {
       pDC->SetTextColor(m_TextColor);
       pDC->DrawText(sCaption, rect, DT_SINGLELINE|DT_VCENTER|DT_CENTER);
    }

    if(m_bFontCreated)
    {
       pDC->SelectObject(def_font);
    }
    }

     

    //******************************************************************
    // Font Setup
    //******************************************************************
    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    BOOL CUniButton::FontStyle(CString sFont, int iHeight, int iWidth, BOOL bFont3D, BOOL bConcave)
    {

    if(m_bFontCreated)
    {
       m_Font.DeleteObject();
    }

    if(0 != m_Font.CreateFont(iHeight, iWidth, 0, 0,
          FW_BOLD, //FW_NORMAL,
          0, 0, 0, 0, 0, 0, 0,0, sFont))
    {
       m_bFontCreated   = TRUE;
       m_bFont3D = bFont3D;
       m_bConcave = bConcave;
       return TRUE;
    }
    else
    {
       m_bFontCreated   = FALSE;
       return FALSE;
    }
    }

    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    void CUniButton::SetTextColor(COLORREF TextColor)
    {
    m_TextColor = TextColor;
    return;
    }

    //******************************************************************
    // WAV related functions
    //******************************************************************
    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    BOOL CUniButton::WAVSupported(void)
    {
    if(waveOutGetDevCaps(WAVE_MAPPER, &m_caps, sizeof(WAVEOUTCAPS)) == MMSYSERR_NOERROR)
    {
       if(m_caps.dwFormats & WAVE_FORMAT_1M08)
       {
        return TRUE;
       }
       else
       {
        return FALSE;
       }
    }
    return FALSE;
    }

    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    BOOL CUniButton::LoadWAV(CString fileName, BOOL loadMEM)
    {
    DWORD dwSize;
    DWORD dwBytesRead;
    BOOL bResult;

    // No support - no load
    //-------------------------------------------
    if(m_bWavSupported == FALSE)
    {
       return FALSE;
    }

    // Get rid of previous assignments if any
    //-------------------------------------------
    if(m_hFile != INVALID_HANDLE_VALUE)
    {
        CloseHandle(m_hFile);
        m_hFile = INVALID_HANDLE_VALUE;
    }

    if(m_lpWave != NULL)
    {
       free((void*)m_lpWave);
       m_lpWave = NULL;
    }

    // Open file
    //--------------------------------------------
    m_SoundFile = fileName;

    m_hFile = CreateFile( m_SoundFile,
            GENERIC_READ|GENERIC_WRITE,
            FILE_SHARE_READ,
            NULL,
            OPEN_ALWAYS,//OPEN_EXISTING,
            FILE_ATTRIBUTE_NORMAL,
            NULL
            );

    if(m_hFile == INVALID_HANDLE_VALUE)
    {
       return FALSE;
    }

    //Load file into memory if requested
    //----------------------------------------
    if(loadMEM)
    {
       // Get file size
       dwSize = GetFileSize(m_hFile, NULL);
       if(dwSize == 0xFFFFFFFF)
       {
        CloseHandle(m_hFile);
        m_hFile = INVALID_HANDLE_VALUE;
        return FALSE;
       }

       // Allocate memory for it
       //---------------------------------
       m_lpWave = (LPCSTR)malloc(dwSize);
       if(m_lpWave == NULL)
       {
        CloseHandle(m_hFile);
        m_hFile = INVALID_HANDLE_VALUE;
        return FALSE;
       }

       // Load into memory
       //---------------------------------
       bResult = ReadFile(m_hFile, (void *)m_lpWave, dwSize, &dwBytesRead, NULL);
       if((bResult == FALSE)||(dwBytesRead != dwSize))
       {
        CloseHandle(m_hFile);
        m_hFile = INVALID_HANDLE_VALUE;
        free((void*)m_lpWave);
        m_lpWave = NULL;
        return FALSE;
       }

       // Get rid of the file
       //-------------------------------------
       CloseHandle(m_hFile);
       m_hFile = INVALID_HANDLE_VALUE;
       return TRUE;
    }
    else
    {
       return TRUE;
    }

    return TRUE;
    }


    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    BOOL CUniButton::BtnPlay(void)
    {
    // Play from buffer
    //-------------------------------------
    if(m_lpWave != NULL)
    {
       sndPlaySound((unsigned short *)m_lpWave, SND_MEMORY|SND_ASYNC);
       return TRUE;
    }

    // Play from file
    //--------------------------------------
    if(m_hFile != INVALID_HANDLE_VALUE)
    {
       sndPlaySound(m_SoundFile, SND_ASYNC);
       return TRUE;
    }

    return FALSE;
    }


    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    BOOL CUniButton::WAVLoaded(void)
    {
    if((m_lpWave != NULL)||(m_hFile != INVALID_HANDLE_VALUE))
    {
       return TRUE;
    }
    return FALSE;
    }


    //******************************************************************
    // Button Message Handlers
    //******************************************************************
    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    void CUniButton::OnLButtonUp(UINT nFlags, CPoint point)
    {
    // TODO: Add your message handler code here and/or call default
    m_iState = BTN_RELEASED_STATE;
    //Invalidate();

    //Default();
    CButton::OnLButtonUp(nFlags, point);
    }

    //------------------------------------------------------------------
    //
    //------------------------------------------------------------------
    void CUniButton::OnLButtonDown(UINT nFlags, CPoint point)
    {
    // TODO: Add your message handler code here and/or call default
    m_iState = BTN_PUSHED_STATE;
    //Invalidate();
    if(WAVLoaded())
    {
       BtnPlay();
    }

    Default();
    //CButton::OnLButtonDown(nFlags, point);
    }

    在BOOL CUniButtonDemoDlg::OnInitDialog()中,添加代码即可,例如

    m_hBmpBkgnd = ::LoadBitmap( AfxGetInstanceHandle(), MAKEINTRESOURCE(IDB_BITMAP_BKGND) );

    m_button1.SetBkgndHandle(m_hBmpBkgnd);
    m_button1.HideText(FALSE);
    m_button1.SetTransparent(TRUE);
    m_button1.HideText(FALSE);
    m_button1.SetTopEdgeColor(RGB(20,20,20));
    m_button1.SetLeftEdgeColor(RGB(40,40,40));

    m_button2.SetBkgndHandle(m_hBmpBkgnd);
    m_button2.HideText(FALSE);
    m_button2.SetTransparent(TRUE);
    m_button2.HideText(FALSE);
    //m_button2.SetTextColor(RGB(200,200,200));
    m_button2.FontStyle("MS Sans Serif", 14, 8, TRUE, FALSE);
    m_button2.FontStyle("MS Sans Serif", 14, 8, TRUE, FALSE);
    m_button2.LoadWAV("Test.WAV", TRUE);
    //m_button2.LoadWAV("Test.WAV", FALSE);

    m_button3.SetWindowPos(this,20,80,177,97,SWP_NOZORDER);
    m_button3.SetBtnUpImg(IDB_BITMAP_BTNUP);
    m_button3.SetBtnDownImg(IDB_BITMAP_BTNDOWN);
    m_button3.SetBkgndHandle(m_hBmpBkgnd);
    m_button3.HideText(FALSE);
    m_button3.SetTransparent(FALSE);
    //m_button3.SetTranspColor(RGB(110,110,110));
    m_button3.HideText(FALSE);
    //m_button3.SetTextColor(RGB(100,100,100));
    m_button3.SetTextColor(RGB(0,0,255));
    m_button3.FontStyle("MS Sans Serif", 14, 8, TRUE, FALSE);

    m_button4.SetBkgndHandle(m_hBmpBkgnd);
    m_button4.HideText(FALSE);
    m_button4.SetTransparent(TRUE);
    m_button4.HideText(FALSE);
    m_button4.FontStyle("Ariel", 14, 6, TRUE, TRUE);

    return TRUE; // return TRUE unless you set the focus to a control

     

    转载于:https://www.cnblogs.com/Torres_fans/archive/2009/12/17/1626206.html

    展开全文
  • 而且把最小化、最大化、关闭按钮移到了标题栏的最左边,平时都是在右边的,有些不习惯了,呵呵,不过,本源码主要演示如何自定义窗口中的元素,在此基础上,你可以定制更多类似的小功能。 运行环境:Visual Studio...
  • VC程序中定制对话框中的回车键  基于对话框的程序中,每当用户按下回车键时,程序都会退出,其效果和按下对话框中的默认"OK"按钮是一样的,即使去掉"OK"按钮的 BS_DEFPUSHBUTTON 属性也没用。那么如何定制...

     

    VC程序中定制对话框中的回车键

       基于对话框的程序中,每当用户按下回车键时,程序都会退出,其效果和按下对话框中的默认"OK"按钮是一样的,即使去掉"OK"按钮的 BS_DEFPUSHBUTTON 属性也没用。那么如何定制回车键的行为呢?这个问题在Windows的开发中由来已久,对于初学者来说,这是个恼人的问题,幸运的是,人们找到了很多种解决这个问题的方案。本实例将告诉你实现定制回车键行为的方法。

      一、实现方法

      如果想要使回车键无效,最简单的方法是重载OnOK()函数,这固然是个不坏的主意,但如果重载OnOK()函数,让它什么事情也不干,那么当用户用鼠标按下"OK"按钮想真正做些什么的时候怎么办呢?你可以改变回车键的ID,如:ID_MY_OK,并写一个调用EndDialog()的处理器,这个方法虽然也能行得通,但显得有点不专业。

      另外一种方法是"disable"回车键的"默认"属性。这也是本文开始所提出的方法,之所以没有成功,是因为仅仅不设置"OK"按钮的BS_DEFPUSHBUTTON 属性是不够的,可以利用Visual C++中的Spy++工具仔细地观察,就能发现回车键仍然我行我素发送退出消息。问题出在哪呢?你必须区分OK按钮和回车键,你可以写一个OnOK处理器调用GetCurrentMessage()函数获取最后发送的消息,应该是WM_COMMAND,再检查WPARAM的低位字(low-order word)看看命令来自何处。

      要解决问题,必须搞清楚背后所发生的一切,在Spy++中可以看到,当用户按下回车键时,Windows发送一个特殊的WM_GETDEFID消息来获得缺省的命令ID,Windows再将它作为WM_COMMAND发送。所以,我们要做的就是重载WM_GETDEFID消息。在有关Windows的文档中是这样描述WM_GETDEFID返回值的:"如果有缺省的按钮,则返回值的高位字包含DC_HASDEFID,低位字包含控制的标识符。否则,返回值是零"。根据这段描述,假设如果没有缺省得按钮,则返回值应该是零。如果想要disable缺省得ID,必须在高位字中返回DC_HASDEFID,为此定义和实现消息映射函数如下:

    BEGIN_MESSAGE_MAP(CMyDlg, CDialog)
    ON_MESSAGE(DM_GETDEFID, OnGetDefID)
    ...
    END_MESSAGE_MAP()
    LRESULT CMyDlg::OnGetDefID(WPARAM wp, LPARAM lp)
    {
     return MAKELONG(0,DC_HASDEFID);
    }


      因为MFC没有对应DM_GETDEFID的宏,你必须使用通用的ON_MASSAGE宏。这样用户可以随意按回车键,但什么事都不会发生。

      上面的做法是解决了按回车键程序退出的问题,但是又产生了另外一个问题:如果想要回车键做些事情怎么办呢?有一些人曾经问过如何将回车键映射到TAB键,既按下回车键就象按下TAB键一样,也就是说输入焦点移动到下一个对话框控制。这需要做一些工作才行,但最简单的方式是使用加速键。许多程序员试图用OnChar()响应函数,但它是一个低级趣味的东西,应该想方设法尽量避免使用它,更糟的还有WM_KEYDOWN,WM_KEYUP之类的消息。谁能处理这些消息呢?OnChar()可以用来限制允许输入编辑框的字符,如:数字,字母等。如果想要将一个键映射到一个命令,加速键才是最好的方法。

      在本实例中为VK_RETURN创建了一个加速键,将它映射到命令ID_MY_ENTER,并写一个命令处理器来实现任何想实现的事情。

      如果你细心的话会发现另外一个还没有得到解决的问题,那就是在MFC对话框不自动处理加速键,你必须自己编写代码来做这件事情。为了理解弄清楚这是为什么,让我们回首Windows开发的历程,在使用C和原始的Windows API的年代,每一个Windows程序中都有一个叫做消息泵的中枢循环:

    while (GetMessage(...)) {
     TranslateMessage(...);
     DispatchMessage(...);
    }


      在这里细节不是最重要的,最重要的是消息并不到达程序的流程,你必须请求消息。这是一种人为的非抢先式多任务方法,这种方法通过每一个任务精诚协作来仿造多任务环境,随着增加的功能越来越多,有人想到了加速键表的主意,这个表用来映射按键和命令IDs。为了实现这个目的,微软发明了一个叫TranslateAccelerator()的函数。现在这个消息泵变成了如下的样子:

    while (GetMessage(...)) {
     if (TranslateAccelerator(hAccel...)) {
      // handled, continue looping
     } else {
      TranslateMessage(...);
      DispatchMessage(...);
     }
    }


      hAccel是个加速键表句柄,在这里细节同样不是重要的,重要的是如何利用加速键表,也就是要有一个专门的函数将按键消息解释为WM_COMMAND消息。TranslateAccelerator()函数寻找WM_KEYDOWN,WM_CHAR,WM_KEYUP序列与表中键值匹配的字符。如果找到,它插入一条WM_COMMAND到消息队列,在消息队列中的命令ID可以是加速键表定义的任何入口。这样你只要设置加速键表(在资源中)并记住调用对应的函数TranslateAccelerator(),就什么都不用担心了。

      随着Visual C++和MFC的日臻成熟,现在几乎整个消息循环(但不是全部)都被隐藏到了MFC中,为了能让任何窗口都有机会获得一点消息泵的行为,MFC提供了一个专门的虚函数PreTranslateMessage(),如果你有足够的勇气去探究CWinThread中的消息处理机制的话,你会遇到类似如下的代码:

    // 简化后的 CWinThread
    while (GetMessage(...)) {
     if (PreTranslateMessage(...)) {
      // continue looping
     } else {
      TranslateMessage(...);
      DispatchMessage(...);
     }
    }


      CWinThread::PreTranslateMessage()是个虚函数,在应用中,其缺省的实现以相同的名字调用另一个虚函数CWnd::PreTranslateMessage()。因此,如果需要在消息循环中做些什么的话,如解释加速键,只要重载PreTranslateMessage()函数即可。实际上,这就是程序的框架CFrameWnd类处理加速键的方法。

    BOOL CFrameWnd::PreTranslateMessage(MSG* pMsg)
    {
     ......
     if (pMsg->message >= WM_KEYFIRST && pMsg->message <= WM_KEYLAST)
     {
      ::TranslateAccelerator(m_hAccelTable,...);
     }
    }


      CFrameWnd类是从哪里获得加速键表呢?当加载框架时,CFrameWnd::LoadFrame()函数使用与文档模板相同的ID(如IDR_MAINFRAME)查找加速键表,并将它加载到m_hAccelTable变量中。所有的处理细节在MFC中都是自动的、隐蔽的,读者朋友不用去操心。但是上述内容仅仅是对主框架而言,如果是对话框,则是另外一种情况,因为CDialog不是从CFrameWnd派生而来,所以不继承任何有关加速键的内容。对于这个问题不用担心,我们可以模仿CFrameWnd的工作,很容易为对话框增加加速键的功能。第一步是加载加速键,加载加速键最好的地方是在对话框的OnInitDialog函数中:

    BOOL CMyDlg::OnInitDialog()
    {
     CDialog::OnInitDialog();
     ......
     // Load accelerators
     m_hAccel = ::LoadAccelerators(AfxGetResourceHandle(), m_lpszTemplateName);
     ASSERT(m_hAccel);
     return TRUE;
    }


      在加速键表中,可以使用任何ID。例如上面的代码使用的是对话框本身的ID,(m_lpszTemplateName既可以是一个串名,也可以是一个MAKEINTRESOURCE使用的整型ID)。

    // 本文例子中的加速键(In DlgKeys.rc )
    IDD_MYDIALOG ACCELERATORS DISCARDABLE
    BEGIN
     VK_RETURN, ID_MY_ENTER, VIRTKEY, NOINVERT
    END


      一旦已经加载加速键,剩下的事情是重载PreTranslateMessage函数,进行消息映射了:

    BOOL CMyDlg::PreTranslateMessage(MSG* pMsg)
    {
     if (WM_KEYFIRST <= pMsg->message && pMsg->message <= WM_KEYLAST)
     {
      HACCEL hAccel = m_hAccel;
      if (hAccel && ::TranslateAccelerator(m_hWnd, hAccel, pMsg))
       return TRUE;
     }
     return CDialog::PreTranslateMessage(pMsg);
    }


      之所以要检查按键类的消息(从WM_ KEYFIRST 到 WM_KEYLAST)是为了提高速度。如果你知道不是一个按键消息,你就不用浪费时间去调用TranslateAccelerator()。再说TranslateAccelerator()是一个虚拟函数,不用增加一个消息映射入口。仅仅写这个函数就可以了。

      二、编程步骤

      1、 启动Visual C++6.0,生成一个Win32应用程序,将该程序命名为"DlgKeys";

      2、 使用CLASSWIZARD为应用程序添加CdlgWithAccelerators和CmyDlg类;

      3、 在程序的资源中添加添加加速键资源,内容如下:ID_MY_ENTER, VK_RETURNVIRTKEY,VIRTKEY;

      4、添加代码,编译运行程序。

    三、程序代码

    /
    #include "stdafx.h"
    // Generic dialog-that-uses-accelerators.
    class CDlgWithAccelerators : public CDialog {
    public:
     CDlgWithAccelerators(UINT nIDTemplate, CWnd* pParentWnd = NULL);
     CDlgWithAccelerators(LPCTSTR lpszTemplateName, CWnd* pParentWnd = NULL);
     ~CDlgWithAccelerators();
    protected:
     HACCEL m_hAccel; // accelerator table
     // MFC overrides
     virtual BOOL OnInitDialog();
     virtual BOOL PreTranslateMessage(MSG* pMsg);
     DECLARE_MESSAGE_MAP()
    };

    ///
    // CDlgWithAccelerators is a general-purpose class that adds accelerators to CDialog.
    #include "stdafx.h"
    #include "dlgaccel.h"
    #ifdef _DEBUG
    #define new DEBUG_NEW
    #undef THIS_FILE
    static char THIS_FILE[] = __FILE__;
    #endif
    BEGIN_MESSAGE_MAP(CDlgWithAccelerators,CDialog)
    END_MESSAGE_MAP()
    CDlgWithAccelerators::CDlgWithAccelerators(LPCTSTR lpszTemplateName,
    CWnd* pParentWnd) : CDialog(lpszTemplateName, pParentWnd)
    {}

    CDlgWithAccelerators::CDlgWithAccelerators(UINT nIDTemplate,
    CWnd* pParentWnd) : CDialog(nIDTemplate, pParentWnd)
    {}

    CDlgWithAccelerators::~CDlgWithAccelerators()
    {}

    /// Pre-translate message: translate keystrokes using acclerator table.
    BOOL CDlgWithAccelerators::PreTranslateMessage(MSG* pMsg)
    {
     if (WM_KEYFIRST <= pMsg->message && pMsg->message <= WM_KEYLAST) {
      HACCEL hAccel = m_hAccel;
      if (hAccel && ::TranslateAccelerator(m_hWnd, hAccel, pMsg))
       return TRUE;
     }
     return CDialog::PreTranslateMessage(pMsg);
    }

    Initialize dialog: load accelerators
    BOOL CDlgWithAccelerators::OnInitDialog()
    {
     BOOL bRet = CDialog::OnInitDialog();
     // Load dialog's accelerators
     m_hAccel = ::LoadAccelerators(AfxGetResourceHandle(),
     m_lpszTemplateName); // use same resource name as dialog
     return bRet;
    }

    /
    #include "stdafx.h"
    #include "resource.h"
    #include "dlgaccel.h"
    #include "TraceWin.h"
    #ifdef _DEBUG
    #define new DEBUG_NEW
    #undef THIS_FILE
    static char THIS_FILE[] = __FILE__;
    #endif

    /MFC app
    class CMyApp : public CWinApp {
    public:
     CMyApp();
     ~CMyApp();
     virtual BOOL InitInstance();
     DECLARE_MESSAGE_MAP()
    };

    CMyApp theApp; // THE one-and-only app

    frame window
    class CMainFrame : public CFrameWnd {
    protected:
     virtual BOOL PreCreateWindow(CREATESTRUCT& cs);
    public:
     CMainFrame();
     ~CMainFrame();
    };

    Typical dialog
    class CMyDlg : public CDlgWithAccelerators {
    public:
     CMyDlg(CWnd* pParent = NULL); // standard constructor
    protected:
     HICON m_hIcon;
     void NextInTabOrder();
     // MFC overrides
     virtual BOOL OnInitDialog();
     afx_msg void OnMyEnter();
     afx_msg LRESULT OnGetDefID(WPARAM wp, LPARAM lp);
     DECLARE_MESSAGE_MAP()
    };

    BEGIN_MESSAGE_MAP(CMyApp, CWinApp)
    END_MESSAGE_MAP()

    CMyApp::CMyApp()
    {
     // nothing to do
    }

    CMyApp::~CMyApp()
    {
     // nothing to do
    }

    InitInstance: create dialog as child
    BOOL CMyApp::InitInstance()
    {
     // create frame window and load it
     CMainFrame* pFrame = new CMainFrame;
     m_pMainWnd = pFrame;
     pFrame->LoadFrame(IDR_MAINFRAME, WS_OVERLAPPED, NULL, NULL);
     CMyDlg dlg(pFrame); // create dialog and run it
     int nResponse = dlg.DoModal();
     if (nResponse == IDOK)
     {}
     else if (nResponse == IDCANCEL)
     {}
     return FALSE; // quit
    }

    CMainFrame::CMainFrame()
    {
     // nothing to do
    }

    CMainFrame::~CMainFrame()
    {
     // nothing to do
    }

    / Pre-create window: set WS_EX_TOOLWINDOW style to hide dialog from task bar
    BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs)
    {
     if (CFrameWnd::PreCreateWindow(cs)) {
      cs.dwExStyle |= WS_EX_TOOLWINDOW;
      return TRUE;
     }
     return FALSE;
    }

    BEGIN_MESSAGE_MAP(CMyDlg, CDlgWithAccelerators)
    ON_COMMAND(ID_MY_ENTER, OnMyEnter)

    // The following is NOT needed since I am using accelerators to map
    // ENTER to ID_MY_ENTER. But if all you want to do is ignore the Enter key,
    // you can handle DM_GETDEFID as below.
    // ON_MESSAGE(DM_GETDEFID, OnGetDefID) // not used
    END_MESSAGE_MAP()

    CMyDlg::CMyDlg(CWnd* pParent) : CDlgWithAccelerators(IDD_MYDIALOG, pParent)
    {}

    Initialize dialog:
    BOOL CMyDlg::OnInitDialog()
    {
     CDlgWithAccelerators::OnInitDialog();
     // Set the icon for this dialog. The framework does this automatically
     // when the application's main window is not a dialog
     m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
     ASSERT(m_hIcon);
     SetIcon(m_hIcon, TRUE); // Set big icon
     SetIcon(m_hIcon, FALSE); // Set small icon
     // use same resource name as dialog to load dialog's accelerators
     m_hAccel = ::LoadAccelerators(AfxGetResourceHandle(),m_lpszTemplateName);
     ASSERT(m_hAccel);
     return TRUE; // return TRUE unless you set the focus to a control
    }

    This is called to handle ID_MY_ENTER--ie, Enter key.
    void CMyDlg::OnMyEnter()
    {
     TRACE(_T("CMyDlg::OnMyEnter\n"));
     NextInTabOrder(); // move to next control
    }

    Helper function to move focus to the next control.
    void CMyDlg::NextInTabOrder()
    {
     CWnd* pWndNext = GetNextDlgTabItem(GetFocus());
     if (pWndNext) {
      pWndNext->SetFocus();
     }
    }

    //
    // This function is not used, since its message map entry is commented out.
    // If all you want to do is ignore the Enter key (not map it to a command),
    // then all you have to do is return zero here. Note that you MUST return
    // the special code DC_HASDEFID in the high-order word!!
    LRESULT CMyDlg::OnGetDefID(WPARAM wp, LPARAM lp)
    {
     TRACE(_T("CMyDlg::OnGetDefID\n"));
     return MAKELONG(0,DC_HASDEFID);
    }


      四、小结

      综上所述,MFC中为对话框添加加速键功能的方法就是:加载加速键和重载PreTranslateMessage()函数。也就是说,如果开发人员决定在对话框中使用加速键,不用去操心OnGetDefID()函数的处理,而是要重点实现加速键对应的WM_COMMAND消息响应处理函数。 

     


    展开全文
  • 在iOS开发中,对于定制返回按钮,相信很多人遇到过,其方法也是很多,这篇文章记录下我的解决办法。 去掉文字类型,只显示”>” 这个方法是网上找来的,使用runtime完成。实现方式特别巧妙,对在某个子VC...

    iOS开发中,对于定制返回按钮,相信很多人遇到过,其方法也是很多,这篇文章记录下我的解决办法。

    去掉文字类型,只显示>

    这个方法是网上找来的,使用runtime完成。实现方式特别巧妙,对在某个子VC中单独设置返回按钮不会影响。创建一个UINavigationItemcategory,名为CustomBackButton,具体实现如下:

    static char kCustomBackButtonKey;

    @implementation UINavigationItem (CustomBackButton)

    + (void)load {

        static dispatch_once_t onceToken;

        dispatch_once(&onceToken, ^{

            Method originalMethodImp = class_getInstanceMethod(self, @selector(backBarButtonItem));

            Method destMethodImp = class_getInstanceMethod(self, @selector(myCustomBackButton_backBarbuttonItem));

            method_exchangeImplementations(originalMethodImp, destMethodImp);

        });

    }

    - (UIBarButtonItem *)myCustomBackButton_backBarbuttonItem {

        UIBarButtonItem *item = [self myCustomBackButton_backBarbuttonItem];

        if (item) {

            return item;

        }

       

        item = objc_getAssociatedObject(self, &kCustomBackButtonKey);

        if (!item) {

            

            item = [[UIBarButtonItem alloc] initWithTitle:@"" style:UIBarButtonItemStyleBordered target:nil action:nil];

            item.tintColor = [UIColor blackColor];

        }

        return item;

    }

    如果只是显示>”的话,使用runtime覆写backBarButtonItem方法就足够了。

    加图片的返回按钮

    但是很多情况下这样的返回按钮会显示的太粗,一般用一张图片来替代。需要注意的是,对图片的要求很高,不要过大,负责会显示错乱。实现代码是:

    //设置返回样式图片

    UIImage *image = [UIImage imageNamed:@"preview_back_black"];

    image = [image imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];

    navigationBar.backIndicatorImage = image;

    navigationBar.backIndicatorTransitionMaskImage = image;

    图片@3x的大小是90*90即可,具体就不给图片了。

    文章来源:Hyyy's blog

    展开全文
  • VC 程序中定制对话框中的回车键

    千次阅读 2013-08-07 14:55:31
    基于对话框的程序中,每当用户按下回车键时,程序都会退出,其效果和按下对话框中的默认"OK"按钮是一样的,即使去掉"OK"按钮的 BS_DEFPUSHBUTTON属性也没用。那么如何定制回车键的行为呢? 要解决问题,必须...


    基于对话框的程序中,每当用户按下回车键时,程序都会退出,其效果和按下对话框中的默认"OK"按钮是一样的,即使去掉"OK"按钮的  

    BS_DEFPUSHBUTTON
    属性也没用。那么如何定制回车键的行为呢?


    要解决问题,必须搞清楚背后所发生的一切,在 Spy++ 中可以看到,当用户按下回车键时,Windows发送一个特殊的 DM_GETDEFID 消息来获得缺省的命令ID,Windows再将它作为 WM_COMMAND 发送。所以,我们要做的就是重载 DM_GETDEFID 消息。

    在有关 Windows 的文档中是这样描述 DM_GETDEFID 返回值的:"如果有缺省的按钮,则返回值的高位字包含 DC_HASDEFID,低位字包含控制的标识符。否则,返回值是零"。根据这段描述,假设如果没有缺省得按钮,则返回值应该是零。如果想要 disable 缺省的 ID,必须在低位字中返回0,在高位字中返回 DC_HASDEFID,。因此定义和实现消息映射函数如下:


    BEGIN_MESSAGE_MAP(CMyDlg, CDialog)
          ON_MESSAGE(DM_GETDEFID, OnGetDefID)
          ...
    END_MESSAGE_MAP()
    
    LRESULT CMyDlg::OnGetDefID(WPARAM wp, LPARAM lp) 
    {
        return MAKELONG(0, DC_HASDEFID); 
    }

    因为 MFC 没有对应 DM_GETDEFID 的宏,你必须使用通用的 ON_MASSAGE 宏。这样用户可以随意按回车键,但什么事都不会发生。


    附:MSDN 的解释:

    DM_GETDEFID message


    Parameters

    wParam

    This parameter is not used and must be zero.

    lParam

    This parameter is not used and must be zero.

    Return value

    If a default push button exists, the high-order word of the return value contains the value DC_HASDEFID and the low-order word contains the control identifier. Otherwise, the return value is zero.

    Remarks

    The DefDlgProc function processes this message. 




    注:本文参考:http://www.cnblogs.com/MayGarden/archive/2010/12/29/1920949.html



    展开全文
  • vc6

    2016-10-24 22:48:00
    1.右击VC6工具栏,选择【自定义...】(或者点击菜单【工具】-【定制】)2.点击【附加项和宏文件】选项卡3.选择【浏览】按钮4.在打开的对话框中【文件类型】列表框选择第二个(Add-ins(.dll))5.选中你下载的那个...
  • VC6风格界面

    2013-07-11 19:38:49
    ...................\VC++6.0定制窗口的方法.doc ...................\VC++中MFC窗口对象的清除.doc ...................\VC++任务栏提示区图标的实现.doc ...................\VC++动态加入和删除菜单的方法....
  • 我用vc6写了一个windows界面的...但是如果要处理工具栏事件需要先添加菜单项,并使菜单项的id与工具栏按钮的相同,但是一个绘图工具栏按钮明显不应该需要一个单独定制的菜单项!请问各位大神有什么解决办法呢?求救!
  • 通过SkinLoadMaker皮肤编辑工具,可以自己定制皮肤。本版去除了原来”Powered by SkinLoad”标志,增加了XP风格的按钮支持,可以供大家在非商业程序中自由使用。开发环境: VC6 Windows XP测试环境: WindowsXP ...
  • 做iOS项目中,可能会经常遇到要定制后退按钮的情况,比如把后退按钮的title固定为“返回”(修改title对后面push的vc生效),比如用图片,这时候大家一般会选择添加一个vc的基类,因为这个问题其实很简单,随便做点...
  • 在开始建MFC(DLL)工程之前我们得下载matcom程序,然后安装,打开vc6.0然后打开 工具-定制-附加项,然后选中visual MATCOM Add-in,成功后在vc6.0工具栏上会有显示。  开始我们的工程:  (1)打开vc6.0建一个...
  • 5.VC6->工程->定制->工具栏,然后打开工具栏上面的“文件”,用鼠标拖着移去“打开”按钮的图标,接着把O用鼠标拖到“打开”的位置;同样的方法设置A到“工程”下的相应位置。 到这里,VC6在WIN7下基本上是没有...
  • VC6.0中不能添加源文件到工程中的解决方案: ...2、打开vc6,上面打开:工具-定制-附加项和宏文件,选中filetool。。。那个文件、关闭之后就出现两个蓝色的小按钮。A就是用来添加的。 备注:下载地址
  • 1、我注意到一些应用程序,当右键单击其任务栏最小化按钮时,在弹出的上下文菜单中具备特殊的命令。例如,WinAmp(一个流行的媒体播放器)有一个附加的 ...我如何处理这些定制的系统菜单消息? 关键字:menu,ta
  • vc-mfc编程实例.rar

    热门讨论 2010-08-27 15:32:21
    7.7 例28 为工具栏添加非按钮控件 131 7.8 例29 修改应用程序的状态栏 136 7.9 例30 更新状态栏窗格 138 7.10 例31 为状态栏添加其他控件 139 第8章 视图 145 8.1 例32 滚动视图 145 8.2 例33 改变鼠标光标形状 147 ...
  • 使用VC2010在MFC基础上基于对话框的项目开发,需要使用到工具栏。效果如上图所示,正常情况显示如图1所示,当有鼠标移动到对应的按钮上时显示不同的状态的图片。 我使用位图资源进行的开发加上CImageList动态设置...
  • 该Excel表加了密码,并且含有很多数据,当在VC中通过 Excel Ole对象打开该Excel文档时候,出现 "服务器正在运行中“对话框,其中有”切换到。。。“按钮。   根本原因:   发现问题我知道这是Ole Server Busy...
  • 用户可根据自己的需要定制快捷菜单中的一些内容。假设用户希望在txt文件类型的右键快捷菜单中关联上自己的应用程序 (用户的应用程序名为mytxtapp.exe,在D盘根目录下) ,步骤如下: 1、在注册表中找到并打开HKEY_...
  • swift-iOS项目框架问题

    2019-08-15 05:07:27
    iOS项目框架问题(baseVC,baseNav、全屏返回手势、旋转屏幕、截获back返回事件、定制不同VC的返回按钮,iOS 11适配等等)
  • FileTool.zip

    2020-07-07 16:17:30
    VC无法导入.c和.h文件,将FileTool.dll拷贝到VC安装目录下,在Visualc + + 中单击 工具菜单中的定制,在定制对话框中单击 附加项和宏文件选项卡,单击 浏览 按钮并找到在目标程序 FileTool.dll 文件,单击 确定 以...
  • 此时VC中会出现一个上面只有两个图标的工具栏,点击其右上角的“X”按钮将其关闭,然后关闭VC6.0并重新启动程序此时打开VC6会有一个浮动工具栏(A O),点击A就是添加文件到工程,点击O就是打开文件8. 还是在VC6.0...
  • 由于兼容性的问题,在WIN7下使用VC++6.0的时候,再点击打开文件按钮...2.强下载下来的文件放到VC的安装目录\Common\MSDev98下,如图: 3.点击“工具-定制按钮,选择附加项和宏文件,最后点击浏览。 4.选择
  • VC++6.0 显示行号

    2019-10-05 16:56:15
    通过VC6LineNumberAddin能够解决这个问题,方法如下。 一、下载该文件。 ...“定制(Customize)”, 选择“附加项和宏文件(Add-ins and Macro Files)”选项卡,点击右 下角的“浏览按钮”,文件...
  • 摘要:VC/C++源码,界面编程,光标,图标 VC++如何修改MFC AppWizard向导生成的框架程序的外观和大小,修改图标、光标、背景的三种方法、如何增加和删除工具栏按钮、如何给应用程序增加工具栏,如何显示和隐藏工具栏。...

空空如也

空空如也

1 2 3
收藏数 51
精华内容 20
关键字:

vc定制按钮