Fixed some message sequences to succeed on XP.
[wine] / dlls / user / tests / listbox.c
1 /* Unit test suite for list boxes.
2  *
3  * Copyright 2003 Ferenc Wagner
4  *
5  * This library is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Lesser General Public
7  * License as published by the Free Software Foundation; either
8  * version 2.1 of the License, or (at your option) any later version.
9  *
10  * This library is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public
16  * License along with this library; if not, write to the Free Software
17  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18  */
19
20 #include <assert.h>
21 #include <windows.h>
22
23 #include "wine/test.h"
24
25 #ifdef VISIBLE
26 #define WAIT Sleep (1000)
27 #define REDRAW RedrawWindow (handle, NULL, 0, RDW_UPDATENOW)
28 #else
29 #define WAIT
30 #define REDRAW
31 #endif
32
33 HWND
34 create_listbox (DWORD add_style)
35 {
36   HWND handle=CreateWindow ("LISTBOX", "TestList",
37                             (LBS_STANDARD & ~LBS_SORT) | add_style,
38                             0, 0, 100, 100,
39                             NULL, NULL, NULL, 0);
40
41   assert (handle);
42   SendMessage (handle, LB_ADDSTRING, 0, (LPARAM) (LPCTSTR) "First added");
43   SendMessage (handle, LB_ADDSTRING, 0, (LPARAM) (LPCTSTR) "Second added");
44   SendMessage (handle, LB_ADDSTRING, 0, (LPARAM) (LPCTSTR) "Third added");
45
46 #ifdef VISIBLE
47   ShowWindow (handle, SW_SHOW);
48 #endif
49   REDRAW;
50
51   return handle;
52 }
53
54 struct listbox_prop {
55   DWORD add_style;
56 };
57
58 struct listbox_stat {
59   int selected, anchor, caret, selcount;
60 };
61
62 struct listbox_test {
63   struct listbox_prop prop;
64   struct listbox_stat  init,  init_todo;
65   struct listbox_stat click, click_todo;
66   struct listbox_stat  step,  step_todo;
67 };
68
69 void
70 listbox_query (HWND handle, struct listbox_stat *results)
71 {
72   results->selected = SendMessage (handle, LB_GETCURSEL, 0, 0);
73   results->anchor   = SendMessage (handle, LB_GETANCHORINDEX, 0, 0);
74   results->caret    = SendMessage (handle, LB_GETCARETINDEX, 0, 0);
75   results->selcount = SendMessage (handle, LB_GETSELCOUNT, 0, 0);
76 }
77
78 void
79 buttonpress (HWND handle, WORD x, WORD y)
80 {
81   LPARAM lp=x+(y<<16);
82
83   WAIT;
84   SendMessage (handle, WM_LBUTTONDOWN, (WPARAM) MK_LBUTTON, lp);
85   SendMessage (handle, WM_LBUTTONUP  , (WPARAM) 0         , lp);
86   REDRAW;
87 }
88
89 void
90 keypress (HWND handle, WPARAM keycode, BYTE scancode, BOOL extended)
91 {
92   LPARAM lp=1+(scancode<<16)+(extended?KEYEVENTF_EXTENDEDKEY:0);
93
94   WAIT;
95   SendMessage (handle, WM_KEYDOWN, keycode, lp);
96   SendMessage (handle, WM_KEYUP  , keycode, lp | 0xc000000);
97   REDRAW;
98 }
99
100 #define listbox_field_ok(t, s, f, got) \
101   ok (t.s.f==got.f, "style %#x, step " #s ", field " #f \
102       ": expected %d, got %d\n", (unsigned int)t.prop.add_style, \
103       t.s.f, got.f)
104
105 #define listbox_todo_field_ok(t, s, f, got) \
106   if (t.s##_todo.f) todo_wine { listbox_field_ok(t, s, f, got); } \
107   else listbox_field_ok(t, s, f, got)
108
109 #define listbox_ok(t, s, got) \
110   listbox_todo_field_ok(t, s, selected, got); \
111   listbox_todo_field_ok(t, s, anchor, got); \
112   listbox_todo_field_ok(t, s, caret, got); \
113   listbox_todo_field_ok(t, s, selcount, got)
114
115 void
116 check (const struct listbox_test test)
117 {
118   struct listbox_stat answer;
119   HWND hLB=create_listbox (test.prop.add_style);
120   RECT second_item;
121
122   listbox_query (hLB, &answer);
123   listbox_ok (test, init, answer);
124
125   SendMessage (hLB, LB_GETITEMRECT, (WPARAM) 1, (LPARAM) &second_item);
126   buttonpress(hLB, (WORD)second_item.left, (WORD)second_item.top);
127
128   listbox_query (hLB, &answer);
129   listbox_ok (test, click, answer);
130
131   keypress (hLB, VK_DOWN, 0x50, TRUE);
132
133   listbox_query (hLB, &answer);
134   listbox_ok (test, step, answer);
135
136   WAIT;
137   DestroyWindow (hLB);
138 }
139
140 START_TEST(listbox)
141 {
142   const struct listbox_test SS =
143 /*   {add_style} */
144     {{0},
145      {LB_ERR, LB_ERR,      0, LB_ERR}, {0,0,0,0},
146      {     1,      1,      1, LB_ERR}, {0,1,0,0},
147      {     2,      2,      2, LB_ERR}, {0,1,0,0}};
148 /* {selected, anchor,  caret, selcount}{TODO fields} */
149   const struct listbox_test SS_NS =
150     {{LBS_NOSEL},
151      {LB_ERR, LB_ERR,      0, LB_ERR}, {0,0,0,0},
152      {     1,      1,      1, LB_ERR}, {1,1,0,0},
153      {     2,      2,      2, LB_ERR}, {1,1,1,0}};
154   const struct listbox_test MS =
155     {{LBS_MULTIPLESEL},
156      {     0, LB_ERR,      0,      0}, {0,0,0,0},
157      {     1,      1,      1,      1}, {0,1,0,0},
158      {     2,      1,      2,      1}, {0,1,0,1}};
159   const struct listbox_test MS_NS =
160     {{LBS_MULTIPLESEL | LBS_NOSEL},
161      {LB_ERR, LB_ERR,      0, LB_ERR}, {1,0,0,1},
162      {     1,      1,      1, LB_ERR}, {0,1,0,1},
163      {     2,      2,      2, LB_ERR}, {0,1,0,1}};
164
165   trace (" Testing single selection...\n");
166   check (SS);
167   trace (" ... with NOSEL\n");
168   check (SS_NS);
169   trace (" Testing multiple selection...\n");
170   check (MS);
171   trace (" ... with NOSEL\n");
172   check (MS_NS);
173 }