From 34b802caf088e526eadc23d785582e81ea5374cd Mon Sep 17 00:00:00 2001 From: Nikolay Sivov Date: Tue, 16 Jun 2009 01:46:11 +0400 Subject: [PATCH] comctl32/listview: Convert forwarded header notifications to ANSI if NFR_ANSI is current format. --- dlls/comctl32/listview.c | 88 +++++++++++++++++++++++++++------- dlls/comctl32/tests/listview.c | 30 +++++++++++- 2 files changed, 99 insertions(+), 19 deletions(-) diff --git a/dlls/comctl32/listview.c b/dlls/comctl32/listview.c index de98e380bc6..ebf49c622eb 100644 --- a/dlls/comctl32/listview.c +++ b/dlls/comctl32/listview.c @@ -701,10 +701,78 @@ static inline LPCSTR debugscrollcode(int nScrollCode) /******** Notification functions ************************************/ +static int get_ansi_notification(UINT unicodeNotificationCode) +{ + switch (unicodeNotificationCode) + { + case LVN_BEGINLABELEDITW: return LVN_BEGINLABELEDITA; + case LVN_ENDLABELEDITW: return LVN_ENDLABELEDITA; + case LVN_GETDISPINFOW: return LVN_GETDISPINFOA; + case LVN_SETDISPINFOW: return LVN_SETDISPINFOA; + case LVN_ODFINDITEMW: return LVN_ODFINDITEMA; + case LVN_GETINFOTIPW: return LVN_GETINFOTIPA; + /* header forwards */ + case HDN_TRACKW: return HDN_TRACKA; + case HDN_ENDTRACKW: return HDN_ENDTRACKA; + case HDN_BEGINDRAG: return HDN_BEGINDRAG; + case HDN_ENDDRAG: return HDN_ENDDRAG; + case HDN_ITEMCHANGINGW: return HDN_ITEMCHANGINGA; + case HDN_ITEMCHANGEDW: return HDN_ITEMCHANGEDA; + case HDN_ITEMCLICKW: return HDN_ITEMCLICKA; + case HDN_DIVIDERDBLCLICKW: return HDN_DIVIDERDBLCLICKA; + } + ERR("unknown notification %x\n", unicodeNotificationCode); + assert(FALSE); + return 0; +} + +/* forwards header notifications to listview parent */ static LRESULT notify_forward_header(const LISTVIEW_INFO *infoPtr, const NMHEADERW *lpnmh) { - return SendMessageW(infoPtr->hwndNotify, WM_NOTIFY, - (WPARAM)lpnmh->hdr.idFrom, (LPARAM)lpnmh); + NMHEADERA nmhA; + HDITEMA hditema; + HD_TEXTFILTERA textfilter; + LPSTR text = NULL, filter = NULL; + LRESULT ret; + + /* on unicode format exit earlier */ + if (infoPtr->notifyFormat == NFR_UNICODE) + return SendMessageW(infoPtr->hwndNotify, WM_NOTIFY, + (WPARAM)lpnmh->hdr.idFrom, (LPARAM)lpnmh); + + /* header always supplies unicode notifications, + all we have to do is to convert strings to ANSI */ + nmhA = *(NMHEADERA*)lpnmh; + if (lpnmh->pitem) + { + hditema = *(HDITEMA*)lpnmh->pitem; + nmhA.pitem = &hditema; + /* convert item text */ + if (lpnmh->pitem->mask & HDI_TEXT) + { + Str_SetPtrWtoA(&hditema.pszText, lpnmh->pitem->pszText); + text = hditema.pszText; + } + /* convert filter text */ + if ((lpnmh->pitem->mask & HDI_FILTER) && (lpnmh->pitem->type == HDFT_ISSTRING) && + lpnmh->pitem->pvFilter) + { + hditema.pvFilter = &textfilter; + textfilter = *(HD_TEXTFILTERA*)(lpnmh->pitem->pvFilter); + Str_SetPtrWtoA(&textfilter.pszText, ((HD_TEXTFILTERW*)lpnmh->pitem->pvFilter)->pszText); + filter = textfilter.pszText; + } + } + nmhA.hdr.code = get_ansi_notification(lpnmh->hdr.code); + + ret = SendMessageW(infoPtr->hwndNotify, WM_NOTIFY, + (WPARAM)nmhA.hdr.idFrom, (LPARAM)&nmhA); + + /* cleanup */ + Free(text); + Free(filter); + + return ret; } static LRESULT notify_hdr(const LISTVIEW_INFO *infoPtr, INT code, LPNMHDR pnmh) @@ -804,22 +872,6 @@ static BOOL notify_deleteitem(const LISTVIEW_INFO *infoPtr, INT nItem) return IsWindow(hwnd); } -static int get_ansi_notification(UINT unicodeNotificationCode) -{ - switch (unicodeNotificationCode) - { - case LVN_BEGINLABELEDITW: return LVN_BEGINLABELEDITA; - case LVN_ENDLABELEDITW: return LVN_ENDLABELEDITA; - case LVN_GETDISPINFOW: return LVN_GETDISPINFOA; - case LVN_SETDISPINFOW: return LVN_SETDISPINFOA; - case LVN_ODFINDITEMW: return LVN_ODFINDITEMA; - case LVN_GETINFOTIPW: return LVN_GETINFOTIPA; - } - ERR("unknown notification %x\n", unicodeNotificationCode); - assert(FALSE); - return 0; -} - /* Send notification. depends on dispinfoW having same structure as dispinfoA. diff --git a/dlls/comctl32/tests/listview.c b/dlls/comctl32/tests/listview.c index d28fc1bb0d2..201826baf61 100644 --- a/dlls/comctl32/tests/listview.c +++ b/dlls/comctl32/tests/listview.c @@ -3177,7 +3177,7 @@ static void test_editbox(void) static void test_notifyformat(void) { - HWND hwnd; + HWND hwnd, header; DWORD r; hwnd = create_listview_control(0); @@ -3212,8 +3212,12 @@ static void test_notifyformat(void) notifyFormat = 0; hwnd = create_listview_control(0); ok(hwnd != NULL, "failed to create a listview window\n"); + header = (HWND)SendMessage(hwnd, LVM_GETHEADER, 0, 0); + ok(IsWindow(header), "expected header to be created\n"); r = SendMessage(hwnd, LVM_GETUNICODEFORMAT, 0, 0); expect(0, r); + r = SendMessage(header, HDM_GETUNICODEFORMAT, 0, 0); + expect(1, r); r = SendMessage(hwnd, WM_NOTIFYFORMAT, 0, NF_QUERY); ok(r != 0, "Expected valid format\n"); @@ -3222,12 +3226,16 @@ static void test_notifyformat(void) expect(NFR_UNICODE, r); r = SendMessage(hwnd, LVM_GETUNICODEFORMAT, 0, 0); expect(1, r); + r = SendMessage(header, HDM_GETUNICODEFORMAT, 0, 0); + expect(1, r); notifyFormat = NFR_ANSI; r = SendMessage(hwnd, WM_NOTIFYFORMAT, 0, NF_REQUERY); expect(NFR_ANSI, r); r = SendMessage(hwnd, LVM_GETUNICODEFORMAT, 0, 0); expect(0, r); + r = SendMessage(header, HDM_GETUNICODEFORMAT, 0, 0); + expect(1, r); DestroyWindow(hwnd); @@ -3245,36 +3253,56 @@ static void test_notifyformat(void) notifyFormat = -1; hwnd = create_listview_controlW(0, hwndparentW); ok(hwnd != NULL, "failed to create a listview window\n"); + header = (HWND)SendMessage(hwnd, LVM_GETHEADER, 0, 0); + ok(IsWindow(header), "expected header to be created\n"); r = SendMessageW(hwnd, LVM_GETUNICODEFORMAT, 0, 0); expect(1, r); + r = SendMessage(header, HDM_GETUNICODEFORMAT, 0, 0); + expect(1, r); DestroyWindow(hwnd); /* recieving error code defaulting to ansi */ notifyFormat = 0; hwnd = create_listview_controlW(0, hwndparentW); ok(hwnd != NULL, "failed to create a listview window\n"); + header = (HWND)SendMessage(hwnd, LVM_GETHEADER, 0, 0); + ok(IsWindow(header), "expected header to be created\n"); r = SendMessageW(hwnd, LVM_GETUNICODEFORMAT, 0, 0); expect(0, r); + r = SendMessage(header, HDM_GETUNICODEFORMAT, 0, 0); + expect(1, r); DestroyWindow(hwnd); /* recieving ansi code from unicode window, use it */ notifyFormat = NFR_ANSI; hwnd = create_listview_controlW(0, hwndparentW); ok(hwnd != NULL, "failed to create a listview window\n"); + header = (HWND)SendMessage(hwnd, LVM_GETHEADER, 0, 0); + ok(IsWindow(header), "expected header to be created\n"); r = SendMessageW(hwnd, LVM_GETUNICODEFORMAT, 0, 0); expect(0, r); + r = SendMessage(header, HDM_GETUNICODEFORMAT, 0, 0); + expect(1, r); DestroyWindow(hwnd); /* unicode listview with ansi parent window */ notifyFormat = -1; hwnd = create_listview_controlW(0, hwndparent); ok(hwnd != NULL, "failed to create a listview window\n"); + header = (HWND)SendMessage(hwnd, LVM_GETHEADER, 0, 0); + ok(IsWindow(header), "expected header to be created\n"); r = SendMessageW(hwnd, LVM_GETUNICODEFORMAT, 0, 0); expect(0, r); + r = SendMessage(header, HDM_GETUNICODEFORMAT, 0, 0); + expect(1, r); DestroyWindow(hwnd); /* unicode listview with ansi parent window, return error code */ notifyFormat = 0; hwnd = create_listview_controlW(0, hwndparent); ok(hwnd != NULL, "failed to create a listview window\n"); + header = (HWND)SendMessage(hwnd, LVM_GETHEADER, 0, 0); + ok(IsWindow(header), "expected header to be created\n"); r = SendMessageW(hwnd, LVM_GETUNICODEFORMAT, 0, 0); expect(0, r); + r = SendMessage(header, HDM_GETUNICODEFORMAT, 0, 0); + expect(1, r); DestroyWindow(hwnd); DestroyWindow(hwndparentW);