]> de.git.xonotic.org Git - xonotic/xonotic-data.pk3dir.git/blob - qcsrc/menu/xonotic/picker.qc
Merge branch 'master' into Mario/monsters_broken
[xonotic/xonotic-data.pk3dir.git] / qcsrc / menu / xonotic / picker.qc
1 #ifndef PICKER_H
2 #define PICKER_H
3 #include "../item.qc"
4 CLASS(XonoticPicker, Item)
5         METHOD(XonoticPicker, configureXonoticPicker, void(entity));
6         METHOD(XonoticPicker, mousePress, float(entity, vector));
7         METHOD(XonoticPicker, mouseRelease, float(entity, vector));
8         METHOD(XonoticPicker, mouseMove, float(entity, vector));
9         METHOD(XonoticPicker, mouseDrag, float(entity, vector));
10         METHOD(XonoticPicker, keyDown, float(entity, float, float, float));
11         METHOD(XonoticPicker, draw, void(entity));
12         ATTRIB(XonoticPicker, focusable, float, 1)
13         ATTRIB(XonoticPicker, disabled, float, 0)
14         ATTRIB(XonoticPicker, alpha, float, 1)
15         ATTRIB(XonoticPicker, disabledAlpha, float, SKINALPHA_DISABLED)
16
17         ATTRIB(XonoticPicker, rows, float, 3)
18         ATTRIB(XonoticPicker, columns, float, 2)
19
20         METHOD(XonoticPicker, moveFocus, void(entity, vector, vector));
21         METHOD(XonoticPicker, cellSelect, void(entity, vector));
22         METHOD(XonoticPicker, cellDraw, void(entity, vector, vector));
23         METHOD(XonoticPicker, cellIsValid, bool(entity, vector));
24         ATTRIB(XonoticPicker, realCellSize, vector, '0 0 0')
25         ATTRIB(XonoticPicker, selectedCell, vector, '-1 -1 0')
26         ATTRIB(XonoticPicker, focusedCell, vector, '-1 -1 0')
27         ATTRIB(XonoticPicker, focusedCellAlpha, float, 0)
28         ATTRIB(XonoticPicker, focusedCellTime, float, 0)
29         ATTRIB(XonoticPicker, pressedCell, vector, '-1 -1 0')
30 ENDCLASS(XonoticPicker)
31 entity makeXonoticPicker();
32 #endif
33
34 #ifdef IMPLEMENTATION
35
36 entity makeXonoticPicker()
37 {
38         entity me;
39         me = NEW(XonoticPicker);
40         me.configureXonoticPicker(me);
41         return me;
42 }
43
44 void XonoticPicker_configureXonoticPicker(entity me)
45 {
46         me.realCellSize = eX / me.columns + eY / me.rows;
47 }
48
49 float XonoticPicker_mouseMove(entity me, vector coords)
50 {
51         vector prevFocusedCell = me.focusedCell;
52         me.focusedCell_x = floor(coords.x * me.columns);
53         me.focusedCell_y = floor(coords.y * me.rows);
54
55         if(me.focusedCell.x < 0 || me.focusedCell.y < 0 ||
56            me.focusedCell.x >= me.columns || me.focusedCell.y >= me.rows)
57         {
58                 me.focusedCell = '-1 -1 0';
59                 return 0;
60         }
61
62         if(me.focusedCell != prevFocusedCell)
63                 me.focusedCellAlpha = SKINALPHA_LISTBOX_FOCUSED;
64
65         return 1;
66 }
67
68 float XonoticPicker_mouseDrag(entity me, vector coords)
69 {
70         return me.mouseMove(me, coords);
71 }
72
73 float XonoticPicker_mousePress(entity me, vector coords)
74 {
75         me.mouseMove(me, coords);
76
77         if(me.focusedCell.x >= 0)
78         {
79                 me.pressed = 1;
80                 me.pressedCell = me.focusedCell;
81         }
82
83         return 1;
84 }
85
86 float XonoticPicker_mouseRelease(entity me, vector coords)
87 {
88         if(!me.pressed)
89                 return 0;
90
91         me.mouseMove(me, coords);
92
93         if(me.focusedCell == me.pressedCell)
94                 me.cellSelect(me, me.focusedCell);
95
96         me.pressed = 0;
97         return 1;
98 }
99
100 float XonoticPicker_keyDown(entity me, float key, float ascii, float shift)
101 {
102         switch(key)
103         {
104                 case K_END:
105                 case K_KP_END:
106                         // lower left cell then left arrow to select the last valid cell
107                         me.focusedCell = eY * (me.rows - 1);
108                 case K_LEFTARROW:
109                 case K_KP_LEFTARROW:
110                         me.moveFocus(me, me.focusedCell, '-1 0 0');
111                         return 1;
112                 case K_HOME:
113                 case K_KP_HOME:
114                         // upper right cell then right arrow to select the first valid cell
115                         me.focusedCell = eX * (me.columns - 1);
116                 case K_RIGHTARROW:
117                 case K_KP_RIGHTARROW:
118                         me.moveFocus(me, me.focusedCell, '1 0 0');
119                         return 1;
120                 case K_UPARROW:
121                 case K_KP_UPARROW:
122                         me.moveFocus(me, me.focusedCell, '0 -1 0');
123                         return 1;
124                 case K_DOWNARROW:
125                 case K_KP_DOWNARROW:
126                         me.moveFocus(me, me.focusedCell, '0 1 0');
127                         return 1;
128                 case K_ENTER:
129                 case K_KP_ENTER:
130                 case K_INS:
131                 case K_KP_INS:
132                         me.cellSelect(me, me.focusedCell);
133                         return 1;
134         }
135         return 0;
136 }
137
138 void XonoticPicker_moveFocus(entity me, vector initialCell, vector step)
139 {
140         me.focusedCell_x = mod(me.focusedCell.x + step.x + me.columns, me.columns);
141         me.focusedCell_y = mod(me.focusedCell.y + step.y + me.rows, me.rows);
142
143         if(me.focusedCell != initialCell) // Recursion break
144                 if(!me.cellIsValid(me, me.focusedCell))
145                         me.moveFocus(me, initialCell, step);
146
147         me.focusedCellAlpha = SKINALPHA_LISTBOX_FOCUSED;
148 }
149
150 void XonoticPicker_cellSelect(entity me, vector cell)
151 {
152         me.selectedCell = cell;
153 }
154
155 bool XonoticPicker_cellIsValid(entity me, vector cell)
156 {
157         return true;
158 }
159
160 void XonoticPicker_cellDraw(entity me, vector cell, vector cellPos)
161 {
162 }
163
164 void XonoticPicker_draw(entity me)
165 {
166         float save;
167
168         me.focusable = !me.disabled;
169
170         save = draw_alpha;
171         if(me.disabled)
172                 draw_alpha *= me.disabledAlpha;
173
174         vector cell, cellPos;
175         cell = '0 0 0';
176         cellPos = '0 0 0';
177
178         for(cell_y = 0; cell.y < me.rows; ++cell.y)
179         {
180                 cellPos_y = mod(cell.y, me.rows) / me.rows;
181                 for(cell_x = 0; cell.x < me.columns; ++cell.x)
182                 {
183                         if(!me.cellIsValid(me, cell))
184                                 continue;
185
186                         cellPos_x = mod(cell.x, me.columns) / me.columns;
187
188                         if(cell == me.selectedCell)
189                                 draw_Fill(cellPos, me.realCellSize, SKINCOLOR_LISTBOX_SELECTED, SKINALPHA_LISTBOX_SELECTED);
190                         else if(cell == me.focusedCell && me.focused)
191                         {
192                                 if(!me.pressed || me.focusedCell == me.pressedCell)
193                                 {
194                                         me.focusedCellAlpha = getFadedAlpha(me.focusedCellAlpha, SKINALPHA_LISTBOX_FOCUSED, SKINFADEALPHA_LISTBOX_FOCUSED);
195                                         draw_Fill(cellPos, me.realCellSize, SKINCOLOR_LISTBOX_FOCUSED, me.focusedCellAlpha);
196                                 }
197                         }
198
199                         me.cellDraw(me, cell, cellPos);
200                 }
201         }
202
203         draw_alpha = save;
204
205         SUPER(XonoticPicker).draw(me);
206 }
207 #endif