您的位置:首页 > 编程语言

Windows界面编程第八篇 listbox彩色显示隔行变色

2013-03-15 20:15 344 查看
在CSDN论坛上看到很多询问如何设置listbox的颜色,如何让listbox隔行变色等等。因此专门写了一篇《Windows界面编程第八篇
listbox彩色显示隔行变色》来为大家解惑。
       首先看看下图(如果看不到,可以通过地址http://blog.csdn.net/morewindows/article/details/8656061访问)。



要设置listbox的颜色及让listbox隔行变色主要是通过处理WM_DRAWITEM消息,这个消息在MSDN的解释如下:

The
WM_DRAWITEM
message is sent to the parent window of an owner-drawn button, combo box, list box, or menu when a visual aspect of the button, combo box, list box, or menu has changed.
通过这个消息最主要可以得到一个DRAWITEMSTRUCT类型的结构体。这个结构体的原型如下:

//By MoreWindows-(http://blog.csdn.net/MoreWindows)
typedef structtagDRAWITEMSTRUCT {
   UINTCtlType;
   UINTCtlID;
   UINTitemID;
   UINTitemAction;
   UINTitemState;
   HWNDhwndItem;
   HDChDC;
   RECT
rcItem;
   ULONG_PTRitemData;
}DRAWITEMSTRUCT;

这个结构体比较复杂,功能也很强大。全部记住它的功能是不必要的。因此直接查看下如何设置listbox的颜色,如何让listbox隔行变色这两个功能是如何完成的即可。完整代码+注释如下(可以直接到http://download.csdn.net/detail/morewindows/5128660(免积分)下载)。

[cpp]view plaincopyprint?

//Windows界面编程第八篇 listbox彩色显示隔行变色 
//http://blog.csdn.net/morewindows/article/details/8656061 
//By MoreWindows-(http://blog.csdn.net/MoreWindows) 

#include "stdafx.h" 
#include "resource.h" 
 
BOOL CALLBACK DlgProc(HWND hDlg,UINT message,
WPARAM wParam,LPARAM lParam); 

//使窗口居中 
void CenterWindow(HWND hwnd); 
 
int APIENTRY WinMain(HINSTANCE hInstance, 
                    
HINSTANCE hPrevInstance, 
                    LPSTR     lpCmdLine, 

                    
int       nCmdShow) 

    // TODO: Place code here. 
    DialogBox(hInstance, MAKEINTRESOURCE(IDD_DIALOG1), NULL, DlgProc); 
    return 0; 

 
constint MAX_NUMBER = 8; 

constint MAX_STRING_LEN = 50; 

constchar STR_TEXT[MAX_NUMBER][MAX_STRING_LEN] = { 
    "MoreWindows",  
   
"Master", 
    "blog.csdn.net/MoreWindows",  
   
"weibo.com/MoreWindows", 
    "Windows界面编程", 
   
"秒杀多线程面试题系列", 
    "Windows界面编程第八篇", 
   
"listbox彩色显示隔行变色" 
}; 
BOOL CALLBACK DlgProc(HWND hDlg,UINT message,
WPARAM wParam,LPARAM lParam) 


   
static HWND s_hLBColorListBox; 
    switch (message) 
    { 
    case WM_INITDIALOG: 
        { 

            CenterWindow(hDlg); 
            s_hLBColorListBox = GetDlgItem(hDlg, IDC_LB_COLORLISTBOX); 
           
//添加数据 
           
for (int i = 0; i < MAX_NUMBER; i++) 
                SendMessage(s_hLBColorListBox, LB_ADDSTRING, 0, (LPARAM)STR_TEXT[i]); 
        } 

       
return FALSE; 
         

         
   
case WM_COMMAND: 
       
switch (LOWORD(wParam)) 
        { 

       
case IDOK: 
       
case IDCANCEL: 
            EndDialog(hDlg, FALSE); 
           
return TRUE; 
 
       
case IDC_LB_COLORLISTBOX:  //listbox control ID 
           
switch (HIWORD(wParam)) 
            { 

           
case LBN_DBLCLK:   //双击事件 
                {    
                   
char szBuffer[MAX_STRING_LEN]; 
                   int nCurSel = SendMessage(s_hLBColorListBox, LB_GETCURSEL, 0, 0); 
                    SendMessage(s_hLBColorListBox, LB_GETTEXT, (WPARAM)nCurSel, (LPARAM)szBuffer); 
                    MessageBox(NULL, szBuffer,"listbox item", MB_OK); 

                } 
               
return TRUE; 
            } 
           
break; 
        } 
       
break; 
 
 
    case WM_DRAWITEM: 
        { 

            LPDRAWITEMSTRUCT lpDrawItem = (LPDRAWITEMSTRUCT)lParam; 
           
if (lpDrawItem->CtlType == ODT_LISTBOX || lpDrawItem->CtlID == IDC_LB_COLORLISTBOX) 
            { 
               
if (lpDrawItem->itemID == -1) 
                   
break; 
                 
               
char szItemString[MAX_STRING_LEN]; 
               
int nItemStringLen; 
                SendMessage(s_hLBColorListBox, LB_GETTEXT, (WPARAM)lpDrawItem->itemID, (LPARAM)szItemString); 
                nItemStringLen = strlen(szItemString); 
 
               
// 设置选中一行时,这一行加边框,反色 
               
if ((lpDrawItem->itemState & ODS_SELECTED) &&    
                    (lpDrawItem->itemAction & (ODA_SELECT | ODA_DRAWENTIRE))) 
                { 
                    DrawFocusRect(lpDrawItem->hDC, &lpDrawItem->rcItem);  
                    InvertRect(lpDrawItem->hDC, &lpDrawItem->rcItem); 
                } 
               
else if (!(lpDrawItem->itemState & ODS_SELECTED) &&  
                    (lpDrawItem->itemAction & ODA_SELECT)) 
                { 
                    DrawFocusRect(lpDrawItem->hDC, &lpDrawItem->rcItem); 
                    InvertRect(lpDrawItem->hDC, &lpDrawItem->rcItem); 
                } 
                 
               
// 隔行变色 
               
if (lpDrawItem->itemID % 2 == 0) 
                    SetTextColor(lpDrawItem->hDC, RGB(25, 125, 0)); 
               
else 
                    SetTextColor(lpDrawItem->hDC, RGB(0, 25, 125)); 
                 
               
// 文字背景色 
               
if (lpDrawItem->itemState & ODS_SELECTED) 
                { 
                    SetBkMode(lpDrawItem->hDC, TRANSPARENT); 
                    SetTextColor(lpDrawItem->hDC, RGB(255, 255, 255)); 
                } 
               
else  
                { 
                    SetBkMode(lpDrawItem->hDC, OPAQUE); 
                    SetBkColor(lpDrawItem->hDC, GetSysColor(COLOR_WINDOW)); 
                } 
                 
               
//输出文字 
                DrawText(lpDrawItem->hDC, szItemString, nItemStringLen, &lpDrawItem->rcItem, DT_LEFT | DT_SINGLELINE); 
               
return TRUE; 
            }    
        } 

       
break; 
    } 
    return FALSE; 

 
void CenterWindow(HWND hwnd) 

    RECT   rcDlg; 
    int    nDlgWidth, nDlgHight; 
   
int    nScreenWidth, nScreenHight; 
     
    nScreenWidth = GetSystemMetrics(SM_CXSCREEN); 
    nScreenHight = GetSystemMetrics(SM_CYSCREEN); 
     
    GetWindowRect(hwnd, &rcDlg); 
    nDlgWidth = rcDlg.right - rcDlg.left; 
    nDlgHight = rcDlg.bottom - rcDlg.top; 
     
    MoveWindow(hwnd, (nScreenWidth  - nDlgWidth) / 2, (nScreenHight - nDlgHight) / 2, nDlgWidth, nDlgHight, FALSE); 


//Windows界面编程第八篇 listbox彩色显示隔行变色
//http://blog.csdn.net/morewindows/article/details/8656061
//By MoreWindows-(http://blog.csdn.net/MoreWindows)
#include "stdafx.h"
#include "resource.h"

BOOL CALLBACK DlgProc(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam);
//使窗口居中
void CenterWindow(HWND hwnd);

int APIENTRY WinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPSTR     lpCmdLine,
int       nCmdShow)
{
// TODO: Place code here.
DialogBox(hInstance, MAKEINTRESOURCE(IDD_DIALOG1), NULL, DlgProc);
return 0;
}

const int MAX_NUMBER = 8;
const int MAX_STRING_LEN = 50;
const char STR_TEXT[MAX_NUMBER][MAX_STRING_LEN] = {
"MoreWindows",
"Master",
"blog.csdn.net/MoreWindows",
"weibo.com/MoreWindows",
"Windows界面编程",
"秒杀多线程面试题系列",
"Windows界面编程第八篇",
"listbox彩色显示隔行变色"
};
BOOL CALLBACK DlgProc(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{
static HWND s_hLBColorListBox;
switch (message)
{
case WM_INITDIALOG:
{
CenterWindow(hDlg);
s_hLBColorListBox = GetDlgItem(hDlg, IDC_LB_COLORLISTBOX);
//添加数据
for (int i = 0; i < MAX_NUMBER; i++)
SendMessage(s_hLBColorListBox, LB_ADDSTRING, 0, (LPARAM)STR_TEXT[i]);
}
return FALSE;

case WM_COMMAND:
switch (LOWORD(wParam))
{
case IDOK:
case IDCANCEL:
EndDialog(hDlg, FALSE);
return TRUE;

case IDC_LB_COLORLISTBOX:  //listbox control ID
switch (HIWORD(wParam))
{
case LBN_DBLCLK:   //双击事件
{
char szBuffer[MAX_STRING_LEN];
int nCurSel = SendMessage(s_hLBColorListBox, LB_GETCURSEL, 0, 0);
SendMessage(s_hLBColorListBox, LB_GETTEXT, (WPARAM)nCurSel, (LPARAM)szBuffer);
MessageBox(NULL, szBuffer, "listbox item", MB_OK);
}
return TRUE;
}
break;
}
break;

case WM_DRAWITEM:
{
LPDRAWITEMSTRUCT lpDrawItem = (LPDRAWITEMSTRUCT)lParam;
if (lpDrawItem->CtlType == ODT_LISTBOX || lpDrawItem->CtlID == IDC_LB_COLORLISTBOX)
{
if (lpDrawItem->itemID == -1)
break;

char szItemString[MAX_STRING_LEN];
int nItemStringLen;
SendMessage(s_hLBColorListBox, LB_GETTEXT, (WPARAM)lpDrawItem->itemID, (LPARAM)szItemString);
nItemStringLen = strlen(szItemString);

// 设置选中一行时,这一行加边框,反色
if ((lpDrawItem->itemState & ODS_SELECTED) &&
(lpDrawItem->itemAction & (ODA_SELECT | ODA_DRAWENTIRE)))
{
DrawFocusRect(lpDrawItem->hDC, &lpDrawItem->rcItem);
InvertRect(lpDrawItem->hDC, &lpDrawItem->rcItem);
}
else if (!(lpDrawItem->itemState & ODS_SELECTED) &&
(lpDrawItem->itemAction & ODA_SELECT))
{
DrawFocusRect(lpDrawItem->hDC, &lpDrawItem->rcItem);
InvertRect(lpDrawItem->hDC, &lpDrawItem->rcItem);
}

// 隔行变色
if (lpDrawItem->itemID % 2 == 0)
SetTextColor(lpDrawItem->hDC, RGB(25, 125, 0));
else
SetTextColor(lpDrawItem->hDC, RGB(0, 25, 125));

// 文字背景色
if (lpDrawItem->itemState & ODS_SELECTED)
{
SetBkMode(lpDrawItem->hDC, TRANSPARENT);
SetTextColor(lpDrawItem->hDC, RGB(255, 255, 255));
}
else
{
SetBkMode(lpDrawItem->hDC, OPAQUE);
SetBkColor(lpDrawItem->hDC, GetSysColor(COLOR_WINDOW));
}

//输出文字
DrawText(lpDrawItem->hDC, szItemString, nItemStringLen, &lpDrawItem->rcItem, DT_LEFT | DT_SINGLELINE);
return TRUE;
}
}
break;
}
return FALSE;
}

void CenterWindow(HWND hwnd)
{
RECT   rcDlg;
int    nDlgWidth, nDlgHight;
int    nScreenWidth, nScreenHight;

nScreenWidth = GetSystemMetrics(SM_CXSCREEN);
nScreenHight = GetSystemMetrics(SM_CYSCREEN);

GetWindowRect(hwnd, &rcDlg);
nDlgWidth = rcDlg.right - rcDlg.left;
nDlgHight = rcDlg.bottom - rcDlg.top;

MoveWindow(hwnd, (nScreenWidth  - nDlgWidth) / 2, (nScreenHight - nDlgHight) / 2, nDlgWidth, nDlgHight, FALSE);
}

下面列出全部目录,方便大家浏览:

1. 《Windows界面编程第一篇位图背景与位图画刷

2. 《Windows界面编程第二篇半透明窗体

3. 《Windows界面编程第三篇异形窗体普通版

4. 《Windows界面编程第四篇异形窗体高富帅版

5. 《Windows界面编程第五篇静态控件背景透明化

6.《Windows界面编程第六篇
动画启动效果(动画效果显示及隐藏窗口)》

7.《Windows界面编程第七篇
文件拖拽(文件拖放)》

8.《Windows界面编程第八篇
listbox彩色显示隔行变色》

本文配套程序下载地址为:http://download.csdn.net/detail/morewindows/5128660

转载请标明出处,原文地址:http://blog.csdn.net/morewindows/article/details/8656061

欢迎关注微博:http://weibo.com/MoreWindows
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息