Exemplo n.º 1
0
/* ChildOf Constraint - set inverse callback */
static int childof_set_inverse_exec (bContext *C, wmOperator *op)
{
	PointerRNA ptr= CTX_data_pointer_get_type(C, "constraint", &RNA_ChildOfConstraint);
	Scene *scene= CTX_data_scene(C);
	Object *ob= ptr.id.data;
	bConstraint *con= ptr.data;
	bChildOfConstraint *data= (bChildOfConstraint *)con->data;
	bPoseChannel *pchan= NULL;

	/* try to find a pose channel */
	// TODO: get from context instead?
	if (ob && ob->pose)
		pchan= get_active_posechannel(ob);
	
	/* calculate/set inverse matrix */
	if (pchan) {
		float pmat[4][4], cinf;
		float imat[4][4], tmat[4][4];
		
		/* make copy of pchan's original pose-mat (for use later) */
		Mat4CpyMat4(pmat, pchan->pose_mat);
		
		/* disable constraint for pose to be solved without it */
		cinf= con->enforce;
		con->enforce= 0.0f;
		
		/* solve pose without constraint */
		where_is_pose(scene, ob);
		
		/* determine effect of constraint by removing the newly calculated 
		 * pchan->pose_mat from the original pchan->pose_mat, thus determining 
		 * the effect of the constraint
		 */
		Mat4Invert(imat, pchan->pose_mat);
		Mat4MulMat4(tmat, imat, pmat);
		Mat4Invert(data->invmat, tmat);
		
		/* recalculate pose with new inv-mat */
		con->enforce= cinf;
		where_is_pose(scene, ob);
	}
	else if (ob) {
		Object workob;
		/* use what_does_parent to find inverse - just like for normal parenting.
		 * NOTE: what_does_parent uses a static workob defined in object.c 
		 */
		what_does_parent(scene, ob, &workob);
		Mat4Invert(data->invmat, workob.obmat);
	}
	else
		Mat4One(data->invmat);
		
	WM_event_add_notifier(C, NC_OBJECT|ND_CONSTRAINT, ob);
		
	return OPERATOR_FINISHED;
}
Exemplo n.º 2
0
/* if object in posemode, active bone constraints, else object constraints */
ListBase *get_active_constraints (Object *ob)
{
	if (ob == NULL)
		return NULL;

	if (ob->mode & OB_MODE_POSE) {
		bPoseChannel *pchan;
		
		pchan = get_active_posechannel(ob);
		if (pchan)
			return &pchan->constraints;
	}
	else 
		return &ob->constraints;

	return NULL;
}
Exemplo n.º 3
0
static void v3d_posearmature_buts(uiLayout *layout, Object *ob)
{
//	uiBlock *block= uiLayoutGetBlock(layout);
//	bArmature *arm;
	bPoseChannel *pchan;
//	TransformProperties *tfp= v3d->properties_storage;
	PointerRNA pchanptr;
	uiLayout *col;
//	uiLayout *row;
//	uiBut *but;

	pchan= get_active_posechannel(ob);

//	row= uiLayoutRow(layout, 0);
	
	if (!pchan)	{
		uiItemL(layout, "No Bone Active", ICON_NONE);
		return; 
	}

	RNA_pointer_create(&ob->id, &RNA_PoseBone, pchan, &pchanptr);

	col= uiLayoutColumn(layout, 0);
	
	/* XXX: RNA buts show data in native types (i.e. quats, 4-component axis/angle, etc.)
	 * but oldskool UI shows in eulers always. Do we want to be able to still display in Eulers?
	 * Maybe needs RNA/ui options to display rotations as different types... */
	v3d_transform_butsR(col, &pchanptr);

#if 0
	uiLayoutAbsoluteBlock(layout);

	if (pchan->rotmode == ROT_MODE_AXISANGLE) {
		float quat[4];
		/* convert to euler, passing through quats... */
		axis_angle_to_quat(quat, pchan->rotAxis, pchan->rotAngle);
		quat_to_eul( tfp->ob_eul,quat);
	}
	else if (pchan->rotmode == ROT_MODE_QUAT)
		quat_to_eul( tfp->ob_eul,pchan->quat);
	else
		copy_v3_v3(tfp->ob_eul, pchan->eul);
	tfp->ob_eul[0]*= 180.0/M_PI;
	tfp->ob_eul[1]*= 180.0/M_PI;
	tfp->ob_eul[2]*= 180.0/M_PI;
	
	uiDefBut(block, LABEL, 0, "Location:",			0, 240, 100, 20, 0, 0, 0, 0, 0, "");
	uiBlockBeginAlign(block);
	
	but= uiDefButF(block, NUM, B_ARMATUREPANEL2, "X:",	0, 220, 120, 19, pchan->loc, -lim, lim, 100, 3, "");
	uiButSetUnitType(but, PROP_UNIT_LENGTH);
	but= uiDefButF(block, NUM, B_ARMATUREPANEL2, "Y:",	0, 200, 120, 19, pchan->loc+1, -lim, lim, 100, 3, "");
	uiButSetUnitType(but, PROP_UNIT_LENGTH);
	but= uiDefButF(block, NUM, B_ARMATUREPANEL2, "Z:",	0, 180, 120, 19, pchan->loc+2, -lim, lim, 100, 3, "");
	uiButSetUnitType(but, PROP_UNIT_LENGTH);
	uiBlockEndAlign(block);
	
	uiBlockBeginAlign(block);
	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");
	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");
	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");
	uiBlockEndAlign(block);
	
	uiDefBut(block, LABEL, 0, "Rotation:",			0, 160, 100, 20, 0, 0, 0, 0, 0, "");
	uiBlockBeginAlign(block);
	uiDefButF(block, NUM, B_ARMATUREPANEL3, "X:",	0, 140, 120, 19, tfp->ob_eul, -1000.0, 1000.0, 100, 3, "");
	uiDefButF(block, NUM, B_ARMATUREPANEL3, "Y:",	0, 120, 120, 19, tfp->ob_eul+1, -1000.0, 1000.0, 100, 3, "");
	uiDefButF(block, NUM, B_ARMATUREPANEL3, "Z:",	0, 100, 120, 19, tfp->ob_eul+2, -1000.0, 1000.0, 100, 3, "");
	uiBlockEndAlign(block);
	
	uiBlockBeginAlign(block);
	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");
	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");
	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");
	uiBlockEndAlign(block);
	
	uiDefBut(block, LABEL, 0, "Scale:",				0, 80, 100, 20, 0, 0, 0, 0, 0, "");
	uiBlockBeginAlign(block);
	uiDefButF(block, NUM, B_ARMATUREPANEL2, "X:",	0, 60, 120, 19, pchan->size, -lim, lim, 10, 3, "");
	uiDefButF(block, NUM, B_ARMATUREPANEL2, "Y:",	0, 40, 120, 19, pchan->size+1, -lim, lim, 10, 3, "");
	uiDefButF(block, NUM, B_ARMATUREPANEL2, "Z:",	0, 20, 120, 19, pchan->size+2, -lim, lim, 10, 3, "");
	uiBlockEndAlign(block);
	
	uiBlockBeginAlign(block);
	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");
	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");
	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");
	uiBlockEndAlign(block);
#endif
}
Exemplo n.º 4
0
int ed_screen_context(const bContext *C, const char *member, bContextDataResult *result)
{
	bScreen *sc= CTX_wm_screen(C);
	Scene *scene= sc->scene;
	Base *base;
	unsigned int lay = scene->lay;

#if 0	/* Using the context breaks adding objects in the UI. Need to find out why - campbell */
	Object *obact= CTX_data_active_object(C);
	Object *obedit= CTX_data_edit_object(C);
	base= CTX_data_active_base(C);
#else
	Object *obedit= scene->obedit; 
	Object *obact= OBACT;
	base= BASACT;
#endif

	if(CTX_data_dir(member)) {
		CTX_data_dir_set(result, screen_context_dir);
		return 1;
	}
	else if(CTX_data_equals(member, "scene")) {
		CTX_data_id_pointer_set(result, &scene->id);
		return 1;
	}
	else if(CTX_data_equals(member, "visible_objects") || CTX_data_equals(member, "visible_bases")) {
		int visible_objects= CTX_data_equals(member, "visible_objects");

		for(base=scene->base.first; base; base=base->next) {
			if(((base->object->restrictflag & OB_RESTRICT_VIEW) == 0) && (base->lay & scene->lay)) {
				if(visible_objects)
					CTX_data_id_list_add(result, &base->object->id);
				else
					CTX_data_list_add(result, &scene->id, &RNA_ObjectBase, base);
			}
		}
		CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
		return 1;
	}
	else if(CTX_data_equals(member, "selectable_objects") || CTX_data_equals(member, "selectable_bases")) {
		int selectable_objects= CTX_data_equals(member, "selectable_objects");

		for(base=scene->base.first; base; base=base->next) {
			if(base->lay & lay) {
				if((base->object->restrictflag & OB_RESTRICT_VIEW)==0 && (base->object->restrictflag & OB_RESTRICT_SELECT)==0) {
					if(selectable_objects)
						CTX_data_id_list_add(result, &base->object->id);
					else
						CTX_data_list_add(result, &scene->id, &RNA_ObjectBase, base);
				}
			}
		}
		CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
		return 1;
	}
	else if(CTX_data_equals(member, "selected_objects") || CTX_data_equals(member, "selected_bases")) {
		int selected_objects= CTX_data_equals(member, "selected_objects");

		for(base=scene->base.first; base; base=base->next) {
			if((base->flag & SELECT) && (base->lay & scene->lay)) {
				if(selected_objects)
					CTX_data_id_list_add(result, &base->object->id);
				else
					CTX_data_list_add(result, &scene->id, &RNA_ObjectBase, base);
			}
		}
		CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
		return 1;
	}
	else if(CTX_data_equals(member, "selected_editable_objects") || CTX_data_equals(member, "selected_editable_bases")) {
		int selected_editable_objects= CTX_data_equals(member, "selected_editable_objects");

		for(base=scene->base.first; base; base=base->next) {
			if((base->flag & SELECT) && (base->lay & scene->lay)) {
				if((base->object->restrictflag & OB_RESTRICT_VIEW)==0) {
					if(0==object_is_libdata(base->object)) {
						if(selected_editable_objects)
							CTX_data_id_list_add(result, &base->object->id);
						else
							CTX_data_list_add(result, &scene->id, &RNA_ObjectBase, base);
					}
				}
			}
		}
		CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
		return 1;
	}
	else if(CTX_data_equals(member, "visible_bones") || CTX_data_equals(member, "editable_bones")) {
		bArmature *arm= (obedit && obedit->type == OB_ARMATURE) ? obedit->data : NULL;
		EditBone *ebone, *flipbone=NULL;
		int editable_bones= CTX_data_equals(member, "editable_bones");
		
		if (arm && arm->edbo) {
			/* Attention: X-Axis Mirroring is also handled here... */
			for (ebone= arm->edbo->first; ebone; ebone= ebone->next) {
				/* first and foremost, bone must be visible and selected */
				if (EBONE_VISIBLE(arm, ebone)) {
					/* Get 'x-axis mirror equivalent' bone if the X-Axis Mirroring option is enabled
					 * so that most users of this data don't need to explicitly check for it themselves.
					 * 
					 * We need to make sure that these mirrored copies are not selected, otherwise some
					 * bones will be operated on twice.
					 */
					if (arm->flag & ARM_MIRROR_EDIT)
						flipbone = ED_armature_bone_get_mirrored(arm->edbo, ebone);
					
					/* if we're filtering for editable too, use the check for that instead, as it has selection check too */
					if (editable_bones) {
						/* only selected + editable */
						if (EBONE_EDITABLE(ebone)) {
							CTX_data_list_add(result, &arm->id, &RNA_EditBone, ebone);
						
							if ((flipbone) && !(flipbone->flag & BONE_SELECTED))
								CTX_data_list_add(result, &arm->id, &RNA_EditBone, flipbone);
						}
					}
					else {
						/* only include bones if visible */
						CTX_data_list_add(result, &arm->id, &RNA_EditBone, ebone);
						
						if ((flipbone) && EBONE_VISIBLE(arm, flipbone)==0)
							CTX_data_list_add(result, &arm->id, &RNA_EditBone, flipbone);
					}
				}
			}	
			CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
			return 1;
		}
	}
	else if(CTX_data_equals(member, "selected_bones") || CTX_data_equals(member, "selected_editable_bones")) {
		bArmature *arm= (obedit && obedit->type == OB_ARMATURE) ? obedit->data : NULL;
		EditBone *ebone, *flipbone=NULL;
		int selected_editable_bones= CTX_data_equals(member, "selected_editable_bones");
		
		if (arm && arm->edbo) {
			/* Attention: X-Axis Mirroring is also handled here... */
			for (ebone= arm->edbo->first; ebone; ebone= ebone->next) {
				/* first and foremost, bone must be visible and selected */
				if (EBONE_VISIBLE(arm, ebone) && (ebone->flag & BONE_SELECTED)) {
					/* Get 'x-axis mirror equivalent' bone if the X-Axis Mirroring option is enabled
					 * so that most users of this data don't need to explicitly check for it themselves.
					 * 
					 * We need to make sure that these mirrored copies are not selected, otherwise some
					 * bones will be operated on twice.
					 */
					if (arm->flag & ARM_MIRROR_EDIT)
						flipbone = ED_armature_bone_get_mirrored(arm->edbo, ebone);
					
					/* if we're filtering for editable too, use the check for that instead, as it has selection check too */
					if (selected_editable_bones) {
						/* only selected + editable */
						if (EBONE_EDITABLE(ebone)) {
							CTX_data_list_add(result, &arm->id, &RNA_EditBone, ebone);
						
							if ((flipbone) && !(flipbone->flag & BONE_SELECTED))
								CTX_data_list_add(result, &arm->id, &RNA_EditBone, flipbone);
						}
					}
					else {
						/* only include bones if selected */
						CTX_data_list_add(result, &arm->id, &RNA_EditBone, ebone);
						
						if ((flipbone) && !(flipbone->flag & BONE_SELECTED))
							CTX_data_list_add(result, &arm->id, &RNA_EditBone, flipbone);
					}
				}
			}	
			CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
			return 1;
		}
	}
	else if(CTX_data_equals(member, "visible_pose_bones")) {
		Object *obpose= ED_object_pose_armature(obact);
		bArmature *arm= (obpose) ? obpose->data : NULL;
		bPoseChannel *pchan;
		
		if (obpose && obpose->pose && arm) {
			for (pchan= obpose->pose->chanbase.first; pchan; pchan= pchan->next) {
				/* ensure that PoseChannel is on visible layer and is not hidden in PoseMode */
				if (PBONE_VISIBLE(arm, pchan->bone)) {
					CTX_data_list_add(result, &obpose->id, &RNA_PoseBone, pchan);
				}
			}
			CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
			return 1;
		}
	}
	else if(CTX_data_equals(member, "selected_pose_bones")) {
		Object *obpose= ED_object_pose_armature(obact);
		bArmature *arm= (obpose) ? obpose->data : NULL;
		bPoseChannel *pchan;
		
		if (obpose && obpose->pose && arm) {
			for (pchan= obpose->pose->chanbase.first; pchan; pchan= pchan->next) {
				/* ensure that PoseChannel is on visible layer and is not hidden in PoseMode */
				if (PBONE_VISIBLE(arm, pchan->bone)) {
					if (pchan->bone->flag & BONE_SELECTED)
						CTX_data_list_add(result, &obpose->id, &RNA_PoseBone, pchan);
				}
			}
			CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
			return 1;
		}
	}
	else if(CTX_data_equals(member, "active_bone")) {
		if(obact && obact->type == OB_ARMATURE) {
			bArmature *arm= obact->data;
			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_pose_bone")) {
		bPoseChannel *pchan;
		Object *obpose= ED_object_pose_armature(obact);
		
		pchan= get_active_posechannel(obpose);
		if (pchan) {
			CTX_data_pointer_set(result, &obpose->id, &RNA_PoseBone, pchan);
			return 1;
		}
	}
	else if(CTX_data_equals(member, "active_base")) {
		if(base)
			CTX_data_pointer_set(result, &scene->id, &RNA_ObjectBase, base);

		return 1;
	}
	else if(CTX_data_equals(member, "active_object")) {
		if(obact)
			CTX_data_id_pointer_set(result, &obact->id);

		return 1;
	}
	else if(CTX_data_equals(member, "object")) {
		if(obact)
			CTX_data_id_pointer_set(result, &obact->id);

		return 1;
	}
	else if(CTX_data_equals(member, "edit_object")) {
		/* convenience for now, 1 object per scene in editmode */
		if(obedit)
			CTX_data_id_pointer_set(result, &obedit->id);
		
		return 1;
	}
	else if(CTX_data_equals(member, "sculpt_object")) {
		if(obact && (obact->mode & OB_MODE_SCULPT))
			CTX_data_id_pointer_set(result, &obact->id);

		return 1;
	}
	else if(CTX_data_equals(member, "vertex_paint_object")) {
		if(obact && (obact->mode & OB_MODE_VERTEX_PAINT))
			CTX_data_id_pointer_set(result, &obact->id);

		return 1;
	}
	else if(CTX_data_equals(member, "weight_paint_object")) {
		if(obact && (obact->mode & OB_MODE_WEIGHT_PAINT))
			CTX_data_id_pointer_set(result, &obact->id);

		return 1;
	}
	else if(CTX_data_equals(member, "image_paint_object")) {
		if(obact && (obact->mode & OB_MODE_TEXTURE_PAINT))
			CTX_data_id_pointer_set(result, &obact->id);

		return 1;
	}
	else if(CTX_data_equals(member, "particle_edit_object")) {
		if(obact && (obact->mode & OB_MODE_PARTICLE_EDIT))
			CTX_data_id_pointer_set(result, &obact->id);

		return 1;
	}
	else if(CTX_data_equals(member, "sequences")) {
		Editing *ed= seq_give_editing(scene, FALSE);
		if(ed) {
			Sequence *seq;
			for (seq= ed->seqbasep->first; seq; seq= seq->next) {
				CTX_data_list_add(result, &scene->id, &RNA_Sequence, seq);
			}
			CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
			return 1;
		}
	}
	else if(CTX_data_equals(member, "selected_sequences")) {
		Editing *ed= seq_give_editing(scene, FALSE);
		if(ed) {
			Sequence *seq;
			for (seq= ed->seqbasep->first; seq; seq= seq->next) {
				if (seq->flag & SELECT) {
					CTX_data_list_add(result, &scene->id, &RNA_Sequence, seq);
				}
			}
			CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
			return 1;
		}
	}
	else if(CTX_data_equals(member, "selected_editable_sequences")) {
		Editing *ed= seq_give_editing(scene, FALSE);
		if(ed) {
			Sequence *seq;
			for (seq= ed->seqbasep->first; seq; seq= seq->next) {
				if (seq->flag & SELECT && !(seq->flag & SEQ_LOCK)) {
					CTX_data_list_add(result, &scene->id, &RNA_Sequence, seq);
				}
			}
			CTX_data_type_set(result, CTX_DATA_TYPE_COLLECTION);
			return 1;
		}
	}
	else {
		return 0; /* not found */
	}

	return -1; /* found but not available */
}
Exemplo n.º 5
0
static void do_view3d_region_buttons(bContext *C, void *UNUSED(index), int event)
{
	Main *bmain= CTX_data_main(C);
	Scene *scene= CTX_data_scene(C);
//	Object *obedit= CTX_data_edit_object(C);
	View3D *v3d= CTX_wm_view3d(C);
//	BoundBox *bb;
	Object *ob= OBACT;
	TransformProperties *tfp= v3d->properties_storage;
	
	switch(event) {
	
	case B_REDR:
		ED_area_tag_redraw(CTX_wm_area(C));
		return; /* no notifier! */
		
	case B_OBJECTPANEL:
		DAG_id_tag_update(&ob->id, OB_RECALC_OB);
		break;

	
	case B_OBJECTPANELMEDIAN:
		if(ob) {
			v3d_editvertex_buts(NULL, v3d, ob, 1.0);
			DAG_id_tag_update(&ob->id, OB_RECALC_DATA);
		}
		break;
		
		/* note; this case also used for parbone */
	case B_OBJECTPANELPARENT:
		if(ob) {
			if(ob->id.lib || test_parent_loop(ob->parent, ob) ) 
				ob->parent= NULL;
			else {
				DAG_scene_sort(bmain, scene);
				DAG_id_tag_update(&ob->id, OB_RECALC_OB);
			}
		}
		break;
		

	case B_ARMATUREPANEL3:  // rotate button on channel
		{
			bPoseChannel *pchan;
			float eul[3];
			
			pchan= get_active_posechannel(ob);
			if (!pchan) return;
			
			/* make a copy to eul[3], to allow TAB on buttons to work */
			eul[0]= (float)M_PI*tfp->ob_eul[0]/180.0f;
			eul[1]= (float)M_PI*tfp->ob_eul[1]/180.0f;
			eul[2]= (float)M_PI*tfp->ob_eul[2]/180.0f;
			
			if (pchan->rotmode == ROT_MODE_AXISANGLE) {
				float quat[4];
				/* convert to axis-angle, passing through quats  */
				eul_to_quat( quat,eul);
				quat_to_axis_angle( pchan->rotAxis, &pchan->rotAngle,quat);
			}
			else if (pchan->rotmode == ROT_MODE_QUAT)
				eul_to_quat( pchan->quat,eul);
			else
				copy_v3_v3(pchan->eul, eul);
		}
		/* no break, pass on */
	case B_ARMATUREPANEL2:
		{
			ob->pose->flag |= (POSE_LOCKED|POSE_DO_UNLOCK);
			DAG_id_tag_update(&ob->id, OB_RECALC_DATA);
		}
		break;
	case B_TRANSFORMSPACEADD:
	{
		char names[sizeof(((TransformOrientation *)NULL)->name)]= "";
		BIF_createTransformOrientation(C, NULL, names, 1, 0);
		break;
	}
	case B_TRANSFORMSPACECLEAR:
		BIF_clearTransformOrientation(C);
		break;
		
#if 0 // XXX
	case B_WEIGHT0_0:
		wpaint->weight = 0.0f;
		break;
		
	case B_WEIGHT1_4:
		wpaint->weight = 0.25f;
		break;
	case B_WEIGHT1_2:
		wpaint->weight = 0.5f;
		break;
	case B_WEIGHT3_4:
		wpaint->weight = 0.75f;
		break;
	case B_WEIGHT1_0:
		wpaint->weight = 1.0f;
		break;
		
	case B_OPA1_8:
		wpaint->a = 0.125f;
		break;
	case B_OPA1_4:
		wpaint->a = 0.25f;
		break;
	case B_OPA1_2:
		wpaint->a = 0.5f;
		break;
	case B_OPA3_4:
		wpaint->a = 0.75f;
		break;
	case B_OPA1_0:
		wpaint->a = 1.0f;
		break;
#endif
	case B_CLR_WPAINT:
//		if(!multires_level1_test()) {
		{
			bDeformGroup *defGroup = BLI_findlink(&ob->defbase, ob->actdef-1);
			if(defGroup) {
				Mesh *me= ob->data;
				int a;
				for(a=0; a<me->totvert; a++)
					ED_vgroup_vert_remove (ob, defGroup, a);
				DAG_id_tag_update(&ob->id, OB_RECALC_DATA);
			}
		}
		break;
	case B_RV3D_LOCKED:
	case B_RV3D_BOXVIEW:
	case B_RV3D_BOXCLIP:
		{
			ScrArea *sa= CTX_wm_area(C);
			ARegion *ar= sa->regionbase.last;
			RegionView3D *rv3d;
			short viewlock;
			
			ar= ar->prev;
			rv3d= ar->regiondata;
			viewlock= rv3d->viewlock;
			
			if((viewlock & RV3D_LOCKED)==0)
				viewlock= 0;
			else if((viewlock & RV3D_BOXVIEW)==0)
				viewlock &= ~RV3D_BOXCLIP;
			
			for(; ar; ar= ar->prev) {
				if(ar->alignment==RGN_ALIGN_QSPLIT) {
					rv3d= ar->regiondata;
					rv3d->viewlock= viewlock;
				}
			}
			
			if(rv3d->viewlock & RV3D_BOXVIEW)
				view3d_boxview_copy(sa, sa->regionbase.last);
			
			ED_area_tag_redraw(sa);
		}
		break;
	}

	/* default for now */
	WM_event_add_notifier(C, NC_SPACE|ND_SPACE_VIEW3D, ob);
}