Loading...
In G6, custom nodes typically require manipulating DOM or Canvas elements, but with the help of the g6-extension-vue
ecosystem library, you can directly use Vue components as node content, enhancing development efficiency and maintainability.
✅ Recommended Scenarios:
For detailed information on how to customize nodes using Canvas graphics, please refer to the Custom Node documentation
✅ Recommended Scenarios:
Before starting, please ensure you have:
To use g6-extension-vue
, run the following command:
npm install g6-extension-vue
Register the Vue node type through the extension mechanism:
import { ExtensionCategory, register } from '@antv/g6';import { VueNode } from 'g6-extension-vue';register(ExtensionCategory.NODE, 'vue-node', VueNode);
The register
method requires three parameters:
ExtensionCategory.NODE
indicates this is a node typevue-node
is the name we give to this custom node, which will be used in the configuration laterg6-extension-vue
Define a simple Vue component as the content of the node:
import { defineComponent, h } from 'vue';const MyVueNode = defineComponent({setup(props, { attrs, slots, expose }) {return () => {return h('div', 'vue node');};},});
Use the custom Vue node in the graph configuration. Specify the node type and style in the graph configuration to use the custom Vue component.
type
: Specify the node type as vue-node
(use the name given during registration)style.component
: Define the Vue component content of the nodeconst graph = new Graph({node: {type: 'vue-node',style: {component: () => <MyVueNode />,},},});graph.render();
In complex graph visualization scenarios, nodes need to dynamically respond to interaction states. We provide two complementary state management solutions:
G6 provides built-in interaction state management states, such as hover-activate
and click-select
. You can get the current node state through the data.states
field in the node data and adjust the node style based on the state.
Example: Change the background color when the node is hovered.
import { ExtensionCategory, register, Graph } from '@antv/g6';import { VueNode } from 'g6-extension-vue';import { computed, defineComponent } from 'vue';register(ExtensionCategory.NODE, 'vue-node', VueNode);const StatefulNode = defineComponent({setup(props, { attrs, slots, expose }) {const isActive = computed(() => props.data.states?.includes('active'));const label = computed(() => props.data.data?.label);return (<divstyle={{width: 100,padding: 5,border: '1px solid #eee',boxShadow: isActive.value ? '0 0 8px rgba(24,144,255,0.8)' : 'none',transform: `scale(${isActive.value ? 1.05 : 1})`,}}>{label.value}</div>);},});const graph = new Graph({data: {nodes: [{ id: 'node1', style: { x: 100, y: 200 }, data: { label: 'node1' } },{ id: 'node2', style: { x: 300, y: 200 }, data: { label: 'node2' } },],},node: {type: 'vue-node',style: {component: (data) => <StatefulNode data={Object.assign({}, data)} />, // data is non-reactive, need to change reference to trigger Vue's props side effects},},behaviors: ['hover-activate'],});graph.render();
When you need to manage business-related states (such as approval status, risk level), you can extend node data to achieve this:
Example: Add a selected
variable through data to achieve style changes for node selection and deselection.
import { ExtensionCategory, register, Graph } from '@antv/g6';import { VueNode } from 'g6-extension-vue';import { defineComponent, computed } from 'vue';register(ExtensionCategory.NODE, 'vue-node', VueNode);const MyVueNode = defineComponent({setup(props, { attrs, slots, expose }) {const isSelected = computed(() => props.data.data.selected);const handleClick = () => {graph.updateNodeData([{ id: props.data.id, data: { selected: !isSelected.value } }]);graph.draw();};return (<divstyle={{width: 200,padding: 10,border: '1px solid red',borderColor: isSelected.value ? 'orange' : '#ddd', // Set border color based on selection statecursor: 'pointer', // Add mouse pointer style}}onClick={handleClick}>Node</div>);},});const graph = new Graph({data: {nodes: [{id: 'node1',style: { x: 100, y: 100 },data: { selected: true },},],},node: {type: 'vue-node',style: {component: (data) => <MyVueNode data={Object.assign({}, data)} graph={graph} />, // data is non-reactive, need to change reference to trigger Vue's props side effects},},});graph.render();
Achieve two-way communication between nodes and graph instances, allowing nodes and graph instances to update each other.
Example: Operate graph data through custom nodes and re-render the graph.
import { ExtensionCategory, register, Graph } from '@antv/g6';import { VueNode } from 'g6-extension-vue';import { defineComponent, computed } from 'vue';register(ExtensionCategory.NODE, 'vue-node', VueNode);const IDCardNode = defineComponent({setup(props, { attrs, slots, expose }) {const isSelected = computed(() => props.data.data.selected);const handleSelect = () => {graph.updateNodeData([{ id: props.data.id, data: { selected: true } }]);graph.draw();};return <Select onChange={handleSelect} style={{ background: isSelected.value ? 'orange' : '#eee' }} />;},});const graph = new Graph({node: {type: 'vue-node',style: {component: ({ id, data }) => <IDCardNode id={id} selected={isSelected.value} graph={graph} />,},},});