2

我正在尝试使用 NM_CUSTOMDRAW 消息自定义树视图控件。我只是想用灰色绘制所有其他可见项目。这是绘制的代码:

INT CResourceOutliner::On_WM_NOTIFY( HWND hDlg, WPARAM wParam, LPARAM lParam )
{
    HWND hTree = GetDlgItem( hDlg, IDC_TREE1 ); 
    switch( ( ( LPNMHDR )lParam )->code )
    {
    ...
    case NM_CUSTOMDRAW:
            {           
                LPNMTVCUSTOMDRAW pCustomDraw = ( LPNMTVCUSTOMDRAW )lParam;
                switch( pCustomDraw->nmcd.dwDrawStage )
                {               
                case CDDS_PREPAINT:
                    return CDRF_NOTIFYITEMDRAW;
                case CDDS_ITEMPREPAINT:
                    {
                        switch ( pCustomDraw->iLevel )                  
                        {
                            // painting all 0-level items blue,                     
                            // and all 1-level items red (GGH)25.                       
                        case 0:
                            {
                            if( pCustomDraw->nmcd.uItemState == ( CDIS_FOCUS | CDIS_SELECTED ) )                            
                                pCustomDraw->clrTextBk = RGB( 255, 255, 255 );                          
                            else                                    
                                pCustomDraw->clrTextBk = RGB( 128, 128, 128 );                          
                                break;
                            }
                        case 1:                         
                            {
                                if( pCustomDraw->nmcd.uItemState == ( CDIS_FOCUS | CDIS_SELECTED ) )                            
                                    pCustomDraw->clrTextBk = RGB( 255, 255, 255 );                          
                                else    
                                    pCustomDraw->clrTextBk = RGB( 128, 128, 128 );
                                break;
                            }
                        default:
                            break;
                        }
                        return CDRF_SKIPDEFAULT;
                    }
                default:
                    break;
                }
            }
    ...
    }
}

这段代码来自这里

问题是在 CDDS_PREPAINT 通知消息上返回 CDRF_NOTIFYITEMDRAW 后,CDDS_ITEMPREPAINT 消息永远不会出现......是否有一个选项可以设置以启用自定义绘图......?我想没有因为 CDDS_PREPAINT 消息是由控件发送的...

...此外,上面的代码并不意味着绘制所有其他项目...它只是 codeguru.com 的一个演示

这是消息处理实现...

int CResourceOutliner::DoModal( int resID, RECT rct, HWND hParent )
{   
    // Set properties
    m_dwpSaveThis = ( DWORD_PTR )this; /// store this pointer
    m_nResId = resID;
    m_hParent = hParent;

    m_hWindow = CreateDialog( GetModuleHandle( NULL ), MAKEINTRESOURCE( m_nResId ), m_hParent, ( DLGPROC )MsgProcStatic );

    // Set window position
    SetWindowPos( m_hWindow, 0, rct.left, rct.top, rct.right, rct.bottom, 0 );

    ShowWindow( m_hWindow, SW_HIDE );

    if( m_hWindow )
        return 1;

    return 0; 
}
INT CALLBACK CResourceOutliner::MsgProcStatic( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam )
{
    if( !m_hWindow )
        m_hWindow = hWnd;

    CResourceOutliner *pDlg = ( CResourceOutliner* )m_dwpSaveThis;
    if( pDlg )
        return pDlg->MsgProc( hWnd, uMsg, wParam, lParam );
    else
        return 0;
}
INT CALLBACK CResourceOutliner::MsgProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam )
{
    switch( uMsg )
    {
    case WM_INITDIALOG:
        On_WM_INITDIALOG( hWnd, wParam, lParam );
        break;
    case WM_COMMAND:
        On_WM_COMMAND( hWnd, wParam, lParam );
        break;
    case WM_NOTIFY:
        {           
            return On_WM_NOTIFY( hWnd, wParam, lParam );
        }
    case WM_LBUTTONDOWN:
        On_WM_LBUTTONDOWN( hWnd, wParam, lParam );
        break;
    case WM_LBUTTONUP:
        On_WM_LBUTTONUP( hWnd, wParam, lParam );
        break;
    case WM_MOUSEMOVE:
        On_WM_MOUSEMOVE( hWnd, wParam, lParam );
        break;
    case WM_PAINT:
        On_WM_PAINT( hWnd, wParam, lParam );
        break;
    case WM_CLOSE:
        On_WM_CLOSE( hWnd, wParam, lParam );
        break;
    default:
        return 0;
    }
    return 0;
}
4

1 回答 1

5

对话过程的大多数返回码都需要通过 设置DWLP_MSGRESULT,例如:

SetWindowLongPtr(hWnd, DWLP_MSGRESULT, CDRF_NOTIFYITEMDRAW);

此规则很少有例外(WM_CTLCOLORSTATIC一个直接返回的示例),因为对话过程通常被定义为返回TRUEFALSE取决于消息是否被处理。

于 2013-09-14T22:03:12.120 回答