4 * ***** BEGIN GPL LICENSE BLOCK *****
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License
8 * as published by the Free Software Foundation; either version 2
9 * of the License, or (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software Foundation,
18 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
20 * The Original Code is Copyright (C) 2009 Blender Foundation.
21 * All rights reserved.
24 * Contributor(s): Blender Foundation
26 * ***** END GPL LICENSE BLOCK *****
34 #include "DNA_armature_types.h"
35 #include "DNA_curve_types.h"
36 #include "DNA_lattice_types.h"
37 #include "DNA_meta_types.h"
38 #include "DNA_meshdata_types.h"
39 #include "DNA_object_types.h"
40 #include "DNA_scene_types.h"
42 #include "MEM_guardedalloc.h"
45 #include "BLI_blenlib.h"
46 #include "BLI_editVert.h"
49 #include "BKE_action.h"
50 #include "BKE_context.h"
51 #include "BKE_curve.h"
52 #include "BKE_customdata.h"
53 #include "BKE_depsgraph.h"
56 #include "BKE_screen.h"
57 #include "BKE_deform.h"
63 #include "RNA_access.h"
65 #include "ED_armature.h"
66 #include "ED_gpencil.h"
68 #include "ED_screen.h"
69 #include "ED_transform.h"
72 #include "UI_interface.h"
73 #include "UI_resources.h"
75 #include "view3d_intern.h" // own include
78 /* ******************* view3d space & buttons ************** */
81 #define B_OBJECTPANELROT 1007
82 #define B_OBJECTPANELMEDIAN 1008
83 #define B_ARMATUREPANEL1 1009
84 #define B_ARMATUREPANEL2 1010
85 #define B_OBJECTPANELPARENT 1011
86 #define B_OBJECTPANEL 1012
87 #define B_ARMATUREPANEL3 1013
88 #define B_OBJECTPANELSCALE 1014
89 #define B_OBJECTPANELDIMS 1015
90 #define B_TRANSFORMSPACEADD 1016
91 #define B_TRANSFORMSPACECLEAR 1017
92 #define B_SETPT_AUTO 2125
93 #define B_SETPT_VECTOR 2126
94 #define B_SETPT_ALIGN 2127
95 #define B_SETPT_FREE 2128
96 #define B_RECALCMBALL 2501
98 #define B_WEIGHT0_0 2840
99 #define B_WEIGHT1_4 2841
100 #define B_WEIGHT1_2 2842
101 #define B_WEIGHT3_4 2843
102 #define B_WEIGHT1_0 2844
104 #define B_OPA1_8 2845
105 #define B_OPA1_4 2846
106 #define B_OPA1_2 2847
107 #define B_OPA3_4 2848
108 #define B_OPA1_0 2849
110 #define B_CLR_WPAINT 2850
112 #define B_RV3D_LOCKED 2900
113 #define B_RV3D_BOXVIEW 2901
114 #define B_RV3D_BOXCLIP 2902
116 #define B_IDNAME 3000
118 /* temporary struct for storing transform properties */
120 float ob_eul[4]; // used for quat too....
121 float ob_scale[3]; // need temp space due to linked values
127 } TransformProperties;
130 /* is used for both read and write... */
131 static void v3d_editvertex_buts(uiLayout *layout, View3D *v3d, Object *ob, float lim)
133 uiBlock *block= (layout)? uiLayoutAbsoluteBlock(layout): NULL;
134 MDeformVert *dvert=NULL;
135 TransformProperties *tfp= v3d->properties_storage;
136 float median[6], ve_median[6];
137 int tot, totw, totweight, totedge, totradius;
140 median[0]= median[1]= median[2]= median[3]= median[4]= median[5]= 0.0;
141 tot= totw= totweight= totedge= totradius= 0;
144 if(ob->type==OB_MESH) {
146 EditMesh *em = BKE_mesh_get_editmesh(me);
147 EditVert *eve, *evedef=NULL;
150 eve= em->verts.first;
152 if(eve->f & SELECT) {
155 add_v3_v3(median, eve->co);
159 eed= em->edges.first;
161 if((eed->f & SELECT)) {
163 median[3]+= eed->crease;
168 /* check for defgroups */
170 dvert= CustomData_em_get(&em->vdata, evedef->data, CD_MDEFORMVERT);
171 if(tot==1 && dvert && dvert->totweight) {
173 int i, max=1, init=1;
176 for (i=0; i<dvert->totweight; i++){
177 dg = BLI_findlink (&ob->defbase, dvert->dw[i].def_nr);
179 max+= BLI_snprintf(str, sizeof(str), "%s %%x%d|", dg->name, dvert->dw[i].def_nr);
180 if(max<320) strcat(defstr, str);
183 if(tfp->curdef==dvert->dw[i].def_nr) {
185 tfp->defweightp= &dvert->dw[i].weight;
189 if(init) { // needs new initialized
190 tfp->curdef= dvert->dw[0].def_nr;
191 tfp->defweightp= &dvert->dw[0].weight;
195 BKE_mesh_end_editmesh(me, em);
197 else if(ob->type==OB_CURVE || ob->type==OB_SURF) {
203 ListBase *nurbs= ED_curve_editnurbs(cu);
207 if(nu->type == CU_BEZIER) {
211 if(bezt->f2 & SELECT) {
212 add_v3_v3(median, bezt->vec[1]);
214 median[4]+= bezt->weight;
216 median[5]+= bezt->radius;
220 if(bezt->f1 & SELECT) {
221 add_v3_v3(median, bezt->vec[0]);
224 if(bezt->f3 & SELECT) {
225 add_v3_v3(median, bezt->vec[2]);
234 a= nu->pntsu*nu->pntsv;
236 if(bp->f1 & SELECT) {
237 add_v3_v3(median, bp->vec);
238 median[3]+= bp->vec[3];
241 median[4]+= bp->weight;
243 median[5]+= bp->radius;
252 else if(ob->type==OB_LATTICE) {
253 Lattice *lt= ob->data;
257 a= lt->editlatt->latt->pntsu*lt->editlatt->latt->pntsv*lt->editlatt->latt->pntsw;
258 bp= lt->editlatt->latt->def;
260 if(bp->f1 & SELECT) {
261 add_v3_v3(median, bp->vec);
263 median[4]+= bp->weight;
272 median[0] /= (float)tot;
273 median[1] /= (float)tot;
274 median[2] /= (float)tot;
275 if(totedge) median[3] /= (float)totedge;
276 else if(totw) median[3] /= (float)totw;
277 if(totweight) median[4] /= (float)totweight;
278 if(totradius) median[5] /= (float)totradius;
280 if(v3d->flag & V3D_GLOBAL_STATS)
281 mul_m4_v3(ob->obmat, median);
283 if(block) { // buttons
286 if((ob->parent) && (ob->partype == PARBONE)) but_y = 135;
291 memcpy(tfp->ve_median, median, sizeof(tfp->ve_median));
293 uiBlockBeginAlign(block);
295 uiDefBut(block, LABEL, 0, "Vertex:", 0, 130, 200, 20, 0, 0, 0, 0, 0, "");
296 uiBlockBeginAlign(block);
298 but= uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "X:", 0, 110, 200, 20, &(tfp->ve_median[0]), -lim, lim, 10, 3, "");
299 uiButSetUnitType(but, PROP_UNIT_LENGTH);
300 but= uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Y:", 0, 90, 200, 20, &(tfp->ve_median[1]), -lim, lim, 10, 3, "");
301 uiButSetUnitType(but, PROP_UNIT_LENGTH);
302 but= uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Z:", 0, 70, 200, 20, &(tfp->ve_median[2]), -lim, lim, 10, 3, "");
303 uiButSetUnitType(but, PROP_UNIT_LENGTH);
306 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "W:", 0, 50, 200, 20, &(tfp->ve_median[3]), 0.01, 100.0, 10, 3, "");
307 uiBlockBeginAlign(block);
308 uiDefButBitS(block, TOG, V3D_GLOBAL_STATS, B_REDR, "Global", 0, 25, 100, 20, &v3d->flag, 0, 0, 0, 0, "Displays global values");
309 uiDefButBitS(block, TOGN, V3D_GLOBAL_STATS, B_REDR, "Local", 100, 25, 100, 20, &v3d->flag, 0, 0, 0, 0, "Displays local values");
310 uiBlockEndAlign(block);
312 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Weight:", 0, 0, 200, 20, &(tfp->ve_median[4]), 0.0, 1.0, 10, 3, "");
314 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Radius:", 0, 0, 200, 20, &(tfp->ve_median[5]), 0.0, 100.0, 10, 3, "Radius of curve CPs");
317 uiBlockBeginAlign(block);
318 uiDefButBitS(block, TOG, V3D_GLOBAL_STATS, B_REDR, "Global", 0, 45, 100, 20, &v3d->flag, 0, 0, 0, 0, "Displays global values");
319 uiDefButBitS(block, TOGN, V3D_GLOBAL_STATS, B_REDR, "Local", 100, 45, 100, 20, &v3d->flag, 0, 0, 0, 0, "Displays local values");
320 uiBlockEndAlign(block);
322 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Weight:", 0, 20, 200, 20, &(tfp->ve_median[4]), 0.0, 1.0, 10, 3, "");
324 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Radius:", 0, 20, 200, 20, &(tfp->ve_median[5]), 0.0, 100.0, 10, 3, "Radius of curve CPs");
328 uiDefBut(block, LABEL, 0, "Median:", 0, 130, 200, 20, 0, 0, 0, 0, 0, "");
329 uiBlockBeginAlign(block);
330 but= uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "X:", 0, 110, 200, 20, &(tfp->ve_median[0]), -lim, lim, 10, 3, "");
331 uiButSetUnitType(but, PROP_UNIT_LENGTH);
332 but= uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Y:", 0, 90, 200, 20, &(tfp->ve_median[1]), -lim, lim, 10, 3, "");
333 uiButSetUnitType(but, PROP_UNIT_LENGTH);
334 but= uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Z:", 0, 70, 200, 20, &(tfp->ve_median[2]), -lim, lim, 10, 3, "");
335 uiButSetUnitType(but, PROP_UNIT_LENGTH);
337 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "W:", 0, 50, 200, 20, &(tfp->ve_median[3]), 0.01, 100.0, 10, 3, "");
338 uiBlockEndAlign(block);
339 uiBlockBeginAlign(block);
340 uiDefButBitS(block, TOG, V3D_GLOBAL_STATS, B_REDR, "Global", 0, 25, 100, 20, &v3d->flag, 0, 0, 0, 0, "Displays global values");
341 uiDefButBitS(block, TOGN, V3D_GLOBAL_STATS, B_REDR, "Local", 100, 25, 100, 20, &v3d->flag, 0, 0, 0, 0, "Displays local values");
342 uiBlockEndAlign(block);
344 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Weight:", 0, 0, 200, 20, &(tfp->ve_median[4]), 0.0, 1.0, 10, 3, "Weight is used for SoftBody Goal");
346 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Radius:", 0, 0, 200, 20, &(tfp->ve_median[5]), 0.0, 100.0, 10, 3, "Radius of curve CPs");
347 uiBlockEndAlign(block);
350 uiBlockBeginAlign(block);
351 uiDefButBitS(block, TOG, V3D_GLOBAL_STATS, B_REDR, "Global", 0, 45, 100, 20, &v3d->flag, 0, 0, 0, 0, "Displays global values");
352 uiDefButBitS(block, TOGN, V3D_GLOBAL_STATS, B_REDR, "Local", 100, 45, 100, 20, &v3d->flag, 0, 0, 0, 0, "Displays local values");
353 uiBlockEndAlign(block);
355 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Weight:", 0, 20, 200, 20, &(tfp->ve_median[4]), 0.0, 1.0, 10, 3, "Weight is used for SoftBody Goal");
357 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Radius:", 0, 0, 200, 20, &(tfp->ve_median[5]), 0.0, 100.0, 10, 3, "Radius of curve CPs");
358 uiBlockEndAlign(block);
363 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Crease:", 0, 20, 200, 20, &(tfp->ve_median[3]), 0.0, 1.0, 10, 3, "");
365 uiDefButF(block, NUM, B_OBJECTPANELMEDIAN, "Mean Crease:", 0, 20, 200, 20, &(tfp->ve_median[3]), 0.0, 1.0, 10, 3, "");
369 memcpy(ve_median, tfp->ve_median, sizeof(tfp->ve_median));
371 if(v3d->flag & V3D_GLOBAL_STATS) {
372 invert_m4_m4(ob->imat, ob->obmat);
373 mul_m4_v3(ob->imat, median);
374 mul_m4_v3(ob->imat, ve_median);
376 sub_v3_v3v3(median, ve_median, median);
377 median[3]= ve_median[3]-median[3];
378 median[4]= ve_median[4]-median[4];
379 median[5]= ve_median[5]-median[5];
381 if(ob->type==OB_MESH) {
383 EditMesh *em = BKE_mesh_get_editmesh(me);
387 eve= em->verts.first;
389 if(eve->f & SELECT) {
390 add_v3_v3(eve->co, median);
395 for(eed= em->edges.first; eed; eed= eed->next) {
396 if(eed->f & SELECT) {
397 /* ensure the median can be set to zero or one */
398 if(ve_median[3]==0.0f) eed->crease= 0.0f;
399 else if(ve_median[3]==1.0f) eed->crease= 1.0f;
401 eed->crease+= median[3];
402 CLAMP(eed->crease, 0.0, 1.0);
407 recalc_editnormals(em);
409 BKE_mesh_end_editmesh(me, em);
411 else if(ob->type==OB_CURVE || ob->type==OB_SURF) {
417 ListBase *nurbs= ED_curve_editnurbs(cu);
421 if(nu->type == CU_BEZIER) {
425 if(bezt->f2 & SELECT) {
426 add_v3_v3(bezt->vec[0], median);
427 add_v3_v3(bezt->vec[1], median);
428 add_v3_v3(bezt->vec[2], median);
429 bezt->weight+= median[4];
430 bezt->radius+= median[5];
433 if(bezt->f1 & SELECT) {
434 add_v3_v3(bezt->vec[0], median);
436 if(bezt->f3 & SELECT) {
437 add_v3_v3(bezt->vec[2], median);
445 a= nu->pntsu*nu->pntsv;
447 if(bp->f1 & SELECT) {
448 add_v3_v3(bp->vec, median);
449 bp->vec[3]+= median[3];
450 bp->weight+= median[4];
451 bp->radius+= median[5];
457 testhandlesNurb(nu); /* test for bezier too */
462 else if(ob->type==OB_LATTICE) {
463 Lattice *lt= ob->data;
467 a= lt->editlatt->latt->pntsu*lt->editlatt->latt->pntsv*lt->editlatt->latt->pntsw;
468 bp= lt->editlatt->latt->def;
470 if(bp->f1 & SELECT) {
471 add_v3_v3(bp->vec, median);
472 bp->weight+= median[4];
478 // ED_undo_push(C, "Transform properties");
481 #define B_VGRP_PNL_COPY 1
482 #define B_VGRP_PNL_NORMALIZE 2
483 #define B_VGRP_PNL_EDIT_SINGLE 8 /* or greater */
484 #define B_VGRP_PNL_COPY_SINGLE 16384 /* or greater */
486 static void act_vert_def(Object *ob, EditVert **eve, MDeformVert **dvert)
488 if(ob && ob->mode & OB_MODE_EDIT && ob->type==OB_MESH && ob->defbase.first) {
490 EditMesh *em = BKE_mesh_get_editmesh(me);
491 EditSelection *ese = ((EditSelection*)em->selected.last);
493 if(ese && ese->type == EDITVERT) {
494 *eve= (EditVert*)ese->data;
495 *dvert= CustomData_em_get(&em->vdata, (*eve)->data, CD_MDEFORMVERT);
499 BKE_mesh_end_editmesh(me, em);
506 static void editvert_mirror_update(Object *ob, EditVert *eve, int def_nr, int index)
509 EditMesh *em = BKE_mesh_get_editmesh(me);
512 eve_mirr= editmesh_get_x_mirror_vert(ob, em, eve, eve->co, index);
514 if(eve_mirr && eve_mirr != eve) {
515 MDeformVert *dvert_src= CustomData_em_get(&em->vdata, eve->data, CD_MDEFORMVERT);
516 MDeformVert *dvert_dst= CustomData_em_get(&em->vdata, eve_mirr->data, CD_MDEFORMVERT);
519 /* all vgroups, add groups where neded */
521 int *flip_map= defgroup_flip_map(ob, 1);
522 defvert_sync_mapped(dvert_dst, dvert_src, flip_map, 1);
527 MDeformWeight *dw= defvert_verify_index(dvert_dst, defgroup_flip_index(ob, def_nr, 1));
529 dw->weight= defvert_find_weight(dvert_src, def_nr);
536 static void vgroup_adjust_active(Object *ob, int def_nr)
539 MDeformVert *dvert_act;
541 act_vert_def(ob, &eve_act, &dvert_act);
544 if(((Mesh *)ob->data)->editflag & ME_EDIT_MIRROR_X)
545 editvert_mirror_update(ob, eve_act, def_nr, -1);
549 static void vgroup_copy_active_to_sel(Object *ob)
552 MDeformVert *dvert_act;
554 act_vert_def(ob, &eve_act, &dvert_act);
556 if(dvert_act==NULL) {
561 EditMesh *em = BKE_mesh_get_editmesh(me);
566 for(eve= em->verts.first; eve; eve= eve->next, index++) {
567 if(eve->f & SELECT && eve != eve_act) {
568 dvert= CustomData_em_get(&em->vdata, eve->data, CD_MDEFORMVERT);
570 defvert_copy(dvert, dvert_act);
572 if(me->editflag & ME_EDIT_MIRROR_X)
573 editvert_mirror_update(ob, eve, -1, index);
581 static void vgroup_copy_active_to_sel_single(Object *ob, int def_nr)
584 MDeformVert *dvert_act;
586 act_vert_def(ob, &eve_act, &dvert_act);
588 if(dvert_act==NULL) {
593 EditMesh *em = BKE_mesh_get_editmesh(me);
597 float act_weight = -1.0f;
601 for(i=0, dw=dvert_act->dw; i < dvert_act->totweight; i++, dw++) {
602 if(def_nr == dw->def_nr) {
603 act_weight= dw->weight;
608 if(act_weight < -0.5f)
611 for(eve= em->verts.first; eve; eve= eve->next, index++) {
612 if(eve->f & SELECT && eve != eve_act) {
613 dvert= CustomData_em_get(&em->vdata, eve->data, CD_MDEFORMVERT);
615 for(i=0, dw=dvert->dw; i < dvert->totweight; i++, dw++) {
616 if(def_nr == dw->def_nr) {
617 dw->weight= act_weight;
619 if(me->editflag & ME_EDIT_MIRROR_X)
620 editvert_mirror_update(ob, eve, -1, index);
629 if(me->editflag & ME_EDIT_MIRROR_X)
630 editvert_mirror_update(ob, eve_act, -1, -1);
635 static void vgroup_normalize_active(Object *ob)
638 MDeformVert *dvert_act;
640 act_vert_def(ob, &eve_act, &dvert_act);
645 defvert_normalize(dvert_act);
647 if(((Mesh *)ob->data)->editflag & ME_EDIT_MIRROR_X)
648 editvert_mirror_update(ob, eve_act, -1, -1);
654 static void do_view3d_vgroup_buttons(bContext *C, void *UNUSED(arg), int event)
656 Scene *scene= CTX_data_scene(C);
659 if(event==B_VGRP_PNL_NORMALIZE) {
660 vgroup_normalize_active(ob);
662 else if(event == B_VGRP_PNL_COPY) {
663 vgroup_copy_active_to_sel(ob);
665 else if(event >= B_VGRP_PNL_COPY_SINGLE) {
666 vgroup_copy_active_to_sel_single(ob, event - B_VGRP_PNL_COPY_SINGLE);
668 else if(event >= B_VGRP_PNL_EDIT_SINGLE) {
669 vgroup_adjust_active(ob, event - B_VGRP_PNL_EDIT_SINGLE);
673 // if(((Mesh *)ob->data)->editflag & ME_EDIT_MIRROR_X)
674 // ED_vgroup_mirror(ob, 1, 1, 0);
676 /* default for now */
677 DAG_id_tag_update(&ob->id, OB_RECALC_DATA);
678 WM_event_add_notifier(C, NC_GEOM|ND_DATA, ob->data);
681 int view3d_panel_vgroup_poll(const bContext *C, PanelType *UNUSED(pt))
683 Scene *scene= CTX_data_scene(C);
686 MDeformVert *dvert_act;
688 act_vert_def(ob, &eve_act, &dvert_act);
690 return dvert_act ? dvert_act->totweight : 0;
694 static void view3d_panel_vgroup(const bContext *C, Panel *pa)
696 uiBlock *block= uiLayoutAbsoluteBlock(pa->layout);
697 Scene *scene= CTX_data_scene(C);
703 act_vert_def(ob, &eve, &dvert);
705 if(dvert && dvert->totweight) {
711 uiBlockSetHandleFunc(block, do_view3d_vgroup_buttons, NULL);
713 col= uiLayoutColumn(pa->layout, 0);
714 block= uiLayoutAbsoluteBlock(col);
716 uiBlockBeginAlign(block);
718 for (i=0; i<dvert->totweight; i++){
719 dg = BLI_findlink (&ob->defbase, dvert->dw[i].def_nr);
721 uiDefButF(block, NUM, B_VGRP_PNL_EDIT_SINGLE + dvert->dw[i].def_nr, dg->name, 0, yco, 180, 20, &dvert->dw[i].weight, 0.0, 1.0, 1, 3, "");
722 uiDefBut(block, BUT, B_VGRP_PNL_COPY_SINGLE + dvert->dw[i].def_nr, "C", 180,yco,20,20, 0, 0, 0, 0, 0, "Copy this groups weight to other selected verts");
728 uiBlockEndAlign(block);
729 uiBlockBeginAlign(block);
730 uiDefBut(block, BUT, B_VGRP_PNL_NORMALIZE, "Normalize", 0, yco,100,20, 0, 0, 0, 0, 0, "Normalize active vertex weights");
731 uiDefBut(block, BUT, B_VGRP_PNL_COPY, "Copy", 100,yco,100,20, 0, 0, 0, 0, 0, "Copy active vertex to other seleted verts");
732 uiBlockEndAlign(block);
736 static void v3d_transform_butsR(uiLayout *layout, PointerRNA *ptr)
738 uiLayout *split, *colsub;
740 split = uiLayoutSplit(layout, 0.8, 0);
742 if (ptr->type == &RNA_PoseBone) {
746 boneptr = RNA_pointer_get(ptr, "bone");
748 uiLayoutSetActive(split, !(bone->parent && bone->flag & BONE_CONNECTED));
750 colsub = uiLayoutColumn(split, 1);
751 uiItemR(colsub, ptr, "location", 0, "Location", 0);
752 colsub = uiLayoutColumn(split, 1);
753 uiItemL(colsub, "", 0);
754 uiItemR(colsub, ptr, "lock_location", UI_ITEM_R_TOGGLE+UI_ITEM_R_ICON_ONLY, "", 0);
756 split = uiLayoutSplit(layout, 0.8, 0);
758 switch(RNA_enum_get(ptr, "rotation_mode")) {
759 case ROT_MODE_QUAT: /* quaternion */
760 colsub = uiLayoutColumn(split, 1);
761 uiItemR(colsub, ptr, "rotation_quaternion", 0, "Rotation", 0);
762 colsub = uiLayoutColumn(split, 1);
763 uiItemR(colsub, ptr, "lock_rotations_4d", UI_ITEM_R_TOGGLE, "4L", 0);
764 if (RNA_boolean_get(ptr, "lock_rotations_4d"))
765 uiItemR(colsub, ptr, "lock_rotation_w", UI_ITEM_R_TOGGLE+UI_ITEM_R_ICON_ONLY, "", 0);
767 uiItemL(colsub, "", 0);
768 uiItemR(colsub, ptr, "lock_rotation", UI_ITEM_R_TOGGLE+UI_ITEM_R_ICON_ONLY, "", 0);
770 case ROT_MODE_AXISANGLE: /* axis angle */
771 colsub = uiLayoutColumn(split, 1);
772 uiItemR(colsub, ptr, "rotation_axis_angle", 0, "Rotation", 0);
773 colsub = uiLayoutColumn(split, 1);
774 uiItemR(colsub, ptr, "lock_rotations_4d", UI_ITEM_R_TOGGLE, "4L", 0);
775 if (RNA_boolean_get(ptr, "lock_rotations_4d"))
776 uiItemR(colsub, ptr, "lock_rotation_w", UI_ITEM_R_TOGGLE+UI_ITEM_R_ICON_ONLY, "", 0);
778 uiItemL(colsub, "", 0);
779 uiItemR(colsub, ptr, "lock_rotation", UI_ITEM_R_TOGGLE+UI_ITEM_R_ICON_ONLY, "", 0);
781 default: /* euler rotations */
782 colsub = uiLayoutColumn(split, 1);
783 uiItemR(colsub, ptr, "rotation_euler", 0, "Rotation", 0);
784 colsub = uiLayoutColumn(split, 1);
785 uiItemL(colsub, "", 0);
786 uiItemR(colsub, ptr, "lock_rotation", UI_ITEM_R_TOGGLE+UI_ITEM_R_ICON_ONLY, "", 0);
789 uiItemR(layout, ptr, "rotation_mode", 0, "", 0);
791 split = uiLayoutSplit(layout, 0.8, 0);
792 colsub = uiLayoutColumn(split, 1);
793 uiItemR(colsub, ptr, "scale", 0, "Scale", 0);
794 colsub = uiLayoutColumn(split, 1);
795 uiItemL(colsub, "", 0);
796 uiItemR(colsub, ptr, "lock_scale", UI_ITEM_R_TOGGLE+UI_ITEM_R_ICON_ONLY, "", 0);
798 if (ptr->type == &RNA_Object) {
799 Object *ob = ptr->data;
800 if (ELEM5(ob->type, OB_MESH, OB_CURVE, OB_SURF, OB_FONT, OB_MBALL))
801 uiItemR(layout, ptr, "dimensions", 0, "Dimensions", 0);
805 static void v3d_posearmature_buts(uiLayout *layout, Object *ob)
807 // uiBlock *block= uiLayoutGetBlock(layout);
810 // TransformProperties *tfp= v3d->properties_storage;
816 pchan= get_active_posechannel(ob);
818 // row= uiLayoutRow(layout, 0);
821 uiItemL(layout, "No Bone Active", 0);
825 RNA_pointer_create(&ob->id, &RNA_PoseBone, pchan, &pchanptr);
827 col= uiLayoutColumn(layout, 0);
829 /* XXX: RNA buts show data in native types (i.e. quats, 4-component axis/angle, etc.)
830 * but oldskool UI shows in eulers always. Do we want to be able to still display in Eulers?
831 * Maybe needs RNA/ui options to display rotations as different types... */
832 v3d_transform_butsR(col, &pchanptr);
835 uiLayoutAbsoluteBlock(layout);
837 if (pchan->rotmode == ROT_MODE_AXISANGLE) {
839 /* convert to euler, passing through quats... */
840 axis_angle_to_quat(quat, pchan->rotAxis, pchan->rotAngle);
841 quat_to_eul( tfp->ob_eul,quat);
843 else if (pchan->rotmode == ROT_MODE_QUAT)
844 quat_to_eul( tfp->ob_eul,pchan->quat);
846 copy_v3_v3(tfp->ob_eul, pchan->eul);
847 tfp->ob_eul[0]*= 180.0/M_PI;
848 tfp->ob_eul[1]*= 180.0/M_PI;
849 tfp->ob_eul[2]*= 180.0/M_PI;
851 uiDefBut(block, LABEL, 0, "Location:", 0, 240, 100, 20, 0, 0, 0, 0, 0, "");
852 uiBlockBeginAlign(block);
854 but= uiDefButF(block, NUM, B_ARMATUREPANEL2, "X:", 0, 220, 120, 19, pchan->loc, -lim, lim, 100, 3, "");
855 uiButSetUnitType(but, PROP_UNIT_LENGTH);
856 but= uiDefButF(block, NUM, B_ARMATUREPANEL2, "Y:", 0, 200, 120, 19, pchan->loc+1, -lim, lim, 100, 3, "");
857 uiButSetUnitType(but, PROP_UNIT_LENGTH);
858 but= uiDefButF(block, NUM, B_ARMATUREPANEL2, "Z:", 0, 180, 120, 19, pchan->loc+2, -lim, lim, 100, 3, "");
859 uiButSetUnitType(but, PROP_UNIT_LENGTH);
860 uiBlockEndAlign(block);
862 uiBlockBeginAlign(block);
863 uiDefIconButBitS(block, ICONTOG, OB_LOCK_LOCX, B_REDR, ICON_UNLOCKED, 125, 220, 25, 19, &(pchan->protectflag), 0, 0, 0, 0, "Protects X Location value from being Transformed");
864 uiDefIconButBitS(block, ICONTOG, OB_LOCK_LOCY, B_REDR, ICON_UNLOCKED, 125, 200, 25, 19, &(pchan->protectflag), 0, 0, 0, 0, "Protects Y Location value from being Transformed");
865 uiDefIconButBitS(block, ICONTOG, OB_LOCK_LOCZ, B_REDR, ICON_UNLOCKED, 125, 180, 25, 19, &(pchan->protectflag), 0, 0, 0, 0, "Protects Z Location value from being Transformed");
866 uiBlockEndAlign(block);
868 uiDefBut(block, LABEL, 0, "Rotation:", 0, 160, 100, 20, 0, 0, 0, 0, 0, "");
869 uiBlockBeginAlign(block);
870 uiDefButF(block, NUM, B_ARMATUREPANEL3, "X:", 0, 140, 120, 19, tfp->ob_eul, -1000.0, 1000.0, 100, 3, "");
871 uiDefButF(block, NUM, B_ARMATUREPANEL3, "Y:", 0, 120, 120, 19, tfp->ob_eul+1, -1000.0, 1000.0, 100, 3, "");
872 uiDefButF(block, NUM, B_ARMATUREPANEL3, "Z:", 0, 100, 120, 19, tfp->ob_eul+2, -1000.0, 1000.0, 100, 3, "");
873 uiBlockEndAlign(block);
875 uiBlockBeginAlign(block);
876 uiDefIconButBitS(block, ICONTOG, OB_LOCK_ROTX, B_REDR, ICON_UNLOCKED, 125, 140, 25, 19, &(pchan->protectflag), 0, 0, 0, 0, "Protects X Rotation value from being Transformed");
877 uiDefIconButBitS(block, ICONTOG, OB_LOCK_ROTY, B_REDR, ICON_UNLOCKED, 125, 120, 25, 19, &(pchan->protectflag), 0, 0, 0, 0, "Protects Y Rotation value from being Transformed");
878 uiDefIconButBitS(block, ICONTOG, OB_LOCK_ROTZ, B_REDR, ICON_UNLOCKED, 125, 100, 25, 19, &(pchan->protectflag), 0, 0, 0, 0, "Protects Z Rotation value from being Transformed");
879 uiBlockEndAlign(block);
881 uiDefBut(block, LABEL, 0, "Scale:", 0, 80, 100, 20, 0, 0, 0, 0, 0, "");
882 uiBlockBeginAlign(block);
883 uiDefButF(block, NUM, B_ARMATUREPANEL2, "X:", 0, 60, 120, 19, pchan->size, -lim, lim, 10, 3, "");
884 uiDefButF(block, NUM, B_ARMATUREPANEL2, "Y:", 0, 40, 120, 19, pchan->size+1, -lim, lim, 10, 3, "");
885 uiDefButF(block, NUM, B_ARMATUREPANEL2, "Z:", 0, 20, 120, 19, pchan->size+2, -lim, lim, 10, 3, "");
886 uiBlockEndAlign(block);
888 uiBlockBeginAlign(block);
889 uiDefIconButBitS(block, ICONTOG, OB_LOCK_SCALEX, B_REDR, ICON_UNLOCKED, 125, 60, 25, 19, &(pchan->protectflag), 0, 0, 0, 0, "Protects X Scale value from being Transformed");
890 uiDefIconButBitS(block, ICONTOG, OB_LOCK_SCALEY, B_REDR, ICON_UNLOCKED, 125, 40, 25, 19, &(pchan->protectflag), 0, 0, 0, 0, "Protects Y Scale value from being Transformed");
891 uiDefIconButBitS(block, ICONTOG, OB_LOCK_SCALEZ, B_REDR, ICON_UNLOCKED, 125, 20, 25, 19, &(pchan->protectflag), 0, 0, 0, 0, "Protects z Scale value from being Transformed");
892 uiBlockEndAlign(block);
896 /* assumes armature editmode */
897 void validate_editbonebutton_cb(bContext *C, void *bonev, void *namev)
899 EditBone *eBone= bonev;
900 char oldname[sizeof(eBone->name)], newname[sizeof(eBone->name)];
902 /* need to be on the stack */
903 BLI_strncpy(newname, eBone->name, sizeof(eBone->name));
904 BLI_strncpy(oldname, (char *)namev, sizeof(eBone->name));
906 BLI_strncpy(eBone->name, oldname, sizeof(eBone->name));
908 ED_armature_bone_rename(CTX_data_edit_object(C)->data, oldname, newname); // editarmature.c
909 WM_event_add_notifier(C, NC_OBJECT|ND_BONE_SELECT, CTX_data_edit_object(C)); // XXX fix
912 static void v3d_editarmature_buts(uiLayout *layout, Object *ob)
914 // uiBlock *block= uiLayoutGetBlock(layout);
915 bArmature *arm= ob->data;
917 // TransformProperties *tfp= v3d->properties_storage;
922 ebone= arm->act_edbone;
924 if (!ebone || (ebone->layer & arm->layer)==0)
927 // row= uiLayoutRow(layout, 0);
928 RNA_pointer_create(&arm->id, &RNA_EditBone, ebone, &eboneptr);
931 col= uiLayoutColumn(layout, 0);
932 uiItemR(col, &eboneptr, "head", 0, "Head", 0);
933 if (ebone->parent && ebone->flag & BONE_CONNECTED ) {
934 PointerRNA parptr = RNA_pointer_get(&eboneptr, "parent");
935 uiItemR(col, &parptr, "tail_radius", 0, "Radius (Parent)", 0);
937 uiItemR(col, &eboneptr, "head_radius", 0, "Radius", 0);
940 uiItemR(col, &eboneptr, "tail", 0, "Tail", 0);
941 uiItemR(col, &eboneptr, "tail_radius", 0, "Radius", 0);
943 uiItemR(col, &eboneptr, "roll", 0, "Roll", 0);
946 static void v3d_editmetaball_buts(uiLayout *layout, Object *ob)
948 PointerRNA mbptr, ptr;
949 MetaBall *mball= ob->data;
953 if (!mball || !(mball->lastelem)) return;
955 RNA_pointer_create(&mball->id, &RNA_MetaBall, mball, &mbptr);
957 // row= uiLayoutRow(layout, 0);
959 RNA_pointer_create(&mball->id, &RNA_MetaElement, mball->lastelem, &ptr);
961 col= uiLayoutColumn(layout, 0);
962 uiItemR(col, &ptr, "co", 0, "Location", 0);
964 uiItemR(col, &ptr, "radius", 0, "Radius", 0);
965 uiItemR(col, &ptr, "stiffness", 0, "Stiffness", 0);
967 uiItemR(col, &ptr, "type", 0, "Type", 0);
969 col= uiLayoutColumn(layout, 1);
970 switch (RNA_enum_get(&ptr, "type")) {
974 uiItemL(col, "Size:", 0);
975 uiItemR(col, &ptr, "size_x", 0, "X", 0);
976 uiItemR(col, &ptr, "size_y", 0, "Y", 0);
977 uiItemR(col, &ptr, "size_z", 0, "Z", 0);
980 uiItemL(col, "Size:", 0);
981 uiItemR(col, &ptr, "size_x", 0, "X", 0);
984 uiItemL(col, "Size:", 0);
985 uiItemR(col, &ptr, "size_x", 0, "X", 0);
986 uiItemR(col, &ptr, "size_y", 0, "Y", 0);
989 uiItemL(col, "Size:", 0);
990 uiItemR(col, &ptr, "size_x", 0, "X", 0);
991 uiItemR(col, &ptr, "size_y", 0, "Y", 0);
992 uiItemR(col, &ptr, "size_z", 0, "Z", 0);
997 /* test if 'ob' is a parent somewhere in par's parents */
998 static int test_parent_loop(Object *par, Object *ob)
1000 if(par == NULL) return 0;
1001 if(ob == par) return 1;
1002 return test_parent_loop(par->parent, ob);
1005 static void do_view3d_region_buttons(bContext *C, void *UNUSED(index), int event)
1007 Main *bmain= CTX_data_main(C);
1008 Scene *scene= CTX_data_scene(C);
1009 // Object *obedit= CTX_data_edit_object(C);
1010 View3D *v3d= CTX_wm_view3d(C);
1013 TransformProperties *tfp= v3d->properties_storage;
1018 ED_area_tag_redraw(CTX_wm_area(C));
1019 return; /* no notifier! */
1022 DAG_id_tag_update(&ob->id, OB_RECALC_OB);
1026 case B_OBJECTPANELMEDIAN:
1028 v3d_editvertex_buts(NULL, v3d, ob, 1.0);
1029 DAG_id_tag_update(&ob->id, OB_RECALC_DATA);
1033 /* note; this case also used for parbone */
1034 case B_OBJECTPANELPARENT:
1036 if(ob->id.lib || test_parent_loop(ob->parent, ob) )
1039 DAG_scene_sort(bmain, scene);
1040 DAG_id_tag_update(&ob->id, OB_RECALC_OB);
1046 case B_ARMATUREPANEL3: // rotate button on channel
1048 bPoseChannel *pchan;
1051 pchan= get_active_posechannel(ob);
1054 /* make a copy to eul[3], to allow TAB on buttons to work */
1055 eul[0]= M_PI*tfp->ob_eul[0]/180.0;
1056 eul[1]= M_PI*tfp->ob_eul[1]/180.0;
1057 eul[2]= M_PI*tfp->ob_eul[2]/180.0;
1059 if (pchan->rotmode == ROT_MODE_AXISANGLE) {
1061 /* convert to axis-angle, passing through quats */
1062 eul_to_quat( quat,eul);
1063 quat_to_axis_angle( pchan->rotAxis, &pchan->rotAngle,quat);
1065 else if (pchan->rotmode == ROT_MODE_QUAT)
1066 eul_to_quat( pchan->quat,eul);
1068 copy_v3_v3(pchan->eul, eul);
1070 /* no break, pass on */
1071 case B_ARMATUREPANEL2:
1073 ob->pose->flag |= (POSE_LOCKED|POSE_DO_UNLOCK);
1074 DAG_id_tag_update(&ob->id, OB_RECALC_DATA);
1077 case B_TRANSFORMSPACEADD:
1079 char names[sizeof(((TransformOrientation *)NULL)->name)]= "";
1080 BIF_createTransformOrientation(C, NULL, names, 1, 0);
1083 case B_TRANSFORMSPACECLEAR:
1084 BIF_clearTransformOrientation(C);
1089 wpaint->weight = 0.0f;
1093 wpaint->weight = 0.25f;
1096 wpaint->weight = 0.5f;
1099 wpaint->weight = 0.75f;
1102 wpaint->weight = 1.0f;
1122 // if(!multires_level1_test()) {
1124 bDeformGroup *defGroup = BLI_findlink(&ob->defbase, ob->actdef-1);
1128 for(a=0; a<me->totvert; a++)
1129 ED_vgroup_vert_remove (ob, defGroup, a);
1130 DAG_id_tag_update(&ob->id, OB_RECALC_DATA);
1135 case B_RV3D_BOXVIEW:
1136 case B_RV3D_BOXCLIP:
1138 ScrArea *sa= CTX_wm_area(C);
1139 ARegion *ar= sa->regionbase.last;
1144 rv3d= ar->regiondata;
1145 viewlock= rv3d->viewlock;
1147 if((viewlock & RV3D_LOCKED)==0)
1149 else if((viewlock & RV3D_BOXVIEW)==0)
1150 viewlock &= ~RV3D_BOXCLIP;
1152 for(; ar; ar= ar->prev) {
1153 if(ar->alignment==RGN_ALIGN_QSPLIT) {
1154 rv3d= ar->regiondata;
1155 rv3d->viewlock= viewlock;
1159 if(rv3d->viewlock & RV3D_BOXVIEW)
1160 view3d_boxview_copy(sa, sa->regionbase.last);
1162 ED_area_tag_redraw(sa);
1167 /* default for now */
1168 WM_event_add_notifier(C, NC_SPACE|ND_SPACE_VIEW3D, ob);
1171 void removeTransformOrientation_func(bContext *C, void *target, void *UNUSED(arg))
1173 BIF_removeTransformOrientation(C, (TransformOrientation *) target);
1176 void selectTransformOrientation_func(bContext *C, void *target, void *UNUSED(arg))
1178 BIF_selectTransformOrientation(C, (TransformOrientation *) target);
1181 static void view3d_panel_object(const bContext *C, Panel *pa)
1184 Scene *scene= CTX_data_scene(C);
1185 Object *obedit= CTX_data_edit_object(C);
1186 View3D *v3d= CTX_wm_view3d(C);
1189 TransformProperties *tfp;
1191 uiLayout *col, *row;
1194 if(ob==NULL) return;
1196 /* make sure we got storage */
1197 if(v3d->properties_storage==NULL)
1198 v3d->properties_storage= MEM_callocN(sizeof(TransformProperties), "TransformProperties");
1199 tfp= v3d->properties_storage;
1201 // XXX uiSetButLock(object_is_libdata(ob), ERROR_LIBDATA_MESSAGE);
1203 if(ob->mode & (OB_MODE_VERTEX_PAINT|OB_MODE_WEIGHT_PAINT|OB_MODE_TEXTURE_PAINT)) {
1206 if((ob->mode & OB_MODE_PARTICLE_EDIT)==0) {
1207 uiBlockEndAlign(block);
1212 lim= 10000.0f*MAX2(1.0, v3d->grid);
1214 block= uiLayoutGetBlock(pa->layout);
1215 uiBlockSetHandleFunc(block, do_view3d_region_buttons, NULL);
1217 col= uiLayoutColumn(pa->layout, 0);
1218 row= uiLayoutRow(col, 0);
1219 RNA_id_pointer_create(&ob->id, &obptr);
1222 if(ob->type==OB_ARMATURE) v3d_editarmature_buts(col, ob);
1223 if(ob->type==OB_MBALL) v3d_editmetaball_buts(col, ob);
1224 else v3d_editvertex_buts(col, v3d, ob, lim);
1226 else if(ob->mode & OB_MODE_POSE) {
1227 v3d_posearmature_buts(col, ob);
1231 v3d_transform_butsR(col, &obptr);
1236 static void view3d_panel_preview(bContext *C, ARegion *ar, short cntrl) // VIEW3D_HANDLER_PREVIEW
1239 View3D *v3d= sa->spacedata.first;
1242 block= uiBeginBlock(C, ar, "view3d_panel_preview", UI_EMBOSS);
1243 uiPanelControl(UI_PNL_SOLID | UI_PNL_CLOSE | UI_PNL_SCALE | cntrl);
1244 uiSetPanelHandler(VIEW3D_HANDLER_PREVIEW); // for close and esc
1246 ofsx= -150+(sa->winx/2)/v3d->blockscale;
1247 ofsy= -100+(sa->winy/2)/v3d->blockscale;
1248 if(uiNewPanel(C, ar, block, "Preview", "View3d", ofsx, ofsy, 300, 200)==0) return;
1250 uiBlockSetDrawExtraFunc(block, BIF_view3d_previewdraw);
1252 if(scene->recalc & SCE_PRV_CHANGED) {
1253 scene->recalc &= ~SCE_PRV_CHANGED;
1254 //printf("found recalc\n");
1255 BIF_view3d_previewrender_free(sa->spacedata.first);
1256 BIF_preview_changed(0);
1261 #if 0 // XXX not used
1262 static void delete_sketch_armature(bContext *C, void *arg1, void *arg2)
1264 BIF_deleteSketch(C);
1267 static void convert_sketch_armature(bContext *C, void *arg1, void *arg2)
1269 BIF_convertSketch(C);
1272 static void assign_template_sketch_armature(bContext *C, void *arg1, void *arg2)
1274 int index = *(int*)arg1;
1275 BIF_setTemplate(C, index);
1279 static int view3d_panel_bonesketch_spaces_poll(const bContext *C, PanelType *pt)
1281 Object *obedit = CTX_data_edit_object(C);
1283 /* replace with check call to sketching lib */
1284 return (obedit && obedit->type == OB_ARMATURE);
1286 static void view3d_panel_bonesketch_spaces(const bContext *C, Panel *pa)
1288 Scene *scene = CTX_data_scene(C);
1289 static int template_index;
1290 static char joint_label[128];
1296 static char subdiv_tooltip[4][64] = {
1297 "Subdivide arcs based on a fixed number of bones",
1298 "Subdivide arcs in bones of equal length",
1299 "Subdivide arcs based on correlation",
1300 "Retarget template to stroke"
1304 block= uiLayoutAbsoluteBlock(pa->layout);
1305 uiBlockSetHandleFunc(block, do_view3d_region_buttons, NULL);
1307 uiBlockBeginAlign(block);
1309 /* use real flag instead of 1 */
1310 uiDefButBitC(block, TOG, BONE_SKETCHING, B_REDR, "Use Bone Sketching", 10, yco, 160, 20, &scene->toolsettings->bone_sketching, 0, 0, 0, 0, "Use sketching to create and edit bones, (Ctrl snaps to mesh volume)");
1311 uiDefButBitC(block, TOG, BONE_SKETCHING_ADJUST, B_REDR, "A", 170, yco, 20, 20, &scene->toolsettings->bone_sketching, 0, 0, 0, 0, "Adjust strokes by drawing near them");
1312 uiDefButBitC(block, TOG, BONE_SKETCHING_QUICK, B_REDR, "Q", 190, yco, 20, 20, &scene->toolsettings->bone_sketching, 0, 0, 0, 0, "Automatically convert and delete on stroke end");
1315 but = uiDefBut(block, BUT, B_REDR, "Convert", 10,yco,100,20, 0, 0, 0, 0, 0, "Convert sketch to armature");
1316 uiButSetFunc(but, convert_sketch_armature, NULL, NULL);
1318 but = uiDefBut(block, BUT, B_REDR, "Delete", 110,yco,100,20, 0, 0, 0, 0, 0, "Delete sketch");
1319 uiButSetFunc(but, delete_sketch_armature, NULL, NULL);
1322 uiBlockEndAlign(block);
1324 uiBlockBeginAlign(block);
1326 uiDefButC(block, MENU, B_REDR, "Subdivision Method%t|Length%x1|Adaptative%x2|Fixed%x0|Template%x3", 10,yco,60,19, &scene->toolsettings->bone_sketching_convert, 0, 0, 0, 0, subdiv_tooltip[(unsigned char)scene->toolsettings->bone_sketching_convert]);
1328 switch(scene->toolsettings->bone_sketching_convert)
1330 case SK_CONVERT_CUT_LENGTH:
1331 uiDefButF(block, NUM, B_REDR, "Lim:", 70, yco, 140, 19, &scene->toolsettings->skgen_length_limit,0.1,50.0, 10, 0, "Maximum length of the subdivided bones");
1334 case SK_CONVERT_CUT_ADAPTATIVE:
1335 uiDefButF(block, NUM, B_REDR, "Thres:", 70, yco, 140, 19, &scene->toolsettings->skgen_correlation_limit,0.0, 1.0, 0.01, 0, "Correlation threshold for subdivision");
1339 case SK_CONVERT_CUT_FIXED:
1340 uiDefButC(block, NUM, B_REDR, "Num:", 70, yco, 140, 19, &scene->toolsettings->skgen_subdivision_number,1, 100, 1, 5, "Number of subdivided bones");
1343 case SK_CONVERT_RETARGET:
1344 uiDefButC(block, ROW, B_NOP, "No", 70, yco, 40,19, &scene->toolsettings->skgen_retarget_roll, 0, 0, 0, 0, "No special roll treatment");
1345 uiDefButC(block, ROW, B_NOP, "View", 110, yco, 50,19, &scene->toolsettings->skgen_retarget_roll, 0, SK_RETARGET_ROLL_VIEW, 0, 0, "Roll bones perpendicular to view");
1346 uiDefButC(block, ROW, B_NOP, "Joint", 160, yco, 50,19, &scene->toolsettings->skgen_retarget_roll, 0, SK_RETARGET_ROLL_JOINT, 0, 0, "Roll bones relative to joint bend");
1349 uiBlockEndAlign(block);
1351 uiBlockBeginAlign(block);
1352 /* button here to select what to do (copy or not), template, ...*/
1354 BIF_makeListTemplates(C);
1355 template_index = BIF_currentTemplate(C);
1357 but = uiDefButI(block, MENU, B_REDR, BIF_listTemplates(C), 10,yco,200,19, &template_index, 0, 0, 0, 0, "Template");
1358 uiButSetFunc(but, assign_template_sketch_armature, &template_index, NULL);
1362 uiDefButF(block, NUM, B_NOP, "A:", 10, yco, 66,19, &scene->toolsettings->skgen_retarget_angle_weight, 0, 10, 1, 0, "Angle Weight");
1363 uiDefButF(block, NUM, B_NOP, "L:", 76, yco, 67,19, &scene->toolsettings->skgen_retarget_length_weight, 0, 10, 1, 0, "Length Weight");
1364 uiDefButF(block, NUM, B_NOP, "D:", 143,yco, 67,19, &scene->toolsettings->skgen_retarget_distance_weight, 0, 10, 1, 0, "Distance Weight");
1367 uiDefBut(block, TEX,B_REDR,"S:", 10, yco, 90, 20, scene->toolsettings->skgen_side_string, 0.0, 8.0, 0, 0, "Text to replace &S with");
1368 uiDefBut(block, TEX,B_REDR,"N:", 100, yco, 90, 20, scene->toolsettings->skgen_num_string, 0.0, 8.0, 0, 0, "Text to replace &N with");
1369 uiDefIconButBitC(block, TOG, SK_RETARGET_AUTONAME, B_NOP, ICON_AUTO,190,yco,20,20, &scene->toolsettings->skgen_retarget_options, 0, 0, 0, 0, "Use Auto Naming");
1372 /* auto renaming magic */
1373 uiBlockEndAlign(block);
1375 nb_joints = BIF_nbJointsTemplate(C);
1377 if (nb_joints == -1)
1380 //nb_joints = G.totvertsel;
1383 bone_name = BIF_nameBoneTemplate(C);
1385 BLI_snprintf(joint_label, 32, "%i joints: %s", nb_joints, bone_name);
1387 uiDefBut(block, LABEL, 1, joint_label, 10, yco, 200, 20, NULL, 0.0, 0.0, 0, 0, "");
1392 uiBlockEndAlign(block);
1395 static void view3d_panel_operator_redo(const bContext *C, Panel *pa)
1397 wmWindowManager *wm= CTX_wm_manager(C);
1402 block= uiLayoutGetBlock(pa->layout);
1404 /* only for operators that are registered and did an undo push */
1405 for(op= wm->operators.last; op; op= op->prev)
1406 if((op->type->flag & OPTYPE_REGISTER) && (op->type->flag & OPTYPE_UNDO))
1412 uiBlockSetFunc(block, ED_undo_operator_repeat_cb, op, NULL);
1414 if(!op->properties) {
1415 IDPropertyTemplate val = {0};
1416 op->properties= IDP_New(IDP_GROUP, val, "wmOperatorProperties");
1419 RNA_pointer_create(&wm->id, op->type->srna, op->properties, &ptr);
1420 uiDefAutoButsRNA(pa->layout, &ptr, 2);
1422 #endif // XXX not used
1424 void view3d_buttons_register(ARegionType *art)
1428 pt= MEM_callocN(sizeof(PanelType), "spacetype view3d panel object");
1429 strcpy(pt->idname, "VIEW3D_PT_object");
1430 strcpy(pt->label, "Transform");
1431 pt->draw= view3d_panel_object;
1432 BLI_addtail(&art->paneltypes, pt);
1434 pt= MEM_callocN(sizeof(PanelType), "spacetype view3d panel gpencil");
1435 strcpy(pt->idname, "VIEW3D_PT_gpencil");
1436 strcpy(pt->label, "Grease Pencil");
1437 pt->draw= gpencil_panel_standard;
1438 BLI_addtail(&art->paneltypes, pt);
1440 pt= MEM_callocN(sizeof(PanelType), "spacetype view3d panel vgroup");
1441 strcpy(pt->idname, "VIEW3D_PT_vgroup");
1442 strcpy(pt->label, "Vertex Groups");
1443 pt->draw= view3d_panel_vgroup;
1444 pt->poll= view3d_panel_vgroup_poll;
1445 BLI_addtail(&art->paneltypes, pt);
1447 // XXX view3d_panel_preview(C, ar, 0);
1450 static int view3d_properties(bContext *C, wmOperator *UNUSED(op))
1452 ScrArea *sa= CTX_wm_area(C);
1453 ARegion *ar= view3d_has_buttons_region(sa);
1456 ED_region_toggle_hidden(C, ar);
1458 return OPERATOR_FINISHED;
1461 void VIEW3D_OT_properties(wmOperatorType *ot)
1463 ot->name= "Properties";
1464 ot->description= "Toggles the properties panel display";
1465 ot->idname= "VIEW3D_OT_properties";
1467 ot->exec= view3d_properties;
1468 ot->poll= ED_operator_view3d_active;