Blender  V2.93
wm_gizmo_group.c
Go to the documentation of this file.
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  *
16  * The Original Code is Copyright (C) 2014 Blender Foundation.
17  * All rights reserved.
18  */
19 
29 #include <stdlib.h>
30 #include <string.h>
31 
32 #include "MEM_guardedalloc.h"
33 
34 #include "BLI_buffer.h"
35 #include "BLI_listbase.h"
36 #include "BLI_rect.h"
37 #include "BLI_string.h"
38 
39 #include "BKE_context.h"
40 #include "BKE_main.h"
41 #include "BKE_report.h"
42 #include "BKE_workspace.h"
43 
44 #include "RNA_access.h"
45 #include "RNA_define.h"
46 
47 #include "WM_api.h"
48 #include "WM_types.h"
49 #include "wm_event_system.h"
50 
51 #include "ED_screen.h"
52 #include "ED_undo.h"
53 
54 /* own includes */
55 #include "wm_gizmo_intern.h"
56 #include "wm_gizmo_wmapi.h"
57 
58 #ifdef WITH_PYTHON
59 # include "BPY_extern.h"
60 #endif
61 
62 /* -------------------------------------------------------------------- */
70 {
71  wmGizmoGroup *gzgroup = MEM_callocN(sizeof(*gzgroup), "gizmo-group");
72 
73  gzgroup->type = gzgt;
74  gzgroup->type->users += 1;
75 
76  /* keep back-link */
77  gzgroup->parent_gzmap = gzmap;
78 
79  BLI_addtail(&gzmap->groups, gzgroup);
80 
81  return gzgroup;
82 }
83 
85 {
86  return BLI_findptr(&gzmap->groups, gzgt, offsetof(wmGizmoGroup, type));
87 }
88 
90 {
91  wmGizmoMap *gzmap = gzgroup->parent_gzmap;
92 
93  /* Similar to WM_gizmo_unlink, but only to keep gzmap state correct,
94  * we don't want to run callbacks. */
95  if (gzmap->gzmap_context.highlight &&
96  gzmap->gzmap_context.highlight->parent_gzgroup == gzgroup) {
97  wm_gizmomap_highlight_set(gzmap, C, NULL, 0);
98  }
99  if (gzmap->gzmap_context.modal && gzmap->gzmap_context.modal->parent_gzgroup == gzgroup) {
100  wm_gizmomap_modal_set(gzmap, C, gzmap->gzmap_context.modal, NULL, false);
101  }
102 
103  for (wmGizmo *gz = gzgroup->gizmos.first, *gz_next; gz; gz = gz_next) {
104  gz_next = gz->next;
105  if (gzmap->gzmap_context.select.len) {
106  WM_gizmo_select_unlink(gzmap, gz);
107  }
108  WM_gizmo_free(gz);
109  }
110  BLI_listbase_clear(&gzgroup->gizmos);
111 
112 #ifdef WITH_PYTHON
113  if (gzgroup->py_instance) {
114  /* do this first in case there are any __del__ functions or
115  * similar that use properties */
117  }
118 #endif
119 
120  if (gzgroup->reports && (gzgroup->reports->flag & RPT_FREE)) {
121  BKE_reports_clear(gzgroup->reports);
122  MEM_freeN(gzgroup->reports);
123  }
124 
125  if (gzgroup->customdata_free) {
126  gzgroup->customdata_free(gzgroup->customdata);
127  }
128  else {
129  MEM_SAFE_FREE(gzgroup->customdata);
130  }
131 
132  BLI_remlink(&gzmap->groups, gzgroup);
133 
134  if (gzgroup->tag_remove == false) {
135  gzgroup->type->users -= 1;
136  }
137 
138  MEM_freeN(gzgroup);
139 }
140 
142 {
143  if (gzgroup->tag_remove == false) {
144  gzgroup->tag_remove = true;
145  gzgroup->type->users -= 1;
146  BLI_assert(gzgroup->type->users >= 0);
148  }
149 }
150 
155 {
156  BLI_assert(BLI_findindex(&gzgroup->gizmos, gz) == -1);
157  BLI_addtail(&gzgroup->gizmos, gz);
158  gz->parent_gzgroup = gzgroup;
159 }
160 
161 int WM_gizmo_cmp_temp_fl(const void *gz_a_ptr, const void *gz_b_ptr)
162 {
163  const wmGizmo *gz_a = gz_a_ptr;
164  const wmGizmo *gz_b = gz_b_ptr;
165  if (gz_a->temp.f < gz_b->temp.f) {
166  return -1;
167  }
168  if (gz_a->temp.f > gz_b->temp.f) {
169  return 1;
170  }
171  return 0;
172 }
173 
174 int WM_gizmo_cmp_temp_fl_reverse(const void *gz_a_ptr, const void *gz_b_ptr)
175 {
176  const wmGizmo *gz_a = gz_a_ptr;
177  const wmGizmo *gz_b = gz_b_ptr;
178  if (gz_a->temp.f < gz_b->temp.f) {
179  return 1;
180  }
181  if (gz_a->temp.f > gz_b->temp.f) {
182  return -1;
183  }
184  return 0;
185 }
186 
188  const wmGizmoGroup *gzgroup,
189  wmGizmo *gz,
190  const int event_modifier,
191  int *r_gzgroup_keymap_uses_modifier)
192 {
193  if (gz->keymap) {
194  wmKeyMap *keymap = WM_keymap_active(wm, gz->keymap);
195  if (!WM_keymap_uses_event_modifier(keymap, event_modifier)) {
196  return false;
197  }
198  }
199  else if (gzgroup->type->keymap) {
200  if (*r_gzgroup_keymap_uses_modifier == -1) {
201  wmKeyMap *keymap = WM_keymap_active(wm, gzgroup->type->keymap);
202  *r_gzgroup_keymap_uses_modifier = WM_keymap_uses_event_modifier(keymap, event_modifier);
203  }
204  if (*r_gzgroup_keymap_uses_modifier == 0) {
205  return false;
206  }
207  }
208  return true;
209 }
210 
212  const wmGizmoGroup *gzgroup,
213  bContext *C,
214  const int event_modifier,
215  const int mval[2],
216  int *r_part)
217 {
218  int gzgroup_keymap_uses_modifier = -1;
219 
220  LISTBASE_FOREACH (wmGizmo *, gz, &gzgroup->gizmos) {
221  if (gz->type->test_select && (gz->flag & (WM_GIZMO_HIDDEN | WM_GIZMO_HIDDEN_SELECT)) == 0) {
222 
224  wm, gzgroup, gz, event_modifier, &gzgroup_keymap_uses_modifier)) {
225  continue;
226  }
227 
228  if ((*r_part = gz->type->test_select(C, gz, mval)) != -1) {
229  return gz;
230  }
231  }
232  }
233 
234  return NULL;
235 }
236 
242  const wmGizmoGroup *gzgroup,
243  const int event_modifier,
244  BLI_Buffer *visible_gizmos)
245 {
246  int gzgroup_keymap_uses_modifier = -1;
247  for (wmGizmo *gz = gzgroup->gizmos.last; gz; gz = gz->prev) {
248  if ((gz->flag & (WM_GIZMO_HIDDEN | WM_GIZMO_HIDDEN_SELECT)) == 0) {
249  if (((gzgroup->type->flag & WM_GIZMOGROUPTYPE_3D) &&
250  (gz->type->draw_select || gz->type->test_select)) ||
251  ((gzgroup->type->flag & WM_GIZMOGROUPTYPE_3D) == 0 && gz->type->test_select)) {
252 
254  wm, gzgroup, gz, event_modifier, &gzgroup_keymap_uses_modifier)) {
255  continue;
256  }
257 
258  BLI_buffer_append(visible_gizmos, wmGizmo *, gz);
259  }
260  }
261  }
262 }
263 
265 {
266  /* prepare for first draw */
267  if (UNLIKELY((gzgroup->init_flag & WM_GIZMOGROUP_INIT_SETUP) == 0)) {
268  gzgroup->type->setup(C, gzgroup);
269 
270  /* Not ideal, initialize keymap here, needed for RNA runtime generated gizmos. */
271  wmGizmoGroupType *gzgt = gzgroup->type;
272  if (gzgt->keymap == NULL) {
275  BLI_assert(gzgt->keymap != NULL);
276  }
278  }
279 
280  /* Refresh may be called multiple times,
281  * this just ensures its called at least once before we draw. */
282  if (UNLIKELY((gzgroup->init_flag & WM_GIZMOGROUP_INIT_REFRESH) == 0)) {
283  /* Clear the flag before calling refresh so the callback
284  * can postpone the refresh by clearing this flag. */
286  WM_gizmo_group_refresh(C, gzgroup);
287  }
288 }
289 
291  Main *bmain,
292  const wmGizmoGroupType *gzgt,
293  const bToolRef *tref)
294 {
295  wmGizmoMapType *gzmap_type = WM_gizmomaptype_find(&gzgt->gzmap_params);
296  for (bScreen *screen = bmain->screens.first; screen; screen = screen->id.next) {
297  LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
298  if (area->runtime.tool == tref) {
299  LISTBASE_FOREACH (ARegion *, region, &area->regionbase) {
300  wmGizmoMap *gzmap = region->gizmo_map;
301  if (gzmap && gzmap->type == gzmap_type) {
302  wmGizmoGroup *gzgroup, *gzgroup_next;
303  for (gzgroup = gzmap->groups.first; gzgroup; gzgroup = gzgroup_next) {
304  gzgroup_next = gzgroup->next;
305  if (gzgroup->type == gzgt) {
306  BLI_assert(gzgroup->parent_gzmap == gzmap);
307  wm_gizmogroup_free(C, gzgroup);
309  }
310  }
311  }
312  }
313  }
314  }
315  }
316 }
317 
319  const eWM_GizmoFlagMapDrawStep drawstep)
320 {
321  switch (drawstep) {
323  return (gzgroup->type->flag & WM_GIZMOGROUPTYPE_3D) == 0;
325  return (gzgroup->type->flag & WM_GIZMOGROUPTYPE_3D);
326  default:
328  return false;
329  }
330 }
331 
333 {
334  if (gzgroup->type->flag & WM_GIZMOGROUPTYPE_SELECT) {
335  LISTBASE_FOREACH (const wmGizmo *, gz, &gzgroup->gizmos) {
336  if (gz->state & WM_GIZMO_STATE_SELECT) {
337  return true;
338  }
339  }
340  }
341  return false;
342 }
343 
346 /* -------------------------------------------------------------------- */
353 static int gizmo_select_invoke(bContext *C, wmOperator *op, const wmEvent *UNUSED(event))
354 {
355  ARegion *region = CTX_wm_region(C);
356  wmGizmoMap *gzmap = region->gizmo_map;
358  wmGizmo *highlight = gzmap->gzmap_context.highlight;
359 
360  bool extend = RNA_boolean_get(op->ptr, "extend");
361  bool deselect = RNA_boolean_get(op->ptr, "deselect");
362  bool toggle = RNA_boolean_get(op->ptr, "toggle");
363 
364  /* deselect all first */
365  if (extend == false && deselect == false && toggle == false) {
367  BLI_assert(msel->items == NULL && msel->len == 0);
368  UNUSED_VARS_NDEBUG(msel);
369  }
370 
371  if (highlight) {
372  const bool is_selected = (highlight->state & WM_GIZMO_STATE_SELECT);
373  bool redraw = false;
374 
375  if (toggle) {
376  /* toggle: deselect if already selected, else select */
377  deselect = is_selected;
378  }
379 
380  if (deselect) {
381  if (is_selected && WM_gizmo_select_set(gzmap, highlight, false)) {
382  redraw = true;
383  }
384  }
385  else if (wm_gizmo_select_and_highlight(C, gzmap, highlight)) {
386  redraw = true;
387  }
388 
389  if (redraw) {
391  }
392 
393  return OPERATOR_FINISHED;
394  }
395 
398 }
399 
401 {
402  /* identifiers */
403  ot->name = "Gizmo Select";
404  ot->description = "Select the currently highlighted gizmo";
405  ot->idname = "GIZMOGROUP_OT_gizmo_select";
406 
407  /* api callbacks */
409 
410  ot->flag = OPTYPE_UNDO;
411 
413 }
414 
415 typedef struct GizmoTweakData {
419 
420  int init_event; /* initial event type */
421  int flag; /* tweak flags */
422 
424 
425 static bool gizmo_tweak_start(bContext *C, wmGizmoMap *gzmap, wmGizmo *gz, const wmEvent *event)
426 {
427  /* activate highlighted gizmo */
428  wm_gizmomap_modal_set(gzmap, C, gz, event, true);
429 
430  return (gz->state & WM_GIZMO_STATE_MODAL);
431 }
432 
434  bContext *C, wmGizmoMap *gzmap, wmGizmo *gz, const wmEvent *event, bool *r_is_modal)
435 {
437  if (r_is_modal) {
438  *r_is_modal = false;
439  }
440  if (gzop && gzop->type) {
441 
442  /* Undo/Redo */
443  if (gzop->is_redo) {
446 
447  /* We may want to enable this, for now the gizmo can manage its own properties. */
448 #if 0
449  IDP_MergeGroup(gzop->ptr.data, op->properties, false);
450 #endif
451 
453  ED_undo_pop_op(C, op);
454  }
455 
456  /* XXX temporary workaround for modal gizmo operator
457  * conflicting with modal operator attached to gizmo */
458  if (gzop->type->modal) {
459  /* activate highlighted gizmo */
460  wm_gizmomap_modal_set(gzmap, C, gz, event, true);
461  if (r_is_modal) {
462  *r_is_modal = true;
463  }
464  }
465  else {
466  if (gz->parent_gzgroup->type->invoke_prepare) {
467  gz->parent_gzgroup->type->invoke_prepare(C, gz->parent_gzgroup, gz, event);
468  }
469  /* Allow for 'button' gizmos, single click to run an action. */
470  WM_gizmo_operator_invoke(C, gz, gzop);
471  }
472  return true;
473  }
474  return false;
475 }
476 
477 static void gizmo_tweak_finish(bContext *C, wmOperator *op, const bool cancel, bool clear_modal)
478 {
479  GizmoTweakData *mtweak = op->customdata;
480  if (mtweak->gz_modal->type->exit) {
481  mtweak->gz_modal->type->exit(C, mtweak->gz_modal, cancel);
482  }
483  if (clear_modal) {
484  /* The gizmo may have been removed. */
485  if ((BLI_findindex(&mtweak->gzmap->groups, mtweak->gzgroup) != -1) &&
486  (BLI_findindex(&mtweak->gzgroup->gizmos, mtweak->gz_modal) != -1)) {
487  wm_gizmomap_modal_set(mtweak->gzmap, C, mtweak->gz_modal, NULL, false);
488  }
489  }
490  MEM_freeN(mtweak);
491 }
492 
493 static int gizmo_tweak_modal(bContext *C, wmOperator *op, const wmEvent *event)
494 {
495  GizmoTweakData *mtweak = op->customdata;
496  wmGizmo *gz = mtweak->gz_modal;
497  int retval = OPERATOR_PASS_THROUGH;
498  bool clear_modal = true;
499 
500  if (gz == NULL) {
503  }
504 
505  if (retval == OPERATOR_FINISHED) {
506  /* pass */
507  }
508  else if (event->type == mtweak->init_event && event->val == KM_RELEASE) {
509  retval = OPERATOR_FINISHED;
510  }
511  else if (event->type == EVT_MODAL_MAP) {
512  switch (event->val) {
513  case TWEAK_MODAL_CANCEL:
514  retval = OPERATOR_CANCELLED;
515  break;
516  case TWEAK_MODAL_CONFIRM:
517  retval = OPERATOR_FINISHED;
518  break;
520  mtweak->flag |= WM_GIZMO_TWEAK_PRECISE;
521  break;
523  mtweak->flag &= ~WM_GIZMO_TWEAK_PRECISE;
524  break;
525 
526  case TWEAK_MODAL_SNAP_ON:
527  mtweak->flag |= WM_GIZMO_TWEAK_SNAP;
528  break;
530  mtweak->flag &= ~WM_GIZMO_TWEAK_SNAP;
531  break;
532  }
533  }
534 
535  if (retval != OPERATOR_PASS_THROUGH) {
536  gizmo_tweak_finish(C, op, retval != OPERATOR_FINISHED, clear_modal);
537  return retval;
538  }
539 
540  /* handle gizmo */
541  wmGizmoFnModal modal_fn = gz->custom_modal ? gz->custom_modal : gz->type->modal;
542  if (modal_fn) {
543  /* Ugly hack to ensure Python won't get 'EVT_MODAL_MAP' which isn't supported, see T73727.
544  * note that we could move away from wrapping modal gizmos in a modal operator,
545  * since it's causing the need for code like this. */
546  wmEvent *evil_event = (wmEvent *)event;
547  short event_modal_val = 0;
548 
549  if (event->type == EVT_MODAL_MAP) {
550  event_modal_val = evil_event->val;
551  evil_event->type = evil_event->prevtype;
552  evil_event->val = evil_event->prevval;
553  }
554 
555  int modal_retval = modal_fn(C, gz, event, mtweak->flag);
556 
557  if (event_modal_val != 0) {
558  evil_event->type = EVT_MODAL_MAP;
559  evil_event->val = event_modal_val;
560  }
561 
562  if ((modal_retval & OPERATOR_RUNNING_MODAL) == 0) {
563  gizmo_tweak_finish(C, op, (modal_retval & OPERATOR_CANCELLED) != 0, true);
564  return OPERATOR_FINISHED;
565  }
566 
567  /* Ugly hack to send gizmo events */
568  evil_event->type = EVT_GIZMO_UPDATE;
569  }
570 
571  /* always return PASS_THROUGH so modal handlers
572  * with gizmos attached can update */
574  return OPERATOR_PASS_THROUGH;
575 }
576 
577 static int gizmo_tweak_invoke(bContext *C, wmOperator *op, const wmEvent *event)
578 {
579  ARegion *region = CTX_wm_region(C);
580  wmGizmoMap *gzmap = region->gizmo_map;
581  wmGizmo *gz = gzmap->gzmap_context.highlight;
582 
583  /* Needed for single click actions which don't enter modal state. */
585 
586  if (!gz) {
587  /* wm_handlers_do_intern shouldn't let this happen */
590  }
591 
592  const int highlight_part_init = gz->highlight_part;
593 
594  if (gz->drag_part != -1) {
595  if (WM_event_is_mouse_drag(event)) {
596  gz->highlight_part = gz->drag_part;
597  }
598  }
599 
600  if (gizmo_tweak_start_and_finish(C, gzmap, gz, event, NULL)) {
601  return OPERATOR_FINISHED;
602  }
603 
604  if (!gizmo_tweak_start(C, gzmap, gz, event)) {
605  /* failed to start */
606  gz->highlight_part = highlight_part_init;
607  return OPERATOR_PASS_THROUGH;
608  }
609 
610  GizmoTweakData *mtweak = MEM_mallocN(sizeof(GizmoTweakData), __func__);
611 
613  mtweak->gz_modal = gzmap->gzmap_context.highlight;
614  mtweak->gzgroup = mtweak->gz_modal->parent_gzgroup;
615  mtweak->gzmap = gzmap;
616  mtweak->flag = 0;
617 
618  op->customdata = mtweak;
619 
621 
622  return OPERATOR_RUNNING_MODAL;
623 }
624 
626 {
627  /* identifiers */
628  ot->name = "Gizmo Tweak";
629  ot->description = "Tweak the active gizmo";
630  ot->idname = "GIZMOGROUP_OT_gizmo_tweak";
631 
632  /* api callbacks */
635 
636  /* TODO(campbell): This causes problems tweaking settings for operators,
637  * need to find a way to support this. */
638 #if 0
639  ot->flag = OPTYPE_UNDO;
640 #endif
641 }
642 
646 {
647  wmKeyMap *keymap;
648  char name[KMAP_MAX_NAME];
649 
650  static EnumPropertyItem modal_items[] = {
651  {TWEAK_MODAL_CANCEL, "CANCEL", 0, "Cancel", ""},
652  {TWEAK_MODAL_CONFIRM, "CONFIRM", 0, "Confirm", ""},
653  {TWEAK_MODAL_PRECISION_ON, "PRECISION_ON", 0, "Enable Precision", ""},
654  {TWEAK_MODAL_PRECISION_OFF, "PRECISION_OFF", 0, "Disable Precision", ""},
655  {TWEAK_MODAL_SNAP_ON, "SNAP_ON", 0, "Enable Snap", ""},
656  {TWEAK_MODAL_SNAP_OFF, "SNAP_OFF", 0, "Disable Snap", ""},
657  {0, NULL, 0, NULL, NULL},
658  };
659 
660  STRNCPY(name, "Generic Gizmo Tweak Modal Map");
661  keymap = WM_modalkeymap_find(keyconf, name);
662 
663  /* this function is called for each spacetype, only needs to add map once */
664  if (keymap && keymap->modal_items) {
665  return NULL;
666  }
667 
668  keymap = WM_modalkeymap_ensure(keyconf, name, modal_items);
669 
670  /* items for modal map */
673 
676 
684 
689 
690  WM_modalkeymap_assign(keymap, "GIZMOGROUP_OT_gizmo_tweak");
691 
692  return keymap;
693 }
694  /* wmGizmoGroup */
696 
697 /* -------------------------------------------------------------------- */
702 {
704 }
705 
707  wmKeyConfig *kc)
708 {
710 }
711 
713  wmKeyConfig *kc)
714 {
716 }
717 
727  wmKeyConfig *kc, const char *name, const struct wmGizmoMapType_Params *params)
728 {
729  /* Use area and region id since we might have multiple gizmos
730  * with the same name in different areas/regions. */
731  wmKeyMap *km = WM_keymap_ensure(kc, name, params->spaceid, params->regionid);
732  const bool do_init = BLI_listbase_is_empty(&km->items);
733 
734  /* FIXME(campbell) */
735 #if 0
736  const int select_mouse = (U.flag & USER_LMOUSESELECT) ? LEFTMOUSE : RIGHTMOUSE;
737  const int select_tweak = (U.flag & USER_LMOUSESELECT) ? EVT_TWEAK_L : EVT_TWEAK_R;
738  const int action_mouse = (U.flag & USER_LMOUSESELECT) ? RIGHTMOUSE : LEFTMOUSE;
739 #else
740  const int select_mouse = RIGHTMOUSE;
741  const int select_tweak = EVT_TWEAK_R;
742  const int action_mouse = LEFTMOUSE;
743 #endif
744 
745  if (do_init) {
746  WM_keymap_add_item(km, "GIZMOGROUP_OT_gizmo_tweak", action_mouse, KM_PRESS, KM_ANY, 0);
747  WM_keymap_add_item(km, "GIZMOGROUP_OT_gizmo_tweak", select_tweak, KM_ANY, 0, 0);
748  }
749 
750  if (do_init) {
752  km, "GIZMOGROUP_OT_gizmo_select", select_mouse, KM_PRESS, 0, 0);
753  RNA_boolean_set(kmi->ptr, "extend", false);
754  RNA_boolean_set(kmi->ptr, "deselect", false);
755  RNA_boolean_set(kmi->ptr, "toggle", false);
756  kmi = WM_keymap_add_item(
757  km, "GIZMOGROUP_OT_gizmo_select", select_mouse, KM_PRESS, KM_SHIFT, 0);
758  RNA_boolean_set(kmi->ptr, "extend", false);
759  RNA_boolean_set(kmi->ptr, "deselect", false);
760  RNA_boolean_set(kmi->ptr, "toggle", true);
761  }
762 
763  return km;
764 }
765 
767  wmKeyConfig *kc)
768 {
769  struct wmGizmoMapType_Params params = {
770  .spaceid = SPACE_EMPTY,
771  .regionid = RGN_TYPE_WINDOW,
772  };
773  return WM_gizmogroup_keymap_template_select_ex(kc, "Generic Gizmo Select", &params);
774 }
775 
776 /* -------------------------------------------------------------------- */
784 {
785  const char *idname = "Generic Gizmo";
787 }
789 {
791 }
792 
794 {
795  const char *idname = "Generic Gizmo Select";
797 }
799 {
801 }
802 
804 {
805  const char *idname = "Generic Gizmo Drag";
807 }
809 {
811 }
812 
814 {
815  const char *idname = "Generic Gizmo Click Drag";
817 }
819 {
821 }
822 
825 {
826  const char *idname = "Generic Gizmo Maybe Drag";
828 }
830 {
832 }
833 
836 /* -------------------------------------------------------------------- */
841  const wmGizmoGroupType *gzgt)
842 {
843  /* could use hash lookups as operator types do, for now simple search. */
844  LISTBASE_FOREACH (wmGizmoGroupTypeRef *, gzgt_ref, &gzmap_type->grouptype_refs) {
845  if (gzgt_ref->type == gzgt) {
846  return gzgt_ref;
847  }
848  }
849  return NULL;
850 }
851 
853  const char *idname)
854 {
855  /* could use hash lookups as operator types do, for now simple search. */
856  LISTBASE_FOREACH (wmGizmoGroupTypeRef *, gzgt_ref, &gzmap_type->grouptype_refs) {
857  if (STREQ(idname, gzgt_ref->type->idname)) {
858  return gzgt_ref;
859  }
860  }
861  return NULL;
862 }
863 
869 {
870  wmGizmoGroupType *gzgt = WM_gizmogrouptype_find(idname, false);
871  BLI_assert(gzgt != NULL);
872  return WM_gizmomaptype_group_link_ptr(gzmap_type, gzgt);
873 }
874 
876  wmGizmoGroupType *gzgt)
877 {
878  wmGizmoGroupTypeRef *gzgt_ref = MEM_callocN(sizeof(wmGizmoGroupTypeRef), "gizmo-group-ref");
879  gzgt_ref->type = gzgt;
880  BLI_addtail(&gzmap_type->grouptype_refs, gzgt_ref);
881  return gzgt_ref;
882 }
883 
885 {
886  /* init keymap - on startup there's an extra call to init keymaps for 'permanent' gizmo-groups */
887  wm_gizmogrouptype_setup_keymap(gzgt, ((wmWindowManager *)bmain->wm.first)->defaultconf);
888 }
889 
891  wmGizmoMapType *gzmap_type,
892  wmGizmoGroupType *gzgt)
893 {
894  /* Tools add themselves. */
895  if (gzgt->flag & WM_GIZMOGROUPTYPE_TOOL_INIT) {
896  return;
897  }
898 
899  /* now create a gizmo for all existing areas */
900  for (bScreen *screen = bmain->screens.first; screen; screen = screen->id.next) {
901  LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
902  LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
903  ListBase *lb = (sl == area->spacedata.first) ? &area->regionbase : &sl->regionbase;
904  LISTBASE_FOREACH (ARegion *, region, lb) {
905  wmGizmoMap *gzmap = region->gizmo_map;
906  if (gzmap && gzmap->type == gzmap_type) {
907  WM_gizmomaptype_group_init_runtime_with_region(gzmap_type, gzgt, region);
908  }
909  }
910  }
911  }
912  }
913 }
914 
916  wmGizmoGroupType *gzgt,
917  ARegion *region)
918 {
919  wmGizmoMap *gzmap = region->gizmo_map;
920  BLI_assert(gzmap && gzmap->type == gzmap_type);
921  UNUSED_VARS_NDEBUG(gzmap_type);
922 
923  wmGizmoGroup *gzgroup = wm_gizmogroup_new_from_type(gzmap, gzgt);
924 
925  /* Don't allow duplicates when switching modes for e.g. see: T66229. */
926  LISTBASE_FOREACH (wmGizmoGroup *, gzgroup_iter, &gzmap->groups) {
927  if (gzgroup_iter->type == gzgt) {
928  if (gzgroup_iter != gzgroup) {
929  WM_gizmo_group_tag_remove(gzgroup_iter);
930  }
931  }
932  }
933 
934  wm_gizmomap_highlight_set(gzmap, NULL, NULL, 0);
935 
937 
938  return gzgroup;
939 }
940 
945 {
946  MEM_freeN(gzgt_ref);
947 }
948 
950  Main *bmain,
951  wmGizmoMapType *gzmap_type,
952  const wmGizmoGroupType *gzgt)
953 {
954  /* Free instances. */
955  for (bScreen *screen = bmain->screens.first; screen; screen = screen->id.next) {
956  LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
957  LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
958  ListBase *lb = (sl == area->spacedata.first) ? &area->regionbase : &sl->regionbase;
959  LISTBASE_FOREACH (ARegion *, region, lb) {
960  wmGizmoMap *gzmap = region->gizmo_map;
961  if (gzmap && gzmap->type == gzmap_type) {
962  wmGizmoGroup *gzgroup, *gzgroup_next;
963  for (gzgroup = gzmap->groups.first; gzgroup; gzgroup = gzgroup_next) {
964  gzgroup_next = gzgroup->next;
965  if (gzgroup->type == gzgt) {
966  BLI_assert(gzgroup->parent_gzmap == gzmap);
967  wm_gizmogroup_free(C, gzgroup);
969  }
970  }
971  }
972  }
973  }
974  }
975  }
976 
977  /* Free types. */
978  wmGizmoGroupTypeRef *gzgt_ref = WM_gizmomaptype_group_find_ptr(gzmap_type, gzgt);
979  if (gzgt_ref) {
980  BLI_remlink(&gzmap_type->grouptype_refs, gzgt_ref);
981  WM_gizmomaptype_group_free(gzgt_ref);
982  }
983 
984  /* TODO(campbell): Gizmos may share keymaps, for now don't
985  * remove however we could flag them as temporary/owned by the gizmo. */
986 #if 0
987  /* Note, we may want to keep this keymap for editing */
988  WM_keymap_remove(gzgt->keyconf, gzgt->keymap);
989 #endif
990 
991  BLI_assert(WM_gizmomaptype_group_find_ptr(gzmap_type, gzgt) == NULL);
992 }
993 
995 {
996  /* Use flag since setup_keymap may return NULL,
997  * in that case we better not keep calling it. */
999  gzgt->keymap = gzgt->setup_keymap(gzgt, keyconf);
1000  gzgt->keyconf = keyconf;
1002  }
1003 }
1004  /* wmGizmoGroupType */
1006 
1007 /* -------------------------------------------------------------------- */
1023 {
1024  WM_gizmomaptype_group_link_ptr(gzmap_type, gzgt);
1025 
1027 }
1029 {
1030  wmGizmoMapType *gzmap_type = WM_gizmomaptype_ensure(&gzgt->gzmap_params);
1031  WM_gizmo_group_type_add_ptr_ex(gzgt, gzmap_type);
1032 }
1033 void WM_gizmo_group_type_add(const char *idname)
1034 {
1035  wmGizmoGroupType *gzgt = WM_gizmogrouptype_find(idname, false);
1036  BLI_assert(gzgt != NULL);
1038 }
1039 
1041 {
1042  wmGizmoGroupTypeRef *gzgt_ref = WM_gizmomaptype_group_find_ptr(gzmap_type, gzgt);
1043  if (gzgt_ref == NULL) {
1044  WM_gizmo_group_type_add_ptr_ex(gzgt, gzmap_type);
1045  return true;
1046  }
1047  return false;
1048 }
1050 {
1051  wmGizmoMapType *gzmap_type = WM_gizmomaptype_ensure(&gzgt->gzmap_params);
1052  return WM_gizmo_group_type_ensure_ptr_ex(gzgt, gzmap_type);
1053 }
1054 bool WM_gizmo_group_type_ensure(const char *idname)
1055 {
1056  wmGizmoGroupType *gzgt = WM_gizmogrouptype_find(idname, false);
1057  BLI_assert(gzgt != NULL);
1058  return WM_gizmo_group_type_ensure_ptr(gzgt);
1059 }
1060 
1065  wmGizmoGroupType *gzgt,
1066  wmGizmoMapType *gzmap_type)
1067 {
1068  WM_gizmomaptype_group_unlink(NULL, bmain, gzmap_type, gzgt);
1069 }
1071 {
1072  wmGizmoMapType *gzmap_type = WM_gizmomaptype_ensure(&gzgt->gzmap_params);
1073  WM_gizmo_group_type_remove_ptr_ex(bmain, gzgt, gzmap_type);
1074 }
1075 void WM_gizmo_group_type_remove(struct Main *bmain, const char *idname)
1076 {
1077  wmGizmoGroupType *gzgt = WM_gizmogrouptype_find(idname, false);
1078  BLI_assert(gzgt != NULL);
1079  WM_gizmo_group_type_remove_ptr(bmain, gzgt);
1080 }
1081 
1083  wmGizmoGroupType *gzgt,
1084  wmGizmoMapType *gzmap_type)
1085 {
1086  wmGizmoGroupTypeRef *gzgt_ref = WM_gizmomaptype_group_find_ptr(gzmap_type, gzgt);
1087  BLI_assert(gzgt_ref != NULL);
1088  UNUSED_VARS_NDEBUG(gzgt_ref);
1089  WM_gizmomaptype_group_unlink(NULL, bmain, gzmap_type, gzgt);
1090  WM_gizmo_group_type_add_ptr_ex(gzgt, gzmap_type);
1091 }
1093 {
1094  wmGizmoMapType *gzmap_type = WM_gizmomaptype_ensure(&gzgt->gzmap_params);
1095  WM_gizmo_group_type_reinit_ptr_ex(bmain, gzgt, gzmap_type);
1096 }
1097 void WM_gizmo_group_type_reinit(struct Main *bmain, const char *idname)
1098 {
1099  wmGizmoGroupType *gzgt = WM_gizmogrouptype_find(idname, false);
1100  BLI_assert(gzgt != NULL);
1101  WM_gizmo_group_type_reinit_ptr(bmain, gzgt);
1102 }
1103 
1104 /* delayed versions */
1105 
1107 {
1109 }
1110 
1112 {
1113  wmGizmoMapType *gzmap_type = WM_gizmomaptype_ensure(&gzgt->gzmap_params);
1115 }
1116 
1117 void WM_gizmo_group_type_unlink_delayed(const char *idname)
1118 {
1119  wmGizmoGroupType *gzgt = WM_gizmogrouptype_find(idname, false);
1120  BLI_assert(gzgt != NULL);
1122 }
1123 
1125  wmGizmoMapType *gzmap_type,
1126  ScrArea *area)
1127 {
1128  LISTBASE_FOREACH (ARegion *, region, &area->regionbase) {
1129  wmGizmoMap *gzmap = region->gizmo_map;
1130  if (gzmap && gzmap->type == gzmap_type) {
1131  LISTBASE_FOREACH (wmGizmoGroup *, gzgroup, &gzmap->groups) {
1132  if (gzgroup->type == gzgt) {
1133  WM_gizmo_group_tag_remove(gzgroup);
1134  }
1135  }
1136  }
1137  }
1138 }
1139 
1142 /* -------------------------------------------------------------------- */
1147 {
1148  /* If we're tagged, only use compatible. */
1149  if (gzgt->owner_id[0] != '\0') {
1150  const WorkSpace *workspace = CTX_wm_workspace(C);
1151  if (BKE_workspace_owner_id_check(workspace, gzgt->owner_id) == false) {
1152  return false;
1153  }
1154  }
1155  /* Check for poll function, if gizmo-group belongs to an operator,
1156  * also check if the operator is running. */
1157  return (!gzgt->poll || gzgt->poll(C, (wmGizmoGroupType *)gzgt));
1158 }
1159 
1161 {
1162  const wmGizmoGroupType *gzgt = gzgroup->type;
1164  wmGizmoMap *gzmap = gzgroup->parent_gzmap;
1165  wmGizmo *gz = wm_gizmomap_highlight_get(gzmap);
1166  if (!gz || gz->parent_gzgroup != gzgroup) {
1167  wmWindow *win = CTX_wm_window(C);
1168  ARegion *region = CTX_wm_region(C);
1169  BLI_assert(region->gizmo_map == gzmap);
1170  /* Check if the tweak event originated from this region. */
1171  if ((win->tweak != NULL) && BLI_rcti_compare(&region->winrct, &win->tweak->winrct)) {
1172  /* We need to run refresh again. */
1175  gzgroup->hide.delay_refresh_for_tweak = true;
1176  return;
1177  }
1178  }
1179  gzgroup->hide.delay_refresh_for_tweak = false;
1180  }
1181 
1182  if (gzgroup->hide.any) {
1183  return;
1184  }
1185 
1186  if (gzgt->refresh) {
1187  gzgt->refresh(C, gzgroup);
1188  }
1189 }
1190 
struct WorkSpace * CTX_wm_workspace(const bContext *C)
Definition: context.c:704
struct wmWindowManager * CTX_wm_manager(const bContext *C)
Definition: context.c:689
struct ARegion * CTX_wm_region(const bContext *C)
Definition: context.c:725
struct wmWindow * CTX_wm_window(const bContext *C)
Definition: context.c:699
void IDP_MergeGroup(struct IDProperty *dest, const struct IDProperty *src, const bool do_overwrite) ATTR_NONNULL()
void BKE_reports_clear(ReportList *reports)
Definition: report.c:84
bool BKE_workspace_owner_id_check(const struct WorkSpace *workspace, const char *owner_id) ATTR_NONNULL()
#define BLI_assert_unreachable()
Definition: BLI_assert.h:96
#define BLI_assert(a)
Definition: BLI_assert.h:58
#define BLI_buffer_append(buffer_, type_, val_)
Definition: BLI_buffer.h:64
BLI_INLINE bool BLI_listbase_is_empty(const struct ListBase *lb)
Definition: BLI_listbase.h:124
#define LISTBASE_FOREACH(type, var, list)
Definition: BLI_listbase.h:172
BLI_INLINE void BLI_listbase_clear(struct ListBase *lb)
Definition: BLI_listbase.h:128
void BLI_addtail(struct ListBase *listbase, void *vlink) ATTR_NONNULL(1)
Definition: listbase.c:110
void BLI_remlink(struct ListBase *listbase, void *vlink) ATTR_NONNULL(1)
Definition: listbase.c:133
int BLI_findindex(const struct ListBase *listbase, const void *vlink) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1)
void * BLI_findptr(const struct ListBase *listbase, const void *ptr, const int offset) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1)
bool BLI_rcti_compare(const struct rcti *rect_a, const struct rcti *rect_b)
#define STRNCPY(dst, src)
Definition: BLI_string.h:163
#define UNUSED_VARS_NDEBUG(...)
#define UNUSED(x)
#define UNLIKELY(x)
#define STREQ(a, b)
void BPY_DECREF_RNA_INVALIDATE(void *pyob_ptr)
@ RGN_TYPE_WINDOW
@ SPACE_EMPTY
@ OPERATOR_CANCELLED
@ OPERATOR_FINISHED
@ OPERATOR_RUNNING_MODAL
@ OPERATOR_PASS_THROUGH
#define KMAP_MAX_NAME
void ED_region_tag_redraw_editor_overlays(struct ARegion *region)
Definition: area.c:706
void ED_undo_pop_op(struct bContext *C, struct wmOperator *op)
Definition: ed_undo.c:432
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum type
Read Guarded memory(de)allocation.
#define MEM_SAFE_FREE(v)
#define C
Definition: RandGen.cpp:39
eWM_GizmoFlagMapDrawStep
@ WM_GIZMOMAP_DRAWSTEP_3D
@ WM_GIZMOMAP_DRAWSTEP_2D
@ WM_GIZMO_TWEAK_PRECISE
@ WM_GIZMO_TWEAK_SNAP
@ WM_GIZMOMAPTYPE_KEYMAP_INIT
@ WM_GIZMOGROUP_INIT_REFRESH
@ WM_GIZMOGROUP_INIT_SETUP
@ WM_GIZMO_HIDDEN
@ WM_GIZMO_HIDDEN_SELECT
@ WM_GIZMOGROUPTYPE_TOOL_INIT
@ WM_GIZMOGROUPTYPE_DELAY_REFRESH_FOR_TWEAK
@ WM_GIZMOGROUPTYPE_3D
@ WM_GIZMOGROUPTYPE_SELECT
@ WM_GIZMO_STATE_MODAL
@ WM_GIZMO_STATE_SELECT
@ OPTYPE_UNDO
Definition: WM_types.h:155
#define KM_SHIFT
Definition: WM_types.h:221
#define KM_ANY
Definition: WM_types.h:240
#define KM_PRESS
Definition: WM_types.h:242
#define KM_RELEASE
Definition: WM_types.h:243
unsigned int U
Definition: btGjkEpa3.h:78
uiWidgetBaseParameters params[MAX_WIDGET_BASE_BATCH]
void(* MEM_freeN)(void *vmemh)
Definition: mallocn.c:41
void *(* MEM_callocN)(size_t len, const char *str)
Definition: mallocn.c:45
void *(* MEM_mallocN)(size_t len, const char *str)
Definition: mallocn.c:47
static void area(int d1, int d2, int e1, int e2, float weights[2])
void RNA_boolean_set(PointerRNA *ptr, const char *name, bool value)
Definition: rna_access.c:6272
bool RNA_boolean_get(PointerRNA *ptr, const char *name)
Definition: rna_access.c:6261
struct wmGizmoMap * gizmo_map
wmGizmoGroup * gzgroup
wmGizmo * gz_modal
wmGizmoMap * gzmap
void * last
Definition: DNA_listBase.h:47
void * first
Definition: DNA_listBase.h:47
Definition: BKE_main.h:116
ListBase wm
Definition: BKE_main.h:175
ListBase screens
Definition: BKE_main.h:161
void * data
Definition: RNA_types.h:52
short val
Definition: WM_types.h:579
short prevtype
Definition: WM_types.h:602
short prevval
Definition: WM_types.h:604
short type
Definition: WM_types.h:577
rcti winrct
Definition: WM_types.h:494
struct wmGizmoGroupType * type
wmGizmoGroupFnSetupKeymap setup_keymap
struct wmKeyConfig * keyconf
wmGizmoGroupFnRefresh refresh
wmGizmoGroupFnInit setup
wmGizmoGroupFnInvokePrepare invoke_prepare
eWM_GizmoFlagGroupTypeFlag flag
struct wmKeyMap * keymap
eWM_GizmoFlagMapTypeUpdateFlag type_update_flag
wmGizmoGroupFnPoll poll
struct wmGizmoMapType_Params gzmap_params
struct wmGizmoGroup * next
union wmGizmoGroup::@1150 hide
ListBase gizmos
struct wmGizmoGroupType * type
eWM_GizmoFlagGroupInitFlag init_flag
void * py_instance
void(* customdata_free)(void *)
struct wmGizmoMap * parent_gzmap
struct ReportList * reports
uint delay_refresh_for_tweak
struct wmGizmo ** items
ListBase grouptype_refs
struct wmGizmoMapType * type
struct wmGizmoMap::@1146 gzmap_context
Gizmo map runtime context.
ListBase groups
struct wmGizmo * modal
struct wmGizmo * highlight
struct wmGizmoMapSelectState select
PointerRNA ptr
struct wmOperatorType * type
wmGizmoFnModal modal
wmGizmoFnExit exit
eWM_GizmoFlagState state
struct wmGizmoGroup * parent_gzgroup
int highlight_part
struct wmKeyMap * keymap
wmGizmoFnModal custom_modal
union wmGizmo::@1148 temp
const struct wmGizmoType * type
struct PointerRNA * ptr
const void * modal_items
int(* invoke)(struct bContext *, struct wmOperator *, const struct wmEvent *) ATTR_WARN_UNUSED_RESULT
Definition: WM_types.h:752
const char * name
Definition: WM_types.h:721
int(* modal)(struct bContext *, struct wmOperator *, const struct wmEvent *) ATTR_WARN_UNUSED_RESULT
Definition: WM_types.h:768
const char * idname
Definition: WM_types.h:723
const char * description
Definition: WM_types.h:726
IDProperty * properties
struct PointerRNA * ptr
struct wmKeyConfig * defaultconf
struct wmGesture * tweak
#define USER_LMOUSESELECT
void WM_operator_free_all_after(wmWindowManager *wm, struct wmOperator *op)
Definition: wm.c:327
bool WM_event_is_mouse_drag(const wmEvent *event)
int WM_userdef_event_type_from_keymap_type(int kmitype)
wmEventHandler_Op * WM_event_add_modal_handler(bContext *C, wmOperator *op)
@ RIGHTMOUSE
@ EVT_MODAL_MAP
@ EVT_RIGHTCTRLKEY
@ EVT_LEFTCTRLKEY
@ EVT_PADENTER
@ EVT_TWEAK_R
@ LEFTMOUSE
@ EVT_ESCKEY
@ EVT_TWEAK_L
@ EVT_GIZMO_UPDATE
@ EVT_RIGHTSHIFTKEY
@ EVT_LEFTSHIFTKEY
@ EVT_RETKEY
wmOperatorType * ot
Definition: wm_files.c:3156
bool wm_gizmo_select_and_highlight(bContext *C, wmGizmoMap *gzmap, wmGizmo *gz)
Definition: wm_gizmo.c:448
int WM_gizmo_operator_invoke(bContext *C, wmGizmo *gz, wmGizmoOpElem *gzop)
Definition: wm_gizmo.c:258
void WM_gizmo_free(wmGizmo *gz)
Definition: wm_gizmo.c:151
bool WM_gizmo_select_unlink(wmGizmoMap *gzmap, wmGizmo *gz)
Definition: wm_gizmo.c:433
struct wmGizmoOpElem * WM_gizmo_operator_get(wmGizmo *gz, int part_index)
Definition: wm_gizmo.c:224
bool WM_gizmo_select_set(wmGizmoMap *gzmap, wmGizmo *gz, bool select)
Definition: wm_gizmo.c:438
int(* wmGizmoFnModal)(struct bContext *, struct wmGizmo *, const struct wmEvent *, eWM_GizmoFlagTweak)
Definition: wm_gizmo_fn.h:56
void WM_gizmo_group_refresh(const bContext *C, wmGizmoGroup *gzgroup)
void WM_gizmomaptype_group_init_runtime_keymap(const Main *bmain, wmGizmoGroupType *gzgt)
int WM_gizmo_cmp_temp_fl_reverse(const void *gz_a_ptr, const void *gz_b_ptr)
wmKeyMap * WM_gizmogroup_setup_keymap_generic_drag(const wmGizmoGroupType *UNUSED(gzgt), wmKeyConfig *kc)
wmGizmoGroup * wm_gizmogroup_new_from_type(wmGizmoMap *gzmap, wmGizmoGroupType *gzgt)
struct wmGizmoGroupTypeRef * WM_gizmomaptype_group_find_ptr(struct wmGizmoMapType *gzmap_type, const wmGizmoGroupType *gzgt)
void WM_gizmomaptype_group_init_runtime(const Main *bmain, wmGizmoMapType *gzmap_type, wmGizmoGroupType *gzgt)
wmGizmoGroupTypeRef * WM_gizmomaptype_group_link(wmGizmoMapType *gzmap_type, const char *idname)
struct wmKeyMap * WM_gizmo_keymap_generic_maybe_drag(wmWindowManager *wm)
void wm_gizmogroup_gizmo_register(wmGizmoGroup *gzgroup, wmGizmo *gz)
void wm_gizmogrouptype_setup_keymap(wmGizmoGroupType *gzgt, wmKeyConfig *keyconf)
void WM_gizmo_group_type_reinit_ptr_ex(struct Main *bmain, wmGizmoGroupType *gzgt, wmGizmoMapType *gzmap_type)
void WM_gizmogroup_ensure_init(const bContext *C, wmGizmoGroup *gzgroup)
bool WM_gizmo_group_type_ensure_ptr(wmGizmoGroupType *gzgt)
static int gizmo_tweak_modal(bContext *C, wmOperator *op, const wmEvent *event)
static wmKeyMap * WM_gizmogroup_keymap_template_select_ex(wmKeyConfig *kc, const char *name, const struct wmGizmoMapType_Params *params)
bool WM_gizmo_group_type_ensure_ptr_ex(wmGizmoGroupType *gzgt, wmGizmoMapType *gzmap_type)
struct wmKeyMap * WM_gizmo_keymap_generic_drag_with_keyconfig(wmKeyConfig *kc)
void WM_gizmo_group_type_unlink_delayed_ptr(wmGizmoGroupType *gzgt)
void WM_gizmo_group_remove_by_tool(bContext *C, Main *bmain, const wmGizmoGroupType *gzgt, const bToolRef *tref)
void WM_gizmo_group_type_add_ptr(wmGizmoGroupType *gzgt)
void WM_gizmo_group_type_remove_ptr_ex(struct Main *bmain, wmGizmoGroupType *gzgt, wmGizmoMapType *gzmap_type)
struct GizmoTweakData GizmoTweakData
void WM_gizmo_group_type_remove(struct Main *bmain, const char *idname)
wmKeyMap * wm_gizmogroup_tweak_modal_keymap(wmKeyConfig *keyconf)
bool wm_gizmogroup_is_visible_in_drawstep(const wmGizmoGroup *gzgroup, const eWM_GizmoFlagMapDrawStep drawstep)
struct wmKeyMap * WM_gizmo_keymap_generic_click_drag(wmWindowManager *wm)
static bool gizmo_tweak_start_and_finish(bContext *C, wmGizmoMap *gzmap, wmGizmo *gz, const wmEvent *event, bool *r_is_modal)
void WM_gizmo_group_unlink_delayed_ptr_from_space(wmGizmoGroupType *gzgt, wmGizmoMapType *gzmap_type, ScrArea *area)
void WM_gizmomaptype_group_free(wmGizmoGroupTypeRef *gzgt_ref)
void WM_gizmo_group_type_add(const char *idname)
void WM_gizmo_group_type_reinit(struct Main *bmain, const char *idname)
static int gizmo_tweak_invoke(bContext *C, wmOperator *op, const wmEvent *event)
static bool gizmo_tweak_start(bContext *C, wmGizmoMap *gzmap, wmGizmo *gz, const wmEvent *event)
bool WM_gizmo_group_type_ensure(const char *idname)
struct wmGizmoGroupTypeRef * WM_gizmomaptype_group_find(struct wmGizmoMapType *gzmap_type, const char *idname)
void wm_gizmogroup_intersectable_gizmos_to_list(wmWindowManager *wm, const wmGizmoGroup *gzgroup, const int event_modifier, BLI_Buffer *visible_gizmos)
void WM_gizmo_group_type_reinit_ptr(struct Main *bmain, wmGizmoGroupType *gzgt)
void WM_gizmo_group_type_unlink_delayed(const char *idname)
void WM_gizmo_group_type_add_ptr_ex(wmGizmoGroupType *gzgt, wmGizmoMapType *gzmap_type)
wmGizmo * wm_gizmogroup_find_intersected_gizmo(wmWindowManager *wm, const wmGizmoGroup *gzgroup, bContext *C, const int event_modifier, const int mval[2], int *r_part)
struct wmKeyMap * WM_gizmo_keymap_generic_drag(wmWindowManager *wm)
wmKeyMap * WM_gizmogroup_setup_keymap_generic_maybe_drag(const wmGizmoGroupType *UNUSED(gzgt), wmKeyConfig *kc)
int WM_gizmo_cmp_temp_fl(const void *gz_a_ptr, const void *gz_b_ptr)
bool WM_gizmo_group_type_poll(const bContext *C, const wmGizmoGroupType *gzgt)
void GIZMOGROUP_OT_gizmo_select(wmOperatorType *ot)
void WM_gizmo_group_tag_remove(wmGizmoGroup *gzgroup)
struct wmKeyMap * WM_gizmo_keymap_generic_maybe_drag_with_keyconfig(wmKeyConfig *kc)
wmGizmoGroupTypeRef * WM_gizmomaptype_group_link_ptr(wmGizmoMapType *gzmap_type, wmGizmoGroupType *gzgt)
bool wm_gizmogroup_is_any_selected(const wmGizmoGroup *gzgroup)
void WM_gizmomaptype_group_unlink(bContext *C, Main *bmain, wmGizmoMapType *gzmap_type, const wmGizmoGroupType *gzgt)
struct wmKeyMap * WM_gizmo_keymap_generic_select_with_keyconfig(wmKeyConfig *kc)
static void gizmo_tweak_finish(bContext *C, wmOperator *op, const bool cancel, bool clear_modal)
static bool wm_gizmo_keymap_uses_event_modifier(wmWindowManager *wm, const wmGizmoGroup *gzgroup, wmGizmo *gz, const int event_modifier, int *r_gzgroup_keymap_uses_modifier)
struct wmKeyMap * WM_gizmo_keymap_generic_click_drag_with_keyconfig(wmKeyConfig *kc)
struct wmKeyMap * WM_gizmo_keymap_generic(wmWindowManager *wm)
static int gizmo_select_invoke(bContext *C, wmOperator *op, const wmEvent *UNUSED(event))
wmGizmoGroup * WM_gizmomaptype_group_init_runtime_with_region(wmGizmoMapType *gzmap_type, wmGizmoGroupType *gzgt, ARegion *region)
wmGizmoGroup * wm_gizmogroup_find_by_type(const wmGizmoMap *gzmap, const wmGizmoGroupType *gzgt)
void WM_gizmo_group_type_unlink_delayed_ptr_ex(wmGizmoGroupType *gzgt, wmGizmoMapType *gzmap_type)
wmKeyMap * WM_gizmogroup_setup_keymap_generic_select(const wmGizmoGroupType *UNUSED(gzgt), wmKeyConfig *kc)
struct wmKeyMap * WM_gizmo_keymap_generic_with_keyconfig(wmKeyConfig *kc)
void wm_gizmogroup_free(bContext *C, wmGizmoGroup *gzgroup)
wmKeyMap * WM_gizmogroup_setup_keymap_generic(const wmGizmoGroupType *UNUSED(gzgt), wmKeyConfig *kc)
struct wmKeyMap * WM_gizmo_keymap_generic_select(wmWindowManager *wm)
void GIZMOGROUP_OT_gizmo_tweak(wmOperatorType *ot)
void WM_gizmo_group_type_remove_ptr(struct Main *bmain, wmGizmoGroupType *gzgt)
wmGizmoGroupType * WM_gizmogrouptype_find(const char *idname, bool quiet)
bool wm_gizmomap_deselect_all(struct wmGizmoMap *gzmap)
Definition: wm_gizmo_map.c:861
@ TWEAK_MODAL_PRECISION_ON
@ TWEAK_MODAL_SNAP_ON
@ TWEAK_MODAL_PRECISION_OFF
@ TWEAK_MODAL_CONFIRM
@ TWEAK_MODAL_SNAP_OFF
@ TWEAK_MODAL_CANCEL
wmGizmoMapType * WM_gizmomaptype_find(const struct wmGizmoMapType_Params *gzmap_params)
void wm_gizmomap_modal_set(wmGizmoMap *gzmap, bContext *C, wmGizmo *gz, const wmEvent *event, bool enable)
eWM_GizmoFlagMapDrawStep WM_gizmomap_drawstep_from_gizmo_group(const wmGizmoGroup *gzgroup)
Definition: wm_gizmo_map.c:303
wmGizmoMapType * WM_gizmomaptype_ensure(const struct wmGizmoMapType_Params *gzmap_params)
wmGizmo * wm_gizmomap_highlight_get(wmGizmoMap *gzmap)
bool wm_gizmomap_highlight_set(wmGizmoMap *gzmap, const bContext *C, wmGizmo *gz, int part)
Definition: wm_gizmo_map.c:999
void WM_gizmomap_tag_refresh_drawstep(wmGizmoMap *gzmap, const eWM_GizmoFlagMapDrawStep drawstep)
Definition: wm_gizmo_map.c:315
void WM_gizmoconfig_update_tag_group_type_init(wmGizmoMapType *gzmap_type, wmGizmoGroupType *gzgt)
void WM_gizmoconfig_update_tag_group_type_remove(wmGizmoMapType *gzmap_type, wmGizmoGroupType *gzgt)
void WM_gizmoconfig_update_tag_group_remove(wmGizmoMap *gzmap)
wmKeyMap * WM_modalkeymap_find(wmKeyConfig *keyconf, const char *idname)
Definition: wm_keymap.c:914
wmKeyMapItem * WM_modalkeymap_add_item(wmKeyMap *km, int type, int val, int modifier, int keymodifier, int value)
Definition: wm_keymap.c:927
wmKeyMap * WM_keymap_ensure(wmKeyConfig *keyconf, const char *idname, int spaceid, int regionid)
Definition: wm_keymap.c:852
void WM_modalkeymap_assign(wmKeyMap *km, const char *opname)
Definition: wm_keymap.c:985
wmKeyMapItem * WM_keymap_add_item(wmKeyMap *keymap, const char *idname, int type, int val, int modifier, int keymodifier)
Definition: wm_keymap.c:506
wmKeyMap * WM_keymap_active(const wmWindowManager *wm, wmKeyMap *keymap)
Definition: wm_keymap.c:1895
bool WM_keymap_remove(wmKeyConfig *keyconf, wmKeyMap *keymap)
Definition: wm_keymap.c:438
wmKeyMap * WM_modalkeymap_ensure(wmKeyConfig *keyconf, const char *idname, const EnumPropertyItem *items)
Definition: wm_keymap.c:888
bool WM_keymap_uses_event_modifier(const wmKeyMap *keymap, const int event_modifier)
void WM_operator_properties_mouse_select(wmOperatorType *ot)
wmOperator * WM_operator_last_redo(const bContext *C)
void WM_tooltip_clear(bContext *C, wmWindow *win)
Definition: wm_tooltip.c:94