Skip to content

Commit

Permalink
✨ Added support for drag and drop from nodes main panel.
Browse files Browse the repository at this point in the history
✨ Added node draggable placeholder.
  • Loading branch information
alexgrozav committed Apr 12, 2022
1 parent 94a52b9 commit 0413004
Show file tree
Hide file tree
Showing 7 changed files with 144 additions and 48 deletions.
10 changes: 6 additions & 4 deletions packages/editor-ui/src/components/NodeCreator/CreatorItem.vue
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@
clickable: props.clickable,
active: props.active,
}"
@click="listeners['click']"
>
@click="listeners.click"
>
<CategoryItem
v-if="props.item.type === 'category'"
:item="props.item"
Expand All @@ -21,7 +21,9 @@
v-else-if="props.item.type === 'node'"
:nodeType="props.item.properties.nodeType"
:bordered="!props.lastNode"
></NodeItem>
@dragstart="listeners.dragstart"
@dragend="listeners.dragend"
/>
</div>
</template>

Expand Down Expand Up @@ -54,4 +56,4 @@ export default {
}
}
</style>
</style>
15 changes: 11 additions & 4 deletions packages/editor-ui/src/components/NodeCreator/ItemIterator.vue
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,22 @@
@before-leave="beforeLeave"
@leave="leave"
>
<div v-for="(item, index) in elements" :key="item.key" :class="item.type" :data-key="item.key">
<div
v-for="(item, index) in elements"
:key="item.key"
:class="item.type"
:data-key="item.key"
>
<CreatorItem
:item="item"
:active="activeIndex === index && !disabled"
:clickable="!disabled"
:lastNode="
index === elements.length - 1 || elements[index + 1].type !== 'node'
"
@click="() => selected(item)"
@click="emit('selected', item, $event)"
@dragstart="emit('dragstart', item, $event)"
@dragend="emit('dragend', item, $event)"
/>
</div>
</div>
Expand All @@ -36,12 +43,12 @@ export default Vue.extend({
},
props: ['elements', 'activeIndex', 'disabled', 'transitionsEnabled'],
methods: {
selected(element: INodeCreateElement) {
emit(eventName: string, element: INodeCreateElement, event: Event) {
if (this.$props.disabled) {
return;
}
this.$emit('selected', element);
this.$emit(eventName, { element, event });
},
beforeEnter(el: HTMLElement) {
el.style.height = '0';
Expand Down
26 changes: 18 additions & 8 deletions packages/editor-ui/src/components/NodeCreator/MainPanel.vue
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@
:activeIndex="activeIndex"
:transitionsEnabled="true"
@selected="selected"
@dragstart="emitNodeEvent('nodeTypeDragStart', $event)"
@dragend="emitNodeEvent('nodeTypeDragEnd', $event)"
/>
</div>
<div
Expand All @@ -33,9 +35,14 @@
:elements="filteredNodeTypes"
:activeIndex="activeIndex"
@selected="selected"
@dragstart="emitNodeEvent('nodeTypeDragStart', $event)"
@dragend="emitNodeEvent('nodeTypeDragEnd', $event)"
/>
</div>
<NoResults v-else @nodeTypeSelected="nodeTypeSelected" />
<NoResults
v-else
@nodeTypeSelected="$emit('nodeTypeSelected', $event)"
/>
</div>
</div>
</template>
Expand All @@ -55,6 +62,7 @@ import { INodeCreateElement, INodeItemProps, ISubcategoryItemProps } from '@/Int
import { ALL_NODE_FILTER, CORE_NODES_CATEGORY, REGULAR_NODE_FILTER, TRIGGER_NODE_FILTER } from '@/constants';
import SlideTransition from '../transitions/SlideTransition.vue';
import { matchesNodeType, matchesSelectType } from './helpers';
import {INodeTypeDescription} from "n8n-workflow";
export default mixins(externalHooks).extend({
Expand Down Expand Up @@ -233,20 +241,15 @@ export default mixins(externalHooks).extend({
this.selected(activeNodeType);
}
},
selected(element: INodeCreateElement) {
selected({ element, event }: { element: INodeCreateElement, event: MouseEvent }) {
if (element.type === 'node') {
const properties = element.properties as INodeItemProps;
this.nodeTypeSelected(properties.nodeType.name);
this.emitNodeEvent('nodeTypeSelected', { element, event });
} else if (element.type === 'category') {
this.onCategorySelected(element.category);
} else if (element.type === 'subcategory') {
this.onSubcategorySelected(element);
}
},
nodeTypeSelected(nodeTypeName: string) {
this.$emit('nodeTypeSelected', nodeTypeName);
},
onCategorySelected(category: string) {
if (this.activeCategory.includes(category)) {
this.activeCategory = this.activeCategory.filter(
Expand Down Expand Up @@ -276,6 +279,13 @@ export default mixins(externalHooks).extend({
onClickInside() {
this.searchEventBus.$emit('focus');
},
emitNodeEvent(eventName: string, { element, event }: { element: INodeCreateElement, event: Event }) {
this.$emit(eventName, {
nodeTypeName: (element.properties as INodeItemProps).nodeType.name,
event,
});
},
},
async mounted() {
this.$nextTick(() => {
Expand Down
18 changes: 16 additions & 2 deletions packages/editor-ui/src/components/NodeCreator/NodeCreator.vue
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,14 @@
<div>
<SlideTransition>
<div class="node-creator" v-if="active" v-click-outside="onClickOutside">
<MainPanel @nodeTypeSelected="nodeTypeSelected" :categorizedItems="categorizedItems" :categoriesWithNodes="categoriesWithNodes" :searchItems="searchItems"></MainPanel>
<MainPanel
@nodeTypeSelected="nodeTypeSelected"
@nodeTypeDragStart="nodeTypeDragStart"
@nodeTypeDragEnd="nodeTypeDragEnd"
:categorizedItems="categorizedItems"
:categoriesWithNodes="categoriesWithNodes"
:searchItems="searchItems"
/>
</div>
</SlideTransition>
</div>
Expand Down Expand Up @@ -91,9 +98,16 @@ export default Vue.extend({
this.$emit('closeNodeCreator');
}
},
nodeTypeSelected (nodeTypeName: string) {
nodeTypeSelected ({ nodeTypeName }: { nodeTypeName: string }) {
this.$emit('nodeTypeSelected', nodeTypeName);
},
nodeTypeDragStart (event: { nodeTypeName: string, event: DragEvent }) {
this.$emit('nodeTypeDragStart', event);
},
nodeTypeDragEnd (event: { nodeTypeName: string, event: DragEvent }) {
this.$emit('closeNodeCreator');
this.$emit('nodeTypeDragEnd', event);
},
},
watch: {
nodeTypes(newList) {
Expand Down
41 changes: 40 additions & 1 deletion packages/editor-ui/src/components/NodeCreator/NodeItem.vue
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@
<template>
<div :class="{[$style['node-item']]: true, [$style.bordered]: bordered}">
<div
draggable
@dragstart="onDragStart"
@dragend="onDragEnd"
:class="{[$style['node-item']]: true, [$style.bordered]: bordered}"
>
<NodeIcon :class="$style['node-icon']" :nodeType="nodeType" />
<div>
<div :class="$style.details">
Expand All @@ -21,6 +26,10 @@
})
}}
</div>

<div :class="$style.draggable" ref="draggable" v-show="dragging">
<NodeIcon class="node-icon" :nodeType="nodeType" :size="40" :shrink="false" />
</div>
</div>
</div>
</template>
Expand All @@ -44,11 +53,28 @@ export default Vue.extend({
'nodeType',
'bordered',
],
data(): { dragging: boolean; } {
return {
dragging: false,
};
},
computed: {
shortNodeType() {
return this.$locale.shortNodeType(this.nodeType.name);
},
},
methods: {
onDragStart(event: DragEvent) {
this.$emit('dragstart', event);
this.$data.dragging = true;
event.dataTransfer!.setDragImage(this.$refs.draggable as Element, 0, 0);
},
onDragEnd(event: Event) {
this.$emit('dragend', event);
this.$data.dragging = false;
},
},
// @ts-ignore
isTrigger (nodeType: INodeTypeDescription): boolean {
return nodeType.group.includes('trigger');
Expand Down Expand Up @@ -100,4 +126,17 @@ export default Vue.extend({
display: flex;
}
.draggable {
width: 100px;
height: 100px;
position: fixed;
top: -100px;
left: -100px;
border: 2px solid var(--color-foreground-xdark);
border-radius: var(--border-radius-large);
background-color: var(--color-background-xlight);
display: flex;
justify-content: center;
align-items: center;
}
</style>
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ export default Vue.extend({
},
},
methods: {
selected(element: INodeCreateElement) {
selected({ element }: { element: INodeCreateElement }) {
this.$emit('selected', element);
},
onBackArrowClick() {
Expand Down Expand Up @@ -101,4 +101,4 @@ export default Vue.extend({
}
}
</style>
</style>
Loading

0 comments on commit 0413004

Please sign in to comment.