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:
authorCharlie Jolly <charlie>2021-03-16 22:11:54 +0300
committerCharlie Jolly <mistajolly@gmail.com>2021-03-17 14:54:16 +0300
commit266cd7bb82ce4bfed20a3d61a84f25e2bacfca2b (patch)
tree963a983f902f5368669c1d93312b53262592e4dc /source/blender/editors
parent20bf736ff81c6fb79558796b74d50d4e7a9c8ef6 (diff)
Nodes: Add support to mute node wires
This patch adds the ability to mute individual wires in the node editor. This is invoked like the cut links operator but with a new shortcut. Mute = Ctrl + Alt Cut = Ctrl Dragging over wires will toggle the mute state for that wire. The muted wires are drawn in red with a bar across the center. Red is used in the nodes context to indicate invalid links, muted links and internal links. When a wire is muted it exposes the original node buttons which are normally hidden when a wire is connected. Downstream and upstream links connected using reroute nodes are also muted. Outside scope of patch: - Add support for pynodes e.g. Animation Nodes - Requires minor change to check for muted links using the `is_muted` link property or the `is_linked` socket property. Maniphest Tasks: T52659 Differential Revision: https://developer.blender.org/D2807
Diffstat (limited to 'source/blender/editors')
-rw-r--r--source/blender/editors/space_node/drawnode.c53
-rw-r--r--source/blender/editors/space_node/node_intern.h1
-rw-r--r--source/blender/editors/space_node/node_ops.c1
-rw-r--r--source/blender/editors/space_node/node_relationships.c111
4 files changed, 155 insertions, 11 deletions
diff --git a/source/blender/editors/space_node/drawnode.c b/source/blender/editors/space_node/drawnode.c
index 0f2b2b435bc..1354c06305c 100644
--- a/source/blender/editors/space_node/drawnode.c
+++ b/source/blender/editors/space_node/drawnode.c
@@ -3751,17 +3751,21 @@ bool node_link_bezier_points(const View2D *v2d,
#define LINK_WIDTH (2.5f * UI_DPI_FAC)
#define ARROW_SIZE (7 * UI_DPI_FAC)
+/* Reroute arrow shape and mute bar. These are expanded here and shrunk in the glsl code.
+ * See: gpu_shader_2D_nodelink_vert.glsl */
static float arrow_verts[3][2] = {{-1.0f, 1.0f}, {0.0f, 0.0f}, {-1.0f, -1.0f}};
static float arrow_expand_axis[3][2] = {{0.7071f, 0.7071f}, {M_SQRT2, 0.0f}, {0.7071f, -0.7071f}};
+static float mute_verts[3][2] = {{0.7071f, 1.0f}, {0.7071f, 0.0f}, {0.7071f, -1.0f}};
+static float mute_expand_axis[3][2] = {{1.0f, 0.0f}, {1.0f, 0.0f}, {1.0f, -0.0f}};
static struct {
GPUBatch *batch; /* for batching line together */
GPUBatch *batch_single; /* for single line */
GPUVertBuf *inst_vbo;
uint p0_id, p1_id, p2_id, p3_id;
- uint colid_id;
+ uint colid_id, muted_id;
GPUVertBufRaw p0_step, p1_step, p2_step, p3_step;
- GPUVertBufRaw colid_step;
+ GPUVertBufRaw colid_step, muted_step;
uint count;
bool enabled;
} g_batch_link = {0};
@@ -3774,6 +3778,8 @@ static void nodelink_batch_reset(void)
GPU_vertbuf_attr_get_raw_data(g_batch_link.inst_vbo, g_batch_link.p3_id, &g_batch_link.p3_step);
GPU_vertbuf_attr_get_raw_data(
g_batch_link.inst_vbo, g_batch_link.colid_id, &g_batch_link.colid_step);
+ GPU_vertbuf_attr_get_raw_data(
+ g_batch_link.inst_vbo, g_batch_link.muted_id, &g_batch_link.muted_step);
g_batch_link.count = 0;
}
@@ -3801,6 +3807,8 @@ static void nodelink_batch_init(void)
int vcount = LINK_RESOL * 2; /* curve */
vcount += 2; /* restart strip */
vcount += 3 * 2; /* arrow */
+ vcount += 2; /* restart strip */
+ vcount += 3 * 2; /* mute */
vcount *= 2; /* shadow */
vcount += 2; /* restart strip */
GPU_vertbuf_data_alloc(vbo, vcount);
@@ -3844,6 +3852,25 @@ static void nodelink_batch_init(void)
}
/* restart */
+ set_nodelink_vertex(vbo, uv_id, pos_id, expand_id, v++, uv, pos, exp);
+
+ uv[0] = 127;
+ uv[1] = 0;
+ copy_v2_v2(pos, mute_verts[0]);
+ copy_v2_v2(exp, mute_expand_axis[0]);
+ set_nodelink_vertex(vbo, uv_id, pos_id, expand_id, v++, uv, pos, exp);
+ /* bar */
+ for (int i = 0; i < 3; ++i) {
+ uv[1] = 0;
+ copy_v2_v2(pos, mute_verts[i]);
+ copy_v2_v2(exp, mute_expand_axis[i]);
+ set_nodelink_vertex(vbo, uv_id, pos_id, expand_id, v++, uv, pos, exp);
+
+ uv[1] = 255;
+ set_nodelink_vertex(vbo, uv_id, pos_id, expand_id, v++, uv, pos, exp);
+ }
+
+ /* restart */
if (k == 0) {
set_nodelink_vertex(vbo, uv_id, pos_id, expand_id, v++, uv, pos, exp);
}
@@ -3867,6 +3894,8 @@ static void nodelink_batch_init(void)
&format_inst, "P3", GPU_COMP_F32, 2, GPU_FETCH_FLOAT);
g_batch_link.colid_id = GPU_vertformat_attr_add(
&format_inst, "colid_doarrow", GPU_COMP_U8, 4, GPU_FETCH_INT);
+ g_batch_link.muted_id = GPU_vertformat_attr_add(
+ &format_inst, "domuted", GPU_COMP_U8, 2, GPU_FETCH_INT);
g_batch_link.inst_vbo = GPU_vertbuf_create_with_format_ex(&format_inst, GPU_USAGE_STREAM);
/* Alloc max count but only draw the range we need. */
GPU_vertbuf_data_alloc(g_batch_link.inst_vbo, NODELINK_GROUP_SIZE);
@@ -3941,12 +3970,13 @@ static void nodelink_batch_add_link(const SpaceNode *snode,
int th_col1,
int th_col2,
int th_col3,
- bool drawarrow)
+ bool drawarrow,
+ bool drawmuted)
{
/* Only allow these colors. If more is needed, you need to modify the shader accordingly. */
BLI_assert(ELEM(th_col1, TH_WIRE_INNER, TH_WIRE, TH_ACTIVE, TH_EDGE_SELECT, TH_REDALERT));
BLI_assert(ELEM(th_col2, TH_WIRE_INNER, TH_WIRE, TH_ACTIVE, TH_EDGE_SELECT, TH_REDALERT));
- BLI_assert(ELEM(th_col3, TH_WIRE, -1));
+ BLI_assert(ELEM(th_col3, TH_WIRE, TH_REDALERT, -1));
g_batch_link.count++;
copy_v2_v2(GPU_vertbuf_raw_step(&g_batch_link.p0_step), p0);
@@ -3958,6 +3988,8 @@ static void nodelink_batch_add_link(const SpaceNode *snode,
colid[1] = nodelink_get_color_id(th_col2);
colid[2] = nodelink_get_color_id(th_col3);
colid[3] = drawarrow;
+ char *muted = GPU_vertbuf_raw_step(&g_batch_link.muted_step);
+ muted[0] = drawmuted;
if (g_batch_link.count == NODELINK_GROUP_SIZE) {
nodelink_batch_draw(snode);
@@ -3977,7 +4009,7 @@ void node_draw_link_bezier(const View2D *v2d,
if (node_link_bezier_handles(v2d, snode, link, vec)) {
int drawarrow = ((link->tonode && (link->tonode->type == NODE_REROUTE)) &&
(link->fromnode && (link->fromnode->type == NODE_REROUTE)));
-
+ int drawmuted = (link->flag & NODE_LINK_MUTED);
if (g_batch_link.batch == NULL) {
nodelink_batch_init();
}
@@ -3985,7 +4017,7 @@ void node_draw_link_bezier(const View2D *v2d,
if (g_batch_link.enabled && !highlighted) {
/* Add link to batch. */
nodelink_batch_add_link(
- snode, vec[0], vec[1], vec[2], vec[3], th_col1, th_col2, th_col3, drawarrow);
+ snode, vec[0], vec[1], vec[2], vec[3], th_col1, th_col2, th_col3, drawarrow, drawmuted);
}
else {
/* Draw single link. */
@@ -4009,6 +4041,7 @@ void node_draw_link_bezier(const View2D *v2d,
GPU_batch_uniform_1f(batch, "expandSize", snode->runtime->aspect * LINK_WIDTH);
GPU_batch_uniform_1f(batch, "arrowSize", ARROW_SIZE);
GPU_batch_uniform_1i(batch, "doArrow", drawarrow);
+ GPU_batch_uniform_1i(batch, "doMuted", drawmuted);
GPU_batch_draw(batch);
}
}
@@ -4041,8 +4074,11 @@ void node_draw_link(View2D *v2d, SpaceNode *snode, bNodeLink *link)
if (link->flag & NODE_LINKFLAG_HILITE) {
th_col1 = th_col2 = TH_ACTIVE;
}
+ else if (link->flag & NODE_LINK_MUTED) {
+ th_col1 = th_col2 = TH_REDALERT;
+ }
else {
- /* regular link */
+ /* Regular link, highlight if connected to selected node. */
if (link->fromnode && link->fromnode->flag & SELECT) {
th_col1 = TH_EDGE_SELECT;
}
@@ -4052,7 +4088,8 @@ void node_draw_link(View2D *v2d, SpaceNode *snode, bNodeLink *link)
}
}
else {
- th_col1 = th_col2 = TH_REDALERT;
+ /* Invalid link. */
+ th_col1 = th_col2 = th_col3 = TH_REDALERT;
// th_col3 = -1; /* no shadow */
}
}
diff --git a/source/blender/editors/space_node/node_intern.h b/source/blender/editors/space_node/node_intern.h
index 1840ec93f6f..21a36ff9683 100644
--- a/source/blender/editors/space_node/node_intern.h
+++ b/source/blender/editors/space_node/node_intern.h
@@ -234,6 +234,7 @@ void NODE_OT_link(struct wmOperatorType *ot);
void NODE_OT_link_make(struct wmOperatorType *ot);
void NODE_OT_links_cut(struct wmOperatorType *ot);
void NODE_OT_links_detach(struct wmOperatorType *ot);
+void NODE_OT_links_mute(struct wmOperatorType *ot);
void NODE_OT_parent_set(struct wmOperatorType *ot);
void NODE_OT_join(struct wmOperatorType *ot);
diff --git a/source/blender/editors/space_node/node_ops.c b/source/blender/editors/space_node/node_ops.c
index ef28cfe8a8b..e35b444aa11 100644
--- a/source/blender/editors/space_node/node_ops.c
+++ b/source/blender/editors/space_node/node_ops.c
@@ -68,6 +68,7 @@ void node_operatortypes(void)
WM_operatortype_append(NODE_OT_link_make);
WM_operatortype_append(NODE_OT_links_cut);
WM_operatortype_append(NODE_OT_links_detach);
+ WM_operatortype_append(NODE_OT_links_mute);
WM_operatortype_append(NODE_OT_add_reroute);
WM_operatortype_append(NODE_OT_group_make);
diff --git a/source/blender/editors/space_node/node_relationships.c b/source/blender/editors/space_node/node_relationships.c
index ee07ec7a55c..2cc44d72c72 100644
--- a/source/blender/editors/space_node/node_relationships.c
+++ b/source/blender/editors/space_node/node_relationships.c
@@ -1227,8 +1227,8 @@ void NODE_OT_link_make(wmOperatorType *ot)
ot->srna, "replace", 0, "Replace", "Replace socket connections with the new links");
}
-/* ********************** Cut Link operator ***************** */
-static bool cut_links_intersect(bNodeLink *link, const float mcoords[][2], int tot)
+/* ********************** Node Link Intersect ***************** */
+static bool node_links_intersect(bNodeLink *link, const float mcoords[][2], int tot)
{
float coord_array[NODE_LINK_RESOL + 1][2];
@@ -1244,6 +1244,7 @@ static bool cut_links_intersect(bNodeLink *link, const float mcoords[][2], int t
return 0;
}
+/* ********************** Cut Link operator ***************** */
static int cut_links_exec(bContext *C, wmOperator *op)
{
Main *bmain = CTX_data_main(C);
@@ -1276,7 +1277,7 @@ static int cut_links_exec(bContext *C, wmOperator *op)
continue;
}
- if (cut_links_intersect(link, mcoords, i)) {
+ if (node_links_intersect(link, mcoords, i)) {
if (found == false) {
/* TODO(sergey): Why did we kill jobs twice? */
@@ -1335,6 +1336,110 @@ void NODE_OT_links_cut(wmOperatorType *ot)
RNA_def_int(ot->srna, "cursor", WM_CURSOR_KNIFE, 0, INT_MAX, "Cursor", "", 0, INT_MAX);
}
+/* ********************** Mute links operator ***************** */
+
+static int mute_links_exec(bContext *C, wmOperator *op)
+{
+ Main *bmain = CTX_data_main(C);
+ SpaceNode *snode = CTX_wm_space_node(C);
+ ARegion *region = CTX_wm_region(C);
+ bool do_tag_update = false;
+
+ int i = 0;
+ float mcoords[256][2];
+ RNA_BEGIN (op->ptr, itemptr, "path") {
+ float loc[2];
+
+ RNA_float_get_array(&itemptr, "loc", loc);
+ UI_view2d_region_to_view(
+ &region->v2d, (int)loc[0], (int)loc[1], &mcoords[i][0], &mcoords[i][1]);
+ i++;
+ if (i >= 256) {
+ break;
+ }
+ }
+ RNA_END;
+
+ if (i > 1) {
+ ED_preview_kill_jobs(CTX_wm_manager(C), bmain);
+
+ /* Count intersected links and clear test flag. */
+ int tot = 0;
+ LISTBASE_FOREACH (bNodeLink *, link, &snode->edittree->links) {
+ if (nodeLinkIsHidden(link)) {
+ continue;
+ }
+ link->flag &= ~NODE_LINK_TEST;
+ if (node_links_intersect(link, mcoords, i)) {
+ tot++;
+ }
+ }
+ if (tot == 0) {
+ return OPERATOR_CANCELLED;
+ }
+
+ /* Mute links. */
+ LISTBASE_FOREACH (bNodeLink *, link, &snode->edittree->links) {
+ if (nodeLinkIsHidden(link) || (link->flag & NODE_LINK_TEST)) {
+ continue;
+ }
+
+ if (node_links_intersect(link, mcoords, i)) {
+ do_tag_update |= (do_tag_update ||
+ node_connected_to_output(bmain, snode->edittree, link->tonode));
+
+ snode_update(snode, link->tonode);
+ nodeMuteLinkToggle(snode->edittree, link);
+ }
+ }
+
+ /* Clear remaining test flags. */
+ LISTBASE_FOREACH (bNodeLink *, link, &snode->edittree->links) {
+ if (nodeLinkIsHidden(link)) {
+ continue;
+ }
+ link->flag &= ~NODE_LINK_TEST;
+ }
+
+ do_tag_update |= ED_node_is_geometry(snode);
+
+ ntreeUpdateTree(CTX_data_main(C), snode->edittree);
+ snode_notify(C, snode);
+ if (do_tag_update) {
+ snode_dag_update(C, snode);
+ }
+
+ return OPERATOR_FINISHED;
+ }
+
+ return OPERATOR_CANCELLED | OPERATOR_PASS_THROUGH;
+}
+
+void NODE_OT_links_mute(wmOperatorType *ot)
+{
+ ot->name = "Mute Links";
+ ot->idname = "NODE_OT_links_mute";
+ ot->description = "Use the mouse to mute links";
+
+ ot->invoke = WM_gesture_lines_invoke;
+ ot->modal = WM_gesture_lines_modal;
+ ot->exec = mute_links_exec;
+ ot->cancel = WM_gesture_lines_cancel;
+
+ ot->poll = ED_operator_node_editable;
+
+ /* flags */
+ ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
+
+ /* properties */
+ PropertyRNA *prop;
+ prop = RNA_def_collection_runtime(ot->srna, "path", &RNA_OperatorMousePath, "Path", "");
+ RNA_def_property_flag(prop, PROP_HIDDEN | PROP_SKIP_SAVE);
+
+ /* internal */
+ RNA_def_int(ot->srna, "cursor", WM_CURSOR_MUTE, 0, INT_MAX, "Cursor", "", 0, INT_MAX);
+}
+
/* ********************** Detach links operator ***************** */
static int detach_links_exec(bContext *C, wmOperator *UNUSED(op))