Blender V4.3
anim_markers.cc
Go to the documentation of this file.
1/* SPDX-FileCopyrightText: 2008 Blender Authors
2 *
3 * SPDX-License-Identifier: GPL-2.0-or-later */
4
8
9#include <cmath>
10
11#include "MEM_guardedalloc.h"
12
13#include "DNA_object_types.h"
14#include "DNA_scene_types.h"
15
16#include "BLI_blenlib.h"
17#include "BLI_utildefines.h"
18
19#include "BLT_translation.hh"
20
21#include "BKE_context.hh"
22#include "BKE_idprop.hh"
23#include "BKE_layer.hh"
24#include "BKE_main.hh"
25#include "BKE_report.hh"
26#include "BKE_scene.hh"
27#include "BKE_screen.hh"
28#include "BKE_unit.hh"
29
30#include "RNA_access.hh"
31#include "RNA_define.hh"
32#include "RNA_enum_types.hh"
33
34#include "WM_api.hh"
35#include "WM_types.hh"
36
37#include "GPU_immediate.hh"
38#include "GPU_matrix.hh"
39#include "GPU_state.hh"
40
41#include "UI_interface.hh"
42#include "UI_interface_icons.hh"
43#include "UI_resources.hh"
44#include "UI_view2d.hh"
45
46#include "ED_anim_api.hh"
47#include "ED_keyframes_edit.hh"
48#include "ED_markers.hh"
49#include "ED_numinput.hh"
50#include "ED_object.hh"
51#include "ED_screen.hh"
52#include "ED_select_utils.hh"
53#include "ED_transform.hh"
54#include "ED_util.hh"
55
56#include "DEG_depsgraph.hh"
58
59/* -------------------------------------------------------------------- */
62
63/* helper function for getting the list of markers to work on */
65{
66 /* local marker sets... */
67 if (area) {
68 if (area->spacetype == SPACE_ACTION) {
69 SpaceAction *saction = (SpaceAction *)area->spacedata.first;
70
71 /* local markers can only be shown when there's only a single active action to grab them from
72 * - flag only takes effect when there's an action, otherwise it can get too confusing?
73 */
74 if (ELEM(saction->mode, SACTCONT_ACTION, SACTCONT_SHAPEKEY) && (saction->action)) {
75 if (saction->flag & SACTION_POSEMARKERS_SHOW) {
76 return &saction->action->markers;
77 }
78 }
79 }
80 }
81
82 /* default to using the scene's markers */
83 return &scene->markers;
84}
85
86/* ............. */
87
92
94{
95 if (ac) {
96 return context_get_markers(ac->scene, ac->area);
97 }
98 return nullptr;
99}
100
101/* --------------------------------- */
102
104 ListBase *markers, Scene *scene, int mode, float value, char side)
105{
106 float cfra = float(scene->r.cfra);
107 int changed_tot = 0;
108
109 /* sanity check - no markers, or locked markers */
110 if ((scene->toolsettings->lock_markers) || (markers == nullptr)) {
111 return changed_tot;
112 }
113
114 /* affect selected markers - it's unlikely that we will want to affect all in this way? */
115 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
116 if (marker->flag & SELECT) {
117 switch (mode) {
119 case TFM_TIME_EXTEND: {
120 /* apply delta if marker is on the right side of the current frame */
121 if ((side == 'B') || (side == 'L' && marker->frame < cfra) ||
122 (side == 'R' && marker->frame >= cfra))
123 {
124 marker->frame += round_fl_to_int(value);
125 changed_tot++;
126 }
127 break;
128 }
129 case TFM_TIME_SCALE: {
130 /* rescale the distance between the marker and the current frame */
131 marker->frame = cfra + round_fl_to_int(float(marker->frame - cfra) * value);
132 changed_tot++;
133 break;
134 }
135 }
136 }
137 }
138
139 return changed_tot;
140}
141
142/* --------------------------------- */
143
145{
146 TimeMarker *nearest = nullptr;
147 float dist, min_dist = 1000000;
148
149 if (markers) {
150 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
151 dist = fabsf(float(marker->frame) - x);
152
153 if (dist < min_dist) {
154 min_dist = dist;
155 nearest = marker;
156 }
157 }
158 }
159
160 return nearest;
161}
162
164{
165 TimeMarker *nearest = ED_markers_find_nearest_marker(markers, x);
166 return (nearest) ? (nearest->frame) : round_fl_to_int(x);
167}
168
169void ED_markers_get_minmax(ListBase *markers, short sel, float *r_first, float *r_last)
170{
171 float min, max;
172
173 /* sanity check */
174 // printf("markers = %p - %p, %p\n", markers, markers->first, markers->last);
175 if (ELEM(nullptr, markers, markers->first, markers->last)) {
176 *r_first = 0.0f;
177 *r_last = 0.0f;
178 return;
179 }
180
181 min = FLT_MAX;
182 max = -FLT_MAX;
183 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
184 if (!sel || (marker->flag & SELECT)) {
185 if (marker->frame < min) {
186 min = float(marker->frame);
187 }
188 if (marker->frame > max) {
189 max = float(marker->frame);
190 }
191 }
192 }
193
194 /* set the min/max values */
195 *r_first = min;
196 *r_last = max;
197}
198
204{
205 ScrArea *area = CTX_wm_area(C);
206 if (area == nullptr) {
207 return false;
208 }
209
210 switch (area->spacetype) {
211 case SPACE_ACTION: {
212 SpaceAction *saction = static_cast<SpaceAction *>(area->spacedata.first);
213 if (saction->flag & SACTION_SHOW_MARKERS) {
214 return true;
215 }
216 break;
217 }
218 case SPACE_GRAPH: {
219 SpaceGraph *sipo = static_cast<SpaceGraph *>(area->spacedata.first);
220 if (sipo->mode != SIPO_MODE_DRIVERS && sipo->flag & SIPO_SHOW_MARKERS) {
221 return true;
222 }
223 break;
224 }
225 case SPACE_NLA: {
226 SpaceNla *snla = static_cast<SpaceNla *>(area->spacedata.first);
227 if (snla->flag & SNLA_SHOW_MARKERS) {
228 return true;
229 }
230 break;
231 }
232 case SPACE_SEQ: {
233 SpaceSeq *seq = static_cast<SpaceSeq *>(area->spacedata.first);
234 if (seq->flag & SEQ_SHOW_MARKERS) {
235 return true;
236 }
237 break;
238 }
239 }
240 return false;
241}
242
243static bool region_position_is_over_marker(View2D *v2d, ListBase *markers, float region_x)
244{
245 if (markers == nullptr || BLI_listbase_is_empty(markers)) {
246 return false;
247 }
248
249 float frame_at_position = UI_view2d_region_to_view_x(v2d, region_x);
250 TimeMarker *nearest_marker = ED_markers_find_nearest_marker(markers, frame_at_position);
251 float pixel_distance = UI_view2d_scale_get_x(v2d) *
252 fabsf(nearest_marker->frame - frame_at_position);
253
254 return pixel_distance <= UI_ICON_SIZE;
255}
256
257/* --------------------------------- */
258
259/* Adds a marker to list of cfra elems */
260static void add_marker_to_cfra_elem(ListBase *lb, TimeMarker *marker, const bool only_selected)
261{
262 CfraElem *ce, *cen;
263
264 /* should this one only be considered if it is selected? */
265 if (only_selected && ((marker->flag & SELECT) == 0)) {
266 return;
267 }
268
269 /* insertion sort - try to find a previous cfra elem */
270 for (ce = static_cast<CfraElem *>(lb->first); ce; ce = ce->next) {
271 if (ce->cfra == marker->frame) {
272 /* do because of double keys */
273 if (marker->flag & SELECT) {
274 ce->sel = marker->flag;
275 }
276 return;
277 }
278 if (ce->cfra > marker->frame) {
279 break;
280 }
281 }
282
283 cen = static_cast<CfraElem *>(MEM_callocN(sizeof(CfraElem), "add_to_cfra_elem"));
284 if (ce) {
285 BLI_insertlinkbefore(lb, ce, cen);
286 }
287 else {
288 BLI_addtail(lb, cen);
289 }
290
291 cen->cfra = marker->frame;
292 cen->sel = marker->flag;
293}
294
295void ED_markers_make_cfra_list(ListBase *markers, ListBase *lb, const bool only_selected)
296{
297 if (lb) {
298 /* Clear the list first, since callers have no way of knowing
299 * whether this terminated early otherwise. This may lead
300 * to crashes if the user didn't clear the memory first.
301 */
302 lb->first = lb->last = nullptr;
303 }
304 else {
305 return;
306 }
307
308 if (markers == nullptr) {
309 return;
310 }
311
312 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
313 add_marker_to_cfra_elem(lb, marker, only_selected);
314 }
315}
316
317void ED_markers_deselect_all(ListBase *markers, int action)
318{
319 if (action == SEL_TOGGLE) {
321 }
322
323 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
324 if (action == SEL_SELECT) {
325 marker->flag |= SELECT;
326 }
327 else if (action == SEL_DESELECT) {
328 marker->flag &= ~SELECT;
329 }
330 else if (action == SEL_INVERT) {
331 marker->flag ^= SELECT;
332 }
333 else {
334 BLI_assert(0);
335 }
336 }
337}
338
339/* --------------------------------- */
340
342{
343 if (markers) {
344 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
345 if (marker->flag & SELECT) {
346 return marker;
347 }
348 }
349 }
350
351 return nullptr;
352}
353
354/* --------------------------------- */
355
357{
358 /* NOTE: do NOT make static or use `ifdef`'s as "unused code".
359 * That's too much trouble when we need to use for quick debugging! */
360 if (markers == nullptr) {
361 printf("No markers list to print debug for\n");
362 return;
363 }
364
365 printf("List of markers follows: -----\n");
366
367 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
368 printf(
369 "\t'%s' on %d at %p with %u\n", marker->name, marker->frame, (void *)marker, marker->flag);
370 }
371
372 printf("End of list ------------------\n");
373}
374
376
377/* -------------------------------------------------------------------- */
380
381static void marker_color_get(const TimeMarker *marker, uchar *r_text_color, uchar *r_line_color)
382{
383 if (marker->flag & SELECT) {
384 UI_GetThemeColor4ubv(TH_TEXT_HI, r_text_color);
386 }
387 else {
388 UI_GetThemeColor4ubv(TH_TEXT, r_text_color);
390 }
391}
392
393static void draw_marker_name(const uchar *text_color,
394 const uiFontStyle *fstyle,
395 TimeMarker *marker,
396 float marker_x,
397 float xmax,
398 float text_y)
399{
400 const char *name = marker->name;
401 uchar final_text_color[4];
402
403 copy_v4_v4_uchar(final_text_color, text_color);
404
405#ifdef DURIAN_CAMERA_SWITCH
406 if (marker->camera) {
407 Object *camera = marker->camera;
408 name = camera->id.name + 2;
409 if (camera->visibility_flag & OB_HIDE_RENDER) {
410 final_text_color[3] = 100;
411 }
412 }
413#endif
414
415 const int icon_half_width = UI_ICON_SIZE * 0.6;
416 uiFontStyleDraw_Params fs_params{};
417 fs_params.align = UI_STYLE_TEXT_LEFT;
418 fs_params.word_wrap = 0;
419
420 rcti rect{};
421 rect.xmin = marker_x + icon_half_width;
422 rect.xmax = xmax - icon_half_width;
423 rect.ymin = text_y;
424 rect.ymax = text_y;
425
426 UI_fontstyle_draw(fstyle, &rect, name, strlen(name), final_text_color, &fs_params);
427}
428
429static void draw_marker_line(const uchar *color, int xpos, int ymin, int ymax)
430{
433
435
436 float viewport_size[4];
437 GPU_viewport_size_get_f(viewport_size);
438 immUniform2f("viewport_size", viewport_size[2] / UI_SCALE_FAC, viewport_size[3] / UI_SCALE_FAC);
439
441 immUniform1i("colors_len", 0); /* "simple" mode */
442 immUniform1f("dash_width", 6.0f);
443 immUniform1f("udash_factor", 0.5f);
444
446 immVertex2f(pos, xpos, ymin);
447 immVertex2f(pos, xpos, ymax);
448 immEnd();
449
451}
452
453static int marker_get_icon_id(TimeMarker *marker, int flag)
454{
455 if (flag & DRAW_MARKERS_LOCAL) {
456 return (marker->flag & SELECT) ? ICON_PMARKER_SEL : ICON_PMARKER;
457 }
458#ifdef DURIAN_CAMERA_SWITCH
459 if (marker->camera) {
460 return (marker->flag & SELECT) ? ICON_OUTLINER_OB_CAMERA : ICON_CAMERA_DATA;
461 }
462#endif
463 return (marker->flag & SELECT) ? ICON_MARKER_HLT : ICON_MARKER;
464}
465
466static void draw_marker(const uiFontStyle *fstyle,
467 TimeMarker *marker,
468 int xpos,
469 int xmax,
470 int flag,
471 int region_height,
472 bool is_elevated)
473{
474 uchar line_color[4], text_color[4];
475
476 marker_color_get(marker, text_color, line_color);
477
479
480 draw_marker_line(line_color, xpos, UI_SCALE_FAC * 28, region_height);
481
482 int icon_id = marker_get_icon_id(marker, flag);
483
484 uchar marker_color[4];
485 if (marker->flag & SELECT) {
487 }
488 else {
489 UI_GetThemeColor4ubv(TH_TEXT, marker_color);
490 }
491
492 UI_icon_draw_ex(xpos - (0.5f * UI_ICON_SIZE) - (0.5f * U.pixelsize),
493 UI_SCALE_FAC * 18,
494 icon_id,
496 1.0f,
497 0.0f,
498 marker_color,
499 false,
501
503
504 float name_y = UI_SCALE_FAC * 18;
505 /* Give an offset to the marker that is elevated. */
506 if (is_elevated) {
507 name_y += UI_SCALE_FAC * 10;
508 }
509 draw_marker_name(text_color, fstyle, marker, xpos, xmax, name_y);
510}
511
530
531static bool marker_is_in_frame_range(TimeMarker *marker, const int frame_range[2])
532{
533 if (marker->frame < frame_range[0]) {
534 return false;
535 }
536 if (marker->frame > frame_range[1]) {
537 return false;
538 }
539 return true;
540}
541
542static void get_marker_region_rect(View2D *v2d, rctf *r_rect)
543{
544 r_rect->xmin = v2d->cur.xmin;
545 r_rect->xmax = v2d->cur.xmax;
546 r_rect->ymin = 0;
547 r_rect->ymax = UI_MARKER_MARGIN_Y;
548}
549
550static void get_marker_clip_frame_range(View2D *v2d, float xscale, int r_range[2])
551{
552 float font_width_max = (10 * UI_SCALE_FAC) / xscale;
553 r_range[0] = v2d->cur.xmin - sizeof(TimeMarker::name) * font_width_max;
554 r_range[1] = v2d->cur.xmax + font_width_max;
555}
556
557static int markers_frame_sort(const void *a, const void *b)
558{
559 const TimeMarker *marker_a = static_cast<const TimeMarker *>(a);
560 const TimeMarker *marker_b = static_cast<const TimeMarker *>(b);
561
562 return marker_a->frame > marker_b->frame;
563}
564
566{
568 if (markers == nullptr || BLI_listbase_is_empty(markers)) {
569 return;
570 }
571
572 ARegion *region = CTX_wm_region(C);
574 int cfra = CTX_data_scene(C)->r.cfra;
575
576 GPU_line_width(1.0f);
577
578 rctf markers_region_rect;
579 get_marker_region_rect(v2d, &markers_region_rect);
580
581 draw_markers_background(&markers_region_rect);
582
583 /* no time correction for framelen! space is drawn with old values */
584 float xscale, dummy;
585 UI_view2d_scale_get(v2d, &xscale, &dummy);
587 GPU_matrix_scale_2f(1.0f / xscale, 1.0f);
588
589 int clip_frame_range[2];
590 get_marker_clip_frame_range(v2d, xscale, clip_frame_range);
591
592 const uiFontStyle *fstyle = UI_FSTYLE_WIDGET;
593
594 /* Markers are not stored by frame order, so we need to sort it here. */
595 ListBase sorted_markers;
596
597 BLI_duplicatelist(&sorted_markers, markers);
598 BLI_listbase_sort(&sorted_markers, markers_frame_sort);
599
604 const int ELEVATED = 0x10;
605 LISTBASE_FOREACH (TimeMarker *, marker, &sorted_markers) {
606 const bool is_elevated = (marker->flag & SELECT) ||
607 (cfra >= marker->frame &&
608 (marker->next == nullptr || cfra < marker->next->frame));
609 SET_FLAG_FROM_TEST(marker->flag, is_elevated, ELEVATED);
610 }
611
612 /* Separate loops in order to draw selected markers on top. */
613
620 LISTBASE_FOREACH (TimeMarker *, marker, &sorted_markers) {
621 if ((marker->flag & ELEVATED) == 0 && marker_is_in_frame_range(marker, clip_frame_range)) {
622 const int xmax = marker->next ? marker->next->frame : clip_frame_range[1] + 1;
624 fstyle, marker, marker->frame * xscale, xmax * xscale, flag, region->winy, false);
625 }
626 }
627
628 /* Now draw the elevated markers */
629 for (TimeMarker *marker = static_cast<TimeMarker *>(sorted_markers.first); marker != nullptr;) {
630
631 /* Skip this marker if it is elevated or out of the frame range. */
632 if ((marker->flag & ELEVATED) == 0 || !marker_is_in_frame_range(marker, clip_frame_range)) {
633 marker = marker->next;
634 continue;
635 }
636
637 /* Find the next elevated marker. */
638 /* We use the next marker to determine how wide our text should be */
639 TimeMarker *next_marker = marker->next;
640 while (next_marker != nullptr && (next_marker->flag & ELEVATED) == 0) {
641 next_marker = next_marker->next;
642 }
643
644 const int xmax = next_marker ? next_marker->frame : clip_frame_range[1] + 1;
645 draw_marker(fstyle, marker, marker->frame * xscale, xmax * xscale, flag, region->winy, true);
646
647 marker = next_marker;
648 }
649
650 /* Reset the elevated flag. */
651 LISTBASE_FOREACH (TimeMarker *, marker, &sorted_markers) {
652 marker->flag &= ~ELEVATED;
653 }
654
655 BLI_freelistN(&sorted_markers);
656
658}
659
661
662/* -------------------------------------------------------------------- */
669
670/* ------------------------ */
671
672/* special poll() which checks if there are selected markers first */
674{
676
678 return false;
679 }
680
681 /* check if some marker is selected */
682 if (ED_markers_get_first_selected(markers) == nullptr) {
683 CTX_wm_operator_poll_msg_set(C, "No markers are selected");
684 return false;
685 }
686
687 return true;
688}
689
691{
694
696 return false;
697 }
698
699 if (ts->lock_markers) {
700 CTX_wm_operator_poll_msg_set(C, "Markers are locked");
701 return false;
702 }
703
704 /* check if some marker is selected */
705 if (ED_markers_get_first_selected(markers) == nullptr) {
706 CTX_wm_operator_poll_msg_set(C, "No markers are selected");
707 return false;
708 }
709
710 return true;
711}
712
713/* special poll() which checks if there are any markers at all first */
715{
718
720 return false;
721 }
722
723 /* list of markers must exist, as well as some markers in it! */
724 return (markers && markers->first);
725}
726
728
729/* -------------------------------------------------------------------- */
732
733/* add TimeMarker at current frame */
735{
737 TimeMarker *marker;
738 int frame = CTX_data_scene(C)->r.cfra;
739
740 if (markers == nullptr) {
741 return OPERATOR_CANCELLED;
742 }
743
744 /* prefer not having 2 markers at the same place,
745 * though the user can move them to overlap once added */
746 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
747 if (marker->frame == frame) {
748 return OPERATOR_CANCELLED;
749 }
750 }
751
752 /* deselect all */
753 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
754 marker->flag &= ~SELECT;
755 }
756
757 marker = static_cast<TimeMarker *>(MEM_callocN(sizeof(TimeMarker), "TimeMarker"));
758 marker->flag = SELECT;
759 marker->frame = frame;
760 SNPRINTF(marker->name, "F_%02d", frame);
761 BLI_addtail(markers, marker);
762
765
766 return OPERATOR_FINISHED;
767}
768
770{
771 /* identifiers */
772 ot->name = "Add Time Marker";
773 ot->description = "Add a new time marker";
774 ot->idname = "MARKER_OT_add";
775
776 /* api callbacks */
777 ot->exec = ed_marker_add_exec;
779
780 /* flags */
782}
783
785
786/* -------------------------------------------------------------------- */
789
790/* operator state vars used:
791 * frames: delta movement
792 *
793 * functions:
794 *
795 * init() check selection, add customdata with old values and some lookups
796 *
797 * apply() do the actual movement
798 *
799 * exit() cleanup, send notifier
800 *
801 * cancel() to escape from modal
802 *
803 * callbacks:
804 *
805 * exec() calls init, apply, exit
806 *
807 * invoke() calls init, adds modal handler
808 *
809 * modal() accept modal events while doing it, ends with apply and exit, or cancel
810 */
811
815 short event_type, event_val; /* store invoke-event, to verify */
818};
819
821{
822 if (((mm->slink->spacetype == SPACE_SEQ) && !(((SpaceSeq *)mm->slink)->flag & SEQ_DRAWFRAMES)) ||
823 ((mm->slink->spacetype == SPACE_ACTION) &&
824 (((SpaceAction *)mm->slink)->flag & SACTION_DRAWTIME)) ||
825 ((mm->slink->spacetype == SPACE_GRAPH) &&
826 (((SpaceGraph *)mm->slink)->flag & SIPO_DRAWTIME)) ||
827 ((mm->slink->spacetype == SPACE_NLA) && (((SpaceNla *)mm->slink)->flag & SNLA_DRAWTIME)))
828 {
829 return true;
830 }
831
832 return false;
833}
834
836{
837 Scene *scene = CTX_data_scene(C);
838 MarkerMove *mm = static_cast<MarkerMove *>(op->customdata);
839 TimeMarker *marker, *selmarker = nullptr;
840 const int ofs = RNA_int_get(op->ptr, "frames");
841 char str[UI_MAX_DRAW_STR];
842 char str_ofs[NUM_STR_REP_LEN];
843 int totmark;
844 const bool use_time = ed_marker_move_use_time(mm);
845
846 for (totmark = 0, marker = static_cast<TimeMarker *>(mm->markers->first); marker;
847 marker = marker->next)
848 {
849 if (marker->flag & SELECT) {
850 selmarker = marker;
851 totmark++;
852 }
853 }
854
855 if (hasNumInput(&mm->num)) {
856 outputNumInput(&mm->num, str_ofs, &scene->unit);
857 }
858 else if (use_time) {
859 SNPRINTF(str_ofs, "%.2f", FRA2TIME(ofs));
860 }
861 else {
862 SNPRINTF(str_ofs, "%d", ofs);
863 }
864
865 if (totmark == 1 && selmarker) {
866 /* we print current marker value */
867 if (use_time) {
868 SNPRINTF(str, IFACE_("Marker %.2f offset %s"), FRA2TIME(selmarker->frame), str_ofs);
869 }
870 else {
871 SNPRINTF(str, IFACE_("Marker %d offset %s"), selmarker->frame, str_ofs);
872 }
873 }
874 else {
875 SNPRINTF(str, IFACE_("Marker offset %s"), str_ofs);
876 }
877
879}
880
881/* copy selection to temp buffer */
882/* return 0 if not OK */
884{
885 Scene *scene = CTX_data_scene(C);
887 MarkerMove *mm;
888 TimeMarker *marker;
889 int a, totmark;
890
891 if (markers == nullptr) {
892 return false;
893 }
894
895 for (totmark = 0, marker = static_cast<TimeMarker *>(markers->first); marker;
896 marker = marker->next)
897 {
898 if (marker->flag & SELECT) {
899 totmark++;
900 }
901 }
902
903 if (totmark == 0) {
904 return false;
905 }
906
907 op->customdata = mm = static_cast<MarkerMove *>(MEM_callocN(sizeof(MarkerMove), "Markermove"));
909 mm->markers = markers;
910 mm->oldframe = static_cast<int *>(MEM_callocN(totmark * sizeof(int), "MarkerMove oldframe"));
911
912 initNumInput(&mm->num);
913 mm->num.idx_max = 0; /* one axis */
914 mm->num.val_flag[0] |= NUM_NO_FRACTION;
915 mm->num.unit_sys = scene->unit.system;
916 /* No time unit supporting frames currently... */
918
919 for (a = 0, marker = static_cast<TimeMarker *>(markers->first); marker; marker = marker->next) {
920 if (marker->flag & SELECT) {
921 mm->oldframe[a] = marker->frame;
922 a++;
923 }
924 }
925
926 return true;
927}
928
929/* free stuff */
931{
932 MarkerMove *mm = static_cast<MarkerMove *>(op->customdata);
933
934 /* free data */
935 MEM_freeN(mm->oldframe);
937 op->customdata = nullptr;
938
939 /* clear custom header prints */
941}
942
943static int ed_marker_move_invoke(bContext *C, wmOperator *op, const wmEvent *event)
944{
945 const bool tweak = RNA_struct_find_property(op->ptr, "tweak") &&
946 RNA_boolean_get(op->ptr, "tweak");
947
948 if (tweak) {
949 ARegion *region = CTX_wm_region(C);
950 View2D *v2d = &region->v2d;
952 if (!region_position_is_over_marker(v2d, markers, event->xy[0] - region->winrct.xmin)) {
954 }
955 }
956
957 if (ed_marker_move_init(C, op)) {
958 MarkerMove *mm = static_cast<MarkerMove *>(op->customdata);
959
960 mm->evtx = event->xy[0];
961 mm->firstx = event->xy[0];
962 mm->event_type = event->type;
963 mm->event_val = event->val;
964
965 /* add temp handler */
967
968 /* Reset frames delta. */
969 RNA_int_set(op->ptr, "frames", 0);
970
972
974 }
975
976 return OPERATOR_CANCELLED;
977}
978
979/* NOTE: init has to be called successfully. */
981{
982#ifdef DURIAN_CAMERA_SWITCH
983 bScreen *screen = CTX_wm_screen(C);
984 Scene *scene = CTX_data_scene(C);
985 Object *camera = scene->camera;
986#endif
987 MarkerMove *mm = static_cast<MarkerMove *>(op->customdata);
988 TimeMarker *marker;
989 int a, ofs;
990
991 ofs = RNA_int_get(op->ptr, "frames");
992 for (a = 0, marker = static_cast<TimeMarker *>(mm->markers->first); marker;
993 marker = marker->next)
994 {
995 if (marker->flag & SELECT) {
996 marker->frame = mm->oldframe[a] + ofs;
997 a++;
998 }
999 }
1000
1003
1004#ifdef DURIAN_CAMERA_SWITCH
1005 /* so we get view3d redraws */
1007
1008 if (camera != scene->camera) {
1009 BKE_screen_view3d_scene_sync(screen, scene);
1011 }
1012#endif
1013}
1014
1015/* only for modal */
1017{
1018 RNA_int_set(op->ptr, "frames", 0);
1021}
1022
1023static int ed_marker_move_modal(bContext *C, wmOperator *op, const wmEvent *event)
1024{
1025 Scene *scene = CTX_data_scene(C);
1026 MarkerMove *mm = static_cast<MarkerMove *>(op->customdata);
1028 const bool has_numinput = hasNumInput(&mm->num);
1029 const bool use_time = ed_marker_move_use_time(mm);
1030
1031 /* Modal numinput active, try to handle numeric inputs first... */
1032 if (event->val == KM_PRESS && has_numinput && handleNumInput(C, &mm->num, event)) {
1033 float value = float(RNA_int_get(op->ptr, "frames"));
1034
1035 applyNumInput(&mm->num, &value);
1036 if (use_time) {
1037 value = TIME2FRA(value);
1038 }
1039
1040 RNA_int_set(op->ptr, "frames", int(value));
1043 }
1044 else {
1045 bool handled = false;
1046 switch (event->type) {
1047 case EVT_ESCKEY:
1049 return OPERATOR_CANCELLED;
1050 case RIGHTMOUSE:
1051 /* press = user manually demands transform to be canceled */
1052 if (event->val == KM_PRESS) {
1054 return OPERATOR_CANCELLED;
1055 }
1056 /* else continue; <--- see if release event should be caught for tweak-end */
1058
1059 case EVT_RETKEY:
1060 case EVT_PADENTER:
1061 case LEFTMOUSE:
1062 case MIDDLEMOUSE:
1063 if (WM_event_is_modal_drag_exit(event, mm->event_type, mm->event_val)) {
1067 return OPERATOR_FINISHED;
1068 }
1069 break;
1070 case MOUSEMOVE:
1071 if (!has_numinput) {
1072 float dx;
1073
1074 dx = BLI_rctf_size_x(&v2d->cur) / BLI_rcti_size_x(&v2d->mask);
1075
1076 if (event->xy[0] != mm->evtx) { /* XXX maybe init for first time */
1077 float fac;
1078
1079 mm->evtx = event->xy[0];
1080 fac = (float(event->xy[0] - mm->firstx) * dx);
1081
1082 apply_keyb_grid((event->modifier & KM_SHIFT) != 0,
1083 (event->modifier & KM_CTRL) != 0,
1084 &fac,
1085 0.0,
1086 FPS,
1087 0.1 * FPS,
1088 0);
1089
1090 RNA_int_set(op->ptr, "frames", int(fac));
1093 }
1094 }
1095 break;
1096 }
1097
1098 if (!handled && event->val == KM_PRESS && handleNumInput(C, &mm->num, event)) {
1099 float value = float(RNA_int_get(op->ptr, "frames"));
1100
1101 applyNumInput(&mm->num, &value);
1102 if (use_time) {
1103 value = TIME2FRA(value);
1104 }
1105
1106 RNA_int_set(op->ptr, "frames", int(value));
1109 }
1110 }
1111
1113}
1114
1116{
1117 if (ed_marker_move_init(C, op)) {
1120 return OPERATOR_FINISHED;
1121 }
1122 return OPERATOR_PASS_THROUGH;
1123}
1124
1126{
1127 /* identifiers */
1128 ot->name = "Move Time Marker";
1129 ot->description = "Move selected time marker(s)";
1130 ot->idname = "MARKER_OT_move";
1131
1132 /* api callbacks */
1133 ot->exec = ed_marker_move_exec;
1134 ot->invoke = ed_marker_move_invoke;
1135 ot->modal = ed_marker_move_modal;
1137 ot->cancel = ed_marker_move_cancel;
1138
1139 /* flags */
1141
1142 /* rna storage */
1143 RNA_def_int(ot->srna, "frames", 0, INT_MIN, INT_MAX, "Frames", "", INT_MIN, INT_MAX);
1145 ot->srna, "tweak", false, "Tweak", "Operator has been activated using a click-drag event");
1147}
1148
1150
1151/* -------------------------------------------------------------------- */
1154
1155/* operator state vars used:
1156 * frames: delta movement
1157 *
1158 * functions:
1159 *
1160 * apply() do the actual duplicate
1161 *
1162 * callbacks:
1163 *
1164 * exec() calls apply, move_exec
1165 *
1166 * invoke() calls apply, move_invoke
1167 *
1168 * modal() uses move_modal
1169 */
1170
1171/* duplicate selected TimeMarkers */
1173{
1174 ListBase *markers = ED_context_get_markers(C);
1175 if (markers == nullptr) {
1176 return;
1177 }
1178
1179 /* go through the list of markers, duplicate selected markers and add duplicated copies
1180 * to the beginning of the list (unselect original markers)
1181 */
1182 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
1183 if (marker->flag & SELECT) {
1184 /* unselect selected marker */
1185 marker->flag &= ~SELECT;
1186
1187 /* create and set up new marker */
1188 TimeMarker *newmarker = static_cast<TimeMarker *>(
1189 MEM_callocN(sizeof(TimeMarker), "TimeMarker"));
1190 newmarker->flag = SELECT;
1191 newmarker->frame = marker->frame;
1192 STRNCPY(newmarker->name, marker->name);
1193
1194#ifdef DURIAN_CAMERA_SWITCH
1195 newmarker->camera = marker->camera;
1196#endif
1197
1198 if (marker->prop != nullptr) {
1199 newmarker->prop = IDP_CopyProperty(marker->prop);
1200 }
1201
1202 /* new marker is added to the beginning of list */
1203 /* FIXME: bad ordering! */
1204 BLI_addhead(markers, newmarker);
1205 }
1206 }
1207}
1208
1210{
1212 ed_marker_move_exec(C, op); /* Assumes frame delta set. */
1213
1214 return OPERATOR_FINISHED;
1215}
1216
1218{
1220 return ed_marker_move_invoke(C, op, event);
1221}
1222
1224{
1225 /* identifiers */
1226 ot->name = "Duplicate Time Marker";
1227 ot->description = "Duplicate selected time marker(s)";
1228 ot->idname = "MARKER_OT_duplicate";
1229
1230 /* api callbacks */
1233 ot->modal = ed_marker_move_modal;
1235 ot->cancel = ed_marker_move_cancel;
1236
1237 /* flags */
1238 ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1239
1240 /* rna storage */
1241 RNA_def_int(ot->srna, "frames", 0, INT_MIN, INT_MAX, "Frames", "", INT_MIN, INT_MAX);
1242}
1243
1245
1246/* -------------------------------------------------------------------- */
1251
1252static void deselect_markers(ListBase *markers)
1253{
1254 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
1255 marker->flag &= ~SELECT;
1256 }
1257}
1258
1260 int frame,
1261 bool extend,
1262 bool wait_to_deselect_others)
1263{
1264 TimeMarker *marker, *marker_cycle_selected = nullptr;
1265 int ret_val = OPERATOR_FINISHED;
1266
1267 if (extend) {
1268 wait_to_deselect_others = false;
1269 }
1270
1271 /* support for selection cycling */
1272 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
1273 if (marker->frame == frame) {
1274 if (marker->flag & SELECT) {
1275 marker_cycle_selected = static_cast<TimeMarker *>(marker->next ? marker->next :
1276 markers->first);
1277 break;
1278 }
1279 }
1280 }
1281
1282 if (wait_to_deselect_others && marker_cycle_selected) {
1283 ret_val = OPERATOR_RUNNING_MODAL;
1284 }
1285 /* if extend is not set, then deselect markers */
1286 else {
1287 if (extend == false) {
1288 deselect_markers(markers);
1289 }
1290
1291 LISTBASE_CIRCULAR_FORWARD_BEGIN (TimeMarker *, markers, marker, marker_cycle_selected) {
1292 /* this way a not-extend select will always give 1 selected marker */
1293 if (marker->frame == frame) {
1294 marker->flag ^= SELECT;
1295 break;
1296 }
1297 }
1298 LISTBASE_CIRCULAR_FORWARD_END(TimeMarker *, markers, marker, marker_cycle_selected);
1299 }
1300
1301 return ret_val;
1302}
1303
1305 bContext *C, bool camera, bool extend, ListBase *markers, int cfra)
1306{
1307 using namespace blender::ed;
1308#ifdef DURIAN_CAMERA_SWITCH
1309 if (camera) {
1311 Scene *scene = CTX_data_scene(C);
1312 ViewLayer *view_layer = CTX_data_view_layer(C);
1313 Base *base;
1314 int sel = 0;
1315
1316 if (!extend) {
1317 BKE_view_layer_base_deselect_all(scene, view_layer);
1318 }
1319
1320 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
1321 if (marker->frame == cfra) {
1322 sel = (marker->flag & SELECT);
1323 break;
1324 }
1325 }
1326
1327 BKE_view_layer_synced_ensure(scene, view_layer);
1328 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
1329 if (marker->camera) {
1330 if (marker->frame == cfra) {
1331 base = BKE_view_layer_base_find(view_layer, marker->camera);
1332 if (base) {
1334 if (sel) {
1335 object::base_activate(C, base);
1336 }
1337 }
1338 }
1339 }
1340 }
1341
1344 }
1345#else
1346 (void)camera;
1347#endif
1348}
1349
1351 bContext *C, const int mval[2], bool extend, bool camera, bool wait_to_deselect_others)
1352{
1353 ListBase *markers = ED_context_get_markers(C);
1355 int ret_val = OPERATOR_FINISHED;
1356
1357 if (region_position_is_over_marker(v2d, markers, mval[0])) {
1358 float frame_at_mouse_position = UI_view2d_region_to_view_x(v2d, mval[0]);
1359 int cfra = ED_markers_find_nearest_marker_time(markers, frame_at_mouse_position);
1360 ret_val = select_timeline_marker_frame(markers, cfra, extend, wait_to_deselect_others);
1361
1362 select_marker_camera_switch(C, camera, extend, markers, cfra);
1363 }
1364 else {
1365 deselect_markers(markers);
1366 }
1367
1370
1371 /* allowing tweaks, but needs OPERATOR_FINISHED, otherwise renaming fails, see #25987. */
1372 return ret_val | OPERATOR_PASS_THROUGH;
1373}
1374
1376{
1377 const bool extend = RNA_boolean_get(op->ptr, "extend");
1378 const bool wait_to_deselect_others = RNA_boolean_get(op->ptr, "wait_to_deselect_others");
1379 bool camera = false;
1380#ifdef DURIAN_CAMERA_SWITCH
1381 camera = RNA_boolean_get(op->ptr, "camera");
1382 if (camera) {
1383 /* Supporting mode switching from this operator doesn't seem so useful.
1384 * So only allow setting the active camera in object-mode. */
1386 BKE_report(
1387 op->reports, RPT_WARNING, "Selecting the camera is only supported in object mode");
1388 camera = false;
1389 }
1390 }
1391#endif
1392 int mval[2];
1393 mval[0] = RNA_int_get(op->ptr, "mouse_x");
1394 mval[1] = RNA_int_get(op->ptr, "mouse_y");
1395
1396 return ed_marker_select(C, mval, extend, camera, wait_to_deselect_others);
1397}
1398
1400{
1401 PropertyRNA *prop;
1402
1403 /* identifiers */
1404 ot->name = "Select Time Marker";
1405 ot->description = "Select time marker(s)";
1406 ot->idname = "MARKER_OT_select";
1407
1408 /* api callbacks */
1410 ot->exec = ed_marker_select_exec;
1411 ot->invoke = WM_generic_select_invoke;
1412 ot->modal = WM_generic_select_modal;
1413
1414 /* flags */
1415 ot->flag = OPTYPE_UNDO;
1416
1418 prop = RNA_def_boolean(ot->srna, "extend", false, "Extend", "Extend the selection");
1420#ifdef DURIAN_CAMERA_SWITCH
1421 prop = RNA_def_boolean(ot->srna, "camera", false, "Camera", "Select the camera");
1423#endif
1424}
1425
1427
1428/* -------------------------------------------------------------------- */
1431
1432/* operator state vars used: (added by default WM callbacks)
1433 * xmin, ymin
1434 * xmax, ymax
1435 *
1436 * customdata: the wmGesture pointer, with sub-window.
1437 *
1438 * callbacks:
1439 *
1440 * exec() has to be filled in by user
1441 *
1442 * invoke() default WM function
1443 * adds modal handler
1444 *
1445 * modal() default WM function
1446 * accept modal events while doing it, calls exec(), handles ESC and border drawing
1447 *
1448 * poll() has to be filled in by user for context
1449 */
1450
1452{
1453 ARegion *region = CTX_wm_region(C);
1454 View2D *v2d = &region->v2d;
1455
1456 ListBase *markers = ED_context_get_markers(C);
1457 bool over_marker = region_position_is_over_marker(
1458 v2d, markers, event->xy[0] - region->winrct.xmin);
1459
1460 bool tweak = RNA_boolean_get(op->ptr, "tweak");
1461 if (tweak && over_marker) {
1463 }
1464
1465 return WM_gesture_box_invoke(C, op, event);
1466}
1467
1469{
1471 ListBase *markers = ED_context_get_markers(C);
1472 rctf rect;
1473
1475 UI_view2d_region_to_view_rctf(v2d, &rect, &rect);
1476
1477 if (markers == nullptr) {
1478 return 0;
1479 }
1480
1481 const eSelectOp sel_op = eSelectOp(RNA_enum_get(op->ptr, "mode"));
1482 const bool select = (sel_op != SEL_OP_SUB);
1483 if (SEL_OP_USE_PRE_DESELECT(sel_op)) {
1485 }
1486
1487 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
1488 if (BLI_rctf_isect_x(&rect, marker->frame)) {
1489 SET_FLAG_FROM_TEST(marker->flag, select, SELECT);
1490 }
1491 }
1492
1495
1496 return 1;
1497}
1498
1500{
1501 /* identifiers */
1502 ot->name = "Marker Box Select";
1503 ot->description = "Select all time markers using box selection";
1504 ot->idname = "MARKER_OT_select_box";
1505
1506 /* api callbacks */
1509 ot->modal = WM_gesture_box_modal;
1510 ot->cancel = WM_gesture_box_cancel;
1511
1513
1514 /* flags */
1515 ot->flag = OPTYPE_UNDO;
1516
1517 /* properties */
1520
1522 ot->srna, "tweak", false, "Tweak", "Operator has been activated using a click-drag event");
1524}
1525
1527
1528/* -------------------------------------------------------------------- */
1531
1533{
1534 ListBase *markers = ED_context_get_markers(C);
1535 if (markers == nullptr) {
1536 return OPERATOR_CANCELLED;
1537 }
1538
1539 int action = RNA_enum_get(op->ptr, "action");
1540 ED_markers_deselect_all(markers, action);
1541
1544
1545 return OPERATOR_FINISHED;
1546}
1547
1549{
1550 /* identifiers */
1551 ot->name = "(De)select all Markers";
1552 ot->description = "Change selection of all time markers";
1553 ot->idname = "MARKER_OT_select_all";
1554
1555 /* api callbacks */
1558
1559 /* flags */
1560 ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1561
1562 /* rna */
1564}
1565
1567
1568/* -------------------------------------------------------------------- */
1571
1576
1578 {MARKERS_LRSEL_LEFT, "LEFT", 0, "Before Current Frame", ""},
1579 {MARKERS_LRSEL_RIGHT, "RIGHT", 0, "After Current Frame", ""},
1580 {0, nullptr, 0, nullptr, nullptr},
1581};
1582
1585 const bool extend)
1586{
1587 ListBase *markers = ac->markers;
1588 Scene *scene = ac->scene;
1589
1590 if (markers == nullptr) {
1591 return;
1592 }
1593
1594 if (!extend) {
1595 deselect_markers(markers);
1596 }
1597
1598 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
1599 if ((mode == MARKERS_LRSEL_LEFT && marker->frame <= scene->r.cfra) ||
1600 (mode == MARKERS_LRSEL_RIGHT && marker->frame >= scene->r.cfra))
1601 {
1602 marker->flag |= SELECT;
1603 }
1604 }
1605}
1606
1608{
1610 RNA_enum_get(op->ptr, "mode"));
1611 const bool extend = RNA_boolean_get(op->ptr, "extend");
1612
1613 bAnimContext ac;
1614 if (ANIM_animdata_get_context(C, &ac) == 0) {
1615 return OPERATOR_CANCELLED;
1616 }
1617
1618 ED_markers_select_leftright(&ac, mode, extend);
1619
1621
1622 return OPERATOR_FINISHED;
1623}
1624
1626{
1627 /* identifiers */
1628 ot->name = "Select Markers Before/After Current Frame";
1629 ot->description = "Select markers on and left/right of the current frame";
1630 ot->idname = "MARKER_OT_select_leftright";
1631
1632 /* api callbacks */
1635
1636 /* flags */
1637 ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1638
1639 /* rna storage */
1641 ot->srna, "mode", prop_markers_select_leftright_modes, MARKERS_LRSEL_LEFT, "Mode", "");
1642 RNA_def_boolean(ot->srna, "extend", false, "Extend Select", "");
1643}
1644
1646
1647/* -------------------------------------------------------------------- */
1652
1654
1655{
1656 ListBase *markers = ED_context_get_markers(C);
1657 TimeMarker *marker, *nmarker;
1658 bool changed = false;
1659
1660 if (markers == nullptr) {
1661 return OPERATOR_CANCELLED;
1662 }
1663
1664 for (marker = static_cast<TimeMarker *>(markers->first); marker; marker = nmarker) {
1665 nmarker = marker->next;
1666 if (marker->flag & SELECT) {
1667 if (marker->prop != nullptr) {
1669 MEM_freeN(marker->prop);
1670 }
1671 BLI_freelinkN(markers, marker);
1672 changed = true;
1673 }
1674 }
1675
1676 if (changed) {
1679 }
1680
1681 return OPERATOR_FINISHED;
1682}
1683
1684static int ed_marker_delete_invoke(bContext *C, wmOperator *op, const wmEvent * /*event*/)
1685{
1686 if (RNA_boolean_get(op->ptr, "confirm")) {
1688 op,
1689 IFACE_("Delete selected markers?"),
1690 nullptr,
1691 IFACE_("Delete"),
1693 false);
1694 }
1695 return ed_marker_delete_exec(C, op);
1696}
1697
1699{
1700 /* identifiers */
1701 ot->name = "Delete Markers";
1702 ot->description = "Delete selected time marker(s)";
1703 ot->idname = "MARKER_OT_delete";
1704
1705 /* api callbacks */
1706 ot->invoke = ed_marker_delete_invoke;
1707 ot->exec = ed_marker_delete_exec;
1709
1710 /* flags */
1711 ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1713}
1714
1716
1717/* -------------------------------------------------------------------- */
1722
1724{
1726
1727 if (marker) {
1728 RNA_string_get(op->ptr, "name", marker->name);
1729
1732
1733 return OPERATOR_FINISHED;
1734 }
1735
1736 return OPERATOR_CANCELLED;
1737}
1738
1739static int ed_marker_rename_invoke(bContext *C, wmOperator *op, const wmEvent *event)
1740{
1741 /* must initialize the marker name first if there is a marker selected */
1743 if (marker) {
1744 RNA_string_set(op->ptr, "name", marker->name);
1745 }
1746
1748 C, op, event, IFACE_("Rename Selected Time Marker"), IFACE_("Rename"));
1749}
1750
1752{
1753 /* identifiers */
1754 ot->name = "Rename Marker";
1755 ot->description = "Rename first selected time marker";
1756 ot->idname = "MARKER_OT_rename";
1757
1758 /* api callbacks */
1759 ot->invoke = ed_marker_rename_invoke;
1760 ot->exec = ed_marker_rename_exec;
1762
1763 /* flags */
1764 ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1765
1766 /* properties */
1767 ot->prop = RNA_def_string(
1768 ot->srna, "name", "RenamedMarker", sizeof(TimeMarker::name), "Name", "New name for marker");
1769#if 0
1770 RNA_def_boolean(ot->srna,
1771 "ensure_unique",
1772 0,
1773 "Ensure Unique",
1774 "Ensure that new name is unique within collection of markers");
1775#endif
1776}
1777
1779
1780/* -------------------------------------------------------------------- */
1783
1785{
1786 Main *bmain = CTX_data_main(C);
1787 ListBase *markers = ED_context_get_markers(C);
1788 Scene *scene_to = static_cast<Scene *>(
1789 BLI_findlink(&bmain->scenes, RNA_enum_get(op->ptr, "scene")));
1790 TimeMarker *marker_new;
1791
1792 if (scene_to == nullptr) {
1793 BKE_report(op->reports, RPT_ERROR, "Scene not found");
1794 return OPERATOR_CANCELLED;
1795 }
1796
1797 if (scene_to == CTX_data_scene(C)) {
1798 BKE_report(op->reports, RPT_ERROR, "Cannot re-link markers into the same scene");
1799 return OPERATOR_CANCELLED;
1800 }
1801
1802 if (scene_to->toolsettings->lock_markers) {
1803 BKE_report(op->reports, RPT_ERROR, "Target scene has locked markers");
1804 return OPERATOR_CANCELLED;
1805 }
1806
1807 /* copy markers */
1808 LISTBASE_FOREACH (TimeMarker *, marker, markers) {
1809 if (marker->flag & SELECT) {
1810 marker_new = static_cast<TimeMarker *>(MEM_dupallocN(marker));
1811 marker_new->prev = marker_new->next = nullptr;
1812
1813 BLI_addtail(&scene_to->markers, marker_new);
1814 }
1815 }
1816
1817 return OPERATOR_FINISHED;
1818}
1819
1821{
1822 PropertyRNA *prop;
1823
1824 /* identifiers */
1825 ot->name = "Copy Markers to Scene";
1826 ot->description = "Copy selected markers to another scene";
1827 ot->idname = "MARKER_OT_make_links_scene";
1828
1829 /* api callbacks */
1831 ot->invoke = WM_menu_invoke;
1833
1834 /* flags */
1835 ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1836
1837 /* properties */
1838 prop = RNA_def_enum(ot->srna, "scene", rna_enum_dummy_NULL_items, 0, "Scene", "");
1841 ot->prop = prop;
1842}
1843
1845
1846/* -------------------------------------------------------------------- */
1849
1850#ifdef DURIAN_CAMERA_SWITCH
1851
1853{
1854 bScreen *screen = CTX_wm_screen(C);
1855 Scene *scene = CTX_data_scene(C);
1857 ListBase *markers = ED_context_get_markers(C);
1858 TimeMarker *marker;
1859
1860 /* Don't do anything if we don't have a camera selected */
1861 if (ob == nullptr) {
1862 BKE_report(op->reports, RPT_ERROR, "Select a camera to bind to a marker on this frame");
1863 return OPERATOR_CANCELLED;
1864 }
1865
1866 /* add new marker, unless we already have one on this frame, in which case, replace it */
1867 if (markers == nullptr) {
1868 return OPERATOR_CANCELLED;
1869 }
1870
1871 marker = ED_markers_find_nearest_marker(markers, scene->r.cfra);
1872 if ((marker == nullptr) || (marker->frame != scene->r.cfra)) {
1873 marker = static_cast<TimeMarker *>(MEM_callocN(sizeof(TimeMarker), "Camera TimeMarker"));
1874 /* This marker's name is only displayed in the viewport statistics, animation editors use the
1875 * camera's name when bound to a marker. */
1876 SNPRINTF(marker->name, "F_%02d", scene->r.cfra);
1877 marker->flag = SELECT;
1878 marker->frame = scene->r.cfra;
1879 BLI_addtail(markers, marker);
1880
1881 /* deselect all others, so that the user can then move it without problems */
1882 LISTBASE_FOREACH (TimeMarker *, m, markers) {
1883 if (m != marker) {
1884 m->flag &= ~SELECT;
1885 }
1886 }
1887 }
1888
1889 /* bind to the nominated camera (as set in operator props) */
1890 marker->camera = ob;
1891
1892 /* camera may have changes */
1894 BKE_screen_view3d_scene_sync(screen, scene);
1896
1899 WM_event_add_notifier(C, NC_SCENE | NA_EDITED, scene); /* so we get view3d redraws */
1900
1901 return OPERATOR_FINISHED;
1902}
1903
1905{
1906 /* identifiers */
1907 ot->name = "Bind Camera to Markers";
1908 ot->description = "Bind the selected camera to a marker on the current frame";
1909 ot->idname = "MARKER_OT_camera_bind";
1910
1911 /* api callbacks */
1914
1915 /* flags */
1916 ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1917}
1918
1919#endif
1920
1922
1923/* -------------------------------------------------------------------- */
1926
1943
1945{
1946 WM_keymap_ensure(keyconf, "Markers", SPACE_EMPTY, RGN_TYPE_WINDOW);
1947}
1948
bScreen * CTX_wm_screen(const bContext *C)
@ CTX_MODE_OBJECT
void CTX_wm_operator_poll_msg_set(bContext *C, const char *msg)
ScrArea * CTX_wm_area(const bContext *C)
Object * CTX_data_active_object(const bContext *C)
SpaceLink * CTX_wm_space_data(const bContext *C)
Scene * CTX_data_scene(const bContext *C)
Main * CTX_data_main(const bContext *C)
ToolSettings * CTX_data_tool_settings(const bContext *C)
ARegion * CTX_wm_region(const bContext *C)
enum eContextObjectMode CTX_data_mode_enum(const bContext *C)
ViewLayer * CTX_data_view_layer(const bContext *C)
void IDP_FreePropertyContent(IDProperty *prop)
Definition idprop.cc:1216
IDProperty * IDP_CopyProperty(const IDProperty *prop) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL()
Definition idprop.cc:861
void BKE_view_layer_synced_ensure(const Scene *scene, ViewLayer *view_layer)
void BKE_view_layer_base_deselect_all(const Scene *scene, ViewLayer *view_layer)
Base * BKE_view_layer_base_find(ViewLayer *view_layer, Object *ob)
void BKE_report(ReportList *reports, eReportType type, const char *message)
Definition report.cc:125
bool BKE_scene_camera_switch_update(Scene *scene)
Definition scene.cc:2213
void BKE_screen_view3d_scene_sync(bScreen *screen, Scene *scene)
Definition screen.cc:963
@ B_UNIT_NONE
Definition BKE_unit.hh:106
@ B_UNIT_TIME
Definition BKE_unit.hh:112
#define BLI_assert(a)
Definition BLI_assert.h:50
#define ATTR_FALLTHROUGH
BLI_INLINE bool BLI_listbase_is_empty(const struct ListBase *lb)
void BLI_addhead(struct ListBase *listbase, void *vlink) ATTR_NONNULL(1)
Definition listbase.cc:90
#define LISTBASE_FOREACH(type, var, list)
void BLI_freelinkN(struct ListBase *listbase, void *vlink) ATTR_NONNULL(1)
Definition listbase.cc:269
#define LISTBASE_CIRCULAR_FORWARD_BEGIN(type, lb, lb_iter, lb_init)
void void void void void void BLI_duplicatelist(struct ListBase *dst, const struct ListBase *src) ATTR_NONNULL(1
void * BLI_findlink(const struct ListBase *listbase, int number) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1)
void void BLI_freelistN(struct ListBase *listbase) ATTR_NONNULL(1)
Definition listbase.cc:496
void void BLI_listbase_sort(struct ListBase *listbase, int(*cmp)(const void *, const void *)) ATTR_NONNULL(1
void BLI_addtail(struct ListBase *listbase, void *vlink) ATTR_NONNULL(1)
Definition listbase.cc:110
void BLI_insertlinkbefore(struct ListBase *listbase, void *vnextlink, void *vnewlink) ATTR_NONNULL(1)
Definition listbase.cc:370
#define LISTBASE_CIRCULAR_FORWARD_END(type, lb, lb_iter, lb_init)
MINLINE int round_fl_to_int(float a)
MINLINE void copy_v4_v4_uchar(unsigned char r[4], const unsigned char a[4])
bool BLI_rctf_isect_x(const rctf *rect, float x)
Definition rct.c:93
BLI_INLINE int BLI_rcti_size_x(const struct rcti *rct)
Definition BLI_rect.h:189
BLI_INLINE float BLI_rctf_size_x(const struct rctf *rct)
Definition BLI_rect.h:197
#define STRNCPY(dst, src)
Definition BLI_string.h:593
#define SNPRINTF(dst, format,...)
Definition BLI_string.h:597
unsigned char uchar
unsigned int uint
#define SET_FLAG_FROM_TEST(value, test, flag)
#define ELEM(...)
#define IFACE_(msgid)
void DEG_id_tag_update(ID *id, unsigned int flags)
void DEG_relations_tag_update(Main *bmain)
@ ID_RECALC_SELECT
Definition DNA_ID.h:1068
@ SACTCONT_ACTION
@ SACTCONT_SHAPEKEY
@ SACTION_POSEMARKERS_SHOW
@ SACTION_SHOW_MARKERS
@ SACTION_DRAWTIME
Object is a sort of wrapper for general info.
@ OB_HIDE_RENDER
#define TIME2FRA(a)
#define FPS
#define FRA2TIME(a)
@ RGN_TYPE_WINDOW
@ SPACE_ACTION
@ SPACE_NLA
@ SPACE_SEQ
@ SPACE_EMPTY
@ SPACE_GRAPH
@ SIPO_MODE_DRIVERS
@ SIPO_DRAWTIME
@ SIPO_SHOW_MARKERS
@ SNLA_DRAWTIME
@ SNLA_SHOW_MARKERS
@ SEQ_DRAWFRAMES
@ SEQ_SHOW_MARKERS
#define UI_SCALE_FAC
#define UI_INV_SCALE_FAC
#define UI_ICON_SIZE
@ OPERATOR_RUNNING_MODAL
@ OPERATOR_PASS_THROUGH
@ DRAW_MARKERS_LOCAL
Definition ED_markers.hh:24
void initNumInput(NumInput *n)
Definition numinput.cc:70
#define NUM_STR_REP_LEN
@ NUM_NO_FRACTION
void outputNumInput(NumInput *n, char *str, const UnitSettings *unit_settings)
Definition numinput.cc:88
bool handleNumInput(bContext *C, NumInput *n, const wmEvent *event)
Definition numinput.cc:312
bool applyNumInput(NumInput *n, float *vec)
Definition numinput.cc:190
bool hasNumInput(const NumInput *n)
Definition numinput.cc:171
void ED_area_status_text(ScrArea *area, const char *str)
Definition area.cc:803
#define SEL_OP_USE_PRE_DESELECT(sel_op)
@ SEL_SELECT
@ SEL_INVERT
@ SEL_DESELECT
@ SEL_TOGGLE
eSelectOp
@ SEL_OP_SUB
@ TFM_TIME_TRANSLATE
@ TFM_TIME_SCALE
@ TFM_TIME_EXTEND
void apply_keyb_grid(bool shift, bool ctrl, float *val, float fac1, float fac2, float fac3, int invert)
Definition ed_util.cc:338
void immUniformColor4ubv(const unsigned char rgba[4])
void immEnd()
void immUnbindProgram()
void immUniform2f(const char *name, float x, float y)
void immVertex2f(uint attr_id, float x, float y)
void immBindBuiltinProgram(eGPUBuiltinShader shader_id)
void immUniform1i(const char *name, int x)
void immUniform1f(const char *name, float x)
GPUVertFormat * immVertexFormat()
void immBegin(GPUPrimType, uint vertex_len)
void immRectf(uint pos, float x1, float y1, float x2, float y2)
void GPU_matrix_scale_2f(float x, float y)
void GPU_matrix_push()
void GPU_matrix_pop()
@ GPU_PRIM_LINES
@ GPU_SHADER_3D_LINE_DASHED_UNIFORM_COLOR
@ GPU_SHADER_3D_UNIFORM_COLOR
@ GPU_BLEND_NONE
Definition GPU_state.hh:85
@ GPU_BLEND_ALPHA
Definition GPU_state.hh:87
void GPU_blend(eGPUBlend blend)
Definition gpu_state.cc:42
void GPU_line_width(float width)
Definition gpu_state.cc:161
void GPU_viewport_size_get_f(float coords[4])
Definition gpu_state.cc:262
@ GPU_FETCH_FLOAT
uint GPU_vertformat_attr_add(GPUVertFormat *, const char *name, GPUVertCompType, uint comp_len, GPUVertFetchMode)
@ GPU_COMP_F32
Read Guarded memory(de)allocation.
Group Output data from inside of a node group A color picker Mix two input colors RGB to Convert a color s luminance to a grayscale value Generate a normal vector and a dot product Brightness Control the brightness and contrast of the input color Vector Map input vector components with curves Camera Retrieve information about the camera and how it relates to the current shading point s position Clamp a value between a minimum and a maximum Vector Perform vector math operation Invert Invert a color
in reality light always falls off quadratically Particle Retrieve the data of the particle that spawned the object for example to give variation to multiple instances of an object Point Retrieve information about points in a point cloud Retrieve the edges of an object as it appears to Cycles topology will always appear triangulated Convert a blackbody temperature to an RGB value Normal Generate a perturbed normal from an RGB normal map image Typically used for faking highly detailed surfaces Generate an OSL shader from a file or text data block Image Sample an image file as a texture Gabor Generate Gabor noise Gradient Generate interpolated color and intensity values based on the input vector Magic Generate a psychedelic color texture Voronoi Generate Worley noise based on the distance to random points Typically used to generate textures such as or biological cells Brick Generate a procedural texture producing bricks Texture Retrieve multiple types of texture coordinates nTypically used as inputs for texture nodes Vector Convert a or normal between camera
const EnumPropertyItem * RNA_scene_itemf(bContext *C, PointerRNA *ptr, PropertyRNA *prop, bool *r_free)
@ PROP_ENUM_NO_TRANSLATE
Definition RNA_types.hh:321
@ PROP_SKIP_SAVE
Definition RNA_types.hh:245
@ PROP_HIDDEN
Definition RNA_types.hh:239
#define C
Definition RandGen.cpp:29
@ UI_STYLE_TEXT_LEFT
#define UI_MAX_DRAW_STR
void UI_fontstyle_draw(const uiFontStyle *fs, const rcti *rect, const char *str, size_t str_len, const uchar col[4], const uiFontStyleDraw_Params *fs_params)
#define UI_FSTYLE_WIDGET
#define UI_NO_ICON_OVERLAY_TEXT
void UI_icon_draw_ex(float x, float y, int icon_id, float aspect, float alpha, float desaturate, const uchar mono_color[4], bool mono_border, const IconTextOverlay *text_overlay, const bool inverted=false)
@ ALERT_ICON_NONE
@ TH_TIME_SCRUB_BACKGROUND
@ TH_TIME_MARKER_LINE
@ TH_TIME_MARKER_LINE_SELECTED
@ TH_TEXT
@ TH_TEXT_HI
void UI_GetThemeColor4ubv(int colorid, unsigned char col[4])
#define UI_MARKER_MARGIN_Y
Definition UI_view2d.hh:471
View2D * UI_view2d_fromcontext(const bContext *C)
Definition view2d.cc:1850
void UI_view2d_scale_get(const View2D *v2d, float *r_x, float *r_y)
Definition view2d.cc:1907
float UI_view2d_region_to_view_x(const View2D *v2d, float x)
Definition view2d.cc:1652
void UI_view2d_region_to_view_rctf(const View2D *v2d, const rctf *rect_src, rctf *rect_dst) ATTR_NONNULL()
Definition view2d.cc:1670
float UI_view2d_scale_get_x(const View2D *v2d)
Definition view2d.cc:1916
@ OPTYPE_BLOCKING
Definition WM_types.hh:164
@ OPTYPE_UNDO
Definition WM_types.hh:162
@ OPTYPE_REGISTER
Definition WM_types.hh:160
@ OPTYPE_GRAB_CURSOR_X
Definition WM_types.hh:170
#define NC_ANIMATION
Definition WM_types.hh:355
#define ND_OB_SELECT
Definition WM_types.hh:409
#define NC_SCENE
Definition WM_types.hh:345
#define NA_EDITED
Definition WM_types.hh:550
#define ND_MARKERS
Definition WM_types.hh:400
@ KM_PRESS
Definition WM_types.hh:284
#define ND_KEYFRAME
Definition WM_types.hh:461
#define NA_SELECTED
Definition WM_types.hh:555
@ KM_CTRL
Definition WM_types.hh:256
@ KM_SHIFT
Definition WM_types.hh:255
bool ANIM_animdata_get_context(const bContext *C, bAnimContext *ac)
static int ed_marker_box_select_invoke(bContext *C, wmOperator *op, const wmEvent *event)
static ListBase * context_get_markers(Scene *scene, ScrArea *area)
static void draw_markers_background(const rctf *rect)
static void ed_marker_duplicate_apply(bContext *C)
static int markers_frame_sort(const void *a, const void *b)
void ED_keymap_marker(wmKeyConfig *keyconf)
static void ed_marker_move_update_header(bContext *C, wmOperator *op)
static void ed_marker_move_exit(bContext *C, wmOperator *op)
static int ed_marker_move_modal(bContext *C, wmOperator *op, const wmEvent *event)
static void marker_color_get(const TimeMarker *marker, uchar *r_text_color, uchar *r_line_color)
static int ed_marker_rename_invoke(bContext *C, wmOperator *op, const wmEvent *event)
eMarkers_LeftRightSelect_Mode
@ MARKERS_LRSEL_RIGHT
@ MARKERS_LRSEL_LEFT
static bool ED_operator_markers_region_active(bContext *C)
static int ed_marker_select_exec(bContext *C, wmOperator *op)
int ED_markers_post_apply_transform(ListBase *markers, Scene *scene, int mode, float value, char side)
static void MARKER_OT_move(wmOperatorType *ot)
static int ed_marker_make_links_scene_exec(bContext *C, wmOperator *op)
static int ed_marker_camera_bind_exec(bContext *C, wmOperator *op)
static void select_marker_camera_switch(bContext *C, bool camera, bool extend, ListBase *markers, int cfra)
static void get_marker_region_rect(View2D *v2d, rctf *r_rect)
static int ed_marker_delete_exec(bContext *C, wmOperator *)
static void MARKER_OT_select_leftright(wmOperatorType *ot)
ListBase * ED_animcontext_get_markers(const bAnimContext *ac)
static void MARKER_OT_add(wmOperatorType *ot)
static void draw_marker_line(const uchar *color, int xpos, int ymin, int ymax)
static int ed_marker_select_leftright_exec(bContext *C, wmOperator *op)
void ED_markers_get_minmax(ListBase *markers, short sel, float *r_first, float *r_last)
static const EnumPropertyItem prop_markers_select_leftright_modes[]
static void add_marker_to_cfra_elem(ListBase *lb, TimeMarker *marker, const bool only_selected)
static bool ed_markers_poll_selected_no_locked_markers(bContext *C)
static int ed_marker_duplicate_exec(bContext *C, wmOperator *op)
static int ed_marker_rename_exec(bContext *C, wmOperator *op)
void ED_operatortypes_marker()
int ED_markers_find_nearest_marker_time(ListBase *markers, float x)
static void draw_marker_name(const uchar *text_color, const uiFontStyle *fstyle, TimeMarker *marker, float marker_x, float xmax, float text_y)
static void MARKER_OT_camera_bind(wmOperatorType *ot)
static void deselect_markers(ListBase *markers)
static bool ed_markers_poll_selected_markers(bContext *C)
static int ed_marker_add_exec(bContext *C, wmOperator *)
static bool ed_marker_move_init(bContext *C, wmOperator *op)
static void MARKER_OT_duplicate(wmOperatorType *ot)
static void ed_marker_move_apply(bContext *C, wmOperator *op)
static int ed_marker_delete_invoke(bContext *C, wmOperator *op, const wmEvent *)
static void ED_markers_select_leftright(bAnimContext *ac, const eMarkers_LeftRightSelect_Mode mode, const bool extend)
static void MARKER_OT_delete(wmOperatorType *ot)
static void draw_marker(const uiFontStyle *fstyle, TimeMarker *marker, int xpos, int xmax, int flag, int region_height, bool is_elevated)
static bool region_position_is_over_marker(View2D *v2d, ListBase *markers, float region_x)
static void MARKER_OT_select_all(wmOperatorType *ot)
static void MARKER_OT_rename(wmOperatorType *ot)
static int ed_marker_move_invoke(bContext *C, wmOperator *op, const wmEvent *event)
static void MARKER_OT_make_links_scene(wmOperatorType *ot)
static void MARKER_OT_select(wmOperatorType *ot)
static bool marker_is_in_frame_range(TimeMarker *marker, const int frame_range[2])
static bool ed_markers_poll_markers_exist(bContext *C)
ListBase * ED_context_get_markers(const bContext *C)
static int ed_marker_box_select_exec(bContext *C, wmOperator *op)
TimeMarker * ED_markers_find_nearest_marker(ListBase *markers, float x)
static void MARKER_OT_select_box(wmOperatorType *ot)
static int ed_marker_move_exec(bContext *C, wmOperator *op)
static int ed_marker_select(bContext *C, const int mval[2], bool extend, bool camera, bool wait_to_deselect_others)
static bool ed_marker_move_use_time(MarkerMove *mm)
TimeMarker * ED_markers_get_first_selected(ListBase *markers)
void ED_markers_deselect_all(ListBase *markers, int action)
void ED_markers_make_cfra_list(ListBase *markers, ListBase *lb, const bool only_selected)
static int ed_marker_duplicate_invoke(bContext *C, wmOperator *op, const wmEvent *event)
void debug_markers_print_list(ListBase *markers)
static int select_timeline_marker_frame(ListBase *markers, int frame, bool extend, bool wait_to_deselect_others)
static int marker_get_icon_id(TimeMarker *marker, int flag)
static void ed_marker_move_cancel(bContext *C, wmOperator *op)
static void get_marker_clip_frame_range(View2D *v2d, float xscale, int r_range[2])
static int ed_marker_select_all_exec(bContext *C, wmOperator *op)
void ED_markers_draw(const bContext *C, int flag)
#define U
local_group_size(16, 16) .push_constant(Type b
#define printf
#define SELECT
#define fabsf(x)
draw_view in_light_buf[] float
#define str(s)
format
void MEM_freeN(void *vmemh)
Definition mallocn.cc:105
void *(* MEM_callocN)(size_t len, const char *str)
Definition mallocn.cc:42
void *(* MEM_dupallocN)(const void *vmemh)
Definition mallocn.cc:39
ccl_device_inline float4 select(const int4 mask, const float4 a, const float4 b)
static ulong * next
void base_activate(bContext *C, Base *base)
void base_select(Base *base, eObjectSelect_Mode mode)
void RNA_string_set(PointerRNA *ptr, const char *name, const char *value)
PropertyRNA * RNA_struct_find_property(PointerRNA *ptr, const char *identifier)
void RNA_int_set(PointerRNA *ptr, const char *name, int value)
void RNA_string_get(PointerRNA *ptr, const char *name, char *value)
int RNA_int_get(PointerRNA *ptr, const char *name)
bool RNA_boolean_get(PointerRNA *ptr, const char *name)
int RNA_enum_get(PointerRNA *ptr, const char *name)
PropertyRNA * RNA_def_string(StructOrFunctionRNA *cont_, const char *identifier, const char *default_value, const int maxlen, const char *ui_name, const char *ui_description)
PropertyRNA * RNA_def_enum(StructOrFunctionRNA *cont_, const char *identifier, const EnumPropertyItem *items, const int default_value, const char *ui_name, const char *ui_description)
PropertyRNA * RNA_def_boolean(StructOrFunctionRNA *cont_, const char *identifier, const bool default_value, const char *ui_name, const char *ui_description)
void RNA_def_property_flag(PropertyRNA *prop, PropertyFlag flag)
void RNA_def_enum_funcs(PropertyRNA *prop, EnumPropertyItemFunc itemfunc)
PropertyRNA * RNA_def_int(StructOrFunctionRNA *cont_, const char *identifier, const int default_value, const int hardmin, const int hardmax, const char *ui_name, const char *ui_description, const int softmin, const int softmax)
const EnumPropertyItem rna_enum_dummy_NULL_items[]
Definition rna_rna.cc:29
#define min(a, b)
Definition sort.c:32
#define FLT_MAX
Definition stdcycles.h:14
CfraElem * next
void * last
void * first
ListBase scenes
Definition BKE_main.hh:210
NumInput num
SpaceLink * slink
ListBase * markers
short idx_max
short val_flag[NUM_MAX_ELEMENTS]
int unit_type[NUM_MAX_ELEMENTS]
struct ToolSettings * toolsettings
struct RenderData r
struct UnitSettings unit
struct Object * camera
ListBase markers
ListBase spacedata
struct TimeMarker * prev
struct IDProperty * prop
struct Object * camera
unsigned int flag
struct TimeMarker * next
ListBase markers
ListBase * markers
ScrArea * area
float xmax
float xmin
float ymax
float ymin
int ymin
int ymax
int xmin
int xmax
short val
Definition WM_types.hh:724
int xy[2]
Definition WM_types.hh:726
uint8_t modifier
Definition WM_types.hh:739
short type
Definition WM_types.hh:722
struct ReportList * reports
struct PointerRNA * ptr
float max
bool WM_event_is_modal_drag_exit(const wmEvent *event, const short init_event_type, const short init_event_val)
wmEventHandler_Op * WM_event_add_modal_handler(bContext *C, wmOperator *op)
void WM_event_add_notifier(const bContext *C, uint type, void *reference)
@ RIGHTMOUSE
@ EVT_PADENTER
@ MOUSEMOVE
@ LEFTMOUSE
@ MIDDLEMOUSE
@ EVT_ESCKEY
@ EVT_RETKEY
wmOperatorType * ot
Definition wm_files.cc:4125
void WM_gesture_box_cancel(bContext *C, wmOperator *op)
int WM_gesture_box_invoke(bContext *C, wmOperator *op, const wmEvent *event)
int WM_gesture_box_modal(bContext *C, wmOperator *op, const wmEvent *event)
wmKeyMap * WM_keymap_ensure(wmKeyConfig *keyconf, const char *idname, int spaceid, int regionid)
Definition wm_keymap.cc:897
void WM_operator_properties_gesture_box(wmOperatorType *ot)
void WM_operator_properties_confirm_or_exec(wmOperatorType *ot)
void WM_operator_properties_select_operation_simple(wmOperatorType *ot)
void WM_operator_properties_border_to_rctf(wmOperator *op, rctf *r_rect)
void WM_operator_properties_generic_select(wmOperatorType *ot)
void WM_operator_properties_select_all(wmOperatorType *ot)
void WM_operatortype_append(void(*opfunc)(wmOperatorType *))
int WM_menu_invoke(bContext *C, wmOperator *op, const wmEvent *)
int WM_operator_confirm_ex(bContext *C, wmOperator *op, const char *title, const char *message, const char *confirm_text, int icon, bool cancel_default)
int WM_operator_props_popup_confirm_ex(bContext *C, wmOperator *op, const wmEvent *, std::optional< std::string > title, std::optional< std::string > confirm_text, const bool cancel_default)
int WM_generic_select_invoke(bContext *C, wmOperator *op, const wmEvent *event)
int WM_generic_select_modal(bContext *C, wmOperator *op, const wmEvent *event)
uint8_t flag
Definition wm_window.cc:138