mirror of
https://github.com/n8n-io/n8n.git
synced 2024-12-25 12:44:07 -08:00
fix(editor): Fixes the issue that Switch Node can not be created (#7516)
Fixes the issue that currently no Switch-Node can be created by for example pressing + on the parent node or via tab when another node is already selected. Github issue / Community forum post (link here to close automatically): --------- Signed-off-by: Oleg Ivaniv <me@olegivaniv.com> Co-authored-by: Oleg Ivaniv <me@olegivaniv.com>
This commit is contained in:
parent
742c8a8534
commit
df89685e15
|
@ -30,6 +30,7 @@ describe('Canvas Node Manipulation and Navigation', () => {
|
|||
|
||||
it('should add switch node and test connections', () => {
|
||||
const desiredOutputs = 4;
|
||||
WorkflowPage.actions.addNodeToCanvas(MANUAL_TRIGGER_NODE_NAME, true);
|
||||
WorkflowPage.actions.addNodeToCanvas(SWITCH_NODE_NAME, true, true);
|
||||
|
||||
for (let i = 0; i < desiredOutputs; i++) {
|
||||
|
@ -43,9 +44,14 @@ describe('Canvas Node Manipulation and Navigation', () => {
|
|||
WorkflowPage.actions.addNodeToCanvas(EDIT_FIELDS_SET_NODE_NAME, false);
|
||||
WorkflowPage.actions.zoomToFit();
|
||||
}
|
||||
WorkflowPage.getters.nodeViewBackground().click({ force: true });
|
||||
WorkflowPage.getters.canvasNodePlusEndpointByName(`${EDIT_FIELDS_SET_NODE_NAME}3`).click();
|
||||
WorkflowPage.actions.addNodeToCanvas(SWITCH_NODE_NAME, false);
|
||||
WorkflowPage.actions.saveWorkflowOnButtonClick();
|
||||
cy.reload();
|
||||
cy.waitForLoad();
|
||||
// Make sure outputless switch was connected correctly
|
||||
cy.get(`[data-target-node="${SWITCH_NODE_NAME}1"][data-source-node="${EDIT_FIELDS_SET_NODE_NAME}3"]`).should('be.visible');
|
||||
// Make sure all connections are there after reload
|
||||
for (let i = 0; i < desiredOutputs; i++) {
|
||||
const setName = `${EDIT_FIELDS_SET_NODE_NAME}${i > 0 ? i : ''}`;
|
||||
|
|
|
@ -265,6 +265,7 @@ import type {
|
|||
IWorkflowBase,
|
||||
Workflow,
|
||||
ConnectionTypes,
|
||||
INodeOutputConfiguration,
|
||||
} from 'n8n-workflow';
|
||||
import {
|
||||
deepCopy,
|
||||
|
@ -1970,29 +1971,47 @@ export default defineComponent({
|
|||
this.canvasStore.newNodeInsertPosition = null;
|
||||
} else {
|
||||
let yOffset = 0;
|
||||
const workflow = this.getCurrentWorkflow();
|
||||
|
||||
if (lastSelectedConnection) {
|
||||
const sourceNodeType = this.nodeTypesStore.getNodeType(
|
||||
lastSelectedNode.type,
|
||||
lastSelectedNode.typeVersion,
|
||||
);
|
||||
const offsets = [
|
||||
[-100, 100],
|
||||
[-140, 0, 140],
|
||||
[-240, -100, 100, 240],
|
||||
];
|
||||
if (sourceNodeType && sourceNodeType.outputs.length > 1) {
|
||||
const offset = offsets[sourceNodeType.outputs.length - 2];
|
||||
const sourceOutputIndex = lastSelectedConnection.__meta
|
||||
? lastSelectedConnection.__meta.sourceOutputIndex
|
||||
: 0;
|
||||
yOffset = offset[sourceOutputIndex];
|
||||
if (sourceNodeType) {
|
||||
const offsets = [
|
||||
[-100, 100],
|
||||
[-140, 0, 140],
|
||||
[-240, -100, 100, 240],
|
||||
];
|
||||
const sourceNodeOutputs = NodeHelpers.getNodeOutputs(
|
||||
workflow,
|
||||
lastSelectedNode!,
|
||||
sourceNodeType,
|
||||
);
|
||||
const sourceNodeOutputTypes = NodeHelpers.getConnectionTypes(sourceNodeOutputs);
|
||||
const sourceNodeOutputMainOutputs = sourceNodeOutputTypes.filter(
|
||||
(output) => output === NodeConnectionType.Main,
|
||||
);
|
||||
if (sourceNodeOutputMainOutputs.length > 1) {
|
||||
const offset = offsets[sourceNodeOutputMainOutputs.length - 2];
|
||||
const sourceOutputIndex = lastSelectedConnection.__meta
|
||||
? lastSelectedConnection.__meta.sourceOutputIndex
|
||||
: 0;
|
||||
yOffset = offset[sourceOutputIndex];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const workflow = this.getCurrentWorkflow();
|
||||
const workflowNode = workflow.getNode(newNodeData.name);
|
||||
const outputs = NodeHelpers.getNodeOutputs(workflow, workflowNode!, nodeTypeData);
|
||||
let outputs: Array<ConnectionTypes | INodeOutputConfiguration> = [];
|
||||
try {
|
||||
// It fails when the outputs are an expression. As those node have
|
||||
// normally no outputs by default and the only reason we need the
|
||||
// outputs here is to calculate the position it is fine to assume
|
||||
// that they have no outputs and are so treated as a regular node
|
||||
// with only "main" outputs.
|
||||
outputs = NodeHelpers.getNodeOutputs(workflow, newNodeData!, nodeTypeData);
|
||||
} catch (e) {}
|
||||
const outputTypes = NodeHelpers.getConnectionTypes(outputs);
|
||||
const lastSelectedNodeType = this.nodeTypesStore.getNodeType(
|
||||
lastSelectedNode.type,
|
||||
|
@ -2000,7 +2019,10 @@ export default defineComponent({
|
|||
);
|
||||
|
||||
// If node has only scoped outputs, position it below the last selected node
|
||||
if (outputTypes.every((outputName) => outputName !== NodeConnectionType.Main)) {
|
||||
if (
|
||||
outputTypes.length > 0 &&
|
||||
outputTypes.every((outputName) => outputName !== NodeConnectionType.Main)
|
||||
) {
|
||||
const lastSelectedNodeWorkflow = workflow.getNode(lastSelectedNode.name);
|
||||
const lastSelectedInputs = NodeHelpers.getNodeInputs(
|
||||
workflow,
|
||||
|
@ -2025,6 +2047,7 @@ export default defineComponent({
|
|||
[100, 0],
|
||||
);
|
||||
} else {
|
||||
// Has only main outputs or no outputs at all
|
||||
const inputs = NodeHelpers.getNodeInputs(
|
||||
workflow,
|
||||
lastSelectedNode,
|
||||
|
|
Loading…
Reference in a new issue