[Bf-blender-cvs] [cd3d261e3c8] soc-2020-outliner: Outliner modifier drop
Nathan Craddock
noreply at git.blender.org
Sat Jul 4 04:57:33 CEST 2020
Commit: cd3d261e3c86d75af93cdd66f30b620b2a5f7c5a
Author: Nathan Craddock
Date: Mon Jun 29 16:20:51 2020 -0600
Branches: soc-2020-outliner
https://developer.blender.org/rBcd3d261e3c86d75af93cdd66f30b620b2a5f7c5a
Outliner modifier drop
Initial implementation. Experimentation to see what types of data
are needed.
===================================================================
M source/blender/editors/space_outliner/outliner_dragdrop.c
M source/blender/editors/space_outliner/outliner_draw.c
M source/blender/editors/space_outliner/outliner_intern.h
M source/blender/editors/space_outliner/outliner_ops.c
M source/blender/windowmanager/WM_api.h
M source/blender/windowmanager/intern/wm_dragdrop.c
===================================================================
diff --git a/source/blender/editors/space_outliner/outliner_dragdrop.c b/source/blender/editors/space_outliner/outliner_dragdrop.c
index 09d7f889bde..5f5ef49f6b1 100644
--- a/source/blender/editors/space_outliner/outliner_dragdrop.c
+++ b/source/blender/editors/space_outliner/outliner_dragdrop.c
@@ -27,6 +27,7 @@
#include "DNA_collection_types.h"
#include "DNA_material_types.h"
+#include "DNA_modifier_types.h"
#include "DNA_object_types.h"
#include "DNA_space_types.h"
@@ -616,6 +617,106 @@ void OUTLINER_OT_material_drop(wmOperatorType *ot)
ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO | OPTYPE_INTERNAL;
}
+/* ******************** Modifier Drop Operator *********************** */
+
+typedef struct ModifierDrop {
+ ModifierData *from;
+ ModifierData *to;
+} ModiferDrop;
+
+static bool outliner_is_modifier_element(TreeElement *te)
+{
+ TreeStoreElem *tselem = TREESTORE(te);
+
+ return tselem->type == TSE_MODIFIER;
+}
+
+static bool modifier_drop_poll(bContext *C,
+ wmDrag *drag,
+ const wmEvent *event,
+ const char **r_tooltip)
+{
+ TreeStoreElem *tselem = drag->poin;
+ if (!tselem) {
+ return false;
+ }
+
+ TreeElementInsertType insert_type;
+ TreeElement *te_target = outliner_drop_insert_find(C, event, &insert_type);
+ if (!te_target) {
+ return false;
+ }
+ TreeStoreElem *tselem_target = TREESTORE(te_target);
+
+ if (outliner_ID_drop_find(C, event, ID_OB)) {
+ *r_tooltip = TIP_("Copy modifier to object");
+ return true;
+ }
+ else if (tselem_target->type == TSE_MODIFIER) {
+ switch (insert_type) {
+ case TE_INSERT_BEFORE:
+ tselem_target->flag |= TSE_DRAG_BEFORE;
+ if (te_target->prev && outliner_is_modifier_element(te_target->prev)) {
+ *r_tooltip = TIP_("Move between modifiers");
+ }
+ else {
+ *r_tooltip = TIP_("Move before modifier");
+ }
+ break;
+ case TE_INSERT_AFTER:
+ tselem_target->flag |= TSE_DRAG_AFTER;
+ if (te_target->next && outliner_is_modifier_element(te_target->next)) {
+ *r_tooltip = TIP_("Move between modifiers");
+ }
+ else {
+ *r_tooltip = TIP_("Move after modifier");
+ }
+ break;
+ default:
+ return false;
+ }
+ return true;
+ }
+
+ return false;
+}
+
+static int modifier_drop_invoke(bContext *C, wmOperator *op, const wmEvent *event)
+{
+ SpaceOutliner *soops = CTX_wm_space_outliner(C);
+ TreeStoreElem *tselem = WM_drag_data_from_event(event);
+
+ TreeElementInsertType insert_type;
+ TreeElement *te = outliner_drop_insert_find(C, event, &insert_type);
+
+ Object *ob = (Object *)tselem->id;
+ TreeElement *te_md = outliner_find_tree_element(&soops->tree, tselem);
+ ModifierData *md = te_md->directdata;
+
+ ED_object_modifier_move_to_index(op->reports, ob, md, te->index);
+
+ DEG_id_tag_update(&ob->id, ID_RECALC_GEOMETRY);
+ WM_event_add_notifier(C, NC_OBJECT | ND_MODIFIER, ob);
+
+ return OPERATOR_FINISHED;
+}
+
+void OUTLINER_OT_modifier_drop(wmOperatorType *ot)
+{
+ /* identifiers */
+ ot->name = "Move Modifier";
+ ot->description = "Drag modifier to object in Outliner";
+ ot->idname = "OUTLINER_OT_modifier_drop";
+
+ /* api callbacks */
+ ot->invoke = modifier_drop_invoke;
+
+ ot->poll = ED_operator_outliner_active;
+
+ /* flags */
+ ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO | OPTYPE_INTERNAL;
+}
+
/* ******************** Collection Drop Operator *********************** */
typedef struct CollectionDrop {
@@ -880,7 +981,8 @@ static int outliner_item_drag_drop_invoke(bContext *C,
return (OPERATOR_CANCELLED | OPERATOR_PASS_THROUGH);
}
- TreeElementIcon data = tree_element_get_icon(TREESTORE(te), te);
+ TreeStoreElem *tselem = TREESTORE(te);
+ TreeElementIcon data = tree_element_get_icon(tselem, te);
if (!data.drag_id) {
return (OPERATOR_CANCELLED | OPERATOR_PASS_THROUGH);
}
@@ -897,13 +999,16 @@ static int outliner_item_drag_drop_invoke(bContext *C,
wmDrag *drag = WM_event_start_drag(C, data.icon, WM_DRAG_ID, NULL, 0.0, WM_DRAG_NOP);
- if (ELEM(GS(data.drag_id->name), ID_OB, ID_GR)) {
+ if (tselem->type == TSE_MODIFIER) {
+ drag->poin = tselem;
+ }
+ else if (ELEM(GS(data.drag_id->name), ID_OB, ID_GR)) {
/* For collections and objects we cheat and drag all selected. */
/* Only drag element under mouse if it was not selected before. */
- if ((TREESTORE(te)->flag & TSE_SELECTED) == 0) {
+ if ((tselem->flag & TSE_SELECTED) == 0) {
outliner_flag_set(&soops->tree, TSE_SELECTED, 0);
- TREESTORE(te)->flag |= TSE_SELECTED;
+ tselem->flag |= TSE_SELECTED;
}
/* Gather all selected elements. */
@@ -1004,5 +1109,6 @@ void outliner_dropboxes(void)
WM_dropbox_add(lb, "OUTLINER_OT_parent_clear", parent_clear_poll, NULL);
WM_dropbox_add(lb, "OUTLINER_OT_scene_drop", scene_drop_poll, NULL);
WM_dropbox_add(lb, "OUTLINER_OT_material_drop", material_drop_poll, NULL);
+ WM_dropbox_add(lb, "OUTLINER_OT_modifier_drop", modifier_drop_poll, NULL);
WM_dropbox_add(lb, "OUTLINER_OT_collection_drop", collection_drop_poll, NULL);
}
diff --git a/source/blender/editors/space_outliner/outliner_draw.c b/source/blender/editors/space_outliner/outliner_draw.c
index b077ad3d300..9f3760af3d7 100644
--- a/source/blender/editors/space_outliner/outliner_draw.c
+++ b/source/blender/editors/space_outliner/outliner_draw.c
@@ -2156,6 +2156,8 @@ TreeElementIcon tree_element_get_icon(TreeStoreElem *tselem, TreeElement *te)
break;
case TSE_MODIFIER: {
Object *ob = (Object *)tselem->id;
+ data.drag_id = tselem->id;
+
if (ob->type != OB_GPENCIL) {
ModifierData *md = BLI_findlink(&ob->modifiers, tselem->nr);
switch ((ModifierType)md->type) {
diff --git a/source/blender/editors/space_outliner/outliner_intern.h b/source/blender/editors/space_outliner/outliner_intern.h
index 868067958ff..5450c0fcb56 100644
--- a/source/blender/editors/space_outliner/outliner_intern.h
+++ b/source/blender/editors/space_outliner/outliner_intern.h
@@ -393,6 +393,7 @@ void OUTLINER_OT_parent_drop(struct wmOperatorType *ot);
void OUTLINER_OT_parent_clear(struct wmOperatorType *ot);
void OUTLINER_OT_scene_drop(struct wmOperatorType *ot);
void OUTLINER_OT_material_drop(struct wmOperatorType *ot);
+void OUTLINER_OT_modifier_drop(struct wmOperatorType *ot);
void OUTLINER_OT_collection_drop(struct wmOperatorType *ot);
/* ...................................................... */
diff --git a/source/blender/editors/space_outliner/outliner_ops.c b/source/blender/editors/space_outliner/outliner_ops.c
index 22541a0ab1f..0760159f61a 100644
--- a/source/blender/editors/space_outliner/outliner_ops.c
+++ b/source/blender/editors/space_outliner/outliner_ops.c
@@ -88,6 +88,7 @@ void outliner_operatortypes(void)
WM_operatortype_append(OUTLINER_OT_parent_clear);
WM_operatortype_append(OUTLINER_OT_scene_drop);
WM_operatortype_append(OUTLINER_OT_material_drop);
+ WM_operatortype_append(OUTLINER_OT_modifier_drop);
WM_operatortype_append(OUTLINER_OT_collection_drop);
/* collections */
diff --git a/source/blender/windowmanager/WM_api.h b/source/blender/windowmanager/WM_api.h
index 482589e2ccb..67ba283c1f1 100644
--- a/source/blender/windowmanager/WM_api.h
+++ b/source/blender/windowmanager/WM_api.h
@@ -673,6 +673,8 @@ void WM_drag_add_ID(struct wmDrag *drag, struct ID *id, struct ID *from_parent);
struct ID *WM_drag_ID(const struct wmDrag *drag, short idcode);
struct ID *WM_drag_ID_from_event(const struct wmEvent *event, short idcode);
+void *WM_drag_data_from_event(const struct wmEvent *event);
+
/* Set OpenGL viewport and scissor */
void wmViewport(const struct rcti *rect);
void wmPartialViewport(rcti *drawrct, const rcti *winrct, const rcti *partialrct);
diff --git a/source/blender/windowmanager/intern/wm_dragdrop.c b/source/blender/windowmanager/intern/wm_dragdrop.c
index ad3fc7a1302..a5018273465 100644
--- a/source/blender/windowmanager/intern/wm_dragdrop.c
+++ b/source/blender/windowmanager/intern/wm_dragdrop.c
@@ -285,6 +285,17 @@ void wm_drags_check_ops(bContext *C, const wmEvent *event)
}
}
+void *WM_drag_data_from_event(const struct wmEvent *event)
+{
+ if (event->custom != EVT_DATA_DRAGDROP) {
+ return NULL;
+ }
+
+ ListBase *lb = event->customdata;
+ wmDrag *drag = lb->first;
+ return drag->poin;
+}
+
/* ************** IDs ***************** */
void WM_drag_add_ID(wmDrag *drag, ID *id, ID *from_parent)
More information about the Bf-blender-cvs
mailing list