This is an automated email from the ASF dual-hosted git repository.

nicholasjiang pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/incubator-paimon-webui.git


The following commit(s) were added to refs/heads/main by this push:
     new a4932f2  [Feature] Introduce x6 dag component (#88)
a4932f2 is described below

commit a4932f2f2207c0e85238410d0847f328682cef1d
Author: labbomb <[email protected]>
AuthorDate: Tue Oct 31 11:08:26 2023 +0800

    [Feature] Introduce x6 dag component (#88)
---
 paimon-web-ui-new/package.json                     |   3 +
 paimon-web-ui-new/pnpm-lock.yaml                   |  57 +++++++++-
 paimon-web-ui-new/src/locales/en/modules/cdc.ts    |   1 +
 paimon-web-ui-new/src/locales/zh/modules/cdc.ts    |   1 +
 paimon-web-ui-new/src/main.ts                      |  13 ---
 .../src/views/cdc/components/dag/custom-node.tsx   |  63 +++++++++++
 .../components/dag/{index.tsx => dag-canvas.tsx}   |  23 +++-
 .../src/views/cdc/components/dag/dag-slider.tsx    | 121 +++++++++++++++++++++
 .../src/views/cdc/components/dag/index.module.scss |  68 ++++++++++++
 .../src/views/cdc/components/dag/index.tsx         |  37 ++++++-
 .../src/views/cdc/components/dag/node-config.ts    | 106 ++++++++++++++++++
 .../views/cdc/components/dag/use-canvas-init.ts    | 113 +++++++++++++++++++
 12 files changed, 585 insertions(+), 21 deletions(-)

diff --git a/paimon-web-ui-new/package.json b/paimon-web-ui-new/package.json
index 27fd659..ae38941 100644
--- a/paimon-web-ui-new/package.json
+++ b/paimon-web-ui-new/package.json
@@ -12,6 +12,9 @@
     "format": "prettier --write src/"
   },
   "dependencies": {
+    "@antv/x6": "^2.15.3",
+    "@antv/x6-plugin-dnd": "^2.1.1",
+    "@antv/x6-vue-shape": "^2.1.1",
     "dart-sass": "^1.25.0",
     "lodash": "^4.17.21",
     "mitt": "^3.0.1",
diff --git a/paimon-web-ui-new/pnpm-lock.yaml b/paimon-web-ui-new/pnpm-lock.yaml
index 6252459..918a970 100644
--- a/paimon-web-ui-new/pnpm-lock.yaml
+++ b/paimon-web-ui-new/pnpm-lock.yaml
@@ -20,6 +20,15 @@
 lockfileVersion: '6.0'
 
 dependencies:
+  '@antv/x6':
+    specifier: ^2.15.3
+    version: 2.15.3
+  '@antv/x6-plugin-dnd':
+    specifier: ^2.1.1
+    version: 2.1.1(@antv/[email protected])
+  '@antv/x6-vue-shape':
+    specifier: ^2.1.1
+    version: 2.1.1(@antv/[email protected])([email protected])
   dart-sass:
     specifier: ^1.25.0
     version: 1.25.0
@@ -147,6 +156,48 @@ packages:
     resolution: {integrity: 
sha512-pvFiLP2BeOKA/ZOS6jxx4XhKzdVLHDhGlFEaZ2flWWYf2xOqVniqpk38I04DFRyz+L0ASggl7SkItTc+ZLju4w==}
     dev: true
 
+  /@antv/[email protected]:
+    resolution: {integrity: 
sha512-9ghYsxbT7WjQ0thqjcQwnjuBdL8DSTptEubf0DvBZOJ0wmapclXqYPOM+XYPNtC1dcKDqqxsw5mdcbcAmQ224Q==}
+    dependencies:
+      lodash-es: 4.17.21
+      utility-types: 3.10.0
+    dev: false
+
+  /@antv/[email protected]:
+    resolution: {integrity: 
sha512-MId6riEQkxphBpVeTcL4ZNXL4lScyvDEPLyIafvWMcWNTGK0jgkK7N20XSzqt8ltJb0mGUso5s56mrk8ysHu2A==}
+    dev: false
+
+  /@antv/[email protected](@antv/[email protected]):
+    resolution: {integrity: 
sha512-v0szzik1RkadPDn4Qi5mOSaB2AeI78D40/YuCYbPVzplG+HydGsHwO3MLTgJPQ+R5n0eM0W5F850p1VfTOHR7g==}
+    peerDependencies:
+      '@antv/x6': ^2.x
+    dependencies:
+      '@antv/x6': 2.15.3
+    dev: false
+
+  /@antv/[email protected](@antv/[email protected])([email protected]):
+    resolution: {integrity: 
sha512-XQwKyQmKH1m12tQ7ybh/p3XXe/XKWEa6zihoIb/IQd+w5WyTTosVfgXbn1io3Nb6zXc2R853R6iGe+T1+tWhfg==}
+    peerDependencies:
+      '@antv/x6': ^2.x
+      '@vue/composition-api': ^1.0.0-rc.1
+      vue: ^2.0.0 || >=3.0.0
+    peerDependenciesMeta:
+      '@vue/composition-api':
+        optional: true
+    dependencies:
+      '@antv/x6': 2.15.3
+      vue: 3.3.4
+      vue-demi: 0.14.6([email protected])
+    dev: false
+
+  /@antv/[email protected]:
+    resolution: {integrity: 
sha512-mI8Aqc/0+/ZlXguibnKovGkKy3w7UFg+CMwAq5oYdBrMEgwgvQ/Rw9tK2LOTgKAINv+5QQ9zJTY058Kv1UfeRA==}
+    dependencies:
+      '@antv/x6-common': 2.0.15
+      '@antv/x6-geometry': 2.0.5
+      utility-types: 3.10.0
+    dev: false
+
   /@babel/[email protected]:
     resolution: {integrity: 
sha512-XktuhWlJ5g+3TJXc5upd9Ks1HutSArik6jf2eAjYFyIOf4ej3RN+184cZbzDvbPnuTJIUhPKKJE3cIsYTiAT3w==}
     engines: {node: '>=6.9.0'}
@@ -2707,7 +2758,6 @@ packages:
 
   /[email protected]:
     resolution: {integrity: 
sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw==}
-    dev: true
 
   /[email protected]:
     resolution: {integrity: 
sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==}
@@ -3828,6 +3878,11 @@ packages:
     resolution: {integrity: 
sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==}
     dev: true
 
+  /[email protected]:
+    resolution: {integrity: 
sha512-O11mqxmi7wMKCo6HKFt5AhO4BwY3VV68YU07tgxfz8zJTIxr4BpsezN49Ffwy9j3ZpwwJp4fkRwjRzq3uWE6Rg==}
+    engines: {node: '>= 4'}
+    dev: false
+
   /[email protected]:
     resolution: {integrity: 
sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==}
     dependencies:
diff --git a/paimon-web-ui-new/src/locales/en/modules/cdc.ts 
b/paimon-web-ui-new/src/locales/en/modules/cdc.ts
index b8d2ca3..5d51dcc 100644
--- a/paimon-web-ui-new/src/locales/en/modules/cdc.ts
+++ b/paimon-web-ui-new/src/locales/en/modules/cdc.ts
@@ -33,4 +33,5 @@ export default {
   task_description: 'Task Description',
   single_table_synchronization: 'Single Table Synchronization',
   whole_database_synchronization: 'Whole Database Synchronization',
+  save: 'Save',
 }
diff --git a/paimon-web-ui-new/src/locales/zh/modules/cdc.ts 
b/paimon-web-ui-new/src/locales/zh/modules/cdc.ts
index f80b3d0..bf7e738 100644
--- a/paimon-web-ui-new/src/locales/zh/modules/cdc.ts
+++ b/paimon-web-ui-new/src/locales/zh/modules/cdc.ts
@@ -33,4 +33,5 @@ export default {
   task_description: '任务描述',
   single_table_synchronization: '单表同步',
   whole_database_synchronization: '整库同步',
+  save: '保存',
 }
diff --git a/paimon-web-ui-new/src/main.ts b/paimon-web-ui-new/src/main.ts
index 303ab83..6c4a9b4 100644
--- a/paimon-web-ui-new/src/main.ts
+++ b/paimon-web-ui-new/src/main.ts
@@ -37,16 +37,3 @@ app.use(naive)
 app.config.globalProperties.mittBus = mitt()
 
 app.mount('#app')
-
-console.clear();
-
-console.log(
-  `%c© Msi%c(Integration)\n%c${Setting.version}`,
-  `padding:24px 0px 12px 0px;
-  font-size:24px;
-  color:#66CCFF;`,
-  'font-size:24px;color:#FFE212;',
-  'font-size:12px;color:#FFBFCB;padding-bottom:24px;',
-);
-
-console.group('%cConsole', 'font-size:12px;color:#39C5BB;font-weight:300;');
diff --git a/paimon-web-ui-new/src/views/cdc/components/dag/custom-node.tsx 
b/paimon-web-ui-new/src/views/cdc/components/dag/custom-node.tsx
new file mode 100644
index 0000000..d90682c
--- /dev/null
+++ b/paimon-web-ui-new/src/views/cdc/components/dag/custom-node.tsx
@@ -0,0 +1,63 @@
+/* Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership.  The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License.  You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied.  See the License for the
+specific language governing permissions and limitations
+under the License. */
+
+import styles from './index.module.scss'
+
+export default defineComponent({
+  name: 'CustomNode',
+  setup() {
+    const getNode = inject('getNode') as any
+    const node = getNode()
+    const data = node.data
+    const onMainMouseEnter = () => {
+      const ports = node.getPorts() || []
+      ports.forEach((port: { id: any }) => {
+        node.setPortProp(port.id, 'attrs/circle', {
+          fill: '#fff',
+          stroke: '#85A5FF',
+        })
+      })
+    }
+
+    const onMainMouseLeave = () => {
+      const ports = node.getPorts() || []
+      ports.forEach((port: { id: any }) => {
+        node.setPortProp(port.id, 'attrs/circle', {
+          fill: 'transparent',
+          stroke: 'transparent',
+        })
+      })
+    }
+
+    return {
+      data,
+      onMainMouseEnter,
+      onMainMouseLeave,
+    }
+  },
+  render() {
+    return (
+      <div
+        class={styles['custom-node']}
+        onMouseenter={this.onMainMouseEnter}
+        onMouseleave={this.onMainMouseLeave}
+      >
+        {this.data.name}
+      </div>
+    )
+  }
+})
diff --git a/paimon-web-ui-new/src/views/cdc/components/dag/index.tsx 
b/paimon-web-ui-new/src/views/cdc/components/dag/dag-canvas.tsx
similarity index 68%
copy from paimon-web-ui-new/src/views/cdc/components/dag/index.tsx
copy to paimon-web-ui-new/src/views/cdc/components/dag/dag-canvas.tsx
index 94eef79..ede6799 100644
--- a/paimon-web-ui-new/src/views/cdc/components/dag/index.tsx
+++ b/paimon-web-ui-new/src/views/cdc/components/dag/dag-canvas.tsx
@@ -15,19 +15,34 @@ KIND, either express or implied.  See the License for the
 specific language governing permissions and limitations
 under the License. */
 
+import { useCanvasInit } from './use-canvas-init'
+import styles from './index.module.scss'
+import DagSlider from './dag-slider'
+
 export default defineComponent({
-  name: 'DagPage',
+  name: 'DagCanvasPage',
   setup() {
     const { t } = useLocaleHooks()
-    
+
+    const { graph, dnd } = useCanvasInit()
+
     return {
       t,
+      graph,
+      dnd
     }
   },
   render() {
     return (
-      <div>
-        DAG
+      <div class={styles.dag}>
+        <div
+          class={styles['dag-container']}
+          id="dag-container"
+        />
+        <DagSlider
+          graph={this.graph}
+          dnd={this.dnd}
+        />
       </div>
     )
   }
diff --git a/paimon-web-ui-new/src/views/cdc/components/dag/dag-slider.tsx 
b/paimon-web-ui-new/src/views/cdc/components/dag/dag-slider.tsx
new file mode 100644
index 0000000..982a474
--- /dev/null
+++ b/paimon-web-ui-new/src/views/cdc/components/dag/dag-slider.tsx
@@ -0,0 +1,121 @@
+/* Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership.  The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License.  You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied.  See the License for the
+specific language governing permissions and limitations
+under the License. */
+
+import styles from './index.module.scss'
+import { getPortsByType } from './node-config'
+
+export default defineComponent({
+  name: 'DagSlider',
+  props: {
+    graph: {
+      type: Object,
+      default: () => {}
+    },
+    dnd: {
+      type: Object,
+      default: () => {}
+    }
+  },
+  setup(props) {
+    const { t } = useLocaleHooks()
+    const sliderVariables = reactive({
+      sourceList: [
+        {
+          name: 'MySQL',
+          value: 'mysql',
+          type: 'INPUT'
+        },
+        {
+          name: 'Kafka',
+          value: 'kafka',
+          type: 'INPUT'
+        },
+        {
+          name: 'MongoDB',
+          value: 'mongodb',
+          type: 'INPUT'
+        },
+        {
+          name: 'PostgreSQL',
+          value: 'postgresql',
+          type: 'INPUT'
+        }
+      ],
+      sinkList: [
+        {
+          name: 'Paimon',
+          value: 'paimon',
+          type: 'OUTPUT'
+        }
+      ]
+    })
+
+    const handleNodeMove = (e: any, item: any) => {
+      const node = props.graph.createNode({
+        id: item.name,
+        shape: 'custom-node',
+        data: item,
+        ports: getPortsByType(item.type, item.name),
+      })
+      props.dnd.start(node, e)
+    }
+
+    return {
+      t,
+      ...toRefs(sliderVariables),
+      handleNodeMove
+    }
+  },
+  render () {
+    return (
+      <div class={styles['dag-slider']} id="dag-slider">
+        <n-card class={styles.card} content-style={'overflow:scroll;'}>
+          <n-space vertical>
+            <div class={styles.source}>
+              <n-space vertical size={15}>
+                <div class={styles['title']}>Source</div>
+                  {
+                    this.sourceList.map((item) => {
+                      return (
+                        <n-button class={styles['list-item']} onMousedown={(e: 
any) => this.handleNodeMove(e, item)}>
+                          {item.name}
+                        </n-button>
+                      )
+                    })
+                  }
+              </n-space>
+            </div>
+            <div class={styles.sink}>
+              <n-space vertical size={15}>
+                <div class={styles['title']}>Sink</div>
+                  {
+                    this.sinkList.map((item) => {
+                      return (
+                        <n-button class={styles['list-item']} onMousedown={(e: 
any) => this.handleNodeMove(e, item)}>
+                          {item.name}
+                        </n-button>
+                      )
+                    })
+                  }
+              </n-space>
+            </div>
+          </n-space>
+        </n-card>
+      </div>
+    )
+  }
+})
diff --git a/paimon-web-ui-new/src/views/cdc/components/dag/index.module.scss 
b/paimon-web-ui-new/src/views/cdc/components/dag/index.module.scss
new file mode 100644
index 0000000..d1dd006
--- /dev/null
+++ b/paimon-web-ui-new/src/views/cdc/components/dag/index.module.scss
@@ -0,0 +1,68 @@
+/* Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership.  The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License.  You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied.  See the License for the
+specific language governing permissions and limitations
+under the License. */
+
+.title {
+  width: 100%;
+  display: flex;
+  justify-content: space-between;
+}
+
+.dag {
+  position: relative;
+  width: 100%;
+  height: calc(100vh - 206px);
+
+  .dag-container {
+    border-radius: 5px;
+  }
+
+  .dag-slider {
+    position: absolute;
+    left: 0;
+    top: 0;
+    width: 250px;
+    height: 100%;
+
+    .card {
+      height: 100%;
+      border-radius: 5px;
+
+      .title {
+        font-size: 18px;
+      }
+
+      .list-item {
+        font-size: 14px;
+        width: 100%;
+        cursor: move;
+      }
+    }
+  }
+}
+
+.custom-node {
+  display: flex;
+  align-items: center;
+  justify-content: center;
+  width: 100%;
+  height: 100%;
+  background-color: #fff;
+  border: 1px solid #c2c8d5;
+  border-left: 4px solid #5F95FF;
+  border-radius: 4px;
+  box-shadow: 0 2px 5px 1px rgba(0, 0, 0, 0.06);
+}
diff --git a/paimon-web-ui-new/src/views/cdc/components/dag/index.tsx 
b/paimon-web-ui-new/src/views/cdc/components/dag/index.tsx
index 94eef79..8ea45a0 100644
--- a/paimon-web-ui-new/src/views/cdc/components/dag/index.tsx
+++ b/paimon-web-ui-new/src/views/cdc/components/dag/index.tsx
@@ -15,6 +15,10 @@ KIND, either express or implied.  See the License for the
 specific language governing permissions and limitations
 under the License. */
 
+import { Leaf, Save } from "@vicons/ionicons5"
+import styles from './index.module.scss';
+import DagCanvas from "./dag-canvas";
+
 export default defineComponent({
   name: 'DagPage',
   setup() {
@@ -26,9 +30,36 @@ export default defineComponent({
   },
   render() {
     return (
-      <div>
-        DAG
-      </div>
+      <n-card>
+        <n-space vertical size={24}>
+          <n-card>
+            <div class={styles.title}>
+              <n-space align="center">
+                <n-icon component={Leaf} color="#2F7BEA" size="18" />
+                <span>{this.t('cdc.synchronization_job_definition')}</span>
+              </n-space>
+              <div class={styles.operation}>
+                <n-space>
+                  <n-popover trigger="hover" placement="bottom"
+                    v-slots={{
+                      trigger: () => (
+                        <n-button
+                          v-slots={{
+                            icon: () => <n-icon component={Save}></n-icon>
+                          }}
+                        >
+                        </n-button>
+                      )
+                    }}>
+                    <span>{this.t('cdc.save')}</span>
+                  </n-popover>
+                </n-space>
+              </div>
+            </div>
+          </n-card>
+          <DagCanvas></DagCanvas>
+        </n-space>
+      </n-card>
     )
   }
 })
diff --git a/paimon-web-ui-new/src/views/cdc/components/dag/node-config.ts 
b/paimon-web-ui-new/src/views/cdc/components/dag/node-config.ts
new file mode 100644
index 0000000..697bb32
--- /dev/null
+++ b/paimon-web-ui-new/src/views/cdc/components/dag/node-config.ts
@@ -0,0 +1,106 @@
+/* Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership.  The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License.  You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied.  See the License for the
+specific language governing permissions and limitations
+under the License. */
+
+export enum NodeType {
+  INPUT = 'INPUT', // 数据输入
+  OUTPUT = 'OUTPUT', // 数据输出
+}
+
+export const getPortsByType = (type: NodeType, nodeId: string) => {
+  let ports = []
+  switch (type) {
+    case NodeType.INPUT:
+      ports = [
+        {
+          id: `${nodeId}-out`,
+          group: 'out',
+        },
+      ]
+      break
+    case NodeType.OUTPUT:
+      ports = [
+        {
+          id: `${nodeId}-in`,
+          group: 'in',
+        },
+      ]
+      break
+    default:
+      ports = [
+        {
+          id: `${nodeId}-in`,
+          group: 'in',
+        },
+        {
+          id: `${nodeId}-out`,
+          group: 'out',
+        },
+      ]
+      break
+  }
+  return ports
+}
+
+export const PORT = {
+  groups: {
+    in: {
+      position: 'left',
+      attrs: {
+        circle: {
+          r: 4,
+          magnet: true,
+          stroke: 'transparent',
+          strokeWidth: 1,
+          fill: 'transparent',
+        },
+      },
+    },
+    out: {
+      position: {
+        name: 'right',
+        args: {
+          dx: 5,
+        },
+      },
+      attrs: {
+        circle: {
+          r: 4,
+          magnet: true,
+          stroke: 'transparent',
+          strokeWidth: 1,
+          fill: 'transparent',
+        },
+      },
+    },
+  },
+}
+
+export const EDGE = {
+  attrs: {
+    line: {
+      stroke: '#1890ff',
+      strokeDasharray: 5,
+      targetMarker: 'classic',
+      style: {
+        animation: 'ant-line 30s infinite linear',
+      },
+    },
+  },
+  connector: {
+    name: 'smooth'
+  }
+}
diff --git a/paimon-web-ui-new/src/views/cdc/components/dag/use-canvas-init.ts 
b/paimon-web-ui-new/src/views/cdc/components/dag/use-canvas-init.ts
new file mode 100644
index 0000000..59791dc
--- /dev/null
+++ b/paimon-web-ui-new/src/views/cdc/components/dag/use-canvas-init.ts
@@ -0,0 +1,113 @@
+/* Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership.  The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License.  You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied.  See the License for the
+specific language governing permissions and limitations
+under the License. */
+
+import { Graph } from '@antv/x6'
+import { Dnd } from '@antv/x6-plugin-dnd'
+import { register } from '@antv/x6-vue-shape'
+import CustomNode from './custom-node'
+import { EDGE, PORT } from './node-config'
+
+register({
+  shape: 'custom-node',
+  width: 150,
+  height: 40,
+  component: CustomNode,
+  ports: {
+    ...PORT
+  }
+})
+
+export function useCanvasInit() {
+  const graph = ref<Graph>()
+  const dnd = ref<Dnd>()
+
+  const graphInit = () => {
+    return new Graph({
+      container: document.getElementById('dag-container') || undefined,
+      // background: {
+      //   color: '#F2F7FA',
+      // },
+      autoResize: true,
+      panning: true,
+      mousewheel: true,
+      grid: {
+        visible: true,
+        type: 'dot',
+        size: 20,
+        args: {
+          color: '#a0a0a0',
+          thickness: 1,
+        },
+      },
+      connecting: {
+        // Whether multiple edges can be created between the same start node 
and end
+        allowMulti: false,
+        // Whether a point is allowed to connect to a blank position on the 
canvas
+        allowBlank: false,
+        // The start node and the end node are the same node
+        allowLoop: false,
+        // Whether an edge is allowed to link to another edge
+        allowEdge: false,
+        // Whether edges are allowed to link to nodes
+        allowNode: true,
+        // Whether to allow edge links to ports
+        allowPort: true,
+        // Whether all available ports or nodes are highlighted when you drag 
the edge
+        highlight: true,
+        createEdge() {
+          return graph.value?.createEdge({
+            shape: 'dag-edge'
+          })
+        },
+        anchor: {
+          name: 'left',
+        },
+      }
+    })
+  }
+
+  const dndInit = () => {
+    const actualGraph = graph.value // get the actual Graph object from the Ref
+    if (!actualGraph) {
+      throw new Error('Graph object is undefined')
+    }
+    return new Dnd({
+      target: actualGraph,
+      dndContainer: document.getElementById('dag-slider') || undefined,
+      getDragNode: (node) => node.clone({ keepId: true }),
+      getDropNode: (node) => node.clone({ keepId: true }),
+    })
+  }
+
+  const registerCustomCells = () => {
+    Graph.unregisterEdge('dag-edge')
+    Graph.registerEdge('dag-edge', { ...EDGE })
+  }
+
+  onMounted(() => {
+    const actualGraph = graphInit() // get the actual Graph object from the 
function
+    graph.value = actualGraph // set the Ref to the actual Graph object
+    const actualDnd = dndInit() // get the actual Dnd object from the function
+    dnd.value = actualDnd // set the Ref to the actual Dnd object
+    registerCustomCells()
+  })
+
+  return {
+    graph,
+    dnd
+  }
+}

Reply via email to