X-Git-Url: https://git.artsoft.org/?a=blobdiff_plain;f=src%2Flibgame%2Fgadgets.c;h=afe5c3a74addaf06cc37ed3e7fae46d6638e4054;hb=8e17da8cdff134bfa0e766a50f408a3c06428f54;hp=678107c6d5ad009319c080373b0ce1260dee41ae;hpb=4dba06ad2079d7f9df56ec5512c6d27a0cf8c18e;p=rocksndiamonds.git diff --git a/src/libgame/gadgets.c b/src/libgame/gadgets.c index 678107c6..afe5c3a7 100644 --- a/src/libgame/gadgets.c +++ b/src/libgame/gadgets.c @@ -71,20 +71,24 @@ static struct GadgetInfo *getGadgetInfoFromMousePosition(int mx, int my, struct GadgetInfo *gi; /* first check for scrollbars in case of mouse scroll wheel button events */ - if (button == 4 || button == 5) + if (IS_WHEEL_BUTTON(button)) { -#if 0 - printf("WHOA! SCROLL WHEEL DETECTED [%d]\n", button); -#endif + /* real horizontal wheel or vertical wheel with modifier key pressed */ + boolean check_horizontal = (IS_WHEEL_BUTTON_HORIZONTAL(button) || + GetKeyModState() & KMOD_Shift); + /* check for the first active scrollbar with matching mouse wheel area */ for (gi = gadget_list_first_entry; gi != NULL; gi = gi->next) { if (gi->mapped && gi->active && - gi->type & GD_TYPE_SCROLLBAR) + ((gi->type & GD_TYPE_SCROLLBAR_HORIZONTAL && check_horizontal) || + (gi->type & GD_TYPE_SCROLLBAR_VERTICAL && !check_horizontal)) && + mx >= gi->wheelarea.x && mx < gi->wheelarea.x + gi->wheelarea.width && + my >= gi->wheelarea.y && my < gi->wheelarea.y + gi->wheelarea.height) return gi; } - /* no active scrollbar found -- ignore this button event */ + /* no active scrollbar found -- ignore this scroll wheel button event */ return NULL; } @@ -995,6 +999,22 @@ static void HandleGadgetTags(struct GadgetInfo *gi, int first_tag, va_list ap) gi->scrollbar.item_position = va_arg(ap, int); break; + case GDI_WHEEL_AREA_X: + gi->wheelarea.x = va_arg(ap, int); + break; + + case GDI_WHEEL_AREA_Y: + gi->wheelarea.y = va_arg(ap, int); + break; + + case GDI_WHEEL_AREA_WIDTH: + gi->wheelarea.width = va_arg(ap, int); + break; + + case GDI_WHEEL_AREA_HEIGHT: + gi->wheelarea.height = va_arg(ap, int); + break; + case GDI_CALLBACK_INFO: gi->callback_info = va_arg(ap, gadget_function); break; @@ -1401,6 +1421,7 @@ void ClickOnGadget(struct GadgetInfo *gi, int button) boolean HandleGadgets(int mx, int my, int button) { static unsigned long pressed_delay = 0; + static unsigned long pressed_delay_value = GADGET_FRAME_DELAY; static int last_button = 0; static int last_mx = 0, last_my = 0; static int pressed_mx = 0, pressed_my = 0; @@ -1516,7 +1537,7 @@ boolean HandleGadgets(int mx, int my, int button) (button != 0 && last_gi != NULL && new_gi == last_gi); gadget_pressed_delay_reached = - DelayReached(&pressed_delay, GADGET_FRAME_DELAY); + DelayReached(&pressed_delay, pressed_delay_value); gadget_released = (release_event && last_gi != NULL); gadget_released_inside = (gadget_released && new_gi == last_gi); @@ -1688,14 +1709,29 @@ boolean HandleGadgets(int mx, int my, int button) if ((gadget_pressed) || (gadget_pressed_repeated && gadget_pressed_delay_reached)) { + if (gadget_pressed) /* gadget pressed the first time */ + { + /* initialize delay counter */ + DelayReached(&pressed_delay, 0); + + /* start gadget delay with longer delay after first click on gadget */ + pressed_delay_value = GADGET_FRAME_DELAY_FIRST; + } + else /* gadget hold pressed for some time */ + { + /* after first repeated gadget click, continue with shorter delay value */ + pressed_delay_value = GADGET_FRAME_DELAY; + } + if (gi->type & GD_TYPE_SCROLLBAR && !gadget_dragging) { int mpos = (gi->type == GD_TYPE_SCROLLBAR_HORIZONTAL ? mx : my); int gpos = (gi->type == GD_TYPE_SCROLLBAR_HORIZONTAL ? gi->x : gi->y); + int slider_start = gpos + gi->scrollbar.position; + int slider_end = gpos + gi->scrollbar.position + gi->scrollbar.size - 1; + boolean inside_slider = (mpos >= slider_start && mpos <= slider_end); - if (button > 3 || - mpos < gpos + gi->scrollbar.position || - mpos >= gpos + gi->scrollbar.position + gi->scrollbar.size) + if (IS_WHEEL_BUTTON(button) || !inside_slider) { /* click scrollbar one scrollbar length up/left or down/right */ @@ -1704,10 +1740,13 @@ boolean HandleGadgets(int mx, int my, int button) int item_steps = gs->items_visible - 1; int item_direction = (mpos < gpos + gi->scrollbar.position ? -1 : +1); - if (button > 3) + if (IS_WHEEL_BUTTON(button)) { - item_steps = 3; - item_direction = (button == 4 ? -1 : +1); + boolean scroll_single_step = (GetKeyModState() & KMOD_Alt); + + item_steps = (scroll_single_step ? 1 : DEFAULT_WHEEL_STEPS); + item_direction = (button == MB_WHEEL_UP || + button == MB_WHEEL_LEFT ? -1 : +1); } changed_position = FALSE; @@ -1782,10 +1821,11 @@ boolean HandleGadgets(int mx, int my, int button) { int mpos = (gi->type == GD_TYPE_SCROLLBAR_HORIZONTAL ? mx : my); int gpos = (gi->type == GD_TYPE_SCROLLBAR_HORIZONTAL ? gi->x : gi->y); + int slider_start = gpos + gi->scrollbar.position; + int slider_end = gpos + gi->scrollbar.position + gi->scrollbar.size - 1; + boolean inside_slider = (mpos >= slider_start && mpos <= slider_end); - if (button >= 1 && button <= 3 && - mpos >= gpos + gi->scrollbar.position && - mpos < gpos + gi->scrollbar.position + gi->scrollbar.size) + if (!IS_WHEEL_BUTTON(button) && inside_slider) { /* start dragging scrollbar */ gi->scrollbar.drag_position = @@ -1806,9 +1846,6 @@ boolean HandleGadgets(int mx, int my, int button) gi->event.button = button; gi->event.off_borders = FALSE; - /* initialize delay counter */ - DelayReached(&pressed_delay, 0); - if (gi->event_mask & GD_EVENT_PRESSED) gi->callback_action(gi); } @@ -1817,14 +1854,8 @@ boolean HandleGadgets(int mx, int my, int button) { gi->event.type = GD_EVENT_PRESSED; -#if 1 if (gi->event_mask & GD_EVENT_REPEATED && gadget_pressed_delay_reached) gi->callback_action(gi); -#else - if (gi->event_mask & GD_EVENT_REPEATED && - DelayReached(&pressed_delay, GADGET_FRAME_DELAY)) - gi->callback_action(gi); -#endif } if (gadget_moving)