diff options
Diffstat (limited to 'src/ui/bindingswidget.c')
-rw-r--r-- | src/ui/bindingswidget.c | 46 |
1 files changed, 43 insertions, 3 deletions
diff --git a/src/ui/bindingswidget.c b/src/ui/bindingswidget.c index a6e9f6a0..ff68ea7b 100644 --- a/src/ui/bindingswidget.c +++ b/src/ui/bindingswidget.c | |||
@@ -75,6 +75,8 @@ struct Impl_BindingsWidget { | |||
75 | iWidget widget; | 75 | iWidget widget; |
76 | iListWidget *list; | 76 | iListWidget *list; |
77 | size_t activePos; | 77 | size_t activePos; |
78 | size_t contextPos; | ||
79 | iWidget *menu; | ||
78 | }; | 80 | }; |
79 | 81 | ||
80 | iDefineObjectConstruction(BindingsWidget) | 82 | iDefineObjectConstruction(BindingsWidget) |
@@ -108,11 +110,17 @@ void init_BindingsWidget(iBindingsWidget *d) { | |||
108 | init_Widget(w); | 110 | init_Widget(w); |
109 | setFlags_Widget(w, resizeChildren_WidgetFlag, iTrue); | 111 | setFlags_Widget(w, resizeChildren_WidgetFlag, iTrue); |
110 | d->activePos = iInvalidPos; | 112 | d->activePos = iInvalidPos; |
113 | d->contextPos = iInvalidPos; | ||
111 | d->list = new_ListWidget(); | 114 | d->list = new_ListWidget(); |
112 | setItemHeight_ListWidget(d->list, lineHeight_Text(uiLabel_FontId) * 1.5f); | 115 | setItemHeight_ListWidget(d->list, lineHeight_Text(uiLabel_FontId) * 1.5f); |
113 | setPadding_Widget(as_Widget(d->list), 0, gap_UI, 0, gap_UI); | 116 | setPadding_Widget(as_Widget(d->list), 0, gap_UI, 0, gap_UI); |
114 | addChild_Widget(w, iClob(d->list)); | 117 | addChild_Widget(w, iClob(d->list)); |
115 | updateItems_BindingsWidget_(d); | 118 | updateItems_BindingsWidget_(d); |
119 | d->menu = makeMenu_Widget( | ||
120 | w, | ||
121 | (iMenuItem[]){ { "Reset to Default", 0, 0, "binding.reset" }, | ||
122 | { uiTextCaution_ColorEscape "Clear", 0, 0, "binding.clear" } }, | ||
123 | 2); | ||
116 | } | 124 | } |
117 | 125 | ||
118 | void deinit_BindingsWidget(iBindingsWidget *d) { | 126 | void deinit_BindingsWidget(iBindingsWidget *d) { |
@@ -145,9 +153,38 @@ static iBool processEvent_BindingsWidget_(iBindingsWidget *d, const SDL_Event *e | |||
145 | iWidget * w = as_Widget(d); | 153 | iWidget * w = as_Widget(d); |
146 | const char *cmd = command_UserEvent(ev); | 154 | const char *cmd = command_UserEvent(ev); |
147 | if (isCommand_Widget(w, ev, "list.clicked")) { | 155 | if (isCommand_Widget(w, ev, "list.clicked")) { |
148 | setActiveItem_BindingsWidget_(d, arg_Command(cmd)); | 156 | const size_t index = (size_t) arg_Command(cmd); |
157 | setActiveItem_BindingsWidget_(d, d->activePos != index ? index : iInvalidPos); | ||
149 | return iTrue; | 158 | return iTrue; |
150 | } | 159 | } |
160 | else if (isCommand_Widget(w, ev, "menu.closed")) { | ||
161 | invalidateItem_ListWidget(d->list, d->contextPos); | ||
162 | } | ||
163 | else if (isCommand_Widget(w, ev, "binding.reset")) { | ||
164 | iBindingItem *item = item_ListWidget(d->list, d->contextPos); | ||
165 | if (item) { | ||
166 | reset_Binding(item->id); | ||
167 | updateItems_BindingsWidget_(d); | ||
168 | } | ||
169 | return iTrue; | ||
170 | } | ||
171 | else if (isCommand_Widget(w, ev, "binding.clear")) { | ||
172 | setKey_BindingItem_(item_ListWidget(d->list, d->contextPos), 0, 0); | ||
173 | invalidateItem_ListWidget(d->list, d->contextPos); | ||
174 | d->contextPos = iInvalidPos; | ||
175 | postCommand_App("bindings.changed"); | ||
176 | return iTrue; | ||
177 | } | ||
178 | if (ev->type == SDL_MOUSEBUTTONDOWN && ev->button.button == SDL_BUTTON_RIGHT) { | ||
179 | if (!isVisible_Widget(d->menu)) { | ||
180 | d->contextPos = hoverItemIndex_ListWidget(d->list); | ||
181 | } | ||
182 | } | ||
183 | if (d->contextPos != iInvalidPos) { | ||
184 | processContextMenuEvent_Widget(d->menu, ev, { | ||
185 | setActiveItem_BindingsWidget_(d, iInvalidPos); | ||
186 | }); | ||
187 | } | ||
151 | /* Waiting for a keypress? */ | 188 | /* Waiting for a keypress? */ |
152 | if (d->activePos != iInvalidPos) { | 189 | if (d->activePos != iInvalidPos) { |
153 | if (ev->type == SDL_KEYDOWN && !isMod_Sym(ev->key.keysym.sym)) { | 190 | if (ev->type == SDL_KEYDOWN && !isMod_Sym(ev->key.keysym.sym)) { |
@@ -175,8 +212,11 @@ static void draw_BindingItem_(const iBindingItem *d, iPaint *p, iRect itemRect, | |||
175 | const int line = lineHeight_Text(font); | 212 | const int line = lineHeight_Text(font); |
176 | int fg = uiText_ColorId; | 213 | int fg = uiText_ColorId; |
177 | const iBool isPressing = isMouseDown_ListWidget(list) || d->isWaitingForEvent; | 214 | const iBool isPressing = isMouseDown_ListWidget(list) || d->isWaitingForEvent; |
178 | const iBool isHover = (isHover_Widget(constAs_Widget(list)) && | 215 | const iBindingsWidget *parent = (const iBindingsWidget *) parent_Widget(list); |
179 | constHoverItem_ListWidget(list) == d); | 216 | const iBool isMenuOpen = isVisible_Widget(parent->menu); |
217 | const iBool isHover = ((!isMenuOpen && isHover_Widget(constAs_Widget(list)) && | ||
218 | constHoverItem_ListWidget(list) == d) || | ||
219 | (isMenuOpen && constItem_ListWidget(list, parent->contextPos) == d)); | ||
180 | if (isHover || isPressing) { | 220 | if (isHover || isPressing) { |
181 | fg = isPressing ? uiTextPressed_ColorId : uiTextFramelessHover_ColorId; | 221 | fg = isPressing ? uiTextPressed_ColorId : uiTextFramelessHover_ColorId; |
182 | fillRect_Paint(p, | 222 | fillRect_Paint(p, |