added support for proxies as drivers back.

This commit is contained in:
2010-02-23 17:56:45 +00:00
parent 0dd58a27e9
commit 3f5786a00e
3 changed files with 40 additions and 35 deletions

View File

@@ -1502,7 +1502,8 @@ void where_is_armature (bArmature *arm)
} }
} }
/* if bone layer is protected, copy the data from from->pose */ /* if bone layer is protected, copy the data from from->pose
* when used with linked libraries this copies from the linked pose into the local pose */
static void pose_proxy_synchronize(Object *ob, Object *from, int layer_protected) static void pose_proxy_synchronize(Object *ob, Object *from, int layer_protected)
{ {
bPose *pose= ob->pose, *frompose= from->pose; bPose *pose= ob->pose, *frompose= from->pose;

View File

@@ -801,13 +801,19 @@ typedef struct DriverVarTypeInfo {
/* ......... */ /* ......... */
static ID *dtar_id_ensure_proxy_from(ID *id)
{
if (id && GS(id->name)==ID_OB && ((Object *)id)->proxy_from)
return (ID *)(((Object *)id)->proxy_from);
return id;
}
/* Helper function to obtain a value using RNA from the specified source (for evaluating drivers) */ /* Helper function to obtain a value using RNA from the specified source (for evaluating drivers) */
static float dtar_get_prop_val (ChannelDriver *driver, DriverTarget *dtar) static float dtar_get_prop_val (ChannelDriver *driver, DriverTarget *dtar)
{ {
PointerRNA id_ptr, ptr; PointerRNA id_ptr, ptr;
PropertyRNA *prop; PropertyRNA *prop;
ID *id; ID *id;
char *path;
int index; int index;
float value= 0.0f; float value= 0.0f;
@@ -815,22 +821,22 @@ static float dtar_get_prop_val (ChannelDriver *driver, DriverTarget *dtar)
if ELEM(NULL, driver, dtar) if ELEM(NULL, driver, dtar)
return 0.0f; return 0.0f;
/* get RNA-pointer for the ID-block given in target */ id= dtar_id_ensure_proxy_from(dtar->id);
RNA_id_pointer_create(dtar->id, &id_ptr);
id= dtar->id;
path= dtar->rna_path;
/* error check for missing pointer... */ /* error check for missing pointer... */
// TODO: tag the specific target too as having issues // TODO: tag the specific target too as having issues
if (id == NULL) { if (id == NULL) {
printf("Error: driver has an invalid target to use \n"); printf("Error: driver has an invalid target to use \n");
if (G.f & G_DEBUG) printf("\tpath = %s\n", path); if (G.f & G_DEBUG) printf("\tpath = %s\n", dtar->rna_path);
driver->flag |= DRIVER_FLAG_INVALID; driver->flag |= DRIVER_FLAG_INVALID;
return 0.0f; return 0.0f;
} }
/* get RNA-pointer for the ID-block given in target */
RNA_id_pointer_create(id, &id_ptr);
/* get property to read from, and get value as appropriate */ /* get property to read from, and get value as appropriate */
if (RNA_path_resolve_full(&id_ptr, path, &ptr, &prop, &index)) { if (RNA_path_resolve_full(&id_ptr, dtar->rna_path, &ptr, &prop, &index)) {
switch (RNA_property_type(prop)) { switch (RNA_property_type(prop)) {
case PROP_BOOLEAN: case PROP_BOOLEAN:
if (RNA_property_array_length(&ptr, prop)) if (RNA_property_array_length(&ptr, prop))
@@ -859,7 +865,7 @@ static float dtar_get_prop_val (ChannelDriver *driver, DriverTarget *dtar)
} }
else { else {
if (G.f & G_DEBUG) if (G.f & G_DEBUG)
printf("Driver Evaluation Error: cannot resolve target for %s -> %s \n", id->name, path); printf("Driver Evaluation Error: cannot resolve target for %s -> %s \n", id->name, dtar->rna_path);
driver->flag |= DRIVER_FLAG_INVALID; driver->flag |= DRIVER_FLAG_INVALID;
return 0.0f; return 0.0f;
@@ -871,14 +877,17 @@ static float dtar_get_prop_val (ChannelDriver *driver, DriverTarget *dtar)
/* Helper function to obtain a pointer to a Pose Channel (for evaluating drivers) */ /* Helper function to obtain a pointer to a Pose Channel (for evaluating drivers) */
static bPoseChannel *dtar_get_pchan_ptr (ChannelDriver *driver, DriverTarget *dtar) static bPoseChannel *dtar_get_pchan_ptr (ChannelDriver *driver, DriverTarget *dtar)
{ {
ID *id;
/* sanity check */ /* sanity check */
if ELEM(NULL, driver, dtar) if ELEM(NULL, driver, dtar)
return NULL; return NULL;
id= dtar_id_ensure_proxy_from(dtar->id);
/* check if the ID here is a valid object */ /* check if the ID here is a valid object */
if ((dtar->id) && GS(dtar->id->name)) { if (id && GS(id->name)) {
Object *ob= (Object *)dtar->id; Object *ob= (Object *)id;
/* get pose, and subsequently, posechannel */ /* get pose, and subsequently, posechannel */
return get_pose_channel(ob->pose, dtar->pchan_name); return get_pose_channel(ob->pose, dtar->pchan_name);
} }
@@ -947,12 +956,12 @@ static float dvar_eval_locDiff (ChannelDriver *driver, DriverVar *dvar)
DRIVER_TARGETS_USED_LOOPER(dvar) DRIVER_TARGETS_USED_LOOPER(dvar)
{ {
/* get pointer to loc values to store in */ /* get pointer to loc values to store in */
Object *ob= (Object *)dtar->id; Object *ob= (Object *)dtar_id_ensure_proxy_from(dtar->id);
bPoseChannel *pchan; bPoseChannel *pchan;
float tmp_loc[3]; float tmp_loc[3];
/* check if this target has valid data */ /* check if this target has valid data */
if ((ob == NULL) || (GS(dtar->id->name) != ID_OB)) { if ((ob == NULL) || (GS(ob->id.name) != ID_OB)) {
/* invalid target, so will not have enough targets */ /* invalid target, so will not have enough targets */
driver->flag |= DRIVER_FLAG_INVALID; driver->flag |= DRIVER_FLAG_INVALID;
return 0.0f; return 0.0f;
@@ -1007,14 +1016,14 @@ static float dvar_eval_locDiff (ChannelDriver *driver, DriverVar *dvar)
static float dvar_eval_transChan (ChannelDriver *driver, DriverVar *dvar) static float dvar_eval_transChan (ChannelDriver *driver, DriverVar *dvar)
{ {
DriverTarget *dtar= &dvar->targets[0]; DriverTarget *dtar= &dvar->targets[0];
Object *ob= (Object *)dtar->id; Object *ob= (Object *)dtar_id_ensure_proxy_from(dtar->id);
bPoseChannel *pchan; bPoseChannel *pchan;
float mat[4][4]; float mat[4][4];
float eul[3] = {0.0f,0.0f,0.0f}; float eul[3] = {0.0f,0.0f,0.0f};
short useEulers=0, rotOrder=ROT_MODE_EUL; short useEulers=0, rotOrder=ROT_MODE_EUL;
/* check if this target has valid data */ /* check if this target has valid data */
if ((ob == NULL) || (GS(dtar->id->name) != ID_OB)) { if ((ob == NULL) || (GS(ob->id.name) != ID_OB)) {
/* invalid target, so will not have enough targets */ /* invalid target, so will not have enough targets */
driver->flag |= DRIVER_FLAG_INVALID; driver->flag |= DRIVER_FLAG_INVALID;
return 0.0f; return 0.0f;
@@ -1281,7 +1290,7 @@ ChannelDriver *fcurve_copy_driver (ChannelDriver *driver)
float driver_get_variable_value (ChannelDriver *driver, DriverVar *dvar) float driver_get_variable_value (ChannelDriver *driver, DriverVar *dvar)
{ {
DriverVarTypeInfo *dvti; DriverVarTypeInfo *dvti;
/* sanity check */ /* sanity check */
if (ELEM(NULL, driver, dvar)) if (ELEM(NULL, driver, dvar))
return 0.0f; return 0.0f;

View File

@@ -158,8 +158,7 @@ float BPY_pydriver_eval (ChannelDriver *driver)
int i; int i;
/* sanity checks - should driver be executed? */ /* sanity checks - should driver be executed? */
if ((driver == NULL) /*|| (G.f & G_DOSCRIPTLINKS)==0*/) /*if (G.f & G_DOSCRIPTLINKS)==0) return result; */
return result;
/* get the py expression to be evaluated */ /* get the py expression to be evaluated */
expr = driver->expression; expr = driver->expression;
@@ -255,24 +254,20 @@ float BPY_pydriver_eval (ChannelDriver *driver)
/* process the result */ /* process the result */
if (retval == NULL) { if (retval == NULL) {
result = pydriver_error(driver); pydriver_error(driver);
PyGILState_Release(gilstate); result = 0.0f;
return result; } else if((result= (float)PyFloat_AsDouble(retval)) == -1.0f && PyErr_Occurred()) {
pydriver_error(driver);
Py_DECREF(retval);
result = 0.0f;
} }
else {
result = (float)PyFloat_AsDouble(retval); /* all fine, make sure the "invalid expression" flag is cleared */
Py_DECREF(retval); driver->flag &= ~DRIVER_FLAG_INVALID;
Py_DECREF(retval);
if ((result == -1) && PyErr_Occurred()) {
result = pydriver_error(driver);
PyGILState_Release(gilstate);
return result;
} }
/* all fine, make sure the "invalid expression" flag is cleared */
driver->flag &= ~DRIVER_FLAG_INVALID;
PyGILState_Release(gilstate); PyGILState_Release(gilstate);
return result; return result;
} }