Rework subflow edit process

This commit is contained in:
Nick O'Leary 2014-11-13 12:59:28 +00:00
parent 5cb9a5b7eb
commit 426fcc2fdd
5 changed files with 145 additions and 90 deletions

View File

@ -51,7 +51,9 @@
<div id="workspace-add-tab"><a id="btn-workspace-add-tab" href="#"><i class="fa fa-plus"></i></a></div>
<div id="chart"></div>
<div id="workspace-toolbar">
<a class="button" id="workspace-edit-subflow" href="#"><i class="fa fa-pencil"></i> edit subflow properties</a>
<a class="button" id="workspace-subflow-edit" href="#"><i class="fa fa-pencil"></i> edit subflow name</a>
<a class="button disabled" id="workspace-subflow-add-input" href="#"><i class="fa fa-plus"></i> input</a>
<a class="button" id="workspace-subflow-add-output" href="#"><i class="fa fa-plus"></i> output</a>
</div>
</div>
@ -82,12 +84,6 @@
<div class="form-row">
<label>Name</label><input type="text" id="subflow-input-name">
</div>
<div class="form-row">
<label>Inputs</label><input style="width: 60px; height: 1.7em;" id="subflow-input-inCount">
</div>
<div class="form-row">
<label>Outputs</label><input style="width: 60px; height: 1.7em;" id="subflow-input-outCount">
</div>
</form>
<div class="form-tips" id="subflow-dialog-user-count"></div>
</div>

View File

@ -129,15 +129,19 @@ RED.history = (function() {
}
}
if (ev.subflow) {
if (ev.node.in.length > ev.subflow.inputCount) {
ev.node.in.splice(ev.subflow.inputCount);
} else if (ev.subflow.inputs.length > 0) {
ev.node.in = ev.node.in.concat(ev.subflow.inputs);
if (ev.subflow.hasOwnProperty('inputCount')) {
if (ev.node.in.length > ev.subflow.inputCount) {
ev.node.in.splice(ev.subflow.inputCount);
} else if (ev.subflow.inputs.length > 0) {
ev.node.in = ev.node.in.concat(ev.subflow.inputs);
}
}
if (ev.node.out.length > ev.subflow.outputCount) {
ev.node.out.splice(ev.subflow.outputCount);
} else if (ev.subflow.outputs.length > 0) {
ev.node.out = ev.node.out.concat(ev.subflow.outputs);
if (ev.subflow.hasOwnProperty('outputCount')) {
if (ev.node.out.length > ev.subflow.outputCount) {
ev.node.out.splice(ev.subflow.outputCount);
} else if (ev.subflow.outputs.length > 0) {
ev.node.out = ev.node.out.concat(ev.subflow.outputs);
}
}
RED.nodes.eachNode(function(n) {
if (n.type == "subflow:"+ev.node.id) {
@ -148,8 +152,6 @@ RED.history = (function() {
}
});
RED.palette.refresh();
} else {
RED.editor.updateNodeProperties(ev.node);

View File

@ -750,74 +750,21 @@ RED.editor = (function() {
var wasDirty = RED.view.dirty();
var newName = $("#subflow-input-name").val();
var newInCount = Number($("#subflow-input-inCount").val())||0;
var newOutCount = Number($("#subflow-input-outCount").val())||0;
var oldInCount = editing_node.in.length;
var oldOutCount = editing_node.out.length;
if (newName != editing_node.name) {
changes['name'] = editing_node.name;
editing_node.name = newName;
changed = true;
$("#btn-workspace-menu-"+editing_node.id.replace(".","-")).text("Subflow: "+newName);
}
var xpos = 40;
var addedOutputs = [];
var removedOutputs = [];
var addedInputs = [];
var removedInputs = [];
var removedLinks = [];
if (editing_node.in.length < newInCount) {
var l = editing_node.in.length;
for (i=l;i<newInCount;i++) {
var newInput = {type:"subflow",direction:"in",z:editing_node.id,i:i,x:xpos,y:70,id:RED.node.id()};
addedInputs.push(newInput);
editing_node.in.push(newInput);
xpos += 55;
}
changed = true;
} else if (editing_node.in.length > newInCount) {
removedInputs = editing_node.in.splice(newInCount);
changed = true;
}
if (editing_node.out.length < newOutCount) {
for (i=editing_node.out.length;i<newOutCount;i++) {
var newOutput = {type:"subflow",direction:"out",z:editing_node.id,i:i,x:xpos,y:70,id:RED.node.id()};
addedOutputs.push(newOutput);
editing_node.out.push(newOutput);
xpos += 55;
}
changed = true;
} else if (editing_node.out.length > newOutCount) {
removedOutputs = editing_node.out.splice(newOutCount);
changed = true;
}
if (removedOutputs.length > 0 || removedInputs.length > 0) {
RED.nodes.eachLink(function(l) {
if (newInCount === 0 && l.source.type == "subflow" && l.source.z == editing_node.id) {
removedLinks.push(l);
return;
}
if (l.target.type == "subflow" && l.target.z == editing_node.id && l.target.i >= newOutCount) {
removedLinks.push(l);
return;
}
});
removedLinks.forEach(function(l) { RED.nodes.removeLink(l)});
}
RED.palette.refresh();
if (changed) {
RED.nodes.eachNode(function(n) {
if (n.type == "subflow:"+editing_node.id) {
n.changed = true;
n.inputs = editing_node.in.length;
n.outputs = editing_node.out.length;
removedLinks = removedLinks.concat(updateNodeProperties(n));
updateNodeProperties(n);
}
});
var wasChanged = editing_node.changed;
@ -827,15 +774,8 @@ RED.editor = (function() {
t:'edit',
node:editing_node,
changes:changes,
links:removedLinks,
dirty:wasDirty,
changed:wasChanged,
subflow: {
outputCount: oldOutCount,
inputCount: oldInCount,
outputs: removedOutputs,
inputs: removedInputs
}
changed:wasChanged
};
RED.history.push(historyEvent);
@ -873,8 +813,6 @@ RED.editor = (function() {
editing_node = subflow;
RED.view.state(RED.state.EDITING);
$("#subflow-input-name").val(subflow.name);
$("#subflow-input-inCount").spinner({ min:0, max:1 }).val(subflow.in.length);
$("#subflow-input-outCount").spinner({ min:0 }).val(subflow.out.length);
var userCount = 0;
var subflowType = "subflow:"+editing_node.id;
@ -884,7 +822,6 @@ RED.editor = (function() {
}
});
$("#subflow-dialog-user-count").html("There "+(userCount==1?"is":"are")+" "+userCount+" instance"+(userCount==1?" ":"s")+" of this subflow").show();
$("#subflow-dialog").dialog("option","title","Edit flow "+subflow.name).dialog( "open" );
}

View File

@ -227,10 +227,24 @@ RED.view = (function() {
var drag_line = vis.append("svg:path").attr("class", "drag_line");
$("#workspace-edit-subflow").click(function(event) {
$("#workspace-subflow-edit").click(function(event) {
showSubflowDialog(activeSubflow.id);
event.preventDefault();
});
$("#workspace-subflow-add-input").click(function(event) {
event.preventDefault();
if ($(this).hasClass("disabled")) {
return;
}
addSubflowInput(activeSubflow.id);
});
$("#workspace-subflow-add-output").click(function(event) {
event.preventDefault();
if ($(this).hasClass("disabled")) {
return;
}
addSubflowOutput(activeSubflow.id);
});
var workspace_tabs = RED.tabs.create({
id: "workspace-tabs",
@ -252,7 +266,9 @@ RED.view = (function() {
activeWorkspace = tab.id;
activeSubflow = RED.nodes.subflow(activeWorkspace);
if (activeSubflow) {
$("#workspace-subflow-add-input").toggleClass("disabled",activeSubflow.in.length > 0);
}
if (workspaceScrollPositions[activeWorkspace]) {
chart.scrollLeft(workspaceScrollPositions[activeWorkspace].left);
chart.scrollTop(workspaceScrollPositions[activeWorkspace].top);
@ -853,14 +869,15 @@ RED.view = (function() {
var subflowRemovedInputLinks = [];
RED.nodes.eachLink(function(l) {
if (l.source.type == "subflow" && l.source.z == activeSubflow.id && l.source.i == input.i) {
subflowRemovedLinks.push(l);
subflowRemovedInputLinks.push(l);
} else if (l.target.type == "subflow:"+activeSubflow.id) {
subflowRemovedLinks.push(l);
subflowRemovedInputLinks.push(l);
}
});
subflowRemovedInputLinks.forEach(function(l) { RED.nodes.removeLink(l)});
removedLinks = removedLinks.concat(subflowRemovedInputLinks);
activeSubflow.in = [];
$("#workspace-subflow-add-input").toggleClass("disabled",false);
}
RED.nodes.eachNode(function(n) {
@ -1817,7 +1834,104 @@ RED.view = (function() {
function showSubflowDialog(id) {
RED.editor.editSubflow(RED.nodes.subflow(id));
}
function findAvailableSubflowIOPosition(subflow) {
var pos = {x:70,y:70};
for (var i=0;i<subflow.out.length+subflow.in.length;i++) {
var port;
if (i < subflow.out.length) {
port = subflow.out[i];
} else {
port = subflow.in[i-subflow.out.length];
}
if (port.x == pos.x && port.y == pos.y) {
pos.x += 55;
i=0;
}
}
return pos;
}
function addSubflowInput(id) {
var subflow = RED.nodes.subflow(id);
var position = findAvailableSubflowIOPosition(subflow);
var newInput = {
type:"subflow",
direction:"in",
z:subflow.id,
i:subflow.in.length,
x:position.x,
y:position.y,
id:RED.nodes.id()
};
var oldInCount = subflow.in.length;
subflow.in.push(newInput);
subflow.dirty = true;
var wasDirty = RED.view.dirty();
var wasChanged = subflow.changed;
subflow.changed = true;
RED.nodes.eachNode(function(n) {
if (n.type == "subflow:"+subflow.id) {
n.changed = true;
n.inputs = subflow.in.length;
RED.editor.updateNodeProperties(n);
}
});
var historyEvent = {
t:'edit',
node:subflow,
dirty:wasDirty,
changed:wasChanged,
subflow: {
inputCount: oldInCount
}
};
RED.history.push(historyEvent);
$("#workspace-subflow-add-input").toggleClass("disabled",true);
updateSelection();
RED.view.redraw();
}
function addSubflowOutput(id) {
var subflow = RED.nodes.subflow(id);
var position = findAvailableSubflowIOPosition(subflow);
var newOutput = {
type:"subflow",
direction:"out",
z:subflow.id,
i:subflow.out.length,
x:position.x,
y:position.y,
id:RED.nodes.id()
};
var oldOutCount = subflow.out.length;
subflow.out.push(newOutput);
subflow.dirty = true;
var wasDirty = RED.view.dirty();
var wasChanged = subflow.changed;
subflow.changed = true;
RED.nodes.eachNode(function(n) {
if (n.type == "subflow:"+subflow.id) {
n.changed = true;
n.outputs = subflow.out.length;
RED.editor.updateNodeProperties(n);
}
});
var historyEvent = {
t:'edit',
node:subflow,
dirty:wasDirty,
changed:wasChanged,
subflow: {
outputCount: oldOutCount
}
};
RED.history.push(historyEvent);
updateSelection();
RED.view.redraw();
}
$("#node-dialog-rename-workspace form" ).submit(function(e) { e.preventDefault();});

View File

@ -137,12 +137,18 @@ span.logo img {
background: #f6f6f6;
vertical-align: middle;
box-shadow: 0 0 2px #888;
margin-right: 5px;
}
#workspace-toolbar .button:hover {
#workspace-toolbar .button.disabled {
box-shadow: 0 0 2px #bbb;
color: #aaa;
cursor: default;
}
#workspace-toolbar .button:not(.disabled):hover {
background: #e6e6e6;
box-shadow: 0 0 2px #666;
}
#workspace-toolbar .button:active {
#workspace-toolbar .button:not(.disabled):active {
background: #e0e0e0;
box-shadow: 0 0 2px #444;
}