6.2 KiB
title | order |
---|---|
使用 React 定义节点 | 5 |
长期以来,定义节点一直是一个比较让大家烦恼的问题,即使推出了 jsx 方案来简化,也依然有一定难度,于是我们推出了 @antv/g6-react-node
这一个包,让大家可以更简单的定义节点,这个包支持 ts 提示,并且包含了高阶的基于 shape 的事件动画等,让大家可以更方便的使用 G6。
怎么使用
首先在安装完 G6 后,你需要额外安装 @antv/g6-react-node
npm install @antv/g6-react-node
// yarn add @antv/g6-react-node
以一个简单的卡片为例子,它包含了定义,自定义事件,节点数据管理等的示例:
import React from 'react';
import G6 from '@antv/g6';
import { Rect, Text, Circle, Image, Group, createNodeFromReact } from '@antv/g6-react-node';
const Tag = ({ text, color }) => (
<Rect
style={{
fill: color,
padding: [5, 10],
width: 'auto',
radius: [4],
margin: [0, 8],
}}
>
<Text style={{ fill: '#fff', fontSize: 10 }}>{text}</Text>
</Rect>
);
const Card = ({ cfg }) => {
const { collapsed = false } = cfg;
return (
<Group draggable>
<Rect
style={{
width: 400,
height: 'auto',
fill: '#fff',
stroke: '#ddd',
shadowColor: '#eee',
shadowBlur: 30,
radius: [8],
justifyContent: 'center',
padding: [18, 0],
}}
draggable
>
<Text
style={{
fill: '#000',
margin: [0, 24],
fontSize: 16,
fontWeight: 'bold',
}}
>
这是一个卡片
</Text>
<Text style={{ fill: '#ccc', fontSize: 12, margin: [12, 24] }}>
我是一段特别特别特别特别特别特别特别长的描述
</Text>
{collapsed && (
<Group>
<Image
style={{
img: 'https://gw.alipayobjects.com/zos/antfincdn/aPkFc8Sj7n/method-draw-image.svg',
width: 200,
height: 200,
margin: [24, 'auto'],
}}
/>
<Rect style={{ width: 'auto', flexDirection: 'row', padding: [4, 12] }}>
<Tag color="#66ccff" text="我是" />
<Tag color="#66ccff" text="很多个" />
<Tag color="#66ccff" text="很多个的" />
<Tag color="#66ccff" text="标签" />
</Rect>
</Group>
)}
<Circle
style={{
position: 'absolute',
x: 380,
y: 20,
r: 5,
fill: collapsed ? 'blue' : 'green',
}}
>
<Text
style={{
fill: '#fff',
fontSize: 10,
margin: [-6, -3, 0],
cursor: 'pointer',
}}
onClick={(evt, node, shape, graph) => {
graph.updateItem(node, {
collapsed: !collapsed,
});
}}
>
{collapsed ? '-' : '+'}
</Text>
</Circle>
</Rect>
</Group>
);
};
G6.registerNode('test', createNodeFromReact(Card));
展示了这样一个卡片的节点:
使用指南
图形 React 组件
定义 React 组件节点的时候,你不能使用任何的 hook 或者异步获取的逻辑,因为目前节点绘制需要是一个同步的过程,并且,我们推荐把所有状态以及数据信息放在节点本身 data 中,这样可以更方便的进行管理。在React组件节点中,所有的数据流动都应该是:节点数据 -> react 组件 props(cfg) -> 节点内容变化。组件本身需要是没有任何副作用的,所有对于节点数据的改变,都是基于 updateItem 的。
React 组件内部的布局
如果你没有做任何定位或者布局,所有布局都会按照正常的文档流,自上而下排布。为了让大家有更自由的布局方式, React 内部还支持了 flex 布局,你可以通过操作:alignContent
,alignItems
,alignSelf
,display
,flex
,flexBasis
,flexGrow
,flexShrink
,flexDirection
,flexWrap
,height
,width
,justifyContent
,margin
,padding
,maxHeight
,maxWidth
,minHeight
,minWidth
这几个属性来控制节点内部的布局。
基于 React 组件 Shape 的事件处理
为了更加方便的控制节点,我们支持了在节点内部的某一个图形进行事件绑定(事件冒泡会在后续版本支持),这些事件绑定函数都有统一的参数: (evt: G6本身的事件, node: 事件发生的节点, shape: 事件发生的Shape, graph: 发出事件的graph)
,目前我们支持了大部分的 G6 事件:onClick
,onDBClick
,onMouseEnter
,onMouseMove
,onMouseOut
,onMouseOver
,onMouseLeave
,onMouseDown
,onMouseUp
,onDragStart
,onDrag
,onDragEnd
,onDragEnter
,onDragLeave
,onDragOver
,onDrop
,onContextMenu
⚠️ 注意: 使用了事件后,需要使用函数 appenAutoShapeListener(graph)
对所进行对图进行事件挂载才可以生效,该方法可以直接从 @antv/g6-react-node
包引出。
基于 React 组件 Shape 的简单动画(alpha)
为了更加方便给节点添加动画,所以我们内置了一些简单的动画来使用,希望能满足基本交互的效果,第一期我们暂时只推出了六种动画, animation
属性设置后就有动画,属性为空则停止动画。
示例:
<Rect
style={{
width: 400,
// ...
}}
draggable
animation={
animated && {
animate: 'rubber', // 同时支持 'spin','flash','pulse','tada','bounce'
repeat: true,
duration: 2000,
}
}
>