Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/source
diff options
context:
space:
mode:
authorCampbell Barton <ideasman42@gmail.com>2009-11-10 00:03:54 +0300
committerCampbell Barton <ideasman42@gmail.com>2009-11-10 00:03:54 +0300
commit5935ef004935b27fc5795349aed32f87cf637049 (patch)
treef36022abb03938420606405e9afc841b14d4bd81 /source
parent3e2766bc2ee7523ea68caedc5b11e9498ddcbbc1 (diff)
use armature active bone as a pointer rather then a flag for each bone that needs looking up.
- rna vars arm.bones.active & rna.edit_bones.active - needed special undo support. - readfile.c loads. - duplicate and copy_armature support. - keep the draw flag, renamed to BONE_DRAW_ACTIVE, only use for openGL drawing. Note: it may be better to allow active/unselected as with objects.
Diffstat (limited to 'source')
-rw-r--r--source/blender/blenkernel/intern/action.c2
-rw-r--r--source/blender/blenkernel/intern/armature.c11
-rw-r--r--source/blender/blenloader/intern/readfile.c5
-rw-r--r--source/blender/blenloader/intern/writefile.c2
-rw-r--r--source/blender/editors/armature/armature_intern.h2
-rw-r--r--source/blender/editors/armature/editarmature.c294
-rw-r--r--source/blender/editors/armature/editarmature_retarget.c10
-rw-r--r--source/blender/editors/armature/poselib.c4
-rw-r--r--source/blender/editors/armature/poseobject.c54
-rw-r--r--source/blender/editors/include/ED_armature.h1
-rw-r--r--source/blender/editors/screen/screen_context.c26
-rw-r--r--source/blender/editors/sculpt_paint/paint_vertex.c10
-rw-r--r--source/blender/editors/space_buttons/buttons_context.c34
-rw-r--r--source/blender/editors/space_outliner/outliner.c31
-rw-r--r--source/blender/editors/space_view3d/drawarmature.c21
-rw-r--r--source/blender/editors/space_view3d/view3d_buttons.c31
-rw-r--r--source/blender/editors/space_view3d/view3d_draw.c24
-rw-r--r--source/blender/editors/space_view3d/view3d_select.c23
-rw-r--r--source/blender/editors/transform/transform_manipulator.c14
-rw-r--r--source/blender/makesdna/DNA_armature_types.h5
-rw-r--r--source/blender/makesrna/intern/rna_armature.c68
-rw-r--r--source/gameengine/Converter/BL_ArmatureChannel.cpp8
-rw-r--r--source/gameengine/Converter/BL_BlenderDataConversion.cpp2
23 files changed, 392 insertions, 290 deletions
diff --git a/source/blender/blenkernel/intern/action.c b/source/blender/blenkernel/intern/action.c
index 2dec76d1b6b..2505a3a70ac 100644
--- a/source/blender/blenkernel/intern/action.c
+++ b/source/blender/blenkernel/intern/action.c
@@ -471,7 +471,7 @@ bPoseChannel *get_active_posechannel (Object *ob)
/* find active */
for (pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
- if ((pchan->bone) && (pchan->bone->flag & BONE_ACTIVE) && (pchan->bone->layer & arm->layer))
+ if ((pchan->bone) && (pchan->bone == arm->act_bone) && (pchan->bone->layer & arm->layer))
return pchan;
}
diff --git a/source/blender/blenkernel/intern/armature.c b/source/blender/blenkernel/intern/armature.c
index f178553d796..b0153a1fca3 100644
--- a/source/blender/blenkernel/intern/armature.c
+++ b/source/blender/blenkernel/intern/armature.c
@@ -169,10 +169,13 @@ void make_local_armature(bArmature *arm)
}
}
-static void copy_bonechildren (Bone* newBone, Bone* oldBone)
+static void copy_bonechildren (Bone* newBone, Bone* oldBone, Bone* actBone, Bone **newActBone)
{
Bone *curBone, *newChildBone;
+ if(oldBone == actBone)
+ *newActBone= newBone;
+
/* Copy this bone's list*/
BLI_duplicatelist(&newBone->childbase, &oldBone->childbase);
@@ -180,7 +183,7 @@ static void copy_bonechildren (Bone* newBone, Bone* oldBone)
newChildBone=newBone->childbase.first;
for (curBone=oldBone->childbase.first;curBone;curBone=curBone->next){
newChildBone->parent=newBone;
- copy_bonechildren(newChildBone,curBone);
+ copy_bonechildren(newChildBone, curBone, actBone, newActBone);
newChildBone=newChildBone->next;
}
}
@@ -189,6 +192,7 @@ bArmature *copy_armature(bArmature *arm)
{
bArmature *newArm;
Bone *oldBone, *newBone;
+ Bone *newActBone= NULL;
newArm= copy_libblock (arm);
BLI_duplicatelist(&newArm->bonebase, &arm->bonebase);
@@ -197,10 +201,11 @@ bArmature *copy_armature(bArmature *arm)
newBone=newArm->bonebase.first;
for (oldBone=arm->bonebase.first;oldBone;oldBone=oldBone->next){
newBone->parent=NULL;
- copy_bonechildren (newBone, oldBone);
+ copy_bonechildren (newBone, oldBone, arm->act_bone, &newActBone);
newBone=newBone->next;
};
+ newArm->act_bone= newActBone;
return newArm;
}
diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c
index 00f7cbd9eeb..e1a13b65efa 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -2333,7 +2333,7 @@ static void lib_link_pose(FileData *fd, Object *ob, bPose *pose)
rebuild= 1;
else if(ob->id.lib==NULL && arm->id.lib) {
/* local pose selection copied to armature, bit hackish */
- pchan->bone->flag &= ~(BONE_SELECTED|BONE_ACTIVE);
+ pchan->bone->flag &= ~BONE_SELECTED;
pchan->bone->flag |= pchan->selectflag;
}
}
@@ -2388,6 +2388,9 @@ static void direct_link_armature(FileData *fd, bArmature *arm)
direct_link_bones(fd, bone);
bone=bone->next;
}
+
+ arm->act_bone= newdataadr(fd, arm->act_bone);
+ arm->act_edbone= NULL;
}
/* ************ READ CAMERA ***************** */
diff --git a/source/blender/blenloader/intern/writefile.c b/source/blender/blenloader/intern/writefile.c
index 8ec12496e59..b2147221f9f 100644
--- a/source/blender/blenloader/intern/writefile.c
+++ b/source/blender/blenloader/intern/writefile.c
@@ -1114,7 +1114,7 @@ static void write_pose(WriteData *wd, bPose *pose)
/* prevent crashes with autosave, when a bone duplicated in editmode has not yet been assigned to its posechannel */
if (chan->bone)
- chan->selectflag= chan->bone->flag & (BONE_SELECTED|BONE_ACTIVE); /* gets restored on read, for library armatures */
+ chan->selectflag= chan->bone->flag & BONE_SELECTED; /* gets restored on read, for library armatures */
writestruct(wd, DATA, "bPoseChannel", 1, chan);
}
diff --git a/source/blender/editors/armature/armature_intern.h b/source/blender/editors/armature/armature_intern.h
index d31a3bda332..012610bfd25 100644
--- a/source/blender/editors/armature/armature_intern.h
+++ b/source/blender/editors/armature/armature_intern.h
@@ -136,7 +136,7 @@ struct bArmature;
struct EditBone;
struct ListBase;
-void make_boneList(struct ListBase *edbo, struct ListBase *bones, struct EditBone *parent);
+EditBone *make_boneList(struct ListBase *edbo, struct ListBase *bones, struct EditBone *parent, struct Bone *actBone);
struct EditBone *addEditBone(struct bArmature *arm, char *name);
void BIF_sk_selectStroke(struct bContext *C, short mval[2], short extend);
diff --git a/source/blender/editors/armature/editarmature.c b/source/blender/editors/armature/editarmature.c
index c5b01f1cab0..6dad0b6e90f 100644
--- a/source/blender/editors/armature/editarmature.c
+++ b/source/blender/editors/armature/editarmature.c
@@ -129,10 +129,30 @@ void ED_armature_sync_selection(ListBase *edbo)
}
}
+void ED_armature_validate_active(struct bArmature *arm)
+{
+ EditBone *ebone= arm->act_edbone;
+
+ if(ebone) {
+ if(ebone->flag & BONE_HIDDEN_A || (ebone->flag & BONE_SELECTED)==0)
+ arm->act_edbone= NULL;
+ }
+}
+
+void free_edit_bone(bArmature *arm, EditBone *bone)
+{
+ if(arm->act_edbone==bone)
+ arm->act_edbone= NULL;
+
+ BLI_freelinkN(arm->edbo, bone);
+}
+
/* converts Bones to EditBone list, used for tools as well */
-void make_boneList(ListBase *edbo, ListBase *bones, EditBone *parent)
+EditBone *make_boneList(ListBase *edbo, ListBase *bones, EditBone *parent, Bone *actBone)
{
EditBone *eBone;
+ EditBone *eBoneAct= NULL;
+ EditBone *eBoneTest= NULL;
Bone *curBone;
float delta[3];
float premat[3][3];
@@ -194,9 +214,17 @@ void make_boneList(ListBase *edbo, ListBase *bones, EditBone *parent)
BLI_addtail(edbo, eBone);
/* Add children if necessary */
- if (curBone->childbase.first)
- make_boneList(edbo, &curBone->childbase, eBone);
+ if (curBone->childbase.first) {
+ eBoneTest= make_boneList(edbo, &curBone->childbase, eBone, actBone);
+ if(eBoneTest)
+ eBoneAct= eBoneTest;
+ }
+
+ if(curBone==actBone)
+ eBoneAct= eBone;
}
+
+ return eBoneAct;
}
/* nasty stuff for converting roll in editbones into bones */
@@ -270,7 +298,7 @@ void ED_armature_from_edit(Object *obedit)
fBone->parent= eBone->parent;
}
printf("Warning: removed zero sized bone: %s\n", eBone->name);
- BLI_freelinkN(arm->edbo, eBone);
+ free_edit_bone(arm, eBone);
}
}
@@ -283,8 +311,12 @@ void ED_armature_from_edit(Object *obedit)
memcpy(newBone->head, eBone->head, sizeof(float)*3);
memcpy(newBone->tail, eBone->tail, sizeof(float)*3);
newBone->flag= eBone->flag;
- if (eBone->flag & BONE_ACTIVE)
+
+ if (eBone == arm->act_edbone) {
newBone->flag |= BONE_SELECTED; /* important, editbones can be active with only 1 point selected */
+ arm->act_edbone= NULL;
+ arm->act_bone= newBone;
+ }
newBone->roll = 0.0f;
newBone->weight = eBone->weight;
@@ -997,7 +1029,7 @@ static void separate_armature_bones (Scene *scene, Object *ob, short sel)
free_constraints(&pchan->constraints);
/* get rid of unneeded bone */
- BLI_freelinkN(arm->edbo, curbone);
+ free_edit_bone(arm, curbone);
BLI_freelinkN(&ob->pose->chanbase, pchan);
}
}
@@ -1633,19 +1665,20 @@ static EditBone *get_nearest_editbonepoint (ViewContext *vc, short mval[2], List
return NULL;
}
-static void delete_bone(ListBase *edbo, EditBone* exBone)
+/* warning, wont clear the active bone */
+static void delete_bone(bArmature *arm, EditBone* exBone)
{
EditBone *curBone;
/* Find any bones that refer to this bone */
- for (curBone=edbo->first;curBone;curBone=curBone->next) {
+ for (curBone=arm->edbo->first; curBone; curBone=curBone->next) {
if (curBone->parent==exBone) {
curBone->parent=exBone->parent;
curBone->flag &= ~BONE_CONNECTED;
}
}
-
- BLI_freelinkN(edbo, exBone);
+
+ free_edit_bone(arm, exBone);
}
/* context: editmode armature */
@@ -1742,8 +1775,10 @@ static int armature_delete_selected_exec(bContext *C, wmOperator *op)
for (curBone=arm->edbo->first;curBone;curBone=next) {
next=curBone->next;
if (arm->layer & curBone->layer) {
- if (curBone->flag & BONE_SELECTED)
- delete_bone(arm->edbo, curBone);
+ if (curBone->flag & BONE_SELECTED) {
+ if(curBone==arm->act_edbone) arm->act_edbone= NULL;
+ delete_bone(arm, curBone);
+ }
}
}
@@ -1795,30 +1830,33 @@ void ED_armature_deselectall(Object *obedit, int toggle, int doundo)
}
else sel= toggle;
- /* Set the flags */
- for (eBone=arm->edbo->first;eBone;eBone=eBone->next) {
- if (sel==3) {
- /* invert selection of bone */
- if ((arm->layer & eBone->layer) && (eBone->flag & BONE_HIDDEN_A)==0) {
- eBone->flag ^= (BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
- eBone->flag &= ~BONE_ACTIVE;
+ if(sel==2) {
+ arm->act_edbone= NULL;
+ } else {
+ /* Set the flags */
+ for (eBone=arm->edbo->first;eBone;eBone=eBone->next) {
+ if (sel==3) {
+ /* invert selection of bone */
+ if ((arm->layer & eBone->layer) && (eBone->flag & BONE_HIDDEN_A)==0) {
+ eBone->flag ^= (BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
+ if(arm->act_edbone==eBone)
+ arm->act_edbone= NULL;
+ }
}
- }
- else if (sel==1) {
- /* select bone */
- if(arm->layer & eBone->layer && (eBone->flag & BONE_HIDDEN_A)==0) {
- eBone->flag |= (BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
- if(eBone->parent)
- eBone->parent->flag |= (BONE_TIPSEL);
+ else if (sel==1) {
+ /* select bone */
+ if(arm->layer & eBone->layer && (eBone->flag & BONE_HIDDEN_A)==0) {
+ eBone->flag |= (BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
+ if(eBone->parent)
+ eBone->parent->flag |= (BONE_TIPSEL);
+ }
+ }
+ else {
+ /* deselect bone */
+ eBone->flag &= ~(BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
+ if(arm->act_edbone==eBone)
+ arm->act_edbone= NULL;
}
- }
- else if (sel==2) {
- /* clear active flag */
- eBone->flag &= ~(BONE_ACTIVE);
- }
- else {
- /* deselect bone */
- eBone->flag &= ~(BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL | BONE_ACTIVE);
}
}
@@ -1836,7 +1874,7 @@ void mouse_armature(bContext *C, short mval[2], int extend)
Object *obedit= CTX_data_edit_object(C);
bArmature *arm= obedit->data;
ViewContext vc;
- EditBone *nearBone = NULL, *ebone;
+ EditBone *nearBone = NULL;
int selmask;
view3d_set_viewcontext(C, &vc);
@@ -1898,8 +1936,7 @@ void mouse_armature(bContext *C, short mval[2], int extend)
if(nearBone) {
/* then now check for active status */
- for (ebone=arm->edbo->first;ebone;ebone=ebone->next) ebone->flag &= ~BONE_ACTIVE;
- if(nearBone->flag & BONE_SELECTED) nearBone->flag |= BONE_ACTIVE;
+ if(nearBone->flag & BONE_SELECTED) arm->act_edbone= nearBone;
}
WM_event_add_notifier(C, NC_OBJECT|ND_BONE_SELECT, vc.obedit);
@@ -1945,7 +1982,8 @@ void ED_armature_to_edit(Object *ob)
ED_armature_edit_free(ob);
arm->edbo= MEM_callocN(sizeof(ListBase), "edbo armature");
- make_boneList(arm->edbo, &arm->bonebase,NULL);
+ arm->act_edbone= make_boneList(arm->edbo, &arm->bonebase, NULL, arm->act_bone);
+ arm->act_bone= NULL;
// BIF_freeTemplates(); /* force template update when entering editmode */
}
@@ -2103,68 +2141,84 @@ void ARMATURE_OT_calculate_roll(wmOperatorType *ot)
/* **************** undo for armatures ************** */
-static void undoBones_to_editBones(void *lbuv, void *lbev)
+typedef struct UndoArmature {
+ EditBone *act_edbone;
+ ListBase lb;
+} UndoArmature;
+
+static void undoBones_to_editBones(void *uarmv, void *armv)
{
- ListBase *lbu= lbuv;
- ListBase *edbo= lbev;
+ UndoArmature *uarm= uarmv;
+ bArmature *arm= armv;
EditBone *ebo, *newebo;
- BLI_freelistN(edbo);
+ BLI_freelistN(arm->edbo);
/* copy */
- for(ebo= lbu->first; ebo; ebo= ebo->next) {
+ for(ebo= uarm->lb.first; ebo; ebo= ebo->next) {
newebo= MEM_dupallocN(ebo);
ebo->temp= newebo;
- BLI_addtail(edbo, newebo);
+ BLI_addtail(arm->edbo, newebo);
}
+ /* active bone */
+ if(uarm->act_edbone) {
+ ebo= uarm->act_edbone;
+ arm->act_edbone= ebo->temp;
+ }
+
/* set pointers */
- for(newebo= edbo->first; newebo; newebo= newebo->next) {
+ for(newebo= arm->edbo->first; newebo; newebo= newebo->next) {
if(newebo->parent) newebo->parent= newebo->parent->temp;
}
/* be sure they dont hang ever */
- for(newebo= edbo->first; newebo; newebo= newebo->next) {
+ for(newebo= arm->edbo->first; newebo; newebo= newebo->next) {
newebo->temp= NULL;
}
}
-static void *editBones_to_undoBones(void *lbev)
+static void *editBones_to_undoBones(void *armv)
{
- ListBase *edbo= lbev;
- ListBase *lb;
+ bArmature *arm= armv;
+ UndoArmature *uarm;
EditBone *ebo, *newebo;
- lb= MEM_callocN(sizeof(ListBase), "listbase undo");
+ uarm= MEM_callocN(sizeof(UndoArmature), "listbase undo");
/* copy */
- for(ebo= edbo->first; ebo; ebo= ebo->next) {
+ for(ebo= arm->edbo->first; ebo; ebo= ebo->next) {
newebo= MEM_dupallocN(ebo);
ebo->temp= newebo;
- BLI_addtail(lb, newebo);
+ BLI_addtail(&uarm->lb, newebo);
}
+ /* active bone */
+ if(arm->act_edbone) {
+ ebo= arm->act_edbone;
+ uarm->act_edbone= ebo->temp;
+ }
+
/* set pointers */
- for(newebo= lb->first; newebo; newebo= newebo->next) {
+ for(newebo= uarm->lb.first; newebo; newebo= newebo->next) {
if(newebo->parent) newebo->parent= newebo->parent->temp;
}
- return lb;
+ return uarm;
}
-static void free_undoBones(void *lbv)
+static void free_undoBones(void *uarmv)
{
- ListBase *lb= lbv;
+ UndoArmature *uarm= uarmv;
- BLI_freelistN(lb);
- MEM_freeN(lb);
+ BLI_freelistN(&uarm->lb);
+ MEM_freeN(uarm);
}
static void *get_armature_edit(bContext *C)
{
Object *obedit= CTX_data_edit_object(C);
if(obedit && obedit->type==OB_ARMATURE) {
- bArmature *arm= obedit->data;
- return arm->edbo;
+ return obedit->data;
}
return NULL;
}
@@ -2270,7 +2324,7 @@ static int armature_click_extrude_exec(bContext *C, wmOperator *op)
/* find the active or selected bone */
for (ebone = arm->edbo->first; ebone; ebone=ebone->next) {
if (EBONE_VISIBLE(arm, ebone)) {
- if (ebone->flag & (BONE_ACTIVE|BONE_TIPSEL))
+ if (ebone->flag & BONE_TIPSEL || arm->act_edbone == ebone)
break;
}
}
@@ -2278,7 +2332,7 @@ static int armature_click_extrude_exec(bContext *C, wmOperator *op)
if (ebone==NULL) {
for (ebone = arm->edbo->first; ebone; ebone=ebone->next) {
if (EBONE_VISIBLE(arm, ebone)) {
- if (ebone->flag & (BONE_ACTIVE|BONE_ROOTSEL))
+ if (ebone->flag & BONE_ROOTSEL || arm->act_edbone == ebone)
break;
}
}
@@ -2305,7 +2359,7 @@ static int armature_click_extrude_exec(bContext *C, wmOperator *op)
}
newbone= add_editbone(obedit, ebone->name);
- newbone->flag |= BONE_ACTIVE;
+ arm->act_edbone= newbone;
if (to_root) {
VECCOPY(newbone->head, ebone->head);
@@ -2635,7 +2689,7 @@ static int armature_duplicate_selected_exec(bContext *C, wmOperator *op)
BLI_addtail(arm->edbo, eBone);
if (!firstDup)
firstDup=eBone;
-
+
/* Lets duplicate the list of constraints that the
* current bone has.
*/
@@ -2719,12 +2773,21 @@ static int armature_duplicate_selected_exec(bContext *C, wmOperator *op)
}
}
+ /* correct the active bone */
+ if(arm->act_edbone) {
+ eBone= arm->act_edbone;
+ if(eBone->temp)
+ arm->act_edbone= eBone->temp;
+ }
+
/* Deselect the old bones and select the new ones */
for (curBone=arm->edbo->first; curBone && curBone!=firstDup; curBone=curBone->next) {
if (EBONE_VISIBLE(arm, curBone))
- curBone->flag &= ~(BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL | BONE_ACTIVE);
+ curBone->flag &= ~(BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
}
+ ED_armature_validate_active(arm);
+
WM_event_add_notifier(C, NC_OBJECT|ND_BONE_SELECT, obedit);
return OPERATOR_FINISHED;
@@ -3046,13 +3109,13 @@ static void bones_merge(Object *obedit, EditBone *start, EditBone *end, EditBone
* - tail = head/tail of end (default tail)
* - parent = parent of start
*/
- if ((start->flag & BONE_TIPSEL) && !(start->flag & (BONE_SELECTED|BONE_ACTIVE))) {
+ if ((start->flag & BONE_TIPSEL) && ((start->flag & BONE_SELECTED) || start==arm->act_edbone)==0) {
VECCOPY(head, start->tail);
}
else {
VECCOPY(head, start->head);
}
- if ((end->flag & BONE_ROOTSEL) && !(end->flag & (BONE_SELECTED|BONE_ACTIVE))) {
+ if ((end->flag & BONE_ROOTSEL) && ((end->flag & BONE_SELECTED) || end==arm->act_edbone)==0) {
VECCOPY(tail, end->head);
}
else {
@@ -3090,7 +3153,7 @@ static void bones_merge(Object *obedit, EditBone *start, EditBone *end, EditBone
/* step 3: delete all bones between and including start and end */
for (ebo= end; ebo; ebo= ebone) {
ebone= (ebo == start) ? (NULL) : (ebo->parent);
- BLI_freelinkN(arm->edbo, ebo);
+ free_edit_bone(arm, ebo);
}
}
@@ -3130,7 +3193,7 @@ static int armature_merge_exec (bContext *C, wmOperator *op)
/* check if visible + selected */
if ( EBONE_VISIBLE(arm, ebo) &&
((ebo->flag & BONE_CONNECTED) || (ebo->parent==NULL)) &&
- (ebo->flag & (BONE_SELECTED|BONE_ACTIVE)) )
+ ((ebo->flag & BONE_SELECTED) || (ebo==arm->act_edbone)) )
{
/* set either end or start (end gets priority, unless it is already set) */
if (bend == NULL) {
@@ -3205,17 +3268,20 @@ void hide_selected_armature_bones(Scene *scene)
for (ebone = arm->edbo->first; ebone; ebone=ebone->next) {
if (EBONE_VISIBLE(arm, ebone)) {
- if (ebone->flag & (BONE_SELECTED)) {
- ebone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL|BONE_ACTIVE);
+ if (ebone->flag & BONE_SELECTED) {
+ ebone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL);
ebone->flag |= BONE_HIDDEN_A;
}
}
}
+ ED_armature_validate_active(arm);
ED_armature_sync_selection(arm->edbo);
BIF_undo_push("Hide Bones");
}
-void hide_unselected_armature_bones(Scene *scene)
+
+#if 0 // remove this?
+static void hide_unselected_armature_bones(Scene *scene)
{
Object *obedit= scene->obedit; // XXX get from context
bArmature *arm= obedit->data;
@@ -3226,15 +3292,18 @@ void hide_unselected_armature_bones(Scene *scene)
if (EBONE_VISIBLE(arm, ebone)) {
if (ebone->flag & (BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL));
else {
- ebone->flag &= ~BONE_ACTIVE;
ebone->flag |= BONE_HIDDEN_A;
}
}
}
+
+ ED_armature_validate_active(arm);
ED_armature_sync_selection(arm->edbo);
BIF_undo_push("Hide Unselected Bones");
}
+#endif
+#if 0 // remove this?
void show_all_armature_bones(Scene *scene)
{
Object *obedit= scene->obedit; // XXX get from context
@@ -3249,9 +3318,11 @@ void show_all_armature_bones(Scene *scene)
}
}
}
+ ED_armature_validate_active(arm);
ED_armature_sync_selection(arm->edbo);
BIF_undo_push("Reveal Bones");
}
+#endif
/* previously extrude_armature */
/* context; editmode armature */
@@ -3301,7 +3372,7 @@ static int armature_extrude_exec(bContext *C, wmOperator *op)
forked= 0; // we extrude 2 different bones
if (flipbone->flag & (BONE_TIPSEL|BONE_ROOTSEL|BONE_SELECTED))
/* don't want this bone to be selected... */
- flipbone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL|BONE_ACTIVE);
+ flipbone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL);
}
if ((flipbone==NULL) && (forked))
flipbone= ebone;
@@ -3373,14 +3444,17 @@ static int armature_extrude_exec(bContext *C, wmOperator *op)
}
/* Deselect the old bone */
- ebone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL|BONE_ACTIVE);
+ ebone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL);
}
}
/* if only one bone, make this one active */
- if (totbone==1 && first) first->flag |= BONE_ACTIVE;
+ if (totbone==1 && first) arm->act_edbone= first;
if (totbone==0) return OPERATOR_CANCELLED;
+ if(arm->act_edbone && (((EditBone *)arm->act_edbone)->flag & BONE_SELECTED)==0)
+ arm->act_edbone= NULL;
+
/* Transform the endpoints */
ED_armature_sync_selection(arm->edbo);
@@ -3965,7 +4039,6 @@ static int armature_select_inverse_exec(bContext *C, wmOperator *op)
if ((ebone->flag & BONE_UNSELECTABLE) == 0) {
/* select bone */
ebone->flag ^= (BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
- ebone->flag &= ~BONE_ACTIVE;
}
}
CTX_DATA_END;
@@ -4009,7 +4082,7 @@ static int armature_de_select_all_exec(bContext *C, wmOperator *op)
}
else {
/* deselect bone */
- ebone->flag &= ~(BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL | BONE_ACTIVE);
+ ebone->flag &= ~(BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
}
}
}
@@ -4053,17 +4126,17 @@ static int armature_select_hierarchy_exec(bContext *C, wmOperator *op)
for (curbone= arm->edbo->first; curbone; curbone= curbone->next) {
/* only work on bone if it is visible and its selection can change */
if (EBONE_VISIBLE(arm, curbone) && (curbone->flag & BONE_UNSELECTABLE)==0) {
- if (curbone->flag & (BONE_ACTIVE)) {
+ if (curbone == arm->act_edbone) {
if (direction == BONE_SELECT_PARENT) {
if (curbone->parent == NULL) continue;
else pabone = curbone->parent;
if (EBONE_VISIBLE(arm, pabone)) {
- pabone->flag |= (BONE_ACTIVE|BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
+ pabone->flag |= (BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
+ arm->act_edbone= pabone;
if (pabone->parent) pabone->parent->flag |= BONE_TIPSEL;
if (!add_to_sel) curbone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
- curbone->flag &= ~BONE_ACTIVE;
break;
}
@@ -4073,13 +4146,13 @@ static int armature_select_hierarchy_exec(bContext *C, wmOperator *op)
if (chbone == NULL) continue;
if (EBONE_VISIBLE(arm, chbone) && (chbone->flag & BONE_UNSELECTABLE)==0) {
- chbone->flag |= (BONE_ACTIVE|BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
+ chbone->flag |= (BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
+ arm->act_edbone= chbone;
if (!add_to_sel) {
curbone->flag &= ~(BONE_SELECTED|BONE_ROOTSEL);
if (curbone->parent) curbone->parent->flag &= ~BONE_TIPSEL;
}
- curbone->flag &= ~BONE_ACTIVE;
break;
}
}
@@ -4256,14 +4329,6 @@ void ARMATURE_OT_align(wmOperatorType *ot)
/* ***************** Pose tools ********************* */
-/* helper for function below */
-static int clear_active_flag(Object *ob, Bone *bone, void *data)
-{
- bone->flag &= ~BONE_ACTIVE;
- return 0;
-}
-
-
// XXX bone_looper is only to be used when we want to access settings (i.e. editability/visibility/selected) that context doesn't offer
static int bone_looper(Object *ob, Bone *bone, void *data,
int (*bone_func)(Object *, Bone *, void *))
@@ -4310,7 +4375,8 @@ int ED_do_pose_selectbuffer(Scene *scene, Base *base, unsigned int *buffer, shor
/* since we do unified select, we don't shift+select a bone if the armature object was not active yet */
if (!(extend) || (base != scene->basact)) {
ED_pose_deselectall(ob, 0, 0);
- nearBone->flag |= (BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL|BONE_ACTIVE);
+ nearBone->flag |= (BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
+ arm->act_bone= nearBone;
// XXX old cruft! use notifiers instead
//select_actionchannel_by_name(ob->action, nearBone->name, 1);
@@ -4318,21 +4384,19 @@ int ED_do_pose_selectbuffer(Scene *scene, Base *base, unsigned int *buffer, shor
else {
if (nearBone->flag & BONE_SELECTED) {
/* if not active, we make it active */
- if((nearBone->flag & BONE_ACTIVE)==0) {
- bone_looper(ob, arm->bonebase.first, NULL, clear_active_flag);
- nearBone->flag |= BONE_ACTIVE;
+ if(nearBone != arm->act_bone) {
+ arm->act_bone= nearBone;
}
else {
- nearBone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL|BONE_ACTIVE);
+ nearBone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
// XXX old cruft! use notifiers instead
//select_actionchannel_by_name(ob->action, nearBone->name, 0);
}
}
else {
- bone_looper(ob, arm->bonebase.first, NULL, clear_active_flag);
-
- nearBone->flag |= (BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL|BONE_ACTIVE);
+ nearBone->flag |= (BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
+ arm->act_bone= nearBone;
// XXX old cruft! use notifiers instead
//select_actionchannel_by_name(ob->action, nearBone->name, 1);
@@ -4341,7 +4405,7 @@ int ED_do_pose_selectbuffer(Scene *scene, Base *base, unsigned int *buffer, shor
/* in weightpaint we select the associated vertex group too */
if (OBACT && OBACT->mode & OB_MODE_WEIGHT_PAINT) {
- if (nearBone->flag & BONE_ACTIVE) {
+ if (nearBone == arm->act_bone) {
ED_vgroup_select_by_name(OBACT, nearBone->name);
DAG_id_flush_update(&OBACT->id, OB_RECALC_DATA);
}
@@ -4387,16 +4451,17 @@ void ED_pose_deselectall (Object *ob, int test, int doundo)
if ((pchan->bone->layer & arm->layer) && !(pchan->bone->flag & (BONE_HIDDEN_P|BONE_UNSELECTABLE))) {
if (test==3) {
pchan->bone->flag ^= (BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
- pchan->bone->flag &= ~BONE_ACTIVE;
}
else {
- if (selectmode==0) pchan->bone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL|BONE_ACTIVE);
+ if (selectmode==0) pchan->bone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
else if (selectmode==1) pchan->bone->flag |= BONE_SELECTED;
- else pchan->bone->flag &= ~BONE_ACTIVE;
}
}
}
+ if(arm->act_bone && (arm->act_bone->flag & BONE_SELECTED)==0)
+ arm->act_bone= NULL;
+
//countall(); // XXX need an equivalent to this...
if (doundo) {
@@ -4990,7 +5055,6 @@ static int pose_select_inverse_exec(bContext *C, wmOperator *op)
CTX_DATA_BEGIN(C, bPoseChannel *, pchan, visible_pchans) {
if ((pchan->bone->flag & BONE_UNSELECTABLE) == 0) {
pchan->bone->flag ^= (BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
- pchan->bone->flag &= ~BONE_ACTIVE;
}
}
CTX_DATA_END;
@@ -5026,12 +5090,13 @@ static int pose_de_select_all_exec(bContext *C, wmOperator *op)
/* Set the flags */
CTX_DATA_BEGIN(C, bPoseChannel *, pchan, visible_pchans) {
/* select pchan only if selectable, but deselect works always */
- if (sel==0)
- pchan->bone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL|BONE_ACTIVE);
+ if (sel==0) {
+ pchan->bone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
+ }
else if ((pchan->bone->flag & BONE_UNSELECTABLE)==0)
pchan->bone->flag |= BONE_SELECTED;
}
- CTX_DATA_END;
+ CTX_DATA_END;
WM_event_add_notifier(C, NC_OBJECT|ND_BONE_SELECT, NULL);
@@ -5062,11 +5127,11 @@ static int pose_select_parent_exec(bContext *C, wmOperator *op)
/* Determine if there is an active bone */
pchan=CTX_data_active_pchan(C);
if (pchan) {
+ bArmature *arm= ob->data;
parent=pchan->parent;
if ((parent) && !(parent->bone->flag & (BONE_HIDDEN_P|BONE_UNSELECTABLE))) {
parent->bone->flag |= BONE_SELECTED;
- parent->bone->flag |= BONE_ACTIVE;
- pchan->bone->flag &= ~BONE_ACTIVE;
+ arm->act_bone= parent->bone;
}
else {
return OPERATOR_CANCELLED;
@@ -5105,7 +5170,8 @@ static int hide_selected_pose_bone(Object *ob, Bone *bone, void *ptr)
if (arm->layer & bone->layer) {
if (bone->flag & BONE_SELECTED) {
bone->flag |= BONE_HIDDEN_P;
- bone->flag &= ~(BONE_SELECTED|BONE_ACTIVE);
+ if(arm->act_bone==bone)
+ arm->act_bone= NULL;
}
}
return 0;
@@ -5117,9 +5183,10 @@ static int hide_unselected_pose_bone(Object *ob, Bone *bone, void *ptr)
if (arm->layer & bone->layer) {
// hrm... typo here?
- if (~bone->flag & BONE_SELECTED) {
+ if ((bone->flag & BONE_SELECTED)==0) {
bone->flag |= BONE_HIDDEN_P;
- bone->flag &= ~BONE_ACTIVE;
+ if(arm->act_bone==bone)
+ arm->act_bone= NULL;
}
}
return 0;
@@ -5576,7 +5643,8 @@ EditBone * subdivideByAngle(Scene *scene, Object *obedit, ReebArc *arc, ReebNode
* */
if (parent == root)
{
- delete_bone(arm->edbo, parent);
+ if(parent==arm->act_edbone) arm->act_edbone= NULL;
+ delete_bone(arm, parent);
parent = NULL;
}
diff --git a/source/blender/editors/armature/editarmature_retarget.c b/source/blender/editors/armature/editarmature_retarget.c
index 4d65059c4c6..824e7be94d9 100644
--- a/source/blender/editors/armature/editarmature_retarget.c
+++ b/source/blender/editors/armature/editarmature_retarget.c
@@ -509,7 +509,7 @@ static RigControl *cloneControl(RigGraph *rg, RigGraph *src_rg, RigControl *src_
renameTemplateBone(name, src_ctrl->bone->name, rg->editbones, side_string, num_string);
ctrl->bone = duplicateEditBoneObjects(src_ctrl->bone, name, rg->editbones, src_rg->ob, rg->ob);
- ctrl->bone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL|BONE_ACTIVE);
+ ctrl->bone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL);
BLI_ghash_insert(ptr_hash, src_ctrl->bone, ctrl->bone);
ctrl->link = src_ctrl->link;
@@ -554,7 +554,7 @@ static RigArc *cloneArc(RigGraph *rg, RigGraph *src_rg, RigArc *src_arc, GHash *
char name[32];
renameTemplateBone(name, src_edge->bone->name, rg->editbones, side_string, num_string);
edge->bone = duplicateEditBoneObjects(src_edge->bone, name, rg->editbones, src_rg->ob, rg->ob);
- edge->bone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL|BONE_ACTIVE);
+ edge->bone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL);
BLI_ghash_insert(ptr_hash, src_edge->bone, edge->bone);
}
@@ -1555,7 +1555,7 @@ RigGraph *RIG_graphFromArmature(const bContext *C, Object *ob, bArmature *arm)
else
{
rg->editbones = MEM_callocN(sizeof(ListBase), "EditBones");
- make_boneList(rg->editbones, &arm->bonebase, NULL);
+ make_boneList(rg->editbones, &arm->bonebase, NULL, NULL);
rg->flag |= RIG_FREE_BONELIST;
}
@@ -1607,7 +1607,7 @@ RigGraph *armatureSelectedToGraph(bContext *C, Object *ob, bArmature *arm)
else
{
rg->editbones = MEM_callocN(sizeof(ListBase), "EditBones");
- make_boneList(rg->editbones, &arm->bonebase, NULL);
+ make_boneList(rg->editbones, &arm->bonebase, NULL, NULL);
rg->flag |= RIG_FREE_BONELIST;
}
@@ -2947,6 +2947,8 @@ void BIF_retargetArc(bContext *C, ReebArc *earc, RigGraph *template_rigg)
}
RIG_freeRigGraph((BGraph*)rigg);
+ ED_armature_validate_active(armedit);
+
// XXX
// allqueue(REDRAWVIEW3D, 0);
}
diff --git a/source/blender/editors/armature/poselib.c b/source/blender/editors/armature/poselib.c
index f67c94eebc3..565a4782377 100644
--- a/source/blender/editors/armature/poselib.c
+++ b/source/blender/editors/armature/poselib.c
@@ -382,7 +382,7 @@ static int poselib_add_exec (bContext *C, wmOperator *op)
for (pchan= pose->chanbase.first; pchan; pchan= pchan->next) {
/* check if available */
if ((pchan->bone) && (arm->layer & pchan->bone->layer)) {
- if (pchan->bone->flag & (BONE_SELECTED|BONE_ACTIVE)) {
+ if (pchan->bone->flag & BONE_SELECTED || pchan->bone==arm->act_bone) {
/* init cks for this PoseChannel, then use the relative KeyingSets to keyframe it */
cks.pchan= pchan;
@@ -762,7 +762,7 @@ static void poselib_apply_pose (tPoseLib_PreviewData *pld)
}
else if (pchan->bone) {
/* only ok if bone is visible and selected */
- if ( (pchan->bone->flag & (BONE_SELECTED|BONE_ACTIVE)) &&
+ if ( (pchan->bone->flag & BONE_SELECTED || pchan->bone == arm->act_bone) &&
(pchan->bone->flag & BONE_HIDDEN_P)==0 &&
(pchan->bone->layer & arm->layer) )
ok = 1;
diff --git a/source/blender/editors/armature/poseobject.c b/source/blender/editors/armature/poseobject.c
index 696fa65b33a..d7741c2a5ef 100644
--- a/source/blender/editors/armature/poseobject.c
+++ b/source/blender/editors/armature/poseobject.c
@@ -158,12 +158,12 @@ static short pose_has_protected_selected(Object *ob, short only_selected, short
if (ob->proxy) {
bPoseChannel *pchan;
bArmature *arm= ob->data;
-
+
for (pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
if (pchan->bone && (pchan->bone->layer & arm->layer)) {
if (pchan->bone->layer & arm->layer_protected) {
- if (only_selected && (pchan->bone->flag & BONE_ACTIVE));
- else if (pchan->bone->flag & (BONE_ACTIVE|BONE_SELECTED))
+ if (only_selected && (pchan->bone == arm->act_bone));
+ else if (pchan->bone->flag & BONE_SELECTED || pchan->bone == arm->act_bone)
break;
}
}
@@ -531,7 +531,7 @@ void pose_select_constraint_target(Scene *scene)
for(pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
if (arm->layer & pchan->bone->layer) {
- if (pchan->bone->flag & (BONE_ACTIVE|BONE_SELECTED)) {
+ if (pchan->bone->flag & BONE_SELECTED || pchan->bone == arm->act_bone) {
for (con= pchan->constraints.first; con; con= con->next) {
bConstraintTypeInfo *cti= constraint_get_typeinfo(con);
ListBase targets = {NULL, NULL};
@@ -570,7 +570,7 @@ static int pose_select_constraint_target_exec(bContext *C, wmOperator *op)
for(pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
if (arm->layer & pchan->bone->layer) {
- if (pchan->bone->flag & (BONE_ACTIVE|BONE_SELECTED)) {
+ if (pchan->bone->flag & BONE_SELECTED || pchan->bone == arm->act_bone) {
for (con= pchan->constraints.first; con; con= con->next) {
bConstraintTypeInfo *cti= constraint_get_typeinfo(con);
ListBase targets = {NULL, NULL};
@@ -635,7 +635,7 @@ static int pose_select_hierarchy_exec(bContext *C, wmOperator *op)
curbone= pchan->bone;
if ((arm->layer & curbone->layer) && (curbone->flag & BONE_UNSELECTABLE)==0) {
- if (curbone->flag & (BONE_ACTIVE)) {
+ if (curbone == arm->act_bone) {
if (direction == BONE_SELECT_PARENT) {
if (pchan->parent == NULL) continue;
@@ -644,8 +644,8 @@ static int pose_select_hierarchy_exec(bContext *C, wmOperator *op)
if ((arm->layer & pabone->layer) && !(pabone->flag & BONE_HIDDEN_P)) {
if (!add_to_sel) curbone->flag &= ~BONE_SELECTED;
- curbone->flag &= ~BONE_ACTIVE;
- pabone->flag |= (BONE_ACTIVE|BONE_SELECTED);
+ pabone->flag |= BONE_SELECTED;
+ arm->act_bone= pabone;
found= 1;
break;
@@ -658,8 +658,8 @@ static int pose_select_hierarchy_exec(bContext *C, wmOperator *op)
if ((arm->layer & chbone->layer) && !(chbone->flag & BONE_HIDDEN_P)) {
if (!add_to_sel) curbone->flag &= ~BONE_SELECTED;
- curbone->flag &= ~BONE_ACTIVE;
- chbone->flag |= (BONE_ACTIVE|BONE_SELECTED);
+ chbone->flag |= BONE_SELECTED;
+ arm->act_bone= chbone;
found= 1;
break;
@@ -717,11 +717,7 @@ void pose_copy_menu(Scene *scene)
if (ELEM(NULL, ob, ob->pose)) return;
if ((ob==obedit) || (ob->mode & OB_MODE_POSE)==0) return;
- /* find active */
- for (pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
- if (pchan->bone->flag & BONE_ACTIVE)
- break;
- }
+ pchan= get_active_posechannel(ob);
if (pchan==NULL) return;
pchanact= pchan;
@@ -1397,7 +1393,7 @@ static int pose_group_unassign_exec (bContext *C, wmOperator *op)
/* ensure that PoseChannel is on visible layer and is not hidden in PoseMode */
// NOTE: sync this view3d_context() in space_view3d.c
if ((pchan->bone) && (arm->layer & pchan->bone->layer) && !(pchan->bone->flag & BONE_HIDDEN_P)) {
- if (pchan->bone->flag & (BONE_SELECTED|BONE_ACTIVE)) {
+ if (pchan->bone->flag & BONE_SELECTED || pchan->bone == arm->act_bone) {
if (pchan->agrp_index) {
pchan->agrp_index= 0;
done= 1;
@@ -1444,7 +1440,7 @@ static short pose_select_same_group (Object *ob)
/* loop in loop... bad and slow! */
for (pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
if (arm->layer & pchan->bone->layer) {
- if (pchan->bone->flag & (BONE_ACTIVE|BONE_SELECTED)) {
+ if (pchan->bone->flag & BONE_SELECTED || pchan->bone == arm->act_bone) {
/* only if group matches (and is not selected or current bone) */
for (chan= ob->pose->chanbase.first; chan; chan= chan->next) {
@@ -1476,7 +1472,7 @@ static short pose_select_same_layer (Object *ob)
/* figure out what bones are selected */
for (pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
if (arm->layer & pchan->bone->layer) {
- if (pchan->bone->flag & (BONE_ACTIVE|BONE_SELECTED)) {
+ if (pchan->bone->flag & BONE_SELECTED || pchan->bone == arm->act_bone) {
layers |= pchan->bone->layer;
}
}
@@ -1637,25 +1633,21 @@ void pose_activate_flipped_bone(Scene *scene)
ob= modifiers_isDeformedByArmature(ob);
}
if(ob && (ob->mode & OB_MODE_POSE)) {
- bPoseChannel *pchan, *pchanf;
+ bPoseChannel *pchanf;
- for(pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
- if(arm->layer & pchan->bone->layer) {
- if(pchan->bone->flag & BONE_ACTIVE)
- break;
- }
- }
- if(pchan) {
+ if(arm->act_bone) {
char name[32];
- BLI_strncpy(name, pchan->name, 32);
+ BLI_strncpy(name, arm->act_bone->name, 32);
bone_flip_name(name, 1); // 0 = do not strip off number extensions
pchanf= get_pose_channel(ob->pose, name);
- if(pchanf && pchanf!=pchan) {
- pchan->bone->flag &= ~(BONE_SELECTED|BONE_ACTIVE);
- pchanf->bone->flag |= (BONE_SELECTED|BONE_ACTIVE);
-
+ if(pchanf && pchanf->bone != arm->act_bone) {
+ arm->act_bone->flag &= ~BONE_SELECTED;
+ pchanf->bone->flag |= BONE_SELECTED;
+
+ arm->act_bone= pchanf->bone;
+
/* in weightpaint we select the associated vertex group too */
if(ob->mode & OB_MODE_WEIGHT_PAINT) {
ED_vgroup_select_by_name(OBACT, name);
diff --git a/source/blender/editors/include/ED_armature.h b/source/blender/editors/include/ED_armature.h
index 5cc35d4ad77..1836729e419 100644
--- a/source/blender/editors/include/ED_armature.h
+++ b/source/blender/editors/include/ED_armature.h
@@ -113,6 +113,7 @@ struct Bone *get_indexed_bone (struct Object *ob, int index);
float ED_rollBoneToVector(EditBone *bone, float new_up_axis[3]);
EditBone *ED_armature_bone_get_mirrored(struct ListBase *edbo, EditBone *ebo); // XXX this is needed for populating the context iterators
void ED_armature_sync_selection(struct ListBase *edbo);
+void ED_armature_validate_active(struct bArmature *arm);
void add_primitive_bone(struct Scene *scene, struct View3D *v3d, struct RegionView3D *rv3d);
EditBone *addEditBone(struct bArmature *arm, char *name); /* used by COLLADA importer */
diff --git a/source/blender/editors/screen/screen_context.c b/source/blender/editors/screen/screen_context.c
index 919cc3f0cfd..c02d86a567e 100644
--- a/source/blender/editors/screen/screen_context.c
+++ b/source/blender/editors/screen/screen_context.c
@@ -215,7 +215,7 @@ int ed_screen_context(const bContext *C, const char *member, bContextDataResult
for (pchan= obact->pose->chanbase.first; pchan; pchan= pchan->next) {
/* ensure that PoseChannel is on visible layer and is not hidden in PoseMode */
if ((pchan->bone) && (arm->layer & pchan->bone->layer) && !(pchan->bone->flag & BONE_HIDDEN_P)) {
- if (pchan->bone->flag & (BONE_SELECTED|BONE_ACTIVE))
+ if (pchan->bone->flag & BONE_SELECTED || pchan->bone == arm->act_bone)
CTX_data_list_add(result, &obact->id, &RNA_PoseChannel, pchan);
}
}
@@ -224,21 +224,19 @@ int ed_screen_context(const bContext *C, const char *member, bContextDataResult
}
}
else if(CTX_data_equals(member, "active_bone")) {
- bArmature *arm= (obedit) ? obedit->data : NULL;
- EditBone *ebone;
-
- if (arm && arm->edbo) {
- for (ebone= arm->edbo->first; ebone; ebone= ebone->next) {
- if (EBONE_VISIBLE(arm, ebone)) {
- if (ebone->flag & BONE_ACTIVE) {
- CTX_data_pointer_set(result, &arm->id, &RNA_EditBone, ebone);
-
- return 1;
- }
- }
+ bArmature *arm= (obact) ? obact->data : NULL;
+ if(arm->edbo) {
+ if(arm->act_edbone) {
+ CTX_data_pointer_set(result, &arm->id, &RNA_EditBone, arm->act_edbone);
+ return 1;
+ }
+ }
+ else {
+ if(arm->act_bone) {
+ CTX_data_pointer_set(result, &arm->id, &RNA_Bone, arm->act_bone);
+ return 1;
}
}
-
}
else if(CTX_data_equals(member, "active_pchan")) {
bPoseChannel *pchan;
diff --git a/source/blender/editors/sculpt_paint/paint_vertex.c b/source/blender/editors/sculpt_paint/paint_vertex.c
index 408f4862b6f..2045397f3c9 100644
--- a/source/blender/editors/sculpt_paint/paint_vertex.c
+++ b/source/blender/editors/sculpt_paint/paint_vertex.c
@@ -1104,12 +1104,10 @@ static int set_wpaint(bContext *C, wmOperator *op) /* toggle */
/* verify if active weight group is also active bone */
par= modifiers_isDeformedByArmature(ob);
if(par && (par->mode & OB_MODE_POSE)) {
- bPoseChannel *pchan;
- for(pchan= par->pose->chanbase.first; pchan; pchan= pchan->next)
- if(pchan->bone->flag & BONE_ACTIVE)
- break;
- if(pchan)
- ED_vgroup_select_by_name(ob, pchan->name);
+ bArmature *arm= ob->data;
+
+ if(arm->act_bone)
+ ED_vgroup_select_by_name(ob, arm->act_bone->name);
}
}
else {
diff --git a/source/blender/editors/space_buttons/buttons_context.c b/source/blender/editors/space_buttons/buttons_context.c
index 026498f17af..47055851e03 100644
--- a/source/blender/editors/space_buttons/buttons_context.c
+++ b/source/blender/editors/space_buttons/buttons_context.c
@@ -243,26 +243,9 @@ static int buttons_context_path_material(ButsContextPath *path)
return 0;
}
-static Bone *find_active_bone(Bone *bone)
-{
- Bone *active;
-
- for(; bone; bone=bone->next) {
- if(bone->flag & BONE_ACTIVE)
- return bone;
-
- active= find_active_bone(bone->childbase.first);
- if(active)
- return active;
- }
-
- return NULL;
-}
-
static int buttons_context_path_bone(ButsContextPath *path)
{
bArmature *arm;
- Bone *bone;
EditBone *edbo;
/* if we have an armature, get the active bone */
@@ -270,19 +253,16 @@ static int buttons_context_path_bone(ButsContextPath *path)
arm= path->ptr[path->len-1].data;
if(arm->edbo) {
- for(edbo=arm->edbo->first; edbo; edbo=edbo->next) {
- if(edbo->flag & BONE_ACTIVE) {
- RNA_pointer_create(&arm->id, &RNA_EditBone, edbo, &path->ptr[path->len]);
- path->len++;
- return 1;
- }
+ if(arm->act_edbone) {
+ edbo= arm->act_edbone;
+ RNA_pointer_create(&arm->id, &RNA_EditBone, edbo, &path->ptr[path->len]);
+ path->len++;
+ return 1;
}
}
else {
- bone= find_active_bone(arm->bonebase.first);
-
- if(bone) {
- RNA_pointer_create(&arm->id, &RNA_Bone, bone, &path->ptr[path->len]);
+ if(arm->act_bone) {
+ RNA_pointer_create(&arm->id, &RNA_Bone, arm->act_bone, &path->ptr[path->len]);
path->len++;
return 1;
}
diff --git a/source/blender/editors/space_outliner/outliner.c b/source/blender/editors/space_outliner/outliner.c
index bc203a9c80b..39eecd7d2de 100644
--- a/source/blender/editors/space_outliner/outliner.c
+++ b/source/blender/editors/space_outliner/outliner.c
@@ -2025,6 +2025,7 @@ static int tree_element_active_posegroup(bContext *C, Scene *scene, TreeElement
static int tree_element_active_posechannel(bContext *C, Scene *scene, TreeElement *te, TreeStoreElem *tselem, int set)
{
Object *ob= (Object *)tselem->id;
+ bArmature *arm= ob->data;
bPoseChannel *pchan= te->directdata;
if(set) {
@@ -2033,10 +2034,14 @@ static int tree_element_active_posechannel(bContext *C, Scene *scene, TreeElemen
if(set==2) ED_pose_deselectall(ob, 2, 0); // 2 = clear active tag
else ED_pose_deselectall(ob, 0, 0); // 0 = deselect
- if(set==2 && (pchan->bone->flag & BONE_SELECTED))
- pchan->bone->flag &= ~(BONE_SELECTED|BONE_ACTIVE);
- else
- pchan->bone->flag |= BONE_SELECTED|BONE_ACTIVE;
+ if(set==2 && (pchan->bone->flag & BONE_SELECTED)) {
+ pchan->bone->flag &= ~BONE_SELECTED;
+ if(arm->act_bone==pchan->bone)
+ arm->act_bone= NULL;
+ } else {
+ pchan->bone->flag |= BONE_SELECTED;
+ arm->act_bone= pchan->bone;
+ }
WM_event_add_notifier(C, NC_OBJECT|ND_BONE_ACTIVE, ob);
@@ -2060,10 +2065,14 @@ static int tree_element_active_bone(bContext *C, Scene *scene, TreeElement *te,
if(set==2) ED_pose_deselectall(OBACT, 2, 0); // 2 is clear active tag
else ED_pose_deselectall(OBACT, 0, 0);
- if(set==2 && (bone->flag & BONE_SELECTED))
- bone->flag &= ~(BONE_SELECTED|BONE_ACTIVE);
- else
- bone->flag |= BONE_SELECTED|BONE_ACTIVE;
+ if(set==2 && (bone->flag & BONE_SELECTED)) {
+ bone->flag &= ~BONE_SELECTED;
+ if(arm->act_bone==bone)
+ arm->act_bone= NULL;
+ } else {
+ bone->flag |= BONE_SELECTED;
+ arm->act_bone= bone;
+ }
WM_event_add_notifier(C, NC_OBJECT|ND_BONE_ACTIVE, OBACT);
}
@@ -2086,11 +2095,13 @@ static int tree_element_active_ebone(bContext *C, Scene *scene, TreeElement *te,
if(set) {
if(!(ebone->flag & BONE_HIDDEN_A)) {
-
+ bArmature *arm= scene->obedit->data;
if(set==2) ED_armature_deselectall(scene->obedit, 2, 0); // only clear active tag
else ED_armature_deselectall(scene->obedit, 0, 0); // deselect
- ebone->flag |= BONE_SELECTED|BONE_ROOTSEL|BONE_TIPSEL|BONE_ACTIVE;
+ ebone->flag |= BONE_SELECTED|BONE_ROOTSEL|BONE_TIPSEL;
+ arm->act_edbone= ebone;
+
// flush to parent?
if(ebone->parent && (ebone->flag & BONE_CONNECTED)) ebone->parent->flag |= BONE_TIPSEL;
diff --git a/source/blender/editors/space_view3d/drawarmature.c b/source/blender/editors/space_view3d/drawarmature.c
index 656d7061d48..230bacf4f7f 100644
--- a/source/blender/editors/space_view3d/drawarmature.c
+++ b/source/blender/editors/space_view3d/drawarmature.c
@@ -166,7 +166,7 @@ static short set_pchan_glColor (short colCode, int armflag, int boneflag, int co
if (bcolor) {
char cp[3];
- if (boneflag & BONE_ACTIVE) {
+ if (boneflag & BONE_DRAW_ACTIVE) {
VECCOPY(cp, bcolor->active);
}
else if (boneflag & BONE_SELECTED) {
@@ -181,7 +181,7 @@ static short set_pchan_glColor (short colCode, int armflag, int boneflag, int co
glColor3ub(cp[0], cp[1], cp[2]);
}
else {
- if (boneflag & BONE_ACTIVE) UI_ThemeColorShade(TH_BONE_POSE, 40);
+ if (boneflag & BONE_DRAW_ACTIVE) UI_ThemeColorShade(TH_BONE_POSE, 40);
else if (boneflag & BONE_SELECTED) UI_ThemeColor(TH_BONE_POSE);
else UI_ThemeColor(TH_WIRE);
}
@@ -225,7 +225,7 @@ static short set_pchan_glColor (short colCode, int armflag, int boneflag, int co
if (bcolor) {
char cp[3];
- if (boneflag & BONE_ACTIVE) {
+ if (boneflag & BONE_DRAW_ACTIVE) {
VECCOPY(cp, bcolor->active);
}
else if (boneflag & BONE_SELECTED) {
@@ -238,7 +238,7 @@ static short set_pchan_glColor (short colCode, int armflag, int boneflag, int co
glColor3ub(cp[0], cp[1], cp[2]);
}
else {
- if (boneflag & BONE_ACTIVE) UI_ThemeColorShade(TH_BONE_POSE, 40);
+ if (boneflag & BONE_DRAW_ACTIVE) UI_ThemeColorShade(TH_BONE_POSE, 40);
else if (boneflag & BONE_SELECTED) UI_ThemeColor(TH_BONE_POSE);
else UI_ThemeColor(TH_BONE_SOLID);
}
@@ -251,7 +251,7 @@ static short set_pchan_glColor (short colCode, int armflag, int boneflag, int co
if (bcolor) {
char cp[3];
- if (boneflag & BONE_ACTIVE) {
+ if (boneflag & BONE_DRAW_ACTIVE) {
VECCOPY(cp, bcolor->active);
cp_shade_color3ub(cp, 10);
}
@@ -267,7 +267,7 @@ static short set_pchan_glColor (short colCode, int armflag, int boneflag, int co
glColor3ub(cp[0], cp[1], cp[2]);
}
else {
- if (boneflag & BONE_ACTIVE) UI_ThemeColorShade(TH_BONE_POSE, 10);
+ if (boneflag & BONE_DRAW_ACTIVE) UI_ThemeColorShade(TH_BONE_POSE, 10);
else if (boneflag & BONE_SELECTED) UI_ThemeColorShade(TH_BONE_POSE, -30);
else UI_ThemeColorShade(TH_BONE_SOLID, -30);
}
@@ -1151,7 +1151,7 @@ static void draw_b_bone(int dt, int armflag, int boneflag, int constflag, unsign
}
else if (armflag & ARM_EDITMODE) {
if (dt==OB_WIRE) {
- if (boneflag & BONE_ACTIVE) UI_ThemeColor(TH_EDGE_SELECT);
+ if (boneflag & BONE_DRAW_ACTIVE) UI_ThemeColor(TH_EDGE_SELECT);
else if (boneflag & BONE_SELECTED) UI_ThemeColorShade(TH_EDGE_SELECT, -20);
else UI_ThemeColor(TH_WIRE);
}
@@ -1236,7 +1236,7 @@ static void draw_bone(int dt, int armflag, int boneflag, int constflag, unsigned
if (dt <= OB_WIRE) {
/* colors */
if (armflag & ARM_EDITMODE) {
- if (boneflag & BONE_ACTIVE) UI_ThemeColor(TH_EDGE_SELECT);
+ if (boneflag & BONE_DRAW_ACTIVE) UI_ThemeColor(TH_EDGE_SELECT);
else if (boneflag & BONE_SELECTED) UI_ThemeColorShade(TH_EDGE_SELECT, -20);
else UI_ThemeColor(TH_WIRE);
}
@@ -1629,7 +1629,10 @@ static void draw_pose_channels(Scene *scene, View3D *v3d, ARegion *ar, Base *bas
flag= bone->flag;
if ( (bone->parent) && (bone->parent->flag & (BONE_HIDDEN_P|BONE_HIDDEN_PG)) )
flag &= ~BONE_CONNECTED;
-
+
+ if(bone==arm->act_bone)
+ flag |= BONE_DRAW_ACTIVE;
+
/* set color-set to use */
set_pchan_colorset(ob, pchan);
diff --git a/source/blender/editors/space_view3d/view3d_buttons.c b/source/blender/editors/space_view3d/view3d_buttons.c
index 2edccacff7a..608a22ea529 100644
--- a/source/blender/editors/space_view3d/view3d_buttons.c
+++ b/source/blender/editors/space_view3d/view3d_buttons.c
@@ -575,22 +575,15 @@ static void v3d_transform_butsR(uiLayout *layout, PointerRNA *ptr)
static void v3d_posearmature_buts(uiLayout *layout, View3D *v3d, Object *ob, float lim)
{
// uiBlock *block= uiLayoutGetBlock(layout);
- bArmature *arm;
+// bArmature *arm;
bPoseChannel *pchan;
- Bone *bone= NULL;
// TransformProperties *tfp= v3d->properties_storage;
PointerRNA pchanptr;
uiLayout *col;
// uiLayout *row;
- arm = ob->data;
- if (!arm || !ob->pose) return;
+ pchan= get_active_posechannel(ob);
- for(pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
- bone = pchan->bone;
- if(bone && (bone->flag & BONE_ACTIVE) && (bone->layer & arm->layer))
- break;
- }
// row= uiLayoutRow(layout, 0);
if (!pchan) {
@@ -691,14 +684,9 @@ static void v3d_editarmature_buts(uiLayout *layout, View3D *v3d, Object *ob, flo
uiLayout *col;
PointerRNA eboneptr;
- ebone= arm->edbo->first;
+ ebone= arm->act_edbone;
- for (ebone = arm->edbo->first; ebone; ebone=ebone->next){
- if ((ebone->flag & BONE_ACTIVE) && (ebone->layer & arm->layer))
- break;
- }
-
- if (!ebone)
+ if (!ebone || (ebone->layer & arm->layer)==0)
return;
// row= uiLayoutRow(layout, 0);
@@ -821,19 +809,10 @@ static void do_view3d_region_buttons(bContext *C, void *arg, int event)
case B_ARMATUREPANEL3: // rotate button on channel
{
- bArmature *arm;
bPoseChannel *pchan;
- Bone *bone;
float eul[3];
- arm = ob->data;
- if (!arm || !ob->pose) return;
-
- for(pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
- bone = pchan->bone;
- if(bone && (bone->flag & BONE_ACTIVE) && (bone->layer & arm->layer))
- break;
- }
+ pchan= get_active_posechannel(ob);
if (!pchan) return;
/* make a copy to eul[3], to allow TAB on buttons to work */
diff --git a/source/blender/editors/space_view3d/view3d_draw.c b/source/blender/editors/space_view3d/view3d_draw.c
index 247800c3077..2879dc3ed22 100644
--- a/source/blender/editors/space_view3d/view3d_draw.c
+++ b/source/blender/editors/space_view3d/view3d_draw.c
@@ -791,21 +791,17 @@ static void draw_selected_name(Scene *scene, Object *ob, View3D *v3d)
/* show name of active bone too (if possible) */
if(arm->edbo) {
- EditBone *ebo;
- for (ebo=arm->edbo->first; ebo; ebo=ebo->next){
- if ((ebo->flag & BONE_ACTIVE) && (ebo->layer & arm->layer)) {
- name= ebo->name;
- break;
- }
- }
+
+ if(arm->act_edbone)
+ name= ((EditBone *)arm->act_edbone)->name;
+
}
- else if(ob->pose && (ob->mode & OB_MODE_POSE)) {
- bPoseChannel *pchan;
- for(pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
- if((pchan->bone->flag & BONE_ACTIVE) && (pchan->bone->layer & arm->layer)) {
- name= pchan->name;
- break;
- }
+ else if(ob->mode & OB_MODE_POSE) {
+ if(arm->act_bone) {
+
+ if(arm->act_bone->layer & arm->layer)
+ name= arm->act_bone->name;
+
}
}
if(name && markern)
diff --git a/source/blender/editors/space_view3d/view3d_select.c b/source/blender/editors/space_view3d/view3d_select.c
index f0425974f29..2505110d766 100644
--- a/source/blender/editors/space_view3d/view3d_select.c
+++ b/source/blender/editors/space_view3d/view3d_select.c
@@ -357,7 +357,14 @@ static void do_lasso_select_pose(ViewContext *vc, short mcords[][2], short moves
if(lasso_inside_edge(mcords, moves, sco1[0], sco1[1], sco2[0], sco2[1])) {
if(select) pchan->bone->flag |= BONE_SELECTED;
- else pchan->bone->flag &= ~(BONE_ACTIVE|BONE_SELECTED);
+ else pchan->bone->flag &= ~BONE_SELECTED;
+ }
+ }
+
+ {
+ bArmature *arm= ob->data;
+ if((arm->act_bone->flag & BONE_SELECTED)==0) {
+ arm->act_bone= NULL;
}
}
}
@@ -638,9 +645,11 @@ static void do_lasso_select_armature(ViewContext *vc, short mcords[][2], short m
/* if one of points selected, we skip the bone itself */
if(didpoint==0 && lasso_inside_edge(mcords, moves, sco1[0], sco1[1], sco2[0], sco2[1])) {
if(select) ebone->flag |= BONE_TIPSEL|BONE_ROOTSEL|BONE_SELECTED;
- else ebone->flag &= ~(BONE_ACTIVE|BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
+ else ebone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
}
}
+
+ ED_armature_validate_active(arm);
}
static void do_lasso_select_facemode(ViewContext *vc, short mcords[][2], short moves, short select)
@@ -1534,8 +1543,12 @@ static int view3d_borderselect_exec(bContext *C, wmOperator *op)
// XXX select_actionchannel_by_name(base->object->action, bone->name, 1);
}
else {
- bone->flag &= ~(BONE_ACTIVE|BONE_SELECTED);
+ bArmature *arm= base->object->data;
+ bone->flag &= ~BONE_SELECTED;
// XXX select_actionchannel_by_name(base->object->action, bone->name, 0);
+ if(arm->act_bone==bone)
+ arm->act_bone= NULL;
+
}
}
}
@@ -1868,9 +1881,11 @@ static void armature_circle_select(ViewContext *vc, int selecting, short *mval,
if (selecting)
ebone->flag |= BONE_TIPSEL|BONE_ROOTSEL|BONE_SELECTED;
else
- ebone->flag &= ~(BONE_ACTIVE|BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
+ ebone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
}
}
+
+ ED_armature_validate_active(arm);
}
/** Callbacks for circle selection in Editmode */
diff --git a/source/blender/editors/transform/transform_manipulator.c b/source/blender/editors/transform/transform_manipulator.c
index 0f4848d9120..86e83715da4 100644
--- a/source/blender/editors/transform/transform_manipulator.c
+++ b/source/blender/editors/transform/transform_manipulator.c
@@ -55,6 +55,7 @@
#include "RNA_access.h"
+#include "BKE_action.h"
#include "BKE_armature.h"
#include "BKE_context.h"
#include "BKE_global.h"
@@ -185,18 +186,9 @@ void gimbal_axis(Object *ob, float gmat[][3])
{
if(ob->mode & OB_MODE_POSE)
{
- bPoseChannel *pchan= NULL;
+ bPoseChannel *pchan= get_active_posechannel(ob);
- /* use channels to get stats */
- for(pchan= ob->pose->chanbase.first; pchan; pchan= pchan->next) {
- if (pchan->bone && pchan->bone->flag & BONE_ACTIVE) {
- if(test_rotmode_euler(pchan->rotmode)) {
- break;
- }
- }
- }
-
- if(pchan) {
+ if(pchan && test_rotmode_euler(pchan->rotmode)) {
float mat[3][3], tmat[3][3], obmat[3][3];
EulToGimbalAxis(mat, pchan->eul, pchan->rotmode);
diff --git a/source/blender/makesdna/DNA_armature_types.h b/source/blender/makesdna/DNA_armature_types.h
index d3e611178fe..7dd90a3cf13 100644
--- a/source/blender/makesdna/DNA_armature_types.h
+++ b/source/blender/makesdna/DNA_armature_types.h
@@ -78,6 +78,9 @@ typedef struct bArmature {
ListBase chainbase;
ListBase *edbo; /* editbone listbase, we use pointer so we can check state */
+ Bone *act_bone;
+ void *act_edbone;
+
void *sketch; /* sketch struct for etch-a-ton */
int flag;
@@ -154,7 +157,7 @@ typedef enum eBone_Flag {
/* 32 used to be quatrot, was always set in files, do not reuse unless you clear it always */
BONE_HIDDEN_P = (1<<6), /* hidden Bones when drawing PoseChannels */
BONE_DONE = (1<<7), /* For detecting cyclic dependancies */
- BONE_ACTIVE = (1<<8), /* active is on mouse clicks only */
+ BONE_DRAW_ACTIVE = (1<<8), /* active is on mouse clicks only - deprecated, ONLY USE FOR DRAWING */
BONE_HINGE = (1<<9), /* No parent rotation or scale */
BONE_HIDDEN_A = (1<<10), /* hidden Bones when drawing Armature Editmode */
BONE_MULT_VG_ENV = (1<<11), /* multiplies vgroup with envelope */
diff --git a/source/blender/makesrna/intern/rna_armature.c b/source/blender/makesrna/intern/rna_armature.c
index 96dde186260..7d88745779d 100644
--- a/source/blender/makesrna/intern/rna_armature.c
+++ b/source/blender/makesrna/intern/rna_armature.c
@@ -56,6 +56,44 @@ static void rna_Armature_update_data(bContext *C, PointerRNA *ptr)
//WM_event_add_notifier(C, NC_OBJECT|ND_POSE, NULL);
}
+
+static void rna_Armature_act_bone_set(PointerRNA *ptr, PointerRNA value)
+{
+ bArmature *arm= (bArmature*)ptr->data;
+
+ if(value.id.data==NULL && value.data==NULL) {
+ arm->act_bone= NULL;
+ }
+ else {
+ if(value.id.data != arm) {
+ /* raise an error! */
+ }
+ else {
+ arm->act_bone= value.data;
+ arm->act_bone->flag |= BONE_SELECTED;
+ }
+ }
+}
+
+static void rna_Armature_act_edit_bone_set(PointerRNA *ptr, PointerRNA value)
+{
+ bArmature *arm= (bArmature*)ptr->data;
+
+ if(value.id.data==NULL && value.data==NULL) {
+ arm->act_edbone= NULL;
+ }
+ else {
+ if(value.id.data != arm) {
+ /* raise an error! */
+ }
+ else {
+ arm->act_edbone= value.data;
+ ((EditBone *)arm->act_edbone)->flag |= BONE_SELECTED;
+ }
+ }
+}
+
+
static void rna_Armature_redraw_data(bContext *C, PointerRNA *ptr)
{
ID *id= ptr->id.data;
@@ -371,11 +409,6 @@ static void rna_def_bone_common(StructRNA *srna, int editbone)
RNA_def_property_ui_text(prop, "Connected", "When bone has a parent, bone's head is struck to the parent's tail.");
RNA_def_property_update(prop, 0, "rna_Armature_update_data");
- prop= RNA_def_property(srna, "active", PROP_BOOLEAN, PROP_NONE);
- RNA_def_property_boolean_sdna(prop, NULL, "flag", BONE_ACTIVE);
- RNA_def_property_ui_text(prop, "Active", "Bone was the last bone clicked on (most operations are applied to only this bone)");
- RNA_def_property_update(prop, 0, "rna_Armature_redraw_data");
-
prop= RNA_def_property(srna, "hinge", PROP_BOOLEAN, PROP_NONE);
RNA_def_property_boolean_negative_sdna(prop, NULL, "flag", BONE_HINGE);
RNA_def_property_ui_text(prop, "Inherit Rotation", "Bone doesn't inherit rotation or scale from parent bone.");
@@ -593,7 +626,7 @@ static void rna_def_edit_bone(BlenderRNA *brna)
static void rna_def_armature(BlenderRNA *brna)
{
StructRNA *srna;
- PropertyRNA *prop;
+ PropertyRNA *prop, *prop_act;
static EnumPropertyItem prop_drawtype_items[] = {
{ARM_OCTA, "OCTAHEDRAL", 0, "Octahedral", "Display bones as octahedral shape (default)."},
@@ -634,11 +667,34 @@ static void rna_def_armature(BlenderRNA *brna)
RNA_def_property_struct_type(prop, "Bone");
RNA_def_property_ui_text(prop, "Bones", "");
+ { /* Collection active property */
+ prop_act= RNA_def_property(srna, "bones_active", PROP_POINTER, PROP_NONE);
+ RNA_def_property_struct_type(prop_act, "Bone");
+ RNA_def_property_pointer_sdna(prop_act, NULL, "act_bone");
+ RNA_def_property_flag(prop_act, PROP_EDITABLE);
+ RNA_def_property_ui_text(prop_act, "Active Bone", "Armatures active bone.");
+ RNA_def_property_pointer_funcs(prop_act, NULL, "rna_Armature_act_bone_set", NULL);
+
+ /* todo, redraw */
+ RNA_def_property_collection_active(prop, prop_act);
+ }
+
prop= RNA_def_property(srna, "edit_bones", PROP_COLLECTION, PROP_NONE);
RNA_def_property_collection_sdna(prop, NULL, "edbo", NULL);
RNA_def_property_struct_type(prop, "EditBone");
RNA_def_property_ui_text(prop, "Edit Bones", "");
+ { /* Collection active property */
+ prop_act= RNA_def_property(srna, "edit_bones_active", PROP_POINTER, PROP_NONE);
+ RNA_def_property_struct_type(prop_act, "EditBone");
+ RNA_def_property_pointer_sdna(prop_act, NULL, "act_edbone");
+ RNA_def_property_flag(prop_act, PROP_EDITABLE);
+ RNA_def_property_ui_text(prop_act, "Active EditBone", "Armatures active edit bone.");
+ //RNA_def_property_update(prop_act, 0, "rna_Armature_act_editbone_update");
+ RNA_def_property_pointer_funcs(prop_act, NULL, "rna_Armature_act_edit_bone_set", NULL);
+ RNA_def_property_collection_active(prop, prop_act);
+ }
+
/* Enum values */
// prop= RNA_def_property(srna, "rest_position", PROP_BOOLEAN, PROP_NONE);
// RNA_def_property_boolean_sdna(prop, NULL, "flag", ARM_RESTPOS);
diff --git a/source/gameengine/Converter/BL_ArmatureChannel.cpp b/source/gameengine/Converter/BL_ArmatureChannel.cpp
index 9a9161b080f..71e91735b24 100644
--- a/source/gameengine/Converter/BL_ArmatureChannel.cpp
+++ b/source/gameengine/Converter/BL_ArmatureChannel.cpp
@@ -180,10 +180,10 @@ int BL_ArmatureChannel::py_attr_setattr(void *self_v, const struct KX_PYATTRIBUT
bPoseChannel* channel = self->m_posechannel;
int attr_order = attrdef-Attributes;
- int ival;
- double dval;
- char* sval;
- KX_GameObject *oval;
+// int ival;
+// double dval;
+// char* sval;
+// KX_GameObject *oval;
if (!channel) {
PyErr_SetString(PyExc_AttributeError, "channel is NULL");
diff --git a/source/gameengine/Converter/BL_BlenderDataConversion.cpp b/source/gameengine/Converter/BL_BlenderDataConversion.cpp
index db32f18f63b..2b3838d4dfe 100644
--- a/source/gameengine/Converter/BL_BlenderDataConversion.cpp
+++ b/source/gameengine/Converter/BL_BlenderDataConversion.cpp
@@ -1818,7 +1818,7 @@ bPoseChannel *get_active_posechannel2 (Object *ob)
/* find active */
for(pchan= (bPoseChannel *)ob->pose->chanbase.first; pchan; pchan= pchan->next) {
- if(pchan->bone && (pchan->bone->flag & BONE_ACTIVE) && (pchan->bone->layer & arm->layer))
+ if(pchan->bone && (pchan->bone == arm->act_bone) && (pchan->bone->layer & arm->layer))
return pchan;
}