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
diff options
context:
space:
mode:
authorJoshua Leung <aligorith@gmail.com>2016-03-29 17:01:27 +0300
committerJoshua Leung <aligorith@gmail.com>2016-03-29 17:21:57 +0300
commitdeffd4352bb0143a69dfa57044152ddac6432468 (patch)
tree58feb02d88d9856eda6e52728d89dcef01ecde49 /source/blender/editors/animation/drivers.c
parent3237ae2855b6dbfad8ba9e86e6e7add0942403d7 (diff)
Drivers Setup: Expose all mapping types for creating drivers
* This includes the "manually create" modes, which correspond to the previous behaviour for setting up drivers. This is necessary when the current screen layout is not well suited to having multiple property editors open (e.g. small screen or heavily subdivided screen). * Only the modes relevant for the current property type (i.e. array vs single) will be shown * The "Add Driver" entries in the RMB context menu have now been replaced by a submenu which will list all the available mapping types. * NOTE: The code for the ANIM_OT_button_driver_add() operator is perhaps a bit hairy. However, it currently allows us to have the desired behaviour. It can always get cleaned up later though.
Diffstat (limited to 'source/blender/editors/animation/drivers.c')
-rw-r--r--source/blender/editors/animation/drivers.c167
1 files changed, 131 insertions, 36 deletions
diff --git a/source/blender/editors/animation/drivers.c b/source/blender/editors/animation/drivers.c
index f94caa4fdd1..eb214e3d1e5 100644
--- a/source/blender/editors/animation/drivers.c
+++ b/source/blender/editors/animation/drivers.c
@@ -155,24 +155,6 @@ FCurve *verify_driver_fcurve(ID *id, const char rna_path[], const int array_inde
/* ************************************************** */
/* Driver Management API */
-/* Mapping Types enum for operators */
-// XXX: These names need reviewing
-EnumPropertyItem prop_driver_create_mapping_types[] = {
- {CREATEDRIVER_MAPPING_1_N, "SINGLE_MANY", 0, "All from Target",
- "Drive all components of this property using the target picked"},
- {CREATEDRIVER_MAPPING_1_1, "DIRECT", 0, "Single from Target",
- "Drive this component of this property using the target picked"},
- {CREATEDRIVER_MAPPING_N_N, "MATCH", 0, "Match Indices",
- "Create drivers for each pair of corresponding elements"},
-
- // XXX: for all vs just one?
- {CREATEDRIVER_MAPPING_NONE, "NONE", 0, "Manually Create Later",
- "Create driver without assigning any targets yet"},
- {0, NULL, 0, NULL, NULL}
-};
-
-/* --------------------------------- */
-
/* Helper for ANIM_add_driver_with_target - Adds the actual driver */
static int add_driver_with_target(
ReportList *UNUSED(reports),
@@ -648,37 +630,144 @@ bool ANIM_paste_driver(ReportList *reports, ID *id, const char rna_path[], int a
/* ************************************************** */
/* UI-Button Interface */
-/* Add Driver Button Operator ------------------------ */
+/* Add Driver - Enum Defines ------------------------- */
-static int add_driver_button_exec(bContext *C, wmOperator *op)
+/* Mapping Types enum for operators */
+/* NOTE: Used by ANIM_OT_driver_button_add and UI_OT_eyedropper_driver */
+// XXX: These names need reviewing
+EnumPropertyItem prop_driver_create_mapping_types[] = {
+ {CREATEDRIVER_MAPPING_1_N, "SINGLE_MANY", 0, "All from Target",
+ "Drive all components of this property using the target picked"},
+ {CREATEDRIVER_MAPPING_1_1, "DIRECT", 0, "Single from Target",
+ "Drive this component of this property using the target picked"},
+ {CREATEDRIVER_MAPPING_N_N, "MATCH", 0, "Match Indices",
+ "Create drivers for each pair of corresponding elements"},
+
+ {CREATEDRIVER_MAPPING_NONE_ALL, "NONE_ALL", 0, "Manually Create Later",
+ "Create drivers for all properites without assigning any targets yet"},
+ {CREATEDRIVER_MAPPING_NONE, "NONE_SINGLE", 0, "Manually Create Later (Single)",
+ "Create driver for this property only and without assigning any targets yet"},
+ {0, NULL, 0, NULL, NULL}
+};
+
+/* Filtering callback for driver mapping types enum */
+static EnumPropertyItem *driver_mapping_type_itemsf(bContext *C, PointerRNA *UNUSED(owner_ptr), PropertyRNA *UNUSED(owner_prop), bool *r_free)
{
+ EnumPropertyItem *input = prop_driver_create_mapping_types;
+ EnumPropertyItem *item = NULL;
+
PointerRNA ptr = {{NULL}};
PropertyRNA *prop = NULL;
int index;
- const bool all = RNA_boolean_get(op->ptr, "all");
- int ret = OPERATOR_CANCELLED;
+ int totitem = 0;
+
+ if (!C) /* needed for docs */
+ return prop_driver_create_mapping_types;
- /* try to create driver using property retrieved from UI */
UI_context_active_but_prop_get(C, &ptr, &prop, &index);
if (ptr.id.data && ptr.data && prop && RNA_property_animateable(&ptr, prop)) {
- wmOperatorType *ot = WM_operatortype_find("UI_OT_eyedropper_driver", true);
- PointerRNA op_ptr;
+ const bool is_array = RNA_property_array_check(prop);
- WM_operator_properties_create_ptr(&op_ptr, ot);
+ while (input->identifier) {
+ if (ELEM(input->value, CREATEDRIVER_MAPPING_1_1, CREATEDRIVER_MAPPING_NONE) || (is_array)) {
+ RNA_enum_item_add(&item, &totitem, input);
+ }
+ input++;
+ }
+ }
+ else {
+ /* We need at least this one! */
+ RNA_enum_items_add_value(&item, &totitem, input, CREATEDRIVER_MAPPING_NONE);
+ }
+
+ RNA_enum_item_end(&item, &totitem);
+
+ *r_free = true;
+ return item;
+}
+
+
+/* Add Driver Button Operator ------------------------ */
+
+static int add_driver_button_poll(bContext *C)
+{
+ PointerRNA ptr = {{NULL}};
+ PropertyRNA *prop = NULL;
+ int index;
+
+ /* this operator can only run if there's a property button active, and it can be animated */
+ UI_context_active_but_prop_get(C, &ptr, &prop, &index);
+ return (ptr.id.data && ptr.data && prop && RNA_property_animateable(&ptr, prop));
+}
+
+/* Wrapper for creating a driver without knowing what the targets will be yet (i.e. "manual/add later") */
+static int add_driver_button_none(bContext *C, wmOperator *op, short mapping_type)
+{
+ PointerRNA ptr = {{NULL}};
+ PropertyRNA *prop = NULL;
+ int index;
+ int success = 0;
+
+ UI_context_active_but_prop_get(C, &ptr, &prop, &index);
+
+ if (mapping_type == CREATEDRIVER_MAPPING_NONE_ALL)
+ index = -1;
+
+ if (ptr.id.data && ptr.data && prop && RNA_property_animateable(&ptr, prop)) {
+ char *path = BKE_animdata_driver_path_hack(C, &ptr, prop, NULL);
+ short flags = CREATEDRIVER_WITH_DEFAULT_DVAR;
- if (all)
- RNA_enum_set(&op_ptr, "mapping_type", CREATEDRIVER_MAPPING_1_N);
- else
- RNA_enum_set(&op_ptr, "mapping_type", CREATEDRIVER_MAPPING_1_1);
+ if (path) {
+ success += ANIM_add_driver(op->reports, ptr.id.data, path, index, flags, DRIVER_TYPE_PYTHON);
+ MEM_freeN(path);
+ }
+ }
+
+ if (success) {
+ /* send updates */
+ UI_context_update_anim_flag(C);
+ DAG_relations_tag_update(CTX_data_main(C));
+ WM_event_add_notifier(C, NC_ANIMATION | ND_FCURVES_ORDER, NULL); // XXX
- ret = WM_operator_name_call_ptr(C, ot, WM_OP_INVOKE_DEFAULT, &op_ptr);
+ return OPERATOR_FINISHED;
+ }
+ else {
+ return OPERATOR_CANCELLED;
+ }
+}
+
+static int add_driver_button_exec(bContext *C, wmOperator *op)
+{
+ short mapping_type = RNA_enum_get(op->ptr, "mapping_type");
+ if (ELEM(mapping_type, CREATEDRIVER_MAPPING_NONE, CREATEDRIVER_MAPPING_NONE_ALL)) {
+ /* Just create driver with no targets */
+ return add_driver_button_none(C, op, mapping_type);
+ }
+ else {
+ /* Create Driver using Eyedropper */
+ wmOperatorType *ot = WM_operatortype_find("UI_OT_eyedropper_driver", true);
- WM_operator_properties_free(&op_ptr);
+ /* XXX: We assume that it's fine to use the same set of properties, since they're actually the same... */
+ return WM_operator_name_call_ptr(C, ot, WM_OP_INVOKE_DEFAULT, op->ptr);
}
+}
+
+/* Show menu or create drivers */
+static int add_driver_button_invoke(bContext *C, wmOperator *op, const wmEvent *event)
+{
+ PropertyRNA *prop;
- return ret;
+ if ((prop = RNA_struct_find_property(op->ptr, "mapping_type")) && RNA_property_is_set(op->ptr, prop)) {
+ /* Mapping Type is Set - Directly go into creating drivers */
+ return add_driver_button_exec(C, op);
+ }
+ else {
+ /* Show menu */
+ // TODO: This should get filtered by the enum filter
+ return WM_menu_invoke(C, op, event);
+ }
}
void ANIM_OT_driver_button_add(wmOperatorType *ot)
@@ -689,14 +778,20 @@ void ANIM_OT_driver_button_add(wmOperatorType *ot)
ot->description = "Add driver(s) for the property(s) connected represented by the highlighted button";
/* callbacks */
+ /* NOTE: No exec, as we need all these to use the current context info
+ * (especially the eyedropper, which is interactive)
+ */
+ ot->invoke = add_driver_button_invoke;
ot->exec = add_driver_button_exec;
- //op->poll = ??? // TODO: need to have some animatable property to do this
+ ot->poll = add_driver_button_poll;
/* flags */
ot->flag = OPTYPE_UNDO | OPTYPE_INTERNAL;
-
+
/* properties */
- RNA_def_boolean(ot->srna, "all", 1, "All", "Create drivers for all elements of the array");
+ ot->prop = RNA_def_enum(ot->srna, "mapping_type", prop_driver_create_mapping_types, 0,
+ "Mapping Type", "Method used to match target and driven properties");
+ RNA_def_enum_funcs(ot->prop, driver_mapping_type_itemsf);
}
/* Remove Driver Button Operator ------------------------ */