Merge branch 'master' into blender2.8
[blender.git] / source / blender / editors / armature / pose_edit.c
1 /*
2  * ***** BEGIN GPL LICENSE BLOCK *****
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17  *
18  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
19  * All rights reserved.
20  *
21  * Contributor(s): Ton Roosendaal, Blender Foundation '05, full recode.
22  *                 Joshua Leung
23  *                 Reevan McKay (original NaN code)
24  *
25  * ***** END GPL LICENSE BLOCK *****
26  *
27  * Pose Mode API's and Operators for Pose Mode armatures
28  */
29
30 /** \file blender/editors/armature/pose_edit.c
31  *  \ingroup edarmature
32  */
33
34 #include "MEM_guardedalloc.h"
35
36 #include "BLI_math.h"
37 #include "BLI_blenlib.h"
38
39 #include "DNA_anim_types.h"
40 #include "DNA_armature_types.h"
41 #include "DNA_scene_types.h"
42 #include "DNA_object_types.h"
43
44 #include "BKE_action.h"
45 #include "BKE_anim.h"
46 #include "BKE_armature.h"
47 #include "BKE_context.h"
48 #include "BKE_deform.h"
49 #include "BKE_object.h"
50 #include "BKE_report.h"
51 #include "BKE_layer.h"
52
53 #include "DEG_depsgraph.h"
54
55 #include "RNA_access.h"
56 #include "RNA_define.h"
57 #include "RNA_enum_types.h"
58
59 #include "WM_api.h"
60 #include "WM_types.h"
61
62 #include "ED_armature.h"
63 #include "ED_keyframing.h"
64 #include "ED_screen.h"
65 #include "ED_object.h"
66 #include "ED_view3d.h"
67
68 #include "UI_interface.h"
69
70 #include "armature_intern.h"
71
72 /* matches logic with ED_operator_posemode_context() */
73 Object *ED_pose_object_from_context(bContext *C)
74 {
75         ScrArea *sa = CTX_wm_area(C);
76         Object *ob;
77
78         /* since this call may also be used from the buttons window, we need to check for where to get the object */
79         if (sa && sa->spacetype == SPACE_BUTS) {
80                 ob = ED_object_context(C);
81         }
82         else {
83                 ob = BKE_object_pose_armature_get(CTX_data_active_object(C));
84         }
85
86         return ob;
87 }
88
89 /* This function is used to process the necessary updates for */
90 bool ED_object_posemode_enter_ex(struct Main *bmain, Object *ob)
91 {
92         BLI_assert(!ID_IS_LINKED(ob));
93         bool ok = false;
94
95         switch (ob->type) {
96                 case OB_ARMATURE:
97                         ob->restore_mode = ob->mode;
98                         ob->mode |= OB_MODE_POSE;
99                         /* Inform all CoW versions that we changed the mode. */
100                         DEG_id_tag_update_ex(bmain, &ob->id, DEG_TAG_COPY_ON_WRITE);
101                         ok = true;
102
103                         break;
104                 default:
105                         break;
106         }
107
108         return ok;
109 }
110 bool ED_object_posemode_enter(bContext *C, Object *ob)
111 {
112         ReportList *reports = CTX_wm_reports(C);
113         if (ID_IS_LINKED(ob)) {
114                 BKE_report(reports, RPT_WARNING, "Cannot pose libdata");
115                 return false;
116         }
117         struct Main *bmain = CTX_data_main(C);
118         bool ok = ED_object_posemode_enter_ex(bmain, ob);
119         if (ok) {
120                 WM_event_add_notifier(C, NC_SCENE | ND_MODE | NS_MODE_POSE, NULL);
121         }
122         return ok;
123 }
124
125 bool ED_object_posemode_exit_ex(struct Main *bmain, Object *ob)
126 {
127         bool ok = false;
128         if (ob) {
129                 ob->restore_mode = ob->mode;
130                 ob->mode &= ~OB_MODE_POSE;
131
132                 /* Inform all CoW versions that we changed the mode. */
133                 DEG_id_tag_update_ex(bmain, &ob->id, DEG_TAG_COPY_ON_WRITE);
134                 ok = true;
135         }
136         return ok;
137 }
138 bool ED_object_posemode_exit(bContext *C, Object *ob)
139 {
140         struct Main *bmain = CTX_data_main(C);
141         bool ok = ED_object_posemode_exit_ex(bmain, ob);
142         if (ok) {
143                 WM_event_add_notifier(C, NC_SCENE | ND_MODE | NS_MODE_OBJECT, NULL);
144         }
145         return ok;
146 }
147
148 /* if a selected or active bone is protected, throw error (oonly if warn == 1) and return 1 */
149 /* only_selected == 1: the active bone is allowed to be protected */
150 #if 0 /* UNUSED 2.5 */
151 static bool pose_has_protected_selected(Object *ob, short warn)
152 {
153         /* check protection */
154         if (ob->proxy) {
155                 bPoseChannel *pchan;
156                 bArmature *arm = ob->data;
157
158                 for (pchan = ob->pose->chanbase.first; pchan; pchan = pchan->next) {
159                         if (pchan->bone && (pchan->bone->layer & arm->layer)) {
160                                 if (pchan->bone->layer & arm->layer_protected) {
161                                         if (pchan->bone->flag & BONE_SELECTED)
162                                                 break;
163                                 }
164                         }
165                 }
166                 if (pchan) {
167                         if (warn) error("Cannot change Proxy protected bones");
168                         return 1;
169                 }
170         }
171         return 0;
172 }
173 #endif
174
175 /* ********************************************** */
176 /* Motion Paths */
177
178 /* For the object with pose/action: update paths for those that have got them
179  * This should selectively update paths that exist...
180  *
181  * To be called from various tools that do incremental updates
182  */
183 void ED_pose_recalculate_paths(bContext *C, Scene *scene, Object *ob)
184 {
185         struct Main *bmain = CTX_data_main(C);
186         Depsgraph *depsgraph = CTX_data_depsgraph(C);
187         ListBase targets = {NULL, NULL};
188
189         /* set flag to force recalc, then grab the relevant bones to target */
190         ob->pose->avs.recalc |= ANIMVIZ_RECALC_PATHS;
191         animviz_get_object_motionpaths(ob, &targets);
192
193         /* recalculate paths, then free */
194         animviz_calc_motionpaths(depsgraph, bmain, scene, &targets);
195         BLI_freelistN(&targets);
196
197         /* tag armature object for copy on write - so paths will draw/redraw */
198         DEG_id_tag_update(&ob->id, DEG_TAG_COPY_ON_WRITE);
199 }
200
201
202 /* show popup to determine settings */
203 static int pose_calculate_paths_invoke(bContext *C, wmOperator *op, const wmEvent *UNUSED(event))
204 {
205         Object *ob = BKE_object_pose_armature_get(CTX_data_active_object(C));
206
207         if (ELEM(NULL, ob, ob->pose))
208                 return OPERATOR_CANCELLED;
209
210         /* set default settings from existing/stored settings */
211         {
212                 bAnimVizSettings *avs = &ob->pose->avs;
213                 PointerRNA avs_ptr;
214
215                 RNA_int_set(op->ptr, "start_frame", avs->path_sf);
216                 RNA_int_set(op->ptr, "end_frame", avs->path_ef);
217
218                 RNA_pointer_create(NULL, &RNA_AnimVizMotionPaths, avs, &avs_ptr);
219                 RNA_enum_set(op->ptr, "bake_location", RNA_enum_get(&avs_ptr, "bake_location"));
220         }
221
222         /* show popup dialog to allow editing of range... */
223         // FIXME: hardcoded dimensions here are just arbitrary
224         return WM_operator_props_dialog_popup(C, op, 10 * UI_UNIT_X, 10 * UI_UNIT_Y);
225 }
226
227 /* For the object with pose/action: create path curves for selected bones
228  * This recalculates the WHOLE path within the pchan->pathsf and pchan->pathef range
229  */
230 static int pose_calculate_paths_exec(bContext *C, wmOperator *op)
231 {
232         Object *ob = BKE_object_pose_armature_get(CTX_data_active_object(C));
233         Scene *scene = CTX_data_scene(C);
234
235         if (ELEM(NULL, ob, ob->pose))
236                 return OPERATOR_CANCELLED;
237
238         /* grab baking settings from operator settings */
239         {
240                 bAnimVizSettings *avs = &ob->pose->avs;
241                 PointerRNA avs_ptr;
242
243                 avs->path_sf = RNA_int_get(op->ptr, "start_frame");
244                 avs->path_ef = RNA_int_get(op->ptr, "end_frame");
245
246                 RNA_pointer_create(NULL, &RNA_AnimVizMotionPaths, avs, &avs_ptr);
247                 RNA_enum_set(&avs_ptr, "bake_location", RNA_enum_get(op->ptr, "bake_location"));
248         }
249
250         /* set up path data for bones being calculated */
251         CTX_DATA_BEGIN (C, bPoseChannel *, pchan, selected_pose_bones)
252         {
253                 /* verify makes sure that the selected bone has a bone with the appropriate settings */
254                 animviz_verify_motionpaths(op->reports, scene, ob, pchan);
255         }
256         CTX_DATA_END;
257
258         /* calculate the bones that now have motionpaths... */
259         /* TODO: only make for the selected bones? */
260         ED_pose_recalculate_paths(C, scene, ob);
261
262         /* notifiers for updates */
263         WM_event_add_notifier(C, NC_OBJECT | ND_POSE, ob);
264
265         return OPERATOR_FINISHED;
266 }
267
268 void POSE_OT_paths_calculate(wmOperatorType *ot)
269 {
270         /* identifiers */
271         ot->name = "Calculate Bone Paths";
272         ot->idname = "POSE_OT_paths_calculate";
273         ot->description = "Calculate paths for the selected bones";
274
275         /* api callbacks */
276         ot->invoke = pose_calculate_paths_invoke;
277         ot->exec = pose_calculate_paths_exec;
278         ot->poll = ED_operator_posemode_exclusive;
279
280         /* flags */
281         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
282
283         /* properties */
284         RNA_def_int(ot->srna, "start_frame", 1, MINAFRAME, MAXFRAME, "Start",
285                     "First frame to calculate bone paths on", MINFRAME, MAXFRAME / 2.0);
286         RNA_def_int(ot->srna, "end_frame", 250, MINAFRAME, MAXFRAME, "End",
287                     "Last frame to calculate bone paths on", MINFRAME, MAXFRAME / 2.0);
288
289         RNA_def_enum(ot->srna, "bake_location", rna_enum_motionpath_bake_location_items, 0,
290                      "Bake Location",
291                      "Which point on the bones is used when calculating paths");
292 }
293
294 /* --------- */
295
296 static int pose_update_paths_poll(bContext *C)
297 {
298         if (ED_operator_posemode_exclusive(C)) {
299                 Object *ob = CTX_data_active_object(C);
300                 return (ob->pose->avs.path_bakeflag & MOTIONPATH_BAKE_HAS_PATHS) != 0;
301         }
302
303         return false;
304 }
305
306 static int pose_update_paths_exec(bContext *C, wmOperator *UNUSED(op))
307 {
308         Object *ob = BKE_object_pose_armature_get(CTX_data_active_object(C));
309         Scene *scene = CTX_data_scene(C);
310
311         if (ELEM(NULL, ob, scene))
312                 return OPERATOR_CANCELLED;
313
314         /* calculate the bones that now have motionpaths... */
315         /* TODO: only make for the selected bones? */
316         ED_pose_recalculate_paths(C, scene, ob);
317
318         /* notifiers for updates */
319         WM_event_add_notifier(C, NC_OBJECT | ND_POSE, ob);
320
321         return OPERATOR_FINISHED;
322 }
323
324 void POSE_OT_paths_update(wmOperatorType *ot)
325 {
326         /* identifiers */
327         ot->name = "Update Bone Paths";
328         ot->idname = "POSE_OT_paths_update";
329         ot->description = "Recalculate paths for bones that already have them";
330
331         /* api callbakcs */
332         ot->exec = pose_update_paths_exec;
333         ot->poll = pose_update_paths_poll;
334
335         /* flags */
336         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
337 }
338
339 /* --------- */
340
341 /* for the object with pose/action: clear path curves for selected bones only */
342 static void ED_pose_clear_paths(Object *ob, bool only_selected)
343 {
344         bPoseChannel *pchan;
345         bool skipped = false;
346
347         if (ELEM(NULL, ob, ob->pose))
348                 return;
349
350         /* free the motionpath blocks for all bones - This is easier for users to quickly clear all */
351         for (pchan = ob->pose->chanbase.first; pchan; pchan = pchan->next) {
352                 if (pchan->mpath) {
353                         if ((only_selected == false) || ((pchan->bone) && (pchan->bone->flag & BONE_SELECTED))) {
354                                 animviz_free_motionpath(pchan->mpath);
355                                 pchan->mpath = NULL;
356                         }
357                         else {
358                                 skipped = true;
359                         }
360                 }
361         }
362
363         /* if nothing was skipped, there should be no paths left! */
364         if (skipped == false)
365                 ob->pose->avs.path_bakeflag &= ~MOTIONPATH_BAKE_HAS_PATHS;
366 }
367
368 /* operator callback - wrapper for the backend function  */
369 static int pose_clear_paths_exec(bContext *C, wmOperator *op)
370 {
371         Object *ob = BKE_object_pose_armature_get(CTX_data_active_object(C));
372         bool only_selected = RNA_boolean_get(op->ptr, "only_selected");
373
374         /* only continue if there's an object */
375         if (ELEM(NULL, ob, ob->pose))
376                 return OPERATOR_CANCELLED;
377
378         /* use the backend function for this */
379         ED_pose_clear_paths(ob, only_selected);
380
381         /* notifiers for updates */
382         WM_event_add_notifier(C, NC_OBJECT | ND_POSE, ob);
383
384         return OPERATOR_FINISHED;
385 }
386
387 /* operator callback/wrapper */
388 static int pose_clear_paths_invoke(bContext *C, wmOperator *op, const wmEvent *evt)
389 {
390         if ((evt->shift) && !RNA_struct_property_is_set(op->ptr, "only_selected")) {
391                 RNA_boolean_set(op->ptr, "only_selected", true);
392         }
393         return pose_clear_paths_exec(C, op);
394 }
395
396 void POSE_OT_paths_clear(wmOperatorType *ot)
397 {
398         /* identifiers */
399         ot->name = "Clear Bone Paths";
400         ot->idname = "POSE_OT_paths_clear";
401         ot->description = "Clear path caches for all bones, hold Shift key for selected bones only";
402
403         /* api callbacks */
404         ot->invoke = pose_clear_paths_invoke;
405         ot->exec = pose_clear_paths_exec;
406         ot->poll = ED_operator_posemode_exclusive;
407
408         /* flags */
409         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
410
411         /* properties */
412         ot->prop = RNA_def_boolean(ot->srna, "only_selected", false, "Only Selected",
413                                    "Only clear paths from selected bones");
414         RNA_def_property_flag(ot->prop, PROP_SKIP_SAVE);
415 }
416
417 /* ********************************************** */
418 #if 0 /* UNUSED 2.5 */
419 static void pose_copy_menu(Scene *scene)
420 {
421         Object *obedit = scene->obedit; // XXX context
422         Object *ob = OBACT;
423         bArmature *arm;
424         bPoseChannel *pchan, *pchanact;
425         short nr = 0;
426         int i = 0;
427
428         /* paranoia checks */
429         if (ELEM(NULL, ob, ob->pose)) return;
430         if ((ob == obedit) || (ob->mode & OB_MODE_POSE) == 0) return;
431
432         pchan = BKE_pose_channel_active(ob);
433
434         if (pchan == NULL) return;
435         pchanact = pchan;
436         arm = ob->data;
437
438         /* if proxy-protected bones selected, some things (such as locks + displays) shouldn't be changeable,
439          * but for constraints (just add local constraints)
440          */
441         if (pose_has_protected_selected(ob, 0)) {
442                 i = BLI_listbase_count(&(pchanact->constraints)); /* if there are 24 or less, allow for the user to select constraints */
443                 if (i < 25)
444                         nr = pupmenu("Copy Pose Attributes %t|Local Location %x1|Local Rotation %x2|Local Size %x3|%l|Visual Location %x9|Visual Rotation %x10|Visual Size %x11|%l|Constraints (All) %x4|Constraints... %x5");
445                 else
446                         nr = pupmenu("Copy Pose Attributes %t|Local Location %x1|Local Rotation %x2|Local Size %x3|%l|Visual Location %x9|Visual Rotation %x10|Visual Size %x11|%l|Constraints (All) %x4");
447         }
448         else {
449                 i = BLI_listbase_count(&(pchanact->constraints)); /* if there are 24 or less, allow for the user to select constraints */
450                 if (i < 25)
451                         nr = pupmenu("Copy Pose Attributes %t|Local Location %x1|Local Rotation %x2|Local Size %x3|%l|Visual Location %x9|Visual Rotation %x10|Visual Size %x11|%l|Constraints (All) %x4|Constraints... %x5|%l|Transform Locks %x6|IK Limits %x7|Bone Shape %x8");
452                 else
453                         nr = pupmenu("Copy Pose Attributes %t|Local Location %x1|Local Rotation %x2|Local Size %x3|%l|Visual Location %x9|Visual Rotation %x10|Visual Size %x11|%l|Constraints (All) %x4|%l|Transform Locks %x6|IK Limits %x7|Bone Shape %x8");
454         }
455
456         if (nr <= 0)
457                 return;
458
459         if (nr != 5) {
460                 for (pchan = ob->pose->chanbase.first; pchan; pchan = pchan->next) {
461                         if ((arm->layer & pchan->bone->layer) &&
462                             (pchan->bone->flag & BONE_SELECTED) &&
463                             (pchan != pchanact) )
464                         {
465                                 switch (nr) {
466                                         case 1: /* Local Location */
467                                                 copy_v3_v3(pchan->loc, pchanact->loc);
468                                                 break;
469                                         case 2: /* Local Rotation */
470                                                 copy_qt_qt(pchan->quat, pchanact->quat);
471                                                 copy_v3_v3(pchan->eul, pchanact->eul);
472                                                 break;
473                                         case 3: /* Local Size */
474                                                 copy_v3_v3(pchan->size, pchanact->size);
475                                                 break;
476                                         case 4: /* All Constraints */
477                                         {
478                                                 ListBase tmp_constraints = {NULL, NULL};
479
480                                                 /* copy constraints to tmpbase and apply 'local' tags before
481                                                  * appending to list of constraints for this channel
482                                                  */
483                                                 BKE_constraints_copy(&tmp_constraints, &pchanact->constraints, true);
484                                                 if ((ob->proxy) && (pchan->bone->layer & arm->layer_protected)) {
485                                                         bConstraint *con;
486
487                                                         /* add proxy-local tags */
488                                                         for (con = tmp_constraints.first; con; con = con->next)
489                                                                 con->flag |= CONSTRAINT_PROXY_LOCAL;
490                                                 }
491                                                 BLI_movelisttolist(&pchan->constraints, &tmp_constraints);
492
493                                                 /* update flags (need to add here, not just copy) */
494                                                 pchan->constflag |= pchanact->constflag;
495
496                                                 if (ob->pose)
497                                                         BKE_pose_tag_recalc(bmain, ob->pose);
498                                         }
499                                         break;
500                                         case 6: /* Transform Locks */
501                                                 pchan->protectflag = pchanact->protectflag;
502                                                 break;
503                                         case 7: /* IK (DOF) settings */
504                                         {
505                                                 pchan->ikflag = pchanact->ikflag;
506                                                 copy_v3_v3(pchan->limitmin, pchanact->limitmin);
507                                                 copy_v3_v3(pchan->limitmax, pchanact->limitmax);
508                                                 copy_v3_v3(pchan->stiffness, pchanact->stiffness);
509                                                 pchan->ikstretch = pchanact->ikstretch;
510                                                 pchan->ikrotweight = pchanact->ikrotweight;
511                                                 pchan->iklinweight = pchanact->iklinweight;
512                                         }
513                                         break;
514                                         case 8: /* Custom Bone Shape */
515                                                 pchan->custom = pchanact->custom;
516                                                 if (pchan->custom) {
517                                                         id_us_plus(&pchan->custom->id);
518                                                 }
519                                                 break;
520                                         case 9: /* Visual Location */
521                                                 BKE_armature_loc_pose_to_bone(pchan, pchanact->pose_mat[3], pchan->loc);
522                                                 break;
523                                         case 10: /* Visual Rotation */
524                                         {
525                                                 float delta_mat[4][4];
526
527                                                 BKE_armature_mat_pose_to_bone(pchan, pchanact->pose_mat, delta_mat);
528
529                                                 if (pchan->rotmode == ROT_MODE_AXISANGLE) {
530                                                         float tmp_quat[4];
531
532                                                         /* need to convert to quat first (in temp var)... */
533                                                         mat4_to_quat(tmp_quat, delta_mat);
534                                                         quat_to_axis_angle(pchan->rotAxis, &pchan->rotAngle, tmp_quat);
535                                                 }
536                                                 else if (pchan->rotmode == ROT_MODE_QUAT)
537                                                         mat4_to_quat(pchan->quat, delta_mat);
538                                                 else
539                                                         mat4_to_eulO(pchan->eul, pchan->rotmode, delta_mat);
540                                         }
541                                         break;
542                                         case 11: /* Visual Size */
543                                         {
544                                                 float delta_mat[4][4], size[4];
545
546                                                 BKE_armature_mat_pose_to_bone(pchan, pchanact->pose_mat, delta_mat);
547                                                 mat4_to_size(size, delta_mat);
548                                                 copy_v3_v3(pchan->size, size);
549                                         }
550                                 }
551                         }
552                 }
553         }
554         else { /* constraints, optional (note: max we can have is 24 constraints) */
555                 bConstraint *con, *con_back;
556                 int const_toggle[24] = {0}; /* XXX, initialize as 0 to quiet errors */
557                 ListBase const_copy = {NULL, NULL};
558
559                 BLI_duplicatelist(&const_copy, &(pchanact->constraints));
560
561                 /* build the puplist of constraints */
562                 for (con = pchanact->constraints.first, i = 0; con; con = con->next, i++) {
563                         const_toggle[i] = 1;
564 //                      add_numbut(i, UI_BTYPE_TOGGLE|INT, con->name, 0, 0, &(const_toggle[i]), "");
565                 }
566
567 //              if (!do_clever_numbuts("Select Constraints", i, REDRAW)) {
568 //                      BLI_freelistN(&const_copy);
569 //                      return;
570 //              }
571
572                 /* now build a new listbase from the options selected */
573                 for (i = 0, con = const_copy.first; con; i++) {
574                         /* if not selected, free/remove it from the list */
575                         if (!const_toggle[i]) {
576                                 con_back = con->next;
577                                 BLI_freelinkN(&const_copy, con);
578                                 con = con_back;
579                         }
580                         else
581                                 con = con->next;
582                 }
583
584                 /* Copy the temo listbase to the selected posebones */
585                 for (pchan = ob->pose->chanbase.first; pchan; pchan = pchan->next) {
586                         if ((arm->layer & pchan->bone->layer) &&
587                             (pchan->bone->flag & BONE_SELECTED) &&
588                             (pchan != pchanact) )
589                         {
590                                 ListBase tmp_constraints = {NULL, NULL};
591
592                                 /* copy constraints to tmpbase and apply 'local' tags before
593                                  * appending to list of constraints for this channel
594                                  */
595                                 BKE_constraints_copy(&tmp_constraints, &const_copy, true);
596                                 if ((ob->proxy) && (pchan->bone->layer & arm->layer_protected)) {
597                                         /* add proxy-local tags */
598                                         for (con = tmp_constraints.first; con; con = con->next)
599                                                 con->flag |= CONSTRAINT_PROXY_LOCAL;
600                                 }
601                                 BLI_movelisttolist(&pchan->constraints, &tmp_constraints);
602
603                                 /* update flags (need to add here, not just copy) */
604                                 pchan->constflag |= pchanact->constflag;
605                         }
606                 }
607                 BLI_freelistN(&const_copy);
608                 BKE_pose_update_constraint_flags(ob->pose); /* we could work out the flags but its simpler to do this */
609
610                 if (ob->pose)
611                         BKE_pose_tag_recalc(bmain, ob->pose);
612         }
613
614         DEG_id_tag_update(&ob->id, OB_RECALC_DATA); // and all its relations
615
616         BIF_undo_push("Copy Pose Attributes");
617
618 }
619 #endif
620
621 /* ********************************************** */
622
623 static int pose_flip_names_exec(bContext *C, wmOperator *op)
624 {
625         ViewLayer *view_layer = CTX_data_view_layer(C);
626         const bool do_strip_numbers = RNA_boolean_get(op->ptr, "do_strip_numbers");
627
628         FOREACH_OBJECT_IN_MODE_BEGIN (view_layer, OB_MODE_POSE, ob)
629         {
630                 bArmature *arm = ob->data;
631                 ListBase bones_names = {NULL};
632
633                 FOREACH_PCHAN_SELECTED_IN_OBJECT_BEGIN (ob, pchan)
634                 {
635                         BLI_addtail(&bones_names, BLI_genericNodeN(pchan->name));
636                 }
637                 FOREACH_PCHAN_SELECTED_IN_OBJECT_END;
638
639                 ED_armature_bones_flip_names(arm, &bones_names, do_strip_numbers);
640
641                 BLI_freelistN(&bones_names);
642
643                 /* since we renamed stuff... */
644                 DEG_id_tag_update(&ob->id, OB_RECALC_DATA);
645
646                 /* note, notifier might evolve */
647                 WM_event_add_notifier(C, NC_OBJECT | ND_POSE, ob);
648         }
649         FOREACH_OBJECT_IN_MODE_END;
650
651         return OPERATOR_FINISHED;
652 }
653
654 void POSE_OT_flip_names(wmOperatorType *ot)
655 {
656         /* identifiers */
657         ot->name = "Flip Names";
658         ot->idname = "POSE_OT_flip_names";
659         ot->description = "Flips (and corrects) the axis suffixes of the names of selected bones";
660
661         /* api callbacks */
662         ot->exec = pose_flip_names_exec;
663         ot->poll = ED_operator_posemode_local;
664
665         /* flags */
666         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
667
668         RNA_def_boolean(ot->srna, "do_strip_numbers", false, "Strip Numbers",
669                         "Try to remove right-most dot-number from flipped names "
670                         "(WARNING: may result in incoherent naming in some cases)");
671 }
672
673 /* ------------------ */
674
675 static int pose_autoside_names_exec(bContext *C, wmOperator *op)
676 {
677         Object *ob = BKE_object_pose_armature_get(CTX_data_active_object(C));
678         bArmature *arm;
679         char newname[MAXBONENAME];
680         short axis = RNA_enum_get(op->ptr, "axis");
681
682         /* paranoia checks */
683         if (ELEM(NULL, ob, ob->pose))
684                 return OPERATOR_CANCELLED;
685         arm = ob->data;
686
687         /* loop through selected bones, auto-naming them */
688         CTX_DATA_BEGIN (C, bPoseChannel *, pchan, selected_pose_bones)
689         {
690                 BLI_strncpy(newname, pchan->name, sizeof(newname));
691                 if (bone_autoside_name(newname, 1, axis, pchan->bone->head[axis], pchan->bone->tail[axis]))
692                         ED_armature_bone_rename(arm, pchan->name, newname);
693         }
694         CTX_DATA_END;
695
696         /* since we renamed stuff... */
697         DEG_id_tag_update(&ob->id, OB_RECALC_DATA);
698
699         /* note, notifier might evolve */
700         WM_event_add_notifier(C, NC_OBJECT | ND_POSE, ob);
701
702         return OPERATOR_FINISHED;
703 }
704
705 void POSE_OT_autoside_names(wmOperatorType *ot)
706 {
707         static const EnumPropertyItem axis_items[] = {
708                 {0, "XAXIS", 0, "X-Axis", "Left/Right"},
709                 {1, "YAXIS", 0, "Y-Axis", "Front/Back"},
710                 {2, "ZAXIS", 0, "Z-Axis", "Top/Bottom"},
711                 {0, NULL, 0, NULL, NULL}
712         };
713
714         /* identifiers */
715         ot->name = "AutoName by Axis";
716         ot->idname = "POSE_OT_autoside_names";
717         ot->description = "Automatically renames the selected bones according to which side of the target axis they fall on";
718
719         /* api callbacks */
720         ot->invoke = WM_menu_invoke;
721         ot->exec = pose_autoside_names_exec;
722         ot->poll = ED_operator_posemode;
723
724         /* flags */
725         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
726
727         /* settings */
728         ot->prop = RNA_def_enum(ot->srna, "axis", axis_items, 0, "Axis", "Axis tag names with");
729 }
730
731 /* ********************************************** */
732
733 static int pose_bone_rotmode_exec(bContext *C, wmOperator *op)
734 {
735         Object *ob = CTX_data_active_object(C);
736         int mode = RNA_enum_get(op->ptr, "type");
737
738         /* set rotation mode of selected bones  */
739         CTX_DATA_BEGIN (C, bPoseChannel *, pchan, selected_pose_bones)
740         {
741                 pchan->rotmode = mode;
742         }
743         CTX_DATA_END;
744
745         /* notifiers and updates */
746         DEG_id_tag_update((ID *)ob, OB_RECALC_DATA);
747         WM_event_add_notifier(C, NC_OBJECT | ND_TRANSFORM, ob);
748
749         return OPERATOR_FINISHED;
750 }
751
752 void POSE_OT_rotation_mode_set(wmOperatorType *ot)
753 {
754         /* identifiers */
755         ot->name = "Set Rotation Mode";
756         ot->idname = "POSE_OT_rotation_mode_set";
757         ot->description = "Set the rotation representation used by selected bones";
758
759         /* callbacks */
760         ot->invoke = WM_menu_invoke;
761         ot->exec = pose_bone_rotmode_exec;
762         ot->poll = ED_operator_posemode;
763
764         /* flags */
765         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
766
767         /* properties */
768         ot->prop = RNA_def_enum(ot->srna, "type", rna_enum_posebone_rotmode_items, 0, "Rotation Mode", "");
769 }
770
771 /* ********************************************** */
772
773 static int armature_layers_poll(bContext *C)
774 {
775         /* Armature layers operators can be used in posemode OR editmode for armatures */
776         return ED_operator_posemode(C) || ED_operator_editarmature(C);
777 }
778
779 static bArmature *armature_layers_get_data(Object **ob)
780 {
781         bArmature *arm = NULL;
782
783         /* Sanity checking and handling of posemode. */
784         if (*ob) {
785                 Object *tob = BKE_object_pose_armature_get(*ob);
786                 if (tob) {
787                         *ob = tob;
788                         arm = (*ob)->data;
789                 }
790                 else if ((*ob)->type == OB_ARMATURE) {
791                         arm = (*ob)->data;
792                 }
793         }
794
795         return arm;
796 }
797
798 /* Show all armature layers */
799
800 static int pose_armature_layers_showall_exec(bContext *C, wmOperator *op)
801 {
802         Object *ob = CTX_data_active_object(C);
803         bArmature *arm = armature_layers_get_data(&ob);
804         PointerRNA ptr;
805         int maxLayers = (RNA_boolean_get(op->ptr, "all")) ? 32 : 16;
806         int layers[32] = {0}; /* hardcoded for now - we can only have 32 armature layers, so this should be fine... */
807         int i;
808
809         /* sanity checking */
810         if (arm == NULL)
811                 return OPERATOR_CANCELLED;
812
813         /* use RNA to set the layers
814          *  although it would be faster to just set directly using bitflags, we still
815          *      need to setup a RNA pointer so that we get the "update" callbacks for free...
816          */
817         RNA_id_pointer_create(&arm->id, &ptr);
818
819         for (i = 0; i < maxLayers; i++)
820                 layers[i] = 1;
821
822         RNA_boolean_set_array(&ptr, "layers", layers);
823
824         /* note, notifier might evolve */
825         WM_event_add_notifier(C, NC_OBJECT | ND_POSE, ob);
826         DEG_id_tag_update(&arm->id, DEG_TAG_COPY_ON_WRITE);
827
828         /* done */
829         return OPERATOR_FINISHED;
830 }
831
832 void ARMATURE_OT_layers_show_all(wmOperatorType *ot)
833 {
834         /* identifiers */
835         ot->name = "Show All Layers";
836         ot->idname = "ARMATURE_OT_layers_show_all";
837         ot->description = "Make all armature layers visible";
838
839         /* callbacks */
840         ot->exec = pose_armature_layers_showall_exec;
841         ot->poll = armature_layers_poll;
842
843         /* flags */
844         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
845
846         /* properties */
847         ot->prop = RNA_def_boolean(ot->srna, "all", 1, "All Layers", "Enable all layers or just the first 16 (top row)");
848 }
849
850 /* ------------------- */
851
852 /* Present a popup to get the layers that should be used */
853 static int armature_layers_invoke(bContext *C, wmOperator *op, const wmEvent *event)
854 {
855         Object *ob = CTX_data_active_object(C);
856         bArmature *arm = armature_layers_get_data(&ob);
857         PointerRNA ptr;
858         int layers[32]; /* hardcoded for now - we can only have 32 armature layers, so this should be fine... */
859
860         /* sanity checking */
861         if (arm == NULL)
862                 return OPERATOR_CANCELLED;
863
864         /* get RNA pointer to armature data to use that to retrieve the layers as ints to init the operator */
865         RNA_id_pointer_create((ID *)arm, &ptr);
866         RNA_boolean_get_array(&ptr, "layers", layers);
867         RNA_boolean_set_array(op->ptr, "layers", layers);
868
869         /* part to sync with other similar operators... */
870         return WM_operator_props_popup(C, op, event);
871 }
872
873 /* Set the visible layers for the active armature (edit and pose modes) */
874 static int armature_layers_exec(bContext *C, wmOperator *op)
875 {
876         Object *ob = CTX_data_active_object(C);
877         bArmature *arm = armature_layers_get_data(&ob);
878         PointerRNA ptr;
879         int layers[32]; /* hardcoded for now - we can only have 32 armature layers, so this should be fine... */
880
881         if (arm == NULL) {
882                 return OPERATOR_CANCELLED;
883         }
884
885         /* get the values set in the operator properties */
886         RNA_boolean_get_array(op->ptr, "layers", layers);
887
888         /* get pointer for armature, and write data there... */
889         RNA_id_pointer_create((ID *)arm, &ptr);
890         RNA_boolean_set_array(&ptr, "layers", layers);
891
892         /* note, notifier might evolve */
893         WM_event_add_notifier(C, NC_OBJECT | ND_POSE, ob);
894         DEG_id_tag_update(&arm->id, DEG_TAG_COPY_ON_WRITE);
895
896         return OPERATOR_FINISHED;
897 }
898
899 void ARMATURE_OT_armature_layers(wmOperatorType *ot)
900 {
901         /* identifiers */
902         ot->name = "Change Armature Layers";
903         ot->idname = "ARMATURE_OT_armature_layers";
904         ot->description = "Change the visible armature layers";
905
906         /* callbacks */
907         ot->invoke = armature_layers_invoke;
908         ot->exec = armature_layers_exec;
909         ot->poll = armature_layers_poll;
910
911         /* flags */
912         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
913
914         /* properties */
915         RNA_def_boolean_layer_member(ot->srna, "layers", 32, NULL, "Layer", "Armature layers to make visible");
916 }
917
918 /* ------------------- */
919
920 /* Present a popup to get the layers that should be used */
921 static int pose_bone_layers_invoke(bContext *C, wmOperator *op, const wmEvent *event)
922 {
923         int layers[32] = {0}; /* hardcoded for now - we can only have 32 armature layers, so this should be fine... */
924
925         /* get layers that are active already */
926         CTX_DATA_BEGIN (C, bPoseChannel *, pchan, selected_pose_bones)
927         {
928                 short bit;
929
930                 /* loop over the bits for this pchan's layers, adding layers where they're needed */
931                 for (bit = 0; bit < 32; bit++) {
932                         layers[bit] = (pchan->bone->layer & (1u << bit)) != 0;
933                 }
934         }
935         CTX_DATA_END;
936
937         /* copy layers to operator */
938         RNA_boolean_set_array(op->ptr, "layers", layers);
939
940         /* part to sync with other similar operators... */
941         return WM_operator_props_popup(C, op, event);
942 }
943
944 /* Set the visible layers for the active armature (edit and pose modes) */
945 static int pose_bone_layers_exec(bContext *C, wmOperator *op)
946 {
947         Object *ob = BKE_object_pose_armature_get(CTX_data_active_object(C));
948         PointerRNA ptr;
949         int layers[32]; /* hardcoded for now - we can only have 32 armature layers, so this should be fine... */
950
951         if (ob == NULL || ob->data == NULL) {
952                 return OPERATOR_CANCELLED;
953         }
954
955         /* get the values set in the operator properties */
956         RNA_boolean_get_array(op->ptr, "layers", layers);
957
958         /* set layers of pchans based on the values set in the operator props */
959         CTX_DATA_BEGIN (C, bPoseChannel *, pchan, selected_pose_bones)
960         {
961                 /* get pointer for pchan, and write flags this way */
962                 RNA_pointer_create((ID *)ob->data, &RNA_Bone, pchan->bone, &ptr);
963                 RNA_boolean_set_array(&ptr, "layers", layers);
964         }
965         CTX_DATA_END;
966
967         /* note, notifier might evolve */
968         WM_event_add_notifier(C, NC_OBJECT | ND_POSE, ob);
969         DEG_id_tag_update((ID *)ob->data, DEG_TAG_COPY_ON_WRITE);
970
971         return OPERATOR_FINISHED;
972 }
973
974 void POSE_OT_bone_layers(wmOperatorType *ot)
975 {
976         /* identifiers */
977         ot->name = "Change Bone Layers";
978         ot->idname = "POSE_OT_bone_layers";
979         ot->description = "Change the layers that the selected bones belong to";
980
981         /* callbacks */
982         ot->invoke = pose_bone_layers_invoke;
983         ot->exec = pose_bone_layers_exec;
984         ot->poll = ED_operator_posemode_exclusive;
985
986         /* flags */
987         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
988
989         /* properties */
990         RNA_def_boolean_layer_member(ot->srna, "layers", 32, NULL, "Layer", "Armature layers that bone belongs to");
991 }
992
993 /* ------------------- */
994
995 /* Present a popup to get the layers that should be used */
996 static int armature_bone_layers_invoke(bContext *C, wmOperator *op, const wmEvent *event)
997 {
998         int layers[32] = {0}; /* hardcoded for now - we can only have 32 armature layers, so this should be fine... */
999
1000         /* get layers that are active already */
1001         CTX_DATA_BEGIN (C, EditBone *, ebone, selected_editable_bones)
1002         {
1003                 short bit;
1004
1005                 /* loop over the bits for this pchan's layers, adding layers where they're needed */
1006                 for (bit = 0; bit < 32; bit++) {
1007                         if (ebone->layer & (1u << bit)) {
1008                                 layers[bit] = 1;
1009                         }
1010                 }
1011         }
1012         CTX_DATA_END;
1013
1014         /* copy layers to operator */
1015         RNA_boolean_set_array(op->ptr, "layers", layers);
1016
1017         /* part to sync with other similar operators... */
1018         return WM_operator_props_popup(C, op, event);
1019 }
1020
1021 /* Set the visible layers for the active armature (edit and pose modes) */
1022 static int armature_bone_layers_exec(bContext *C, wmOperator *op)
1023 {
1024         Object *ob = CTX_data_edit_object(C);
1025         PointerRNA ptr;
1026         int layers[32]; /* hardcoded for now - we can only have 32 armature layers, so this should be fine... */
1027
1028         /* get the values set in the operator properties */
1029         RNA_boolean_get_array(op->ptr, "layers", layers);
1030
1031         /* set layers of pchans based on the values set in the operator props */
1032         CTX_DATA_BEGIN_WITH_ID (C, EditBone *, ebone, selected_editable_bones, bArmature *, arm)
1033         {
1034                 /* get pointer for pchan, and write flags this way */
1035                 RNA_pointer_create((ID *)arm, &RNA_EditBone, ebone, &ptr);
1036                 RNA_boolean_set_array(&ptr, "layers", layers);
1037         }
1038         CTX_DATA_END;
1039
1040         /* note, notifier might evolve */
1041         WM_event_add_notifier(C, NC_OBJECT | ND_POSE, ob);
1042
1043         return OPERATOR_FINISHED;
1044 }
1045
1046 void ARMATURE_OT_bone_layers(wmOperatorType *ot)
1047 {
1048         /* identifiers */
1049         ot->name = "Change Bone Layers";
1050         ot->idname = "ARMATURE_OT_bone_layers";
1051         ot->description = "Change the layers that the selected bones belong to";
1052
1053         /* callbacks */
1054         ot->invoke = armature_bone_layers_invoke;
1055         ot->exec = armature_bone_layers_exec;
1056         ot->poll = ED_operator_editarmature;
1057
1058         /* flags */
1059         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1060
1061         /* properties */
1062         RNA_def_boolean_layer_member(ot->srna, "layers", 32, NULL, "Layer", "Armature layers that bone belongs to");
1063 }
1064
1065 /* ********************************************** */
1066 /* Show/Hide Bones */
1067
1068 static int hide_pose_bone_fn(Object *ob, Bone *bone, void *ptr)
1069 {
1070         bArmature *arm = ob->data;
1071         const bool hide_select = (bool)GET_INT_FROM_POINTER(ptr);
1072         int count = 0;
1073         if (arm->layer & bone->layer) {
1074                 if (((bone->flag & BONE_SELECTED) != 0) == hide_select) {
1075                         bone->flag |= BONE_HIDDEN_P;
1076                         /* only needed when 'hide_select' is true, but harmless. */
1077                         bone->flag &= ~BONE_SELECTED;
1078                         if (arm->act_bone == bone) {
1079                                 arm->act_bone = NULL;
1080                         }
1081                         count += 1;
1082                 }
1083         }
1084         return count;
1085 }
1086
1087 /* active object is armature in posemode, poll checked */
1088 static int pose_hide_exec(bContext *C, wmOperator *op)
1089 {
1090         ViewLayer *view_layer = CTX_data_view_layer(C);
1091         uint objects_len;
1092         Object **objects = BKE_object_pose_array_get_unique(view_layer, &objects_len);
1093         bool changed_multi = false;
1094
1095         const int hide_select = !RNA_boolean_get(op->ptr, "unselected");
1096         void     *hide_select_p = SET_INT_IN_POINTER(hide_select);
1097
1098         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1099                 Object *ob_iter = objects[ob_index];
1100                 bArmature *arm = ob_iter->data;
1101
1102                 if (ob_iter->proxy != NULL) {
1103                         BKE_report(op->reports, RPT_INFO, "Undo of hiding can only be done with Reveal Selected");
1104                 }
1105
1106                 bool changed = bone_looper(ob_iter, arm->bonebase.first, hide_select_p, hide_pose_bone_fn) != 0;
1107                 if (changed) {
1108                         changed_multi = true;
1109                         WM_event_add_notifier(C, NC_OBJECT | ND_BONE_SELECT, ob_iter);
1110                         DEG_id_tag_update(&arm->id, DEG_TAG_COPY_ON_WRITE);
1111                 }
1112         }
1113         MEM_freeN(objects);
1114
1115         return changed_multi ? OPERATOR_FINISHED : OPERATOR_CANCELLED;
1116 }
1117
1118 void POSE_OT_hide(wmOperatorType *ot)
1119 {
1120         /* identifiers */
1121         ot->name = "Hide Selected";
1122         ot->idname = "POSE_OT_hide";
1123         ot->description = "Tag selected bones to not be visible in Pose Mode";
1124
1125         /* api callbacks */
1126         ot->exec = pose_hide_exec;
1127         ot->poll = ED_operator_posemode;
1128
1129         /* flags */
1130         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1131
1132         /* props */
1133         RNA_def_boolean(ot->srna, "unselected", 0, "Unselected", "");
1134 }
1135
1136 static int show_pose_bone_cb(Object *ob, Bone *bone, void *data)
1137 {
1138         const bool select = GET_INT_FROM_POINTER(data);
1139
1140         bArmature *arm = ob->data;
1141         int count = 0;
1142         if (arm->layer & bone->layer) {
1143                 if (bone->flag & BONE_HIDDEN_P) {
1144                         if (!(bone->flag & BONE_UNSELECTABLE)) {
1145                                 SET_FLAG_FROM_TEST(bone->flag, select, BONE_SELECTED);
1146                         }
1147                         bone->flag &= ~BONE_HIDDEN_P;
1148                         count += 1;
1149                 }
1150         }
1151
1152         return count;
1153 }
1154
1155 /* active object is armature in posemode, poll checked */
1156 static int pose_reveal_exec(bContext *C, wmOperator *op)
1157 {
1158         ViewLayer *view_layer = CTX_data_view_layer(C);
1159         uint objects_len;
1160         Object **objects = BKE_object_pose_array_get_unique(view_layer, &objects_len);
1161         bool changed_multi = false;
1162         const bool select = RNA_boolean_get(op->ptr, "select");
1163         void *select_p = SET_INT_IN_POINTER(select);
1164
1165         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1166                 Object *ob_iter = objects[ob_index];
1167                 bArmature *arm = ob_iter->data;
1168
1169                 bool changed = bone_looper(ob_iter, arm->bonebase.first, select_p, show_pose_bone_cb);
1170                 if (changed) {
1171                         changed_multi = true;
1172                         WM_event_add_notifier(C, NC_OBJECT | ND_BONE_SELECT, ob_iter);
1173                         DEG_id_tag_update(&arm->id, DEG_TAG_COPY_ON_WRITE);
1174                 }
1175         }
1176         MEM_freeN(objects);
1177
1178         return changed_multi ? OPERATOR_FINISHED : OPERATOR_CANCELLED;
1179 }
1180
1181 void POSE_OT_reveal(wmOperatorType *ot)
1182 {
1183         /* identifiers */
1184         ot->name = "Reveal Selected";
1185         ot->idname = "POSE_OT_reveal";
1186         ot->description = "Reveal all bones hidden in Pose Mode";
1187
1188         /* api callbacks */
1189         ot->exec = pose_reveal_exec;
1190         ot->poll = ED_operator_posemode;
1191
1192         /* flags */
1193         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1194
1195         RNA_def_boolean(ot->srna, "select", true, "Select", "");
1196 }
1197
1198 /* ********************************************** */
1199 /* Flip Quats */
1200
1201 static int pose_flip_quats_exec(bContext *C, wmOperator *UNUSED(op))
1202 {
1203         Scene *scene = CTX_data_scene(C);
1204         KeyingSet *ks = ANIM_builtin_keyingset_get_named(NULL, ANIM_KS_LOC_ROT_SCALE_ID);
1205
1206         bool changed_multi = false;
1207
1208         ViewLayer *view_layer = CTX_data_view_layer(C);
1209         FOREACH_OBJECT_IN_MODE_BEGIN (view_layer, OB_MODE_POSE, ob_iter) {
1210                 bool changed = false;
1211                 /* loop through all selected pchans, flipping and keying (as needed) */
1212                 FOREACH_PCHAN_SELECTED_IN_OBJECT_BEGIN (ob_iter, pchan) {
1213                         /* only if bone is using quaternion rotation */
1214                         if (pchan->rotmode == ROT_MODE_QUAT) {
1215                                 changed = true;
1216                                 /* quaternions have 720 degree range */
1217                                 negate_v4(pchan->quat);
1218
1219                                 ED_autokeyframe_pchan(C, scene, ob_iter, pchan, ks);
1220                         }
1221                 } FOREACH_PCHAN_SELECTED_IN_OBJECT_END;
1222
1223                 if (changed) {
1224                         changed_multi = true;
1225                         /* notifiers and updates */
1226                         DEG_id_tag_update(&ob_iter->id, OB_RECALC_DATA);
1227                         WM_event_add_notifier(C, NC_OBJECT | ND_TRANSFORM, ob_iter);
1228                 }
1229         } FOREACH_OBJECT_IN_MODE_END;
1230
1231         return changed_multi ? OPERATOR_FINISHED : OPERATOR_CANCELLED;
1232 }
1233
1234 void POSE_OT_quaternions_flip(wmOperatorType *ot)
1235 {
1236         /* identifiers */
1237         ot->name = "Flip Quats";
1238         ot->idname = "POSE_OT_quaternions_flip";
1239         ot->description = "Flip quaternion values to achieve desired rotations, while maintaining the same orientations";
1240
1241         /* callbacks */
1242         ot->exec = pose_flip_quats_exec;
1243         ot->poll = ED_operator_posemode;
1244
1245         /* flags */
1246         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1247 }
1248
1249 /* -------------------------------------------------------------------- */
1250 /** \name Toggle Bone selection Overlay Operator
1251  * \{ */
1252
1253 static int toggle_bone_selection_exec(bContext *C, wmOperator *UNUSED(op))
1254 {
1255         View3D *v3d = CTX_wm_view3d(C);
1256         v3d->overlay.flag ^= V3D_OVERLAY_BONE_SELECTION;
1257         ED_view3d_shade_update(CTX_data_main(C), v3d, CTX_wm_area(C));
1258         WM_event_add_notifier(C, NC_SPACE | ND_SPACE_VIEW3D, v3d);
1259         return OPERATOR_FINISHED;
1260 }
1261
1262 static int pose_select_linked_poll(bContext *C)
1263 {
1264         return (ED_operator_view3d_active(C) && ED_operator_posemode(C));
1265 }
1266
1267 void POSE_OT_toggle_bone_selection_overlay(wmOperatorType *ot)
1268 {
1269         /* identifiers */
1270         ot->name = "Toggle Bone Selection Overlay";
1271         ot->description = "Toggle bone selection overlay of the viewport";
1272         ot->idname = "POSE_OT_toggle_bone_selection_overlay";
1273
1274         /* api callbacks */
1275         ot->exec = toggle_bone_selection_exec;
1276         ot->poll = pose_select_linked_poll;
1277 }
1278
1279 /** \} */