diff options
author | Campbell Barton <ideasman42@gmail.com> | 2019-03-21 06:19:45 +0300 |
---|---|---|
committer | Campbell Barton <ideasman42@gmail.com> | 2019-03-21 06:19:45 +0300 |
commit | b98fe9e70740ebfbd8910454036819d3a5fcd330 (patch) | |
tree | eba9f5b9dbcec092abea15759c1b16788dce611c /source/blender/editors/interface/interface_handlers.c | |
parent | 9b3818762a6ce717539885cb99cdb98abc78ed1a (diff) |
Cleanup: move functions into doxy sections
Also use const args for queries.
Diffstat (limited to 'source/blender/editors/interface/interface_handlers.c')
-rw-r--r-- | source/blender/editors/interface/interface_handlers.c | 783 |
1 files changed, 392 insertions, 391 deletions
diff --git a/source/blender/editors/interface/interface_handlers.c b/source/blender/editors/interface/interface_handlers.c index 03f11e1e3f2..5c8099eb205 100644 --- a/source/blender/editors/interface/interface_handlers.c +++ b/source/blender/editors/interface/interface_handlers.c @@ -391,10 +391,11 @@ typedef struct uiAfterFunc { } uiAfterFunc; - static bool ui_but_is_interactive(const uiBut *but, const bool labeledit); -static bool ui_but_contains_pt(uiBut *but, float mx, float my); -static bool ui_but_contains_point_px(ARegion *ar, uiBut *but, int x, int y); +static bool ui_but_contains_pt(const uiBut *but, float mx, float my); +static bool ui_but_contains_point_px(ARegion *ar, const uiBut *but, int x, int y); +static bool ui_but_contains_point_px_icon(const uiBut *but, ARegion *ar, const wmEvent *event); +static bool ui_region_contains_point_px(const ARegion *ar, int x, int y); static uiBut *ui_but_find_mouse_over_ex(ARegion *ar, const int x, const int y, const bool labeledit); static void button_activate_init(bContext *C, ARegion *ar, uiBut *but, uiButtonActivateType type); static void button_activate_state(bContext *C, uiBut *but, uiHandleButtonState state); @@ -416,39 +417,206 @@ static bool but_copypaste_curve_alive = false; /** \} */ + /* -------------------------------------------------------------------- */ -/** \name Snap Values +/** \name UI Queries * \{ */ -enum eSnapType { - SNAP_OFF = 0, - SNAP_ON, - SNAP_ON_SMALL, -}; +void ui_but_pie_dir(RadialDirection dir, float vec[2]) +{ + float angle; -static enum eSnapType ui_event_to_snap(const wmEvent *event) + BLI_assert(dir != UI_RADIAL_NONE); + + angle = DEG2RADF((float)ui_radial_dir_to_angle[dir]); + vec[0] = cosf(angle); + vec[1] = sinf(angle); +} + +static bool ui_but_isect_pie_seg(const uiBlock *block, const uiBut *but) { - return (event->ctrl) ? (event->shift) ? SNAP_ON_SMALL : SNAP_ON : SNAP_OFF; + const float angle_range = (block->pie_data.flags & UI_PIE_DEGREES_RANGE_LARGE) ? M_PI_4 : M_PI_4 / 2.0; + float vec[2]; + + if (block->pie_data.flags & UI_PIE_INVALID_DIR) + return false; + + ui_but_pie_dir(but->pie_dir, vec); + + if (saacos(dot_v2v2(vec, block->pie_data.pie_dir)) < angle_range) + return true; + + return false; } -static bool ui_event_is_snap(const wmEvent *event) +static bool ui_but_contains_pt(const uiBut *but, float mx, float my) { - return (ELEM(event->type, LEFTCTRLKEY, RIGHTCTRLKEY) || - ELEM(event->type, LEFTSHIFTKEY, RIGHTSHIFTKEY)); + return BLI_rctf_isect_pt(&but->rect, mx, my); } -static void ui_color_snap_hue(const enum eSnapType snap, float *r_hue) +static bool ui_but_contains_point_px(ARegion *ar, const uiBut *but, int x, int y) { - const float snap_increment = (snap == SNAP_ON_SMALL) ? 24 : 12; - BLI_assert(snap != SNAP_OFF); - *r_hue = roundf((*r_hue) * snap_increment) / snap_increment; + uiBlock *block = but->block; + float mx, my; + if (!ui_region_contains_point_px(ar, x, y)) + return false; + + mx = x; + my = y; + + ui_window_to_block_fl(ar, block, &mx, &my); + + if (but->pie_dir != UI_RADIAL_NONE) { + if (!ui_but_isect_pie_seg(block, but)) { + return false; + } + } + else if (!ui_but_contains_pt(but, mx, my)) { + return false; + } + + return true; } -/** \} */ +static bool ui_but_contains_point_px_icon(const uiBut *but, ARegion *ar, const wmEvent *event) +{ + rcti rect; + int x = event->x, y = event->y; -/* -------------------------------------------------------------------- */ -/** \name General Utilities - * \{ */ + ui_window_to_block(ar, but->block, &x, &y); + + BLI_rcti_rctf_copy(&rect, &but->rect); + + if (but->imb || but->type == UI_BTYPE_COLOR) { + /* use button size itself */ + } + else if (but->drawflag & UI_BUT_ICON_LEFT) { + rect.xmax = rect.xmin + (BLI_rcti_size_y(&rect)); + } + else { + int delta = BLI_rcti_size_x(&rect) - BLI_rcti_size_y(&rect); + rect.xmin += delta / 2; + rect.xmax -= delta / 2; + } + + return BLI_rcti_isect_pt(&rect, x, y); +} + +static bool ui_region_contains_point_px(const ARegion *ar, int x, int y) +{ + rcti winrct; + + /* scale down area rect to exclude shadow */ + ui_region_winrct_get_no_margin(ar, &winrct); + + /* check if the mouse is in the region */ + if (!BLI_rcti_isect_pt(&winrct, x, y)) { + for (uiBlock *block = ar->uiblocks.first; block; block = block->next) + block->auto_open = false; + + return false; + } + + /* also, check that with view2d, that the mouse is not over the scrollbars + * NOTE: care is needed here, since the mask rect may include the scrollbars + * even when they are not visible, so we need to make a copy of the mask to + * use to check + */ + if (ar->v2d.mask.xmin != ar->v2d.mask.xmax) { + const View2D *v2d = &ar->v2d; + int mx, my; + + /* convert window coordinates to region coordinates */ + mx = x; + my = y; + ui_window_to_region(ar, &mx, &my); + + /* check if in the rect */ + if (!BLI_rcti_isect_pt(&v2d->mask, mx, my) || UI_view2d_mouse_in_scrollers(ar, &ar->v2d, x, y)) { + return false; + } + } + + return true; +} + +/* x and y are only used in case event is NULL... */ +static uiBut *ui_but_find_mouse_over_ex(ARegion *ar, const int x, const int y, const bool labeledit) +{ + uiBlock *block; + uiBut *but, *butover = NULL; + float mx, my; + +// if (!win->active) +// return NULL; + if (!ui_region_contains_point_px(ar, x, y)) + return NULL; + + for (block = ar->uiblocks.first; block; block = block->next) { + mx = x; + my = y; + ui_window_to_block_fl(ar, block, &mx, &my); + + for (but = block->buttons.last; but; but = but->prev) { + if (ui_but_is_interactive(but, labeledit)) { + if (but->pie_dir != UI_RADIAL_NONE) { + if (ui_but_isect_pie_seg(block, but)) { + butover = but; + break; + } + } + else if (ui_but_contains_pt(but, mx, my)) { + butover = but; + break; + } + } + } + + /* CLIP_EVENTS prevents the event from reaching other blocks */ + if (block->flag & UI_BLOCK_CLIP_EVENTS) { + /* check if mouse is inside block */ + if (BLI_rctf_isect_pt(&block->rect, mx, my)) { + break; + } + } + } + + return butover; +} + +uiBut *ui_but_find_mouse_over(ARegion *ar, const wmEvent *event) +{ + return ui_but_find_mouse_over_ex(ar, event->x, event->y, event->ctrl != 0); +} + +static uiBut *ui_list_find_mouse_over_ex(ARegion *ar, int x, int y) +{ + uiBlock *block; + uiBut *but; + float mx, my; + + if (!ui_region_contains_point_px(ar, x, y)) + return NULL; + + for (block = ar->uiblocks.first; block; block = block->next) { + mx = x; + my = y; + ui_window_to_block_fl(ar, block, &mx, &my); + + for (but = block->buttons.last; but; but = but->prev) { + if (but->type == UI_BTYPE_LISTBOX && ui_but_contains_pt(but, mx, my)) { + return but; + } + } + } + + return NULL; +} + +static uiBut *ui_list_find_mouse_over(ARegion *ar, const wmEvent *event) +{ + return ui_list_find_mouse_over_ex(ar, event->x, event->y); +} /* assumes event type is MOUSEPAN */ void ui_pan_to_scroll(const wmEvent *event, int *type, int *val) @@ -525,7 +693,7 @@ static uiBut *ui_but_last(uiBlock *block) return NULL; } -static bool ui_but_is_cursor_warp(uiBut *but) +static bool ui_but_is_cursor_warp(const uiBut *but) { if (U.uiflag & USER_CONTINUOUS_MOUSE) { if (ELEM(but->type, @@ -539,28 +707,96 @@ static bool ui_but_is_cursor_warp(uiBut *but) return false; } +static bool ui_but_contains_password(const uiBut *but) +{ + return but->rnaprop && (RNA_property_subtype(but->rnaprop) == PROP_PASSWORD); +} + /** - * Ignore mouse movements within some horizontal pixel threshold before starting to drag + * Can we mouse over the button or is it hidden/disabled/layout. + * \note ctrl is kind of a hack currently, + * so that non-embossed UI_BTYPE_TEXT button behaves as a label when ctrl is not pressed. */ -static bool ui_but_dragedit_update_mval(uiHandleButtonData *data, int mx) +static bool ui_but_is_interactive(const uiBut *but, const bool labeledit) { - if (mx == data->draglastx) + /* note, UI_BTYPE_LABEL is included for highlights, this allows drags */ + if ((but->type == UI_BTYPE_LABEL) && but->dragpoin == NULL) + return false; + if (ELEM(but->type, UI_BTYPE_ROUNDBOX, UI_BTYPE_SEPR, UI_BTYPE_SEPR_LINE, UI_BTYPE_LISTBOX)) + return false; + if (but->flag & UI_HIDDEN) + return false; + if (but->flag & UI_SCROLLED) + return false; + if ((but->type == UI_BTYPE_TEXT) && (but->dt == UI_EMBOSS_NONE) && !labeledit) + return false; + if ((but->type == UI_BTYPE_LISTROW) && labeledit) return false; - if (data->draglock) { - if (ABS(mx - data->dragstartx) <= BUTTON_DRAGLOCK_THRESH) { - return false; - } -#ifdef USE_DRAG_MULTINUM - if (ELEM(data->multi_data.init, BUTTON_MULTI_INIT_UNSET, BUTTON_MULTI_INIT_SETUP)) { - return false; + return true; +} + +static bool ui_but_find_select_in_enum__cmp(const uiBut *but_a, const uiBut *but_b) +{ + return ((but_a->type == but_b->type) && + (but_a->alignnr == but_b->alignnr) && + (but_a->poin == but_b->poin) && + (but_a->rnapoin.type == but_b->rnapoin.type) && + (but_a->rnaprop == but_b->rnaprop)); +} + +/** + * Finds the pressed button in an aligned row (typically an expanded enum). + * + * \param direction: Use when there may be multiple buttons pressed. + */ +uiBut *ui_but_find_select_in_enum(uiBut *but, int direction) +{ + uiBut *but_iter = but; + uiBut *but_found = NULL; + BLI_assert(ELEM(direction, -1, 1)); + + while ((but_iter->prev) && + ui_but_find_select_in_enum__cmp(but_iter->prev, but)) + { + but_iter = but_iter->prev; + } + + while (but_iter && ui_but_find_select_in_enum__cmp(but_iter, but)) { + if (but_iter->flag & UI_SELECT) { + but_found = but_iter; + if (direction == 1) { + break; + } } -#endif - data->draglock = false; - data->dragstartx = mx; /* ignore mouse movement within drag-lock */ + but_iter = but_iter->next; } - return true; + return but_found; +} + +uiBut *ui_but_find_active_in_region(ARegion *ar) +{ + uiBlock *block; + uiBut *but; + + for (block = ar->uiblocks.first; block; block = block->next) + for (but = block->buttons.first; but; but = but->next) + if (but->active) + return but; + + return NULL; +} + +bool ui_but_is_active(ARegion *ar) +{ + return (ui_but_find_active_in_region(ar) != NULL); +} + +bool ui_but_is_editing(uiBut *but) +{ + uiHandleButtonData *data = but->active; + return (data && ELEM(data->state, BUTTON_STATE_TEXT_EDITING, BUTTON_STATE_NUM_EDITING)); } static float ui_mouse_scale_warp_factor(const bool shift) @@ -594,6 +830,67 @@ bool ui_but_is_utf8(const uiBut *but) /** \} */ /* -------------------------------------------------------------------- */ +/** \name UI Utilities + * \{ */ + +/** + * Ignore mouse movements within some horizontal pixel threshold before starting to drag + */ +static bool ui_but_dragedit_update_mval(uiHandleButtonData *data, int mx) +{ + if (mx == data->draglastx) + return false; + + if (data->draglock) { + if (ABS(mx - data->dragstartx) <= BUTTON_DRAGLOCK_THRESH) { + return false; + } +#ifdef USE_DRAG_MULTINUM + if (ELEM(data->multi_data.init, BUTTON_MULTI_INIT_UNSET, BUTTON_MULTI_INIT_SETUP)) { + return false; + } +#endif + data->draglock = false; + data->dragstartx = mx; /* ignore mouse movement within drag-lock */ + } + + return true; +} + +/** \} */ + +/* -------------------------------------------------------------------- */ +/** \name Button Snap Values + * + * \{ */ + +enum eSnapType { + SNAP_OFF = 0, + SNAP_ON, + SNAP_ON_SMALL, +}; + +static enum eSnapType ui_event_to_snap(const wmEvent *event) +{ + return (event->ctrl) ? (event->shift) ? SNAP_ON_SMALL : SNAP_ON : SNAP_OFF; +} + +static bool ui_event_is_snap(const wmEvent *event) +{ + return (ELEM(event->type, LEFTCTRLKEY, RIGHTCTRLKEY) || + ELEM(event->type, LEFTSHIFTKEY, RIGHTSHIFTKEY)); +} + +static void ui_color_snap_hue(const enum eSnapType snap, float *r_hue) +{ + const float snap_increment = (snap == SNAP_ON_SMALL) ? 24 : 12; + BLI_assert(snap != SNAP_OFF); + *r_hue = roundf((*r_hue) * snap_increment) / snap_increment; +} + +/** \} */ + +/* -------------------------------------------------------------------- */ /** \name Button Apply/Revert * \{ */ @@ -1735,31 +2032,6 @@ static void ui_selectcontext_apply( #endif /* USE_ALLSELECT */ - -static bool ui_but_contains_point_px_icon(uiBut *but, ARegion *ar, const wmEvent *event) -{ - rcti rect; - int x = event->x, y = event->y; - - ui_window_to_block(ar, but->block, &x, &y); - - BLI_rcti_rctf_copy(&rect, &but->rect); - - if (but->imb || but->type == UI_BTYPE_COLOR) { - /* use button size itself */ - } - else if (but->drawflag & UI_BUT_ICON_LEFT) { - rect.xmax = rect.xmin + (BLI_rcti_size_y(&rect)); - } - else { - int delta = BLI_rcti_size_x(&rect) - BLI_rcti_size_y(&rect); - rect.xmin += delta / 2; - rect.xmax -= delta / 2; - } - - return BLI_rcti_isect_pt(&rect, x, y); -} - /** \} */ /* -------------------------------------------------------------------- */ @@ -2122,11 +2394,6 @@ static void ui_but_drop(bContext *C, const wmEvent *event, uiBut *but, uiHandleB /** \name Button Copy & Paste * \{ */ -static bool ui_but_contains_password(uiBut *but) -{ - return but->rnaprop && (RNA_property_subtype(but->rnaprop) == PROP_PASSWORD); -} - static void ui_but_get_pasted_text_from_clipboard(char **buf_paste, int *buf_len) { char *text; @@ -2604,6 +2871,11 @@ static void ui_but_text_clear(bContext *C, uiBut *but, uiHandleButtonData *data) button_activate_state(C, but, BUTTON_STATE_EXIT); } +void ui_but_clipboard_free(void) +{ + curvemapping_free_data(&but_copypaste_curve); +} + /** \} */ /* -------------------------------------------------------------------- */ @@ -6946,154 +7218,9 @@ static int ui_do_button(bContext *C, uiBlock *block, uiBut *but, const wmEvent * /** \} */ /* -------------------------------------------------------------------- */ -/** \name Button Utilities +/** \name Button Tool Tip * \{ */ -static bool ui_but_contains_pt(uiBut *but, float mx, float my) -{ - return BLI_rctf_isect_pt(&but->rect, mx, my); -} - -void ui_but_pie_dir(RadialDirection dir, float vec[2]) -{ - float angle; - - BLI_assert(dir != UI_RADIAL_NONE); - - angle = DEG2RADF((float)ui_radial_dir_to_angle[dir]); - vec[0] = cosf(angle); - vec[1] = sinf(angle); -} - -static bool ui_but_isect_pie_seg(uiBlock *block, uiBut *but) -{ - const float angle_range = (block->pie_data.flags & UI_PIE_DEGREES_RANGE_LARGE) ? M_PI_4 : M_PI_4 / 2.0; - float vec[2]; - - if (block->pie_data.flags & UI_PIE_INVALID_DIR) - return false; - - ui_but_pie_dir(but->pie_dir, vec); - - if (saacos(dot_v2v2(vec, block->pie_data.pie_dir)) < angle_range) - return true; - - return false; -} - -static bool ui_but_find_select_in_enum__cmp(const uiBut *but_a, const uiBut *but_b) -{ - return ((but_a->type == but_b->type) && - (but_a->alignnr == but_b->alignnr) && - (but_a->poin == but_b->poin) && - (but_a->rnapoin.type == but_b->rnapoin.type) && - (but_a->rnaprop == but_b->rnaprop)); -} - -/** - * Finds the pressed button in an aligned row (typically an expanded enum). - * - * \param direction: Use when there may be multiple buttons pressed. - */ -uiBut *ui_but_find_select_in_enum(uiBut *but, int direction) -{ - uiBut *but_iter = but; - uiBut *but_found = NULL; - BLI_assert(ELEM(direction, -1, 1)); - - while ((but_iter->prev) && - ui_but_find_select_in_enum__cmp(but_iter->prev, but)) - { - but_iter = but_iter->prev; - } - - while (but_iter && ui_but_find_select_in_enum__cmp(but_iter, but)) { - if (but_iter->flag & UI_SELECT) { - but_found = but_iter; - if (direction == 1) { - break; - } - } - but_iter = but_iter->next; - } - - return but_found; -} - -uiBut *ui_but_find_active_in_region(ARegion *ar) -{ - uiBlock *block; - uiBut *but; - - for (block = ar->uiblocks.first; block; block = block->next) - for (but = block->buttons.first; but; but = but->next) - if (but->active) - return but; - - return NULL; -} - -bool ui_but_is_active(ARegion *ar) -{ - return (ui_but_find_active_in_region(ar) != NULL); -} - -bool ui_but_is_editing(uiBut *but) -{ - uiHandleButtonData *data = but->active; - return (data && ELEM(data->state, BUTTON_STATE_TEXT_EDITING, BUTTON_STATE_NUM_EDITING)); -} - -/* is called by notifier */ -void UI_screen_free_active_but(const bContext *C, bScreen *screen) -{ - wmWindow *win = CTX_wm_window(C); - - ED_screen_areas_iter(win, screen, area) { - for (ARegion *region = area->regionbase.first; region; region = region->next) { - uiBut *but = ui_but_find_active_in_region(region); - if (but) { - uiHandleButtonData *data = but->active; - - if (data->menu == NULL && data->searchbox == NULL) - if (data->state == BUTTON_STATE_HIGHLIGHT) - ui_but_active_free(C, but); - } - } - } -} - - - -/* returns true if highlighted button allows drop of names */ -/* called in region context */ -bool UI_but_active_drop_name(bContext *C) -{ - ARegion *ar = CTX_wm_region(C); - uiBut *but = ui_but_find_active_in_region(ar); - - if (but) { - if (ELEM(but->type, UI_BTYPE_TEXT, UI_BTYPE_SEARCH_MENU)) - return 1; - } - - return 0; -} - -bool UI_but_active_drop_color(bContext *C) -{ - ARegion *ar = CTX_wm_region(C); - - if (ar) { - uiBut *but = ui_but_find_active_in_region(ar); - - if (but && but->type == UI_BTYPE_COLOR) - return true; - } - - return false; -} - static void ui_blocks_set_tooltips(ARegion *ar, const bool enable) { uiBlock *block; @@ -7107,177 +7234,6 @@ static void ui_blocks_set_tooltips(ARegion *ar, const bool enable) block->tooltipdisabled = !enable; } -static bool ui_region_contains_point_px(ARegion *ar, int x, int y) -{ - rcti winrct; - - /* scale down area rect to exclude shadow */ - ui_region_winrct_get_no_margin(ar, &winrct); - - /* check if the mouse is in the region */ - if (!BLI_rcti_isect_pt(&winrct, x, y)) { - for (uiBlock *block = ar->uiblocks.first; block; block = block->next) - block->auto_open = false; - - return false; - } - - /* also, check that with view2d, that the mouse is not over the scrollbars - * NOTE: care is needed here, since the mask rect may include the scrollbars - * even when they are not visible, so we need to make a copy of the mask to - * use to check - */ - if (ar->v2d.mask.xmin != ar->v2d.mask.xmax) { - View2D *v2d = &ar->v2d; - int mx, my; - - /* convert window coordinates to region coordinates */ - mx = x; - my = y; - ui_window_to_region(ar, &mx, &my); - - /* check if in the rect */ - if (!BLI_rcti_isect_pt(&v2d->mask, mx, my) || UI_view2d_mouse_in_scrollers(ar, &ar->v2d, x, y)) { - return false; - } - } - - return true; -} - -static bool ui_but_contains_point_px(ARegion *ar, uiBut *but, int x, int y) -{ - uiBlock *block = but->block; - float mx, my; - if (!ui_region_contains_point_px(ar, x, y)) - return false; - - mx = x; - my = y; - - ui_window_to_block_fl(ar, block, &mx, &my); - - if (but->pie_dir != UI_RADIAL_NONE) { - if (!ui_but_isect_pie_seg(block, but)) { - return false; - } - } - else if (!ui_but_contains_pt(but, mx, my)) { - return false; - } - - return true; -} - -/** - * Can we mouse over the button or is it hidden/disabled/layout. - * \note ctrl is kind of a hack currently, - * so that non-embossed UI_BTYPE_TEXT button behaves as a label when ctrl is not pressed. - */ -static bool ui_but_is_interactive(const uiBut *but, const bool labeledit) -{ - /* note, UI_BTYPE_LABEL is included for highlights, this allows drags */ - if ((but->type == UI_BTYPE_LABEL) && but->dragpoin == NULL) - return false; - if (ELEM(but->type, UI_BTYPE_ROUNDBOX, UI_BTYPE_SEPR, UI_BTYPE_SEPR_LINE, UI_BTYPE_LISTBOX)) - return false; - if (but->flag & UI_HIDDEN) - return false; - if (but->flag & UI_SCROLLED) - return false; - if ((but->type == UI_BTYPE_TEXT) && (but->dt == UI_EMBOSS_NONE) && !labeledit) - return false; - if ((but->type == UI_BTYPE_LISTROW) && labeledit) - return false; - - return true; -} - -/* x and y are only used in case event is NULL... */ -static uiBut *ui_but_find_mouse_over_ex(ARegion *ar, const int x, const int y, const bool labeledit) -{ - uiBlock *block; - uiBut *but, *butover = NULL; - float mx, my; - -// if (!win->active) -// return NULL; - if (!ui_region_contains_point_px(ar, x, y)) - return NULL; - - for (block = ar->uiblocks.first; block; block = block->next) { - mx = x; - my = y; - ui_window_to_block_fl(ar, block, &mx, &my); - - for (but = block->buttons.last; but; but = but->prev) { - if (ui_but_is_interactive(but, labeledit)) { - if (but->pie_dir != UI_RADIAL_NONE) { - if (ui_but_isect_pie_seg(block, but)) { - butover = but; - break; - } - } - else if (ui_but_contains_pt(but, mx, my)) { - butover = but; - break; - } - } - } - - /* CLIP_EVENTS prevents the event from reaching other blocks */ - if (block->flag & UI_BLOCK_CLIP_EVENTS) { - /* check if mouse is inside block */ - if (BLI_rctf_isect_pt(&block->rect, mx, my)) { - break; - } - } - } - - return butover; -} - -uiBut *ui_but_find_mouse_over(ARegion *ar, const wmEvent *event) -{ - return ui_but_find_mouse_over_ex(ar, event->x, event->y, event->ctrl != 0); -} - - -static uiBut *ui_list_find_mouse_over_ex(ARegion *ar, int x, int y) -{ - uiBlock *block; - uiBut *but; - float mx, my; - - if (!ui_region_contains_point_px(ar, x, y)) - return NULL; - - for (block = ar->uiblocks.first; block; block = block->next) { - mx = x; - my = y; - ui_window_to_block_fl(ar, block, &mx, &my); - - for (but = block->buttons.last; but; but = but->prev) { - if (but->type == UI_BTYPE_LISTBOX && ui_but_contains_pt(but, mx, my)) { - return but; - } - } - } - - return NULL; -} - -static uiBut *ui_list_find_mouse_over(ARegion *ar, const wmEvent *event) -{ - return ui_list_find_mouse_over_ex(ar, event->x, event->y); -} - -/** \} */ - -/* -------------------------------------------------------------------- */ -/** \name Button Tool Tip - * \{ */ - /** * Recreate tooltip (use to update dynamic tips) */ @@ -7371,7 +7327,6 @@ static bool button_modal_state(uiHandleButtonState state) BUTTON_STATE_MENU_OPEN); } - static void button_activate_state(bContext *C, uiBut *but, uiHandleButtonState state) { uiHandleButtonData *data; @@ -8801,10 +8756,7 @@ static bool ui_menu_scroll_step(ARegion *ar, uiBlock *block, const int scroll_di BLI_assert(0); } - if (!ui_menu_scroll_to_y(ar, block, my)) { - return false; - } - return true; + return ui_menu_scroll_to_y(ar, block, my); } /** \} */ @@ -10274,10 +10226,59 @@ bool UI_textbutton_activate_but(const bContext *C, uiBut *actbut) } } +/** \} */ -void ui_but_clipboard_free(void) +/* -------------------------------------------------------------------- */ +/** \name Public Utilities + * \{ */ + +/* is called by notifier */ +void UI_screen_free_active_but(const bContext *C, bScreen *screen) { - curvemapping_free_data(&but_copypaste_curve); + wmWindow *win = CTX_wm_window(C); + + ED_screen_areas_iter(win, screen, area) { + for (ARegion *region = area->regionbase.first; region; region = region->next) { + uiBut *but = ui_but_find_active_in_region(region); + if (but) { + uiHandleButtonData *data = but->active; + + if (data->menu == NULL && data->searchbox == NULL) + if (data->state == BUTTON_STATE_HIGHLIGHT) + ui_but_active_free(C, but); + } + } + } +} + + +/* returns true if highlighted button allows drop of names */ +/* called in region context */ +bool UI_but_active_drop_name(bContext *C) +{ + ARegion *ar = CTX_wm_region(C); + uiBut *but = ui_but_find_active_in_region(ar); + + if (but) { + if (ELEM(but->type, UI_BTYPE_TEXT, UI_BTYPE_SEARCH_MENU)) + return 1; + } + + return 0; +} + +bool UI_but_active_drop_color(bContext *C) +{ + ARegion *ar = CTX_wm_region(C); + + if (ar) { + uiBut *but = ui_but_find_active_in_region(ar); + + if (but && but->type == UI_BTYPE_COLOR) + return true; + } + + return false; } /** \} */ |