程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> .NET網頁編程 >> .NET實例教程 >> WTL分列顯示的ListBox

WTL分列顯示的ListBox

編輯:.NET實例教程
 在界面數據顯示時一般使用ListBox或支持分列顯示的ListCtrl,如果同一個界面中有兩個以上關聯數據表格要顯示,那麼使用ListBox的好處在任何時候都可以清晰的表明數據行選中/未選中狀態,從而表示表格之間的關系,而使用ListCtrl中則狀態不明顯,比如MFC類向導,其中的數據顯示使用ListBox,在多個ListBox窗口中可以同時顯示每個窗口的數據選中狀態,注意一點,MFC類向導使用的ListBox是分列顯示的。那麼我們能否也實現一個分列顯示的ListBox。在WTL可以輕易實現這一點。代碼隊在最後:

     如何使用:在WTL使用時,需要注意的是在資源編輯器中將ListBox屬性設計為LBS_OWNERDRAWFIXED和LBS_HASSTRINGS,需要在消息宏添加REFLECT_NOTIFICATION()以支持自畫消息。



BEGIN_MSG_MAP(CMainDlg)
    ...
    REFLECT_NOTIFICATION()
END_MSG_MAP()

在添加數據時數據之間使用“;”來進行列之間分開,當然你也可以修改源代碼使用其他分隔符或者定義一個變量來指示分隔符,CDevListBoxImpl中的m_nDivider 用來控制列的寬度,如果某一行的列寬超過這個寬度將自動增加寬度來容納內容,就象MFC的類向導所做的一樣,我並沒有指定具體一列的寬度,對於我來言,兩列足夠了。然後需要的話你也可以修改代碼使用一個int數組來保存列寬,我相信這對你來言相當容易。



CDevListBoxImpl m_list

m_list.SubclassWindow(GetDlgItem(IDC_LISTBOX1);
m_list.AddString(_T("Item0;True");
m_lsit.AddString(_T("Item1;False");
....

CDevListBoxImpl的代碼



class CDevListBoxImpl : public CWindowImpl<CDevListBoxImpl, CListBox>,                        public COwnerDraw<CDevListBoxImpl>
...{
public:
    CDevListBoxImpl()
    ...{
        m_nDivider = 200; 
    }

    BEGIN_MSG_MAP(CDevListBoxImpl)
    MESSAGE_HANDLER(WM_CREATE, OnCreate)
    CHAIN_MSG_MAP_ALT(COwnerDraw<CDevListBoxImpl>, 1)
                     DEFAULT_REFLECTION_HANDLER()
    END_MSG_MAP()

    //

overridden to provide proper initialization
    BOOL SubclassWindow(HWND hWnd)
    ...{
        BOOL bRet = CWindowImpl<CDevListBoxImpl, CListBox>::SubclassWindow(hWnd);
        if(bRet)
            Init();
        return bRet;
    }
    LRESULT OnCreate(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
    ...{
        // TODO : Add Code for message handler. Call DefWindowProc if necessary.
        Init();
        bHandled = FALSE;
        return 1;
    }
// Implementation
    void Init()
    ...{
        // We need this style to prevent Windows from painting the button
        ModifyStyle(0, BS_OWNERDRAW | LBS_OWNERDRAWFIXED | LBS_HASSTRINGS );
    }

    void DrawItem ( LPDRAWITEMSTRUCT lpDIS )
 ...{
        CDCHandle dc = lpDIS->hDC;
        CRect rect = lpDIS->rcItem;
        if (m_nDivider==0)
            m_nDivider = rect.Width() / 2;

        
        if (lpDIS->itemID != (UINT) -1)
        ...{
            TCHAR sz[128] = ...{0};
            CListBox::GetText(lpDIS->itemID,sz);
            COLORREF oldColor;
            //draw two rectangles, one for each row column
            if (lpDIS->itemState & ODS_SELECTED  == ODS_SELECTED )
            ...{
                dc.FillSolidRect(&lpDIS->rcItem,RGB(0,0,128));
       oldColor = dc.SetTextColor(RGB(255,255,255));
            }
            else
            ...{
                dc.FillSolidRect(&lpDIS->rcItem,RGB(255,255,255));
                oldColor = dc.SetTextColor(RGB(0,0,0));
            }

            dc.SetBkMode(TRANSPARENT);

            TCHAR * tok = ::_tcstok(sz,_T(";"));
            while (tok != NULL)
            ...{
                dc.DrawText(tok,lstrlen(tok),rect,DT_LEFT | DT_SINGLELINE);
                rect.left += m_nDivider;
                SIZE sz;
                dc.GetTextExtent(tok,-1,&sz);
                if (sz.cx >= 2*m_nDivider)
           &nbsp;    ...{
                    rect.left = rect.left-m_nDivider+sz.cx+20;
                }
                else if (sz.cx >= m_nDivider)
                ...{
                    rect.left += m_nDivider;
                }
                tok = ::_tcstok(NULL,_T(";"));
            }

            dc.SetTextColor(oldColor);
        }
        SetMsgHandled(FALSE);
    }
    int    m_nDivider;
};


  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved