关于windows的list view使用的两点经验
2014-01-14 14:58
267 查看
前段时间写一个虚拟桌面的demo,是使用shell接口以及list展现桌面图标以及行为的功能。如图
实现上包括右键菜单的行为。以下是我在开发过程中碰到的一些难点或者说是不注意就会出错的地方,花了不少时间找资料测试。
我的程序是基于vs2008的SDK所带的例子VListvw所做的修改:
C:\Program Files\Microsoft SDKs\Windows\v7.0\Samples\winui\controls\common\vlistvw
1. 原程序中在创建list view的时候,使用的style是加了LVS_OWNERDATA;这个风格是基于大数据部分显示功能使用的,每次显示数据更新的时候都需要发送LVN_GETDISPINFO消息给控件,让控件返回显示的数据。我的程序基于已经存储下来的数据,不要使用这个风格来获取信息。应该删除LVS_OWNERDATA风格。
2. 另外一个问题,困扰了我几天,就是在响应右键菜单行为的时候,怎么样去获取已经存储的那个节点的数据信息。我原来在加入list view的数据的时候,设置了重要的对象信息到LVITEM里面的lparam这个变量中,但是通过下面的代码中的ListView_GetItem宏来发送消息取得Item的信息;但是我发现,以下代码死活无法取得LPARAM变量的值回来。而在处理LVN_GETDISPINFO这个消息的时候,是会传进去Lparam数据的,但是返回来的时候是没有的。原则上,已经在lvitem.mask中设置了LVIF_PARAM标记,就会返回LPARAM数据,但是没有成功!
我查一下MSDN中的描述:
iSubItem
Type: int
One-based index of the subitem to which this structure refers, or zero if this structure refers to an item rather than a subitem.
这里也没有完全说明白,但试过了之后,就发现,把这个值设置为0,就可以了!!!在ListView_GetItem的时候也不会发送LVN_GETDISPINFO消息了,返回来的值中带了Lparam的值!追究起来,这个iSubItem应该是指iItem这一行的一个子项目上附加的数据,这样一来,即使标记了LVIF_PARAM标志,也没法取得对iIem这个项目设置的值了!
附加我的demo程序:http://download.csdn.net/detail/eagleatustb/6847501
实现上包括右键菜单的行为。以下是我在开发过程中碰到的一些难点或者说是不注意就会出错的地方,花了不少时间找资料测试。
我的程序是基于vs2008的SDK所带的例子VListvw所做的修改:
C:\Program Files\Microsoft SDKs\Windows\v7.0\Samples\winui\controls\common\vlistvw
1. 原程序中在创建list view的时候,使用的style是加了LVS_OWNERDATA;这个风格是基于大数据部分显示功能使用的,每次显示数据更新的时候都需要发送LVN_GETDISPINFO消息给控件,让控件返回显示的数据。我的程序基于已经存储下来的数据,不要使用这个风格来获取信息。应该删除LVS_OWNERDATA风格。
HWND CreateListView(HINSTANCE hInstance, HWND hwndParent) { DWORD dwStyle; HWND hwndListView; HIMAGELIST himlSmall; HIMAGELIST himlLarge; BOOL bSuccess = TRUE; dwStyle = WS_TABSTOP | WS_CHILD | WS_BORDER | WS_VISIBLE | LVS_AUTOARRANGE | LVS_REPORT | LVS_OWNERDATA; hwndListView = CreateWindowEx( WS_EX_CLIENTEDGE, // ex style WC_LISTVIEW, // class name - defined in commctrl.h TEXT(""), // dummy text dwStyle, // style 0, // x position 0, // y position 0, // width 0, // height hwndParent, // parent (HMENU)ID_LISTVIEW, // ID g_hInst, // instance NULL); // no extra data if(!hwndListView) return NULL; ResizeListView(hwndListView, hwndParent); //set the image lists himlSmall = ImageList_Create(16, 16, ILC_COLORDDB | ILC_MASK, 1, 0); himlLarge = ImageList_Create(64, 32, ILC_COLORDDB | ILC_MASK, 1, 0); if (himlSmall && himlLarge) { HICON hIcon; //set up the small image list hIcon = LoadImage(g_hInst, MAKEINTRESOURCE(IDI_DISK), IMAGE_ICON, 16, 16, LR_DEFAULTCOLOR); ImageList_AddIcon(himlSmall, hIcon); //set up the large image list hIcon = LoadIcon(g_hInst, MAKEINTRESOURCE(IDI_DISK)); ImageList_AddIcon(himlLarge, hIcon); ListView_SetImageList(hwndListView, himlSmall, LVSIL_SMALL); ListView_SetImageList(hwndListView, himlLarge, LVSIL_NORMAL); } return hwndListView; }
2. 另外一个问题,困扰了我几天,就是在响应右键菜单行为的时候,怎么样去获取已经存储的那个节点的数据信息。我原来在加入list view的数据的时候,设置了重要的对象信息到LVITEM里面的lparam这个变量中,但是通过下面的代码中的ListView_GetItem宏来发送消息取得Item的信息;但是我发现,以下代码死活无法取得LPARAM变量的值回来。而在处理LVN_GETDISPINFO这个消息的时候,是会传进去Lparam数据的,但是返回来的时候是没有的。原则上,已经在lvitem.mask中设置了LVIF_PARAM标记,就会返回LPARAM数据,但是没有成功!
BOOL DoContextMenu( HWND hWnd, WPARAM wParam, LPARAM lParam) { HWND hwndListView = (HWND)wParam; if(hwndListView != GetDlgItem(hWnd, ID_LISTVIEW)) return FALSE; POINT p; p.x = LOWORD(lParam); p.y = HIWORD(lParam); ::ScreenToClient(hWnd, &p); LVHITTESTINFO lvHittestInfo; lvHittestInfo.pt.x = p.x; lvHittestInfo.pt.y = p.y; int index = ListView_HitTest(hwndListView,&lvHittestInfo); if (index<0) { return FALSE; } LVITEM lvitem; lvitem.mask = LVIF_TEXT|LVIF_PARAM; lvitem.iItem = index; lvitem.iSubItem = index; TCHAR szText[256] = {0}; lvitem.pszText = szText; lvitem.cchTextMax = 256; BOOL brc = ListView_GetItem(hwndListView,&lvitem); DWORD address = *(DWORD*)(lvitem.pszText); LVITEMDATA *pData = (LVITEMDATA*)(address); CShellPidl& pidlParent = pData->pidlAbs; if (!pData->IsValid()) return FALSE;开始以为是设置回调函数的问题,经过多次测试,才发现一个重点问题:lvitem.iSubItem!!!
我查一下MSDN中的描述:
iSubItem
Type: int
One-based index of the subitem to which this structure refers, or zero if this structure refers to an item rather than a subitem.
这里也没有完全说明白,但试过了之后,就发现,把这个值设置为0,就可以了!!!在ListView_GetItem的时候也不会发送LVN_GETDISPINFO消息了,返回来的值中带了Lparam的值!追究起来,这个iSubItem应该是指iItem这一行的一个子项目上附加的数据,这样一来,即使标记了LVIF_PARAM标志,也没法取得对iIem这个项目设置的值了!
附加我的demo程序:http://download.csdn.net/detail/eagleatustb/6847501
相关文章推荐
- 关于log4j2在windows和ubuntu上的部分使用经验
- 笔记一:关于在Windows环境下使用cmd向mysql数据库中导入.sql数据表文件
- 关于spotlight for Windows和spotlight for oracle的使用
- Windows下的进程创建API--CreateProcess使用经验漫谈
- 分享我的Windows live writer 使用经验
- 关于LineChart使用上的一些体会与经验分享
- 关于OPENSSL在WINDOWS下编译和使用的坑
- Windows Socket API 使用经验
- 关于在android项目中使用fragment的个人经验
- 关于文件查找遍历,windows下的使用
- 关于Javascript定义函数和this使用的两点注意的地方
- 关于NandFlash在实际产品使用上的一些经验
- 关于Windows 8使用WMP播放音乐时WUDFHost跑CPU和硬盘的问题解决
- 鉴于本人的经验,我不推荐使用sqlite for wp. Windows Phone(二) WP7数据库连接(SQLite数据库) 转:http://www.cnblogs.com/ry123/archive/2012/05/31/2528281.html
- 在Windows Embedded CE下进行Native C++开发,一次错误使用多线程的经验教训
- 关于Windows 8 开发之测试代码的使用方法
- 关于WINDOWS超级终端的使用来调试MODEM,串口.
- Windows Socket API 使用经验
- 关于WPF中使用AxWindowsMediaPlayer的一些心得体会
- 关于在Windows 7中在桌面使用TextOut函数的一些问题