mirror of
https://gitee.com/antv/g6.git
synced 2024-12-02 19:58:46 +08:00
fix: graph disapears when it is dragged out of the view. fix: when the graph is out of the view, it can not be dragged back. fix: linkPoints size and radius problem. feat: focusItem with animation. docs: animateCfg.
This commit is contained in:
parent
9d521e1a35
commit
b54dd5ada1
@ -34,7 +34,7 @@ The life cycle of an instance of Graph is: Initialize -> Load data -> Render ->
|
||||
| defaultCombo | Object | {} | Default combo configurations in global, including type, size, color and so on. Its priority is lower than the configurations in data. It is a new feature of G6 3.5. |
|
||||
| plugins | Array | [] | Plugins for graph. Please refer to [Plugin](/en/docs/manual/tutorial/plugins##plugin) for detail. |
|
||||
| animate | Boolean | false | Wheter activate the global animation. Which will take effect while changing layouts, changing data, and other global operations. |
|
||||
| animateCfg | Object | | The configurations for global animation. Takes effect only when `animate: true`. |
|
||||
| animateCfg | Object | | The configurations for global animation. Takes effect only when `animate: true`. For more detail about animateCfg, see [Basic Animation Docs](/en/docs/manual/advanced/animation#animatecfg). |
|
||||
| animateCfg.<br />onFrame | Function | null | The callback function for every frame of animation. The path of custom animation for node can be defined here. The nodes will move linearly when `onFrame` is null. |
|
||||
| animateCfg.<br />duration | Number | 500 | Duration of animation with unit millisecond. |
|
||||
| animateCfg.<br />easing | string | easeLinear | The easing function name of animation. Please refer to ease in d3. |
|
||||
@ -1224,7 +1224,7 @@ graph.zoomTo(3, { x: 100, y: 100 });
|
||||
graph.zoomTo(0.5);
|
||||
```
|
||||
|
||||
### focusItem(item)
|
||||
### focusItem(item, animate)
|
||||
|
||||
Move the graph to center at the item. This operation can be used as easing animation after searching a node.
|
||||
|
||||
@ -1233,11 +1233,16 @@ Move the graph to center at the item. This operation can be used as easing anima
|
||||
| Name | Type | Required | Description |
|
||||
| ---- | --------------- | -------- | ----------------------------------- |
|
||||
| item | string / Object | true | The id or the instance of the item. |
|
||||
| animate | boolean | false | Whether move the graph with animation. |
|
||||
| animateCfg | Object | false | The animation's configuraiton. Its configurations can be found in [Basic Animation Docs](/en/docs/manual/advanced/animation#animatecfg) |
|
||||
|
||||
**Usage**
|
||||
|
||||
```javascript
|
||||
graph.focusItem(item);
|
||||
|
||||
// focus with animation
|
||||
graph.focusItem(item, true);
|
||||
```
|
||||
|
||||
### changeSize(width, height)
|
||||
|
@ -34,7 +34,7 @@ Graph 的生命周期为:初始化—>加载数据—>渲染—>更新—>销
|
||||
| defaultCombo | Object | {} | 默认状态下 Combo 的配置,比如 `type`, `color`。会被写入的 data 覆盖。3.5 版本新增。 |
|
||||
| plugins | Array | [] | 向 graph 注册插件。插件机制请见:[插件](/zh/docs/manual/tutorial/plugins#插件) |
|
||||
| animate | Boolean | false | 是否启用全局动画。 |
|
||||
| animateCfg | Object | | 动画配置项,仅在 `animate` 为 `true` 时有效。 |
|
||||
| animateCfg | Object | | 动画配置项,仅在 `animate` 为 `true` 时有效。关于 `animateCfg` 的更多配置项参见[基础动画教程](/zh/docs/manual/advanced/animation#animatecfg)。 |
|
||||
| animateCfg.<br />onFrame | Function | null | 回调函数,用于自定义节点运动路径,为空时线性运动。 |
|
||||
| animateCfg.<br />duration | Number | 500 | 动画时长,单位为毫秒。 |
|
||||
| animateCfg.<br />easing | string | easeLinear | 动画动效,可参见 d3 ease。 |
|
||||
@ -1213,18 +1213,23 @@ graph.zoomTo(0.5);
|
||||
|
||||
### focusItem(item)
|
||||
|
||||
将元素移动到视口中心,该方法可用于做搜索后的缓动动画。
|
||||
移动图,使得 item 对齐到视口中心,该方法可用于做搜索后的缓动动画。
|
||||
|
||||
**参数**
|
||||
|
||||
| 名称 | 类型 | 是否必选 | 描述 |
|
||||
| ---- | --------------- | -------- | ------------------ |
|
||||
| item | string / Object | true | 元素 ID 或元素实例 |
|
||||
| animate | boolean | false | 是否带有动画 |
|
||||
| animateCfg | Object | false | 若带有动画,可配置动画,参见[基础动画教程](/zh/docs/manual/advanced/animation#animatecfg) |
|
||||
|
||||
**用法**
|
||||
|
||||
```javascript
|
||||
graph.focusItem(item);
|
||||
|
||||
// 动画地移动
|
||||
graph.focusItem(item, true);
|
||||
```
|
||||
|
||||
### changeSize(width, height)
|
||||
|
@ -9,13 +9,14 @@ There are two levels of animation in G6:
|
||||
- Item animation: The animation on a node or an edge.
|
||||
|
||||
<br />
|
||||
|
||||
## Global Animation
|
||||
The global animation is controlled by Graph instance. It takes effect when some global changes happen, such as:
|
||||
|
||||
- `graph.updateLayout(cfg)` change the layout;
|
||||
- `graph.changeData()` change the data.
|
||||
|
||||
Configure `animate: true` when instantiating a graph to achieve it. <br />
|
||||
Configure `animate: true` when instantiating a graph to achieve it. And the `animateCfg` is the configurations for the animate, see [animateCfg](#animateCfg) for more detail. <br />
|
||||
|
||||
```javascript
|
||||
const graph = new G6.Graph({
|
||||
@ -28,9 +29,6 @@ const graph = new G6.Graph({
|
||||
});
|
||||
```
|
||||
|
||||
G6 supports all the easing functions in d3.js. Thus, the options of `easing` in `animateCfg`: <br />`'easeLinear'`, <br />`'easePolyIn'`, `'easePolyOut'`, `'easePolyInOut'` , <br />`'easeQuad'`, `'easeQuadIn'`, `'easeQuadOut'`, `'easeQuadInOut'` .
|
||||
|
||||
For more detail of the easing functions, please refer to: <a href='https://github.com/d3/d3/blob/master/API.md#easings-d3-ease' target='_blank'>d3 Easings</a>.
|
||||
|
||||
## Item Animation
|
||||
|
||||
@ -57,7 +55,7 @@ In this example, we are going to magnify and shrink the node. <br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*aAjWQ4n_OOEAAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
We first find the graphics shape to be animated by `group.get('children')[0]`. Here we find the 0th graphics shape of this type of node. Then, we call `animate` for the node to define the properties for each frame(The first parameter is a function which returns the properties of each frame, the second parameter defines the configuration for animation).
|
||||
We first find the graphics shape to be animated by `group.get('children')[0]`. Here we find the 0th graphics shape of this type of node. Then, we call `animate` for the node to define the properties for each frame(The first parameter is a function which returns the properties of each frame; the second parameter defines the configuration for animation, see [animateCfg](#animateCfg)).
|
||||
|
||||
```javascript
|
||||
// Magnify and shrink animation
|
||||
@ -96,7 +94,7 @@ G6.registerNode(
|
||||
|
||||
You can add extra shape with animation in `afterDraw`.<br />
|
||||
|
||||
In `afterDraw` of this demo, we draw three background circle shape with different filling colors. And the `animate` is called for magnifying and fading out the three circles. We do not use set the first parameter as a function here, but assign the target style for each animation to the input paramter: magify the radius to 10 and reduce the opacity to 0.1. The second parameter defines the configuration for the animation.<br />
|
||||
In `afterDraw` of this demo, we draw three background circle shape with different filling colors. And the `animate` is called for magnifying and fading out the three circles. We do not use set the first parameter as a function here, but assign the target style for each animation to the input paramter: magify the radius to 10 and reduce the opacity to 0.1. The second parameter defines the configuration for the animation, see [animateCfg](#animateCfg).<br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*FxDJQ5eY-5oAAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
@ -186,7 +184,7 @@ G6.registerNode('background-animate', {
|
||||
|
||||
#### Partial Animation
|
||||
|
||||
In this demo, we add extra graphics shape(an image) in `afterDraw`, and set a rotation animation for it. Note that the rotation animation is a little complicated, which should be manipulated by matrix.<br />
|
||||
In this demo, we add extra graphics shape(an image) in `afterDraw`, and set a rotation animation for it. Note that the rotation animation is a little complicated, which should be manipulated by matrix. The first parameter of `animate()` is a function which returns the properties of each frame; the second parameter defines the configuration for animation, see [animateCfg](#animateCfg)<br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*uFQsQqxIa_QAAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
@ -252,7 +250,7 @@ The code of the three demo can be found in: <a href='/en/examples/scatter/edge'
|
||||
|
||||
#### A Moving Circle
|
||||
|
||||
In this demo, we add a circle shape with moving animation in `afterDraw`. In each frame, we return the relative position of the circle on the edge.<br />
|
||||
In this demo, we add a circle shape with moving animation in `afterDraw`. In each frame, we return the relative position of the circle on the edge. The first parameter of `animate()` is a function which returns the properties of each frame; the second parameter defines the configuration for animation, see [animateCfg](#animateCfg)<br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*OAGPRZbYpw4AAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
@ -303,58 +301,37 @@ G6.registerEdge(
|
||||
|
||||
#### Running Dashed Line
|
||||
|
||||
The running dashed line is achieved by modifying the `lineDash` in every frame.<br />
|
||||
The running dashed line is achieved by modifying the `lineDash` in every frame. The first parameter of `animate()` is a function which returns the properties of each frame; the second parameter defines the configuration for animation, see [animateCfg](#animateCfg)<br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*VUgETK6aMzcAAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
```javascript
|
||||
// The values of the lineDash. It can be calculated by util
|
||||
const dashArray = [
|
||||
[0, 1],
|
||||
[0, 2],
|
||||
[1, 2],
|
||||
[0, 1, 1, 2],
|
||||
[0, 2, 1, 2],
|
||||
[1, 2, 1, 2],
|
||||
[2, 2, 1, 2],
|
||||
[3, 2, 1, 2],
|
||||
[4, 2, 1, 2],
|
||||
];
|
||||
|
||||
const lineDash = [4, 2, 1, 2];
|
||||
const interval = 9; // The total length of the lineDash
|
||||
|
||||
G6.registerEdge(
|
||||
'line-dash',
|
||||
{
|
||||
afterDraw(cfg, group) {
|
||||
// Get the first graphics shape of this type of edge, which is the edge's path
|
||||
const shape = group.get('children')[0];
|
||||
// The start point of the edge's path
|
||||
const length = shape.getTotalLength();
|
||||
let totalArray = [];
|
||||
// Calculate the lineDash for the whole line
|
||||
for (var i = 0; i < length; i += interval) {
|
||||
totalArray = totalArray.concat(lineDash);
|
||||
}
|
||||
|
||||
let index = 0;
|
||||
// Define the animation
|
||||
shape.animate(
|
||||
ratio => {
|
||||
// Returns the properties for each frame. The input parameter ratio is a number that range from 0 to 1. The return value is an object that defines the properties for this frame
|
||||
const cfg = {
|
||||
lineDash: dashArray[index].concat(totalArray),
|
||||
() => {
|
||||
index++;
|
||||
if (index > 9) {
|
||||
index = 0;
|
||||
}
|
||||
const res = {
|
||||
lineDash,
|
||||
lineDashOffset: -index,
|
||||
};
|
||||
// Move 1 each frame
|
||||
index = (index + 1) % interval;
|
||||
// Return the properties of this frame, lineDash for this demo
|
||||
return cfg;
|
||||
// Returns the configurations to be modified in this frame. Here the return value contains lineDash and lineDashOffset
|
||||
return res;
|
||||
},
|
||||
{
|
||||
repeat: true, // Play the animation repeatly
|
||||
duration: 3000, // The duration for one animation
|
||||
repeat: true, // whether executed repeatly
|
||||
duration: 3000, // animation's duration
|
||||
},
|
||||
); // The duration for one animation
|
||||
);
|
||||
},
|
||||
},
|
||||
'cubic',
|
||||
@ -363,7 +340,7 @@ G6.registerEdge(
|
||||
|
||||
#### A Growing Edge
|
||||
|
||||
A growing edge can also be implemented by calculating the `lineDash`. <br />
|
||||
A growing edge can also be implemented by calculating the `lineDash`. The first parameter of `animate()` is a function which returns the properties of each frame; the second parameter defines the configuration for animation, see [animateCfg](#animateCfg) <br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*-l9lQ7Ck1QcAAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
@ -406,25 +383,13 @@ This kind of animation is related to the [State](/en/docs/manual/middle/states/s
|
||||
|
||||
The code below is a part of the code in <a href='/en/examples/scatter/stateChange' target='_blank'>Animation of State Changing</a>. Please note that we have omit some code to emphasize the code related to the animation.
|
||||
|
||||
The first parameter of `animate()` is a function which returns the properties of each frame; the second parameter defines the configuration for animation, see [animateCfg](#animateCfg)
|
||||
|
||||
```javascript
|
||||
// const data = ...
|
||||
// const graph = new G6.Graph({...});
|
||||
|
||||
// The values of the lineDash. It can be calculated by util
|
||||
const dashArray = [
|
||||
[0, 1],
|
||||
[0, 2],
|
||||
[1, 2],
|
||||
[0, 1, 1, 2],
|
||||
[0, 2, 1, 2],
|
||||
[1, 2, 1, 2],
|
||||
[2, 2, 1, 2],
|
||||
[3, 2, 1, 2],
|
||||
[4, 2, 1, 2],
|
||||
];
|
||||
|
||||
const lineDash = [4, 2, 1, 2];
|
||||
const interval = 9; // The total length of the lineDash
|
||||
|
||||
// Register a type of edge named 'can-running'
|
||||
G6.registerEdge(
|
||||
@ -437,24 +402,23 @@ G6.registerEdge(
|
||||
if (name === 'running') {
|
||||
// When the running state is turned to be true
|
||||
if (value) {
|
||||
const length = shape.getTotalLength();
|
||||
let totalArray = [];
|
||||
for (var i = 0; i < length; i += interval) {
|
||||
totalArray = totalArray.concat(lineDash);
|
||||
}
|
||||
let index = 0;
|
||||
shape.animate(
|
||||
ratio => {
|
||||
// Returns the properties for each frame. The input parameter ratio is a number that range from 0 to 1. The return value is an object that defines the properties for this frame
|
||||
const cfg = {
|
||||
lineDash: dashArray[index].concat(totalArray),
|
||||
() => {
|
||||
index++;
|
||||
if (index > 9) {
|
||||
index = 0;
|
||||
}
|
||||
const res = {
|
||||
lineDash,
|
||||
lineDashOffset: -index,
|
||||
};
|
||||
index = (index + 1) % interval;
|
||||
return cfg;
|
||||
// Returns the configurations to be modified in this frame. Here the return value contains lineDash and lineDashOffset
|
||||
return res;
|
||||
},
|
||||
{
|
||||
repeat: true, // Play the animation repeatly
|
||||
duration: 3000, // The duration for one animation
|
||||
repeat: true, // whether executed repeatly
|
||||
duration: 3000, // animation's duration
|
||||
},
|
||||
);
|
||||
} else {
|
||||
@ -495,3 +459,23 @@ graph.on('node:mouseleave', ev => {
|
||||
```
|
||||
|
||||
<span style="background-color: rgb(251, 233, 231); color: rgb(139, 53, 56)"> <strong>⚠️Attention:</strong></span> When `running` is turned to be `false`, the animation should be stopped and the `lineDash` should be cleared.
|
||||
|
||||
|
||||
## animateCfg
|
||||
|
||||
| Configuration | Type | Default Value | Description |
|
||||
| ---- | --------------- | -------- | ----------------------------------- |
|
||||
| duration | Number | 500 | The duration for animating once |
|
||||
| easing | boolean | 'linearEasing' | The easing function for the animation, see [Easing Function](#easing-Function) for more detail |
|
||||
| delay | Number | 0 | Execute the animation with delay |
|
||||
| repeat | boolean | false | Whether execute the animation repeatly |
|
||||
| callback | Function | undefined | Callback function after the animation finish |
|
||||
| pauseCallback | Function | undefined | Callback function after the animation is paused by shape.pause() |
|
||||
| resumeCallback | Function | undefined | Callback function after the animation is resume by shape.resume() |
|
||||
|
||||
|
||||
### Easing Function
|
||||
|
||||
G6 supports all the easing functions in d3.js. Thus, the options of `easing` in `animateCfg`: <br />`'easeLinear'`, <br />`'easePolyIn'`, `'easePolyOut'`, `'easePolyInOut'` , <br />`'easeQuad'`, `'easeQuadIn'`, `'easeQuadOut'`, `'easeQuadInOut'` .
|
||||
|
||||
For more detail of the easing functions, please refer to: <a href='https://github.com/d3/d3/blob/master/API.md#easings-d3-ease' target='_blank'>d3 Easings</a>.
|
@ -9,13 +9,14 @@ G6 中的动画分为两个层次:
|
||||
- 元素(边和节点)动画:节点或边上的独立动画。
|
||||
|
||||
<br />
|
||||
|
||||
## 全局动画
|
||||
G6 的全局动画指通过图实例进行某些全局操作时,产生的动画效果。例如:
|
||||
|
||||
- `graph.updateLayout(cfg)` 布局的变化
|
||||
- `graph.changeData()` 数据的变化
|
||||
|
||||
通过实例化图时配置 `animate: true`,可以达到每次进行上述操作时,动画效果变化的目的。配合 `animateCfg` 配置动画参数:<br />
|
||||
通过实例化图时配置 `animate: true`,可以达到每次进行上述操作时,动画效果变化的目的。配合 `animateCfg` 配置动画参数,`animateCfg` 具体配置参见 [animateCfg](#animateCfg)<br />
|
||||
|
||||
```javascript
|
||||
const graph = new G6.Graph({
|
||||
@ -28,12 +29,6 @@ const graph = new G6.Graph({
|
||||
});
|
||||
```
|
||||
|
||||
### easing 函数
|
||||
|
||||
easing 函数是指动画的函数。例如线性插值、先快后慢等。<br />G6 支持所有 d3.js 中的动画函数。因此,上面代码中 `animateCfg` 配置中的 String 类型的 `easing` 可以取值有:<br />`'easeLinear'` ,<br />`'easePolyIn'` ,`'easePolyOut'` , `'easePolyInOut'` ,<br />`'easeQuad'` ,`'easeQuadIn'` ,`'easeQuadOut'` , `'easeQuadInOut'` 。
|
||||
|
||||
更多取值及所有取值含义参见:<a href='https://github.com/d3/d3/blob/master/API.md#easings-d3-ease' target='_blank'>d3 Easings</a>。
|
||||
|
||||
## 元素动画
|
||||
|
||||
由于 G6 的内置节点和边是没有动画的,需要实现节点和边上的动画需要通过[自定义节点](/zh/docs/manual/advanced/custom-node)、[自定义边](/zh/docs/manual/advanced/custom-edge)时复写 `afterDraw` 实现。
|
||||
@ -59,7 +54,7 @@ easing 函数是指动画的函数。例如线性插值、先快后慢等。<br
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*aAjWQ4n_OOEAAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
本例实现节点放大缩小,通过 `group.get('children')[0]` 找到需要更新的图形(这里找到该节点上第 0 个图形),然后调用该图形的 `animate` 方法指定动画的参数及每一帧的变化( 第一个参数是返回每一帧需要变化的参数集的函数,其参数 `ratio` 是当前正在进行的一次动画的进度,范围 [0, 1],第二个参数是动画的参数)。
|
||||
本例实现节点放大缩小,通过 `group.get('children')[0]` 找到需要更新的图形(这里找到该节点上第 0 个图形),然后调用该图形的 `animate` 方法指定动画的参数及每一帧的变化( 第一个参数是返回每一帧需要变化的参数集的函数,其参数 `ratio` 是当前正在进行的一次动画的进度,范围 [0, 1];第二个参数是动画的参数,动画参数的具体配置参见 [animateCfg](#animateCfg))。
|
||||
|
||||
```javascript
|
||||
// 放大、变小动画
|
||||
@ -99,7 +94,7 @@ G6.registerNode(
|
||||
|
||||
在 `afterDraw` 方法中为已有节点添加额外的 shape ,并为这些新增的图形设置动画。<br />
|
||||
|
||||
本例在 `afterDraw` 方法中,绘制了三个背景 circle ,分别使用不同的颜色填充,再调用 `animate` 方法实现这三个 circle 逐渐变大、变淡的动画。本例中没有使用函数参数的形式,直接在 `animate` 函数的第一个参数中设置每次动画结束时的最终目标样式,即半径增大 10,透明度降为 0.1。第二个参数设置动画的配置。<br />
|
||||
本例在 `afterDraw` 方法中,绘制了三个背景 circle ,分别使用不同的颜色填充,再调用 `animate` 方法实现这三个 circle 逐渐变大、变淡的动画。本例中没有使用函数参数的形式,直接在 `animate` 函数的第一个参数中设置每次动画结束时的最终目标样式,即半径增大 10,透明度降为 0.1。第二个参数设置动画的配置,动画参数的具体配置参见 [animateCfg](#animateCfg)。<br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*FxDJQ5eY-5oAAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
@ -189,7 +184,7 @@ G6.registerNode('background-animate', {
|
||||
|
||||
#### 部分图形旋转动画
|
||||
|
||||
这一例也是在 `afterDraw` 方法中为已有节点添加额外的 shape (本例中为 image),并为这些新增的图形设置旋转动画。旋转动画较为复杂,需要通过矩阵的操作实现。<br />
|
||||
这一例也是在 `afterDraw` 方法中为已有节点添加额外的 shape (本例中为 image),并为这些新增的图形设置旋转动画。旋转动画较为复杂,需要通过矩阵的操作实现。`animate` 函数的第一个参数是返回每一帧需要变化的参数集的函数,其参数 `ratio` 是当前正在进行的一次动画的进度,范围 [0, 1];第二个参数是动画的参数,动画参数的具体配置参见 [animateCfg](#animateCfg)<br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*uFQsQqxIa_QAAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
@ -255,7 +250,7 @@ G6.registerNode(
|
||||
|
||||
#### 圆点运动
|
||||
|
||||
本例通过在 `afterDraw` 方法中为边增加了一个 circle 图形,该图形沿着线运动。沿着线运动的原理:设定每一帧中,该 circle 在线上的相对位置。<br />
|
||||
本例通过在 `afterDraw` 方法中为边增加了一个 circle 图形,该图形沿着线运动。沿着线运动的原理:设定每一帧中,该 circle 在线上的相对位置。`animate` 函数的第一个参数是返回每一帧需要变化的参数集的函数,其参数 `ratio` 是当前正在进行的一次动画的进度,范围 [0, 1];第二个参数是动画的参数,动画参数的具体配置参见 [animateCfg](#animateCfg)<br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*OAGPRZbYpw4AAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
@ -306,58 +301,39 @@ G6.registerEdge(
|
||||
|
||||
#### 虚线运动的效果
|
||||
|
||||
虚线运动的效果是通过计算线的 `lineDash` ,并在每一帧中不断修改实现。<br />
|
||||
虚线运动的效果是通过计算线的 `lineDash` ,并在每一帧中不断修改实现。`animate` 函数的第一个参数是返回每一帧需要变化的参数集的函数,其参数 `ratio` 是当前正在进行的一次动画的进度,范围 [0, 1];第二个参数是动画的参数,动画参数的具体配置参见 [animateCfg](#animateCfg)<br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*VUgETK6aMzcAAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
```javascript
|
||||
// lineDash 的差值,可以在后面提供 util 方法自动计算
|
||||
const dashArray = [
|
||||
[0, 1],
|
||||
[0, 2],
|
||||
[1, 2],
|
||||
[0, 1, 1, 2],
|
||||
[0, 2, 1, 2],
|
||||
[1, 2, 1, 2],
|
||||
[2, 2, 1, 2],
|
||||
[3, 2, 1, 2],
|
||||
[4, 2, 1, 2],
|
||||
];
|
||||
|
||||
const lineDash = [4, 2, 1, 2];
|
||||
const interval = 9; // lineDash 的和
|
||||
G6.registerEdge(
|
||||
'line-dash',
|
||||
{
|
||||
afterDraw(cfg, group) {
|
||||
// 获得该边的第一个图形,这里是边的 path
|
||||
const shape = group.get('children')[0];
|
||||
// 获得边的 path 的总长度
|
||||
const length = shape.getTotalLength();
|
||||
let totalArray = [];
|
||||
// 计算出整条线的 lineDash
|
||||
for (var i = 0; i < length; i += interval) {
|
||||
totalArray = totalArray.concat(lineDash);
|
||||
}
|
||||
|
||||
let index = 0;
|
||||
// 边 path 图形的动画
|
||||
shape.animate(
|
||||
ratio => {
|
||||
// 每一帧的操作,入参 ratio:这一帧的比例值(Number)。返回值:这一帧需要变化的参数集(Object)。
|
||||
const cfg = {
|
||||
lineDash: dashArray[index].concat(totalArray),
|
||||
() => {
|
||||
index++;
|
||||
if (index > 9) {
|
||||
index = 0;
|
||||
}
|
||||
const res = {
|
||||
lineDash,
|
||||
lineDashOffset: -index,
|
||||
};
|
||||
// 每次移动 1
|
||||
index = (index + 1) % interval;
|
||||
// 返回需要修改的参数集,这里只修改了 lineDash
|
||||
return cfg;
|
||||
// 返回需要修改的参数集,这里修改了 lineDash,lineDashOffset
|
||||
return res;
|
||||
},
|
||||
{
|
||||
repeat: true, // 动画重复
|
||||
duration: 3000,
|
||||
duration: 3000, // 一次动画的时长为 3000
|
||||
},
|
||||
); // 一次动画的时长为 3000
|
||||
);
|
||||
},
|
||||
},
|
||||
'cubic',
|
||||
@ -366,7 +342,7 @@ G6.registerEdge(
|
||||
|
||||
#### 线从无到有
|
||||
|
||||
线从无到有的动画效果,同样可以通过计算 `lineDash` 来实现。<br />
|
||||
线从无到有的动画效果,同样可以通过计算 `lineDash` 来实现。`animate` 函数的第一个参数是返回每一帧需要变化的参数集的函数,其参数 `ratio` 是当前正在进行的一次动画的进度,范围 [0, 1];第二个参数是动画的参数,动画参数的具体配置参见 [animateCfg](#animateCfg)<br />
|
||||
|
||||
<img src='https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*-l9lQ7Ck1QcAAAAAAAAAAABkARQnAQ' alt='download' width='150'/>
|
||||
|
||||
@ -379,17 +355,16 @@ G6.registerEdge(
|
||||
const length = group.getTotalLength();
|
||||
shape.animate(
|
||||
ratio => {
|
||||
// 每一帧的操作,入参 ratio:这一帧的比例值(Number)。返回值:这一帧需要变化的参数集(Object)。
|
||||
const startLen = ratio * length;
|
||||
// 计算线的lineDash
|
||||
// 计算 lineDash
|
||||
const cfg = {
|
||||
lineDash: [startLen, length - startLen],
|
||||
};
|
||||
return cfg;
|
||||
},
|
||||
{
|
||||
repeat: true, // 动画重复
|
||||
duration: 2000, // 一次动画的时长为 2000
|
||||
repeat: true, // 是否重复执行
|
||||
duration: 2000, // 一次动画持续时长
|
||||
},
|
||||
);
|
||||
},
|
||||
@ -398,6 +373,7 @@ G6.registerEdge(
|
||||
); // 该自定义边继承了内置三阶贝塞尔曲线边 cubic
|
||||
```
|
||||
|
||||
|
||||
### 交互动画
|
||||
|
||||
在交互的过程中也可以添加动画。如下图所示,当鼠标移到节点上时,所有与该节点相关联的边都展示虚线运动的动画。<br />![交互动画.gif](https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*-90pSrm4hkUAAAAAAAAAAABkARQnAQ)<br />上图完整 demo 即代码参见:<a href='/zh/examples/scatter/stateChange' target='_blank'>状态切换动画</a>。
|
||||
@ -407,27 +383,13 @@ G6.registerEdge(
|
||||
- 自定义边中复写 `setState` 方法监听该边的状态,以及某状态下的动画效果;
|
||||
- 监听中间的节点的 `mouseenter` 和 `mouseleave` 事件,触发相关边的状态变化。
|
||||
|
||||
下面代码节选自 demo <a href='/zh/examples/scatter/stateChange' target='_blank'>状态切换动画</a>,请注意省略了部分代码,只展示了交互相关以及边动画相关的代码。
|
||||
下面代码节选自 demo <a href='/zh/examples/scatter/stateChange' target='_blank'>状态切换动画</a>,请注意省略了部分代码,只展示了交互相关以及边动画相关的代码。`animate` 函数的第一个参数是返回每一帧需要变化的参数集的函数,其参数 `ratio` 是当前正在进行的一次动画的进度,范围 [0, 1];第二个参数是动画的参数,动画参数的具体配置参见 [animateCfg](#animateCfg)
|
||||
|
||||
```javascript
|
||||
// const data = ...
|
||||
// const graph = new G6.Graph({...});
|
||||
|
||||
// lineDash 的差值,可以在后面提供 util 方法自动计算
|
||||
const dashArray = [
|
||||
[0, 1],
|
||||
[0, 2],
|
||||
[1, 2],
|
||||
[0, 1, 1, 2],
|
||||
[0, 2, 1, 2],
|
||||
[1, 2, 1, 2],
|
||||
[2, 2, 1, 2],
|
||||
[3, 2, 1, 2],
|
||||
[4, 2, 1, 2],
|
||||
];
|
||||
|
||||
const lineDash = [4, 2, 1, 2];
|
||||
const interval = 9; // lineDash 的总长度。
|
||||
|
||||
// 注册名为 'can-running' 的边
|
||||
G6.registerEdge(
|
||||
@ -440,20 +402,19 @@ G6.registerEdge(
|
||||
if (name === 'running') {
|
||||
// running 状态为 true 时
|
||||
if (value) {
|
||||
const length = shape.getTotalLength();
|
||||
let totalArray = [];
|
||||
for (var i = 0; i < length; i += interval) {
|
||||
totalArray = totalArray.concat(lineDash);
|
||||
}
|
||||
let index = 0;
|
||||
let index = 0;// 边 path 图形的动画
|
||||
shape.animate(
|
||||
ratio => {
|
||||
// 每一帧的操作,入参 ratio:这一帧的比例值(Number)。返回值:这一帧需要变化的参数集(Object)。
|
||||
const cfg = {
|
||||
lineDash: dashArray[index].concat(totalArray),
|
||||
() => {
|
||||
index++;
|
||||
if (index > 9) {
|
||||
index = 0;
|
||||
}
|
||||
const res = {
|
||||
lineDash,
|
||||
lineDashOffset: -index,
|
||||
};
|
||||
index = (index + 1) % interval;
|
||||
return cfg;
|
||||
// 返回需要修改的参数集,这里修改了 lineDash,lineDashOffset
|
||||
return res;
|
||||
},
|
||||
{
|
||||
repeat: true, // 动画重复
|
||||
@ -498,3 +459,23 @@ graph.on('node:mouseleave', ev => {
|
||||
```
|
||||
|
||||
<span style="background-color: rgb(251, 233, 231); color: rgb(139, 53, 56)"> <strong>⚠️ 注意:</strong></span> `running` 为 `false` 时,要停止动画,同时把 `lineDash` 清空。
|
||||
|
||||
|
||||
## animateCfg
|
||||
|
||||
| 配置项 | 类型 | 默认值 | 描述 |
|
||||
| ---- | --------------- | -------- | ----------------------------------- |
|
||||
| duration | Number | 500 | 一次动画的时长 |
|
||||
| easing | boolean | 'linearEasing' | 动画函数,见 [easing 函数](#easing-函数) |
|
||||
| delay | Number | 0 | 延迟一段时间后执行动画 |
|
||||
| repeat | boolean | false | 是否重复执行动画 |
|
||||
| callback | Function | undefined | 动画执行完时的回调函数 |
|
||||
| pauseCallback | Function | undefined | 动画暂停时(`shape.pause()`)的回调函数 |
|
||||
| resumeCallback | Function | undefined | 动画恢复时(`shape.resume()`)的回调函数 |
|
||||
|
||||
|
||||
### easing 函数
|
||||
|
||||
easing 函数是指动画的函数。例如线性插值、先快后慢等。<br />G6 支持所有 d3.js 中的动画函数。因此,上面代码中 `animateCfg` 配置中的 String 类型的 `easing` 可以取值有:<br />`'easeLinear'` ,<br />`'easePolyIn'` ,`'easePolyOut'` , `'easePolyInOut'` ,<br />`'easeQuad'` ,`'easeQuadIn'` ,`'easeQuadOut'` , `'easeQuadInOut'` 。
|
||||
|
||||
更多取值及所有取值含义参见:<a href='https://github.com/d3/d3/blob/master/API.md#easings-d3-ease' target='_blank'>d3 Easings</a>。
|
||||
|
@ -34,23 +34,23 @@ const graph = new G6.Graph({
|
||||
},
|
||||
position: 'bottom',
|
||||
},
|
||||
// 节点上左右上下四个方向上的链接circle配置
|
||||
// configurations for four linkpoints
|
||||
linkPoints: {
|
||||
top: true,
|
||||
right: true,
|
||||
bottom: true,
|
||||
left: true,
|
||||
// circle的大小
|
||||
size: 5,
|
||||
// the diameter of the linkPoint
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#fff',
|
||||
stroke: '#1890FF',
|
||||
},
|
||||
// 节点中icon配置
|
||||
// icon configuration
|
||||
icon: {
|
||||
// 是否显示icon,值为 false 则不渲染icon
|
||||
// whether show the icon
|
||||
show: true,
|
||||
// icon的地址,字符串类型
|
||||
// icon's img address, string type
|
||||
img:
|
||||
'https://gw.alipayobjects.com/zos/basement_prod/012bcf4f-423b-4922-8c24-32a89f8c41ce.svg',
|
||||
width: 60,
|
||||
@ -61,11 +61,11 @@ const graph = new G6.Graph({
|
||||
default: ['drag-canvas', 'drag-node'],
|
||||
},
|
||||
nodeStateStyles: {
|
||||
// 鼠标hover状态下的配置
|
||||
// node style of hover state
|
||||
hover: {
|
||||
fillOpacity: 0.8,
|
||||
},
|
||||
// 选中节点状态下的配置
|
||||
// node style of selected state
|
||||
selected: {
|
||||
lineWidth: 5,
|
||||
},
|
||||
|
@ -34,22 +34,23 @@ const graph = new G6.Graph({
|
||||
},
|
||||
position: 'bottom',
|
||||
},
|
||||
// 节点上左右上下四个方向上的链接circle配置
|
||||
// configurations for four linkpoints
|
||||
linkPoints: {
|
||||
top: false,
|
||||
bottom: false,
|
||||
left: true,
|
||||
right: true,
|
||||
size: 5,
|
||||
// the diameter of the linkPoint
|
||||
size: 10,
|
||||
fill: '#fff',
|
||||
lineWidth: 1,
|
||||
stroke: '#1890FF',
|
||||
},
|
||||
// 节点中icon配置
|
||||
// icon configuration
|
||||
icon: {
|
||||
// 是否显示icon,值为 false 则不渲染icon
|
||||
// whether show the icon
|
||||
show: true,
|
||||
// icon的地址,字符串类型
|
||||
// icon's img address, string type
|
||||
img:
|
||||
'https://gw.alipayobjects.com/zos/basement_prod/012bcf4f-423b-4922-8c24-32a89f8c41ce.svg',
|
||||
width: 60,
|
||||
@ -60,11 +61,11 @@ const graph = new G6.Graph({
|
||||
default: ['drag-canvas', 'drag-node'],
|
||||
},
|
||||
nodeStateStyles: {
|
||||
// 鼠标hover状态下的配置
|
||||
// node style of hover state
|
||||
hover: {
|
||||
fillOpacity: 0.8,
|
||||
},
|
||||
// 选中节点状态下的配置
|
||||
// node style of selected state
|
||||
selected: {
|
||||
lineWidth: 5,
|
||||
},
|
||||
|
@ -34,23 +34,23 @@ const graph = new G6.Graph({
|
||||
},
|
||||
position: 'bottom',
|
||||
},
|
||||
// 节点上左右上下四个方向上的链接circle配置
|
||||
// configurations for four linkpoints
|
||||
linkPoints: {
|
||||
top: true,
|
||||
right: false,
|
||||
bottom: true,
|
||||
left: false,
|
||||
// circle的大小
|
||||
size: 5,
|
||||
// the diameter of the linkPoint
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#fff',
|
||||
stroke: '#1890FF',
|
||||
},
|
||||
// 节点中icon配置
|
||||
// icon configuration
|
||||
icon: {
|
||||
// 是否显示icon,值为 false 则不渲染icon
|
||||
// whether show the icon
|
||||
show: true,
|
||||
// icon的地址,字符串类型
|
||||
// icon's img address, string type
|
||||
img:
|
||||
'https://gw.alipayobjects.com/zos/basement_prod/012bcf4f-423b-4922-8c24-32a89f8c41ce.svg',
|
||||
width: 60,
|
||||
@ -61,11 +61,11 @@ const graph = new G6.Graph({
|
||||
default: ['drag-canvas', 'drag-node'],
|
||||
},
|
||||
nodeStateStyles: {
|
||||
// 鼠标hover状态下的配置
|
||||
// node style of hover state
|
||||
hover: {
|
||||
fillOpacity: 0.8,
|
||||
},
|
||||
// 选中节点状态下的配置
|
||||
// node style of selected state
|
||||
selected: {
|
||||
lineWidth: 5,
|
||||
},
|
||||
|
@ -52,7 +52,7 @@ const graph = new G6.Graph({
|
||||
bottom: false,
|
||||
left: false,
|
||||
// the size of the linkpoints' circle
|
||||
size: 3,
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#72CC4A',
|
||||
stroke: '#72CC4A',
|
||||
|
@ -36,7 +36,7 @@ const graph = new G6.Graph({
|
||||
bottom: true,
|
||||
left: true,
|
||||
right: true,
|
||||
size: 5,
|
||||
size: 10,
|
||||
fill: '#fff',
|
||||
lineWidth: 1,
|
||||
stroke: '#1890FF',
|
||||
|
@ -41,7 +41,7 @@ const graph = new G6.Graph({
|
||||
leftBottom: true,
|
||||
rightBottom: true,
|
||||
// the size of the linkpoints' circle
|
||||
size: 5,
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#fff',
|
||||
stroke: '#1890FF',
|
||||
|
@ -42,7 +42,7 @@ const graph = new G6.Graph({
|
||||
bottom: true,
|
||||
left: true,
|
||||
// the size of the linkpoints' circle
|
||||
size: 5,
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#fff',
|
||||
stroke: '#1890FF',
|
||||
|
@ -5,10 +5,10 @@ G6.registerEdge(
|
||||
'line-dash',
|
||||
{
|
||||
afterDraw(cfg, group) {
|
||||
// 获得该边的第一个图形,这里是边的 path
|
||||
// get the first shape in the group, it is the edge's path here=
|
||||
const shape = group.get('children')[0];
|
||||
let index = 0;
|
||||
// 边 path 图形的动画
|
||||
// Define the animation
|
||||
shape.animate(
|
||||
() => {
|
||||
index++;
|
||||
@ -19,18 +19,18 @@ G6.registerEdge(
|
||||
lineDash,
|
||||
lineDashOffset: -index,
|
||||
};
|
||||
// 返回需要修改的参数集,这里修改了 lineDash,lineDashOffset
|
||||
// returns the modified configurations here, lineDash and lineDashOffset here
|
||||
return res;
|
||||
},
|
||||
{
|
||||
repeat: true, // 动画重复
|
||||
duration: 3000, // 一次动画的时长为 3000
|
||||
repeat: true, // whether executes the animation repeatly
|
||||
duration: 3000, // the duration for executing once
|
||||
},
|
||||
);
|
||||
},
|
||||
},
|
||||
'cubic',
|
||||
); // 该自定义边继承了内置三阶贝塞尔曲线边 cubic
|
||||
'cubic', // extend the built-in edge 'cubic'
|
||||
);
|
||||
|
||||
const data = {
|
||||
nodes: [
|
||||
|
@ -8,23 +8,23 @@ G6.registerEdge(
|
||||
const length = shape.getTotalLength();
|
||||
shape.animate(
|
||||
ratio => {
|
||||
// 每一帧的操作,入参 ratio:这一帧的比例值(Number)。返回值:这一帧需要变化的参数集(Object)。
|
||||
// the operations in each frame. Ratio ranges from 0 to 1 indicating the prograss of the animation. Returns the modified configurations
|
||||
const startLen = ratio * length;
|
||||
// 计算线的lineDash
|
||||
// Calculate the lineDash
|
||||
const cfg = {
|
||||
lineDash: [startLen, length - startLen],
|
||||
};
|
||||
return cfg;
|
||||
},
|
||||
{
|
||||
repeat: true, // 动画重复
|
||||
duration: 2000, // 一次动画的时长为 2000
|
||||
repeat: true, // Whether executes the animation repeatly
|
||||
duration: 2000, // the duration for executing once
|
||||
},
|
||||
);
|
||||
},
|
||||
},
|
||||
'cubic',
|
||||
); // 该自定义边继承了内置三阶贝塞尔曲线边 cubic
|
||||
'cubic', // extend the built-in edge 'cubic'
|
||||
);
|
||||
|
||||
const data = {
|
||||
nodes: [
|
||||
|
@ -3,12 +3,12 @@ G6.registerEdge(
|
||||
'circle-running',
|
||||
{
|
||||
afterDraw(cfg, group) {
|
||||
// 获得当前边的第一个图形,这里是边本身的 path
|
||||
// get the first shape in the group, it is the edge's path here=
|
||||
const shape = group.get('children')[0];
|
||||
// 边 path 的起点位置
|
||||
// the start position of the edge's path
|
||||
const startPoint = shape.getPoint(0);
|
||||
|
||||
// 添加红色 circle 图形
|
||||
// add red circle shape
|
||||
const circle = group.addShape('circle', {
|
||||
attrs: {
|
||||
x: startPoint.x,
|
||||
@ -19,27 +19,27 @@ G6.registerEdge(
|
||||
name: 'circle-shape',
|
||||
});
|
||||
|
||||
// 对红色圆点添加动画
|
||||
// animation for the red circle
|
||||
circle.animate(
|
||||
ratio => {
|
||||
// 每一帧的操作,入参 ratio:这一帧的比例值(Number)。返回值:这一帧需要变化的参数集(Object)。
|
||||
// 根据比例值,获得在边 path 上对应比例的位置。
|
||||
// the operations in each frame. Ratio ranges from 0 to 1 indicating the prograss of the animation. Returns the modified configurations
|
||||
// get the position on the edge according to the ratio
|
||||
const tmpPoint = shape.getPoint(ratio);
|
||||
// 返回需要变化的参数集,这里返回了位置 x 和 y
|
||||
// returns the modified configurations here, x and y here
|
||||
return {
|
||||
x: tmpPoint.x,
|
||||
y: tmpPoint.y,
|
||||
};
|
||||
},
|
||||
{
|
||||
repeat: true, // 动画重复
|
||||
duration: 3000, // 一次动画的时间长度
|
||||
repeat: true, // Whether executes the animation repeatly
|
||||
duration: 3000, // the duration for executing once
|
||||
},
|
||||
);
|
||||
},
|
||||
},
|
||||
'cubic',
|
||||
); // 该自定义边继承内置三阶贝塞尔曲线 cubic
|
||||
'cubic', // extend the built-in edge 'cubic'
|
||||
);
|
||||
|
||||
const data = {
|
||||
nodes: [
|
||||
|
@ -44,10 +44,12 @@ export default {
|
||||
const width = this.graph.get('width');
|
||||
const height = this.graph.get('height');
|
||||
const graphCanvasBBox = this.graph.get('canvas').getCanvasBBox();
|
||||
if (graphCanvasBBox.minX + dx > width || graphCanvasBBox.maxX + dx < 0) {
|
||||
if ((graphCanvasBBox.minX <= width && graphCanvasBBox.minX + dx > width)
|
||||
|| (graphCanvasBBox.maxX >= 0 && graphCanvasBBox.maxX + dx < 0)) {
|
||||
dx = 0;
|
||||
}
|
||||
if (graphCanvasBBox.minY + dy > height || graphCanvasBBox.maxY + dy < 0) {
|
||||
if ((graphCanvasBBox.minY <= height && graphCanvasBBox.minY + dy > height)
|
||||
|| (graphCanvasBBox.maxY >= 0 && graphCanvasBBox.maxY + dy < 0)) {
|
||||
dy = 0;
|
||||
}
|
||||
this.graph.translate(dx, dy);
|
||||
|
@ -3,7 +3,7 @@ import { Point } from '@antv/g-base/lib/types';
|
||||
import Group from '@antv/g-canvas/lib/group';
|
||||
import isNumber from '@antv/util/lib/is-number';
|
||||
import isString from '@antv/util/lib/is-string';
|
||||
import { Item, Matrix, Padding } from '../../types';
|
||||
import { Item, Matrix, Padding, GraphAnimateConfig } from '../../types';
|
||||
import { formatPadding } from '../../util/base';
|
||||
import { applyMatrix, invertMatrix } from '../../util/math';
|
||||
import Graph from '../graph';
|
||||
@ -82,15 +82,41 @@ export default class ViewController {
|
||||
return formatPadding(padding);
|
||||
}
|
||||
|
||||
public focusPoint(point: Point) {
|
||||
public focusPoint(point: Point, animate?: boolean, animateCfg?: GraphAnimateConfig) {
|
||||
const viewCenter = this.getViewCenter();
|
||||
const modelCenter = this.getPointByCanvas(viewCenter.x, viewCenter.y);
|
||||
let viewportMatrix: Matrix = this.graph.get('group').getMatrix();
|
||||
if (!viewportMatrix) viewportMatrix = mat3.create();
|
||||
this.graph.translate(
|
||||
(modelCenter.x - point.x) * viewportMatrix[0],
|
||||
(modelCenter.y - point.y) * viewportMatrix[4],
|
||||
);
|
||||
if (animate) {
|
||||
const dx = (modelCenter.x - point.x) * viewportMatrix[0];
|
||||
const dy = (modelCenter.y - point.y) * viewportMatrix[4];
|
||||
let lastX = 0;
|
||||
let lastY = 0;
|
||||
let newX = 0;
|
||||
let newY = 0;
|
||||
const cfg = Object.assign({}, {
|
||||
duration: 300,
|
||||
easing: 'easeCubic'
|
||||
}, animateCfg)
|
||||
// 动画每次平移一点,直到目标位置
|
||||
this.graph.get('canvas').animate(
|
||||
ratio => {
|
||||
newX = dx * ratio;
|
||||
newY = dy * ratio;
|
||||
this.graph.translate(newX - lastX, newY - lastY);
|
||||
lastX = newX;
|
||||
lastY = newY;
|
||||
},
|
||||
{
|
||||
...cfg
|
||||
},
|
||||
);
|
||||
} else {
|
||||
this.graph.translate(
|
||||
(modelCenter.x - point.x) * viewportMatrix[0],
|
||||
(modelCenter.y - point.y) * viewportMatrix[4],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@ -147,21 +173,23 @@ export default class ViewController {
|
||||
/**
|
||||
* 将元素移动到画布中心
|
||||
* @param item Item 实例或 id
|
||||
* @param {boolean} animate 是否带有动画地移动
|
||||
* @param {GraphAnimateConfig} animateCfg 若带有动画,动画的配置项
|
||||
*/
|
||||
public focus(item: string | Item) {
|
||||
public focus(item: string | Item, animate?: boolean, animateCfg?: GraphAnimateConfig) {
|
||||
if (isString(item)) {
|
||||
item = this.graph.findById(item);
|
||||
}
|
||||
const group: Group = item.get('group');
|
||||
let matrix: Matrix = group.getMatrix();
|
||||
if (!matrix) matrix = mat3.create();
|
||||
|
||||
if (item) {
|
||||
const group: Group = item.get('group');
|
||||
let matrix: Matrix = group.getMatrix();
|
||||
if (!matrix) matrix = mat3.create();
|
||||
// 用实际位置而不是model中的x,y,防止由于拖拽等的交互导致model的x,y并不是当前的x,y
|
||||
this.focusPoint({
|
||||
x: matrix[6],
|
||||
y: matrix[7],
|
||||
});
|
||||
}, animate, animateCfg);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -675,10 +675,12 @@ export default class Graph extends EventEmitter implements IGraph {
|
||||
/**
|
||||
* 将元素移动到视口中心
|
||||
* @param {Item} item 指定元素
|
||||
* @param {boolean} animate 是否带有动画地移动
|
||||
* @param {GraphAnimateConfig} animateCfg 若带有动画,动画的配置项
|
||||
*/
|
||||
public focusItem(item: Item | string): void {
|
||||
public focusItem(item: Item | string, animate?: boolean, animateCfg?: GraphAnimateConfig): void {
|
||||
const viewController: ViewController = this.get('viewController');
|
||||
viewController.focus(item);
|
||||
viewController.focus(item, animate, animateCfg);
|
||||
|
||||
this.autoPaint();
|
||||
}
|
||||
|
@ -15,7 +15,8 @@ import {
|
||||
GraphOptions,
|
||||
ModeOption,
|
||||
ModeType,
|
||||
ComboConfig
|
||||
ComboConfig,
|
||||
GraphAnimateConfig
|
||||
} from '../types';
|
||||
import { IEdge, INode, ICombo } from './item';
|
||||
import PluginBase from '../plugins/base';
|
||||
@ -97,8 +98,10 @@ export interface IGraph extends EventEmitter {
|
||||
/**
|
||||
* 将元素移动到视口中心
|
||||
* @param {Item} item 指定元素
|
||||
* @param {boolean} animate 是否带有动画地移动
|
||||
* @param {GraphAnimateConfig} animateCfg 若带有动画,动画的配置项
|
||||
*/
|
||||
focusItem(item: Item | string): void;
|
||||
focusItem(item: Item | string, animate?: boolean, animateCfg?: GraphAnimateConfig): void;
|
||||
|
||||
/**
|
||||
* 调整视口适应视图
|
||||
|
@ -5,6 +5,7 @@ import { Item, NodeConfig, ShapeStyle, ModelConfig } from '../../types';
|
||||
import Global from '../../global';
|
||||
import Shape from '../shape';
|
||||
import { ShapeOptions } from '../../interface/shape';
|
||||
import { isNumber, isArray } from '@antv/util';
|
||||
|
||||
// 带有图标的圆,可用于拓扑图中
|
||||
Shape.registerNode(
|
||||
@ -32,7 +33,7 @@ Shape.registerNode(
|
||||
bottom: false,
|
||||
left: false,
|
||||
// circle的大小
|
||||
size: 3,
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#72CC4A',
|
||||
stroke: '#72CC4A',
|
||||
@ -88,9 +89,9 @@ Shape.registerNode(
|
||||
const { linkPoints: defaultLinkPoints } = this.options as ModelConfig;
|
||||
const linkPoints = deepMix({}, defaultLinkPoints, cfg.linkPoints);
|
||||
|
||||
const { top, left, right, bottom, size: markSize, ...markStyle } = linkPoints;
|
||||
const { top, left, right, bottom, size: markSize, r: markR, ...markStyle } = linkPoints;
|
||||
const size = this.getSize!(cfg);
|
||||
const r = size[0] / 2;
|
||||
let r = size[0] / 2;
|
||||
if (left) {
|
||||
// left circle
|
||||
group.addShape('circle', {
|
||||
@ -98,7 +99,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: -r,
|
||||
y: 0,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-left',
|
||||
name: 'link-point-left',
|
||||
@ -113,7 +114,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: r,
|
||||
y: 0,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-right',
|
||||
name: 'link-point-right',
|
||||
@ -128,7 +129,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: 0,
|
||||
y: -r,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-top',
|
||||
name: 'link-point-top',
|
||||
@ -143,7 +144,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: 0,
|
||||
y: r,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-bottom',
|
||||
name: 'link-point-bottom',
|
||||
|
@ -30,7 +30,7 @@ Shape.registerNode(
|
||||
bottom: false,
|
||||
left: false,
|
||||
// circle的大小
|
||||
size: 3,
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#72CC4A',
|
||||
stroke: '#72CC4A',
|
||||
@ -88,7 +88,7 @@ Shape.registerNode(
|
||||
const { linkPoints: defaultLinkPoints } = this.options as ModelConfig;
|
||||
const linkPoints = mix({}, defaultLinkPoints, cfg.linkPoints);
|
||||
|
||||
const { top, left, right, bottom, size: markSize, ...markStyle } = linkPoints;
|
||||
const { top, left, right, bottom, size: markSize, r: markR, ...markStyle } = linkPoints;
|
||||
const size = this.getSize!(cfg);
|
||||
const width = size[0];
|
||||
const height = size[1];
|
||||
@ -99,7 +99,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: -width / 2,
|
||||
y: 0,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-left',
|
||||
name: 'link-point-left',
|
||||
@ -114,7 +114,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: width / 2,
|
||||
y: 0,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-right',
|
||||
name: 'link-point-right',
|
||||
@ -129,7 +129,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: 0,
|
||||
y: -height / 2,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-top',
|
||||
name: 'link-point-top',
|
||||
@ -144,7 +144,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: 0,
|
||||
y: height / 2,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-bottom',
|
||||
name: 'link-point-bottom',
|
||||
|
@ -35,7 +35,7 @@ Shape.registerNode(
|
||||
bottom: false,
|
||||
left: false,
|
||||
// circle的大小
|
||||
size: 3,
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#72CC4A',
|
||||
stroke: '#72CC4A',
|
||||
@ -93,7 +93,7 @@ Shape.registerNode(
|
||||
const { linkPoints: defaultLinkPoints } = this.options as ModelConfig;
|
||||
const linkPoints = mix({}, defaultLinkPoints, cfg.linkPoints);
|
||||
|
||||
const { top, left, right, bottom, size: markSize, ...markStyle } = linkPoints;
|
||||
const { top, left, right, bottom, size: markSize, r: markR, ...markStyle } = linkPoints;
|
||||
const size = this.getSize!(cfg);
|
||||
const rx = size[0] / 2;
|
||||
const ry = size[1] / 2;
|
||||
@ -105,7 +105,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: -rx,
|
||||
y: 0,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-left',
|
||||
name: 'link-point-left',
|
||||
@ -120,7 +120,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: rx,
|
||||
y: 0,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-right',
|
||||
name: 'link-point-right',
|
||||
@ -135,7 +135,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: 0,
|
||||
y: -ry,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-top',
|
||||
name: 'link-point-top',
|
||||
@ -150,7 +150,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: 0,
|
||||
y: ry,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-bottom',
|
||||
name: 'link-point-bottom',
|
||||
|
@ -48,7 +48,7 @@ Shape.registerNode(
|
||||
bottom: false,
|
||||
left: false,
|
||||
// circle的大小
|
||||
size: 3,
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#72CC4A',
|
||||
stroke: '#72CC4A',
|
||||
@ -189,7 +189,7 @@ Shape.registerNode(
|
||||
const { linkPoints: defaultLinkPoints } = this.options as ModelConfig;
|
||||
const linkPoints = mix({}, defaultLinkPoints, cfg.linkPoints);
|
||||
|
||||
const { top, left, right, bottom, size: markSize, ...markStyle } = linkPoints;
|
||||
const { top, left, right, bottom, size: markSize, r: markR, ...markStyle } = linkPoints;
|
||||
const size = (this as ShapeOptions).getSize!(cfg);
|
||||
const width = size[0];
|
||||
const height = size[1];
|
||||
@ -201,7 +201,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: -width / 2,
|
||||
y: 0,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-left',
|
||||
name: 'link-point-left',
|
||||
@ -216,7 +216,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: width / 2,
|
||||
y: 0,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-right',
|
||||
name: 'link-point-right',
|
||||
@ -231,7 +231,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: 0,
|
||||
y: -height / 2,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-top',
|
||||
name: 'link-point-top',
|
||||
@ -246,7 +246,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: 0,
|
||||
y: height / 2,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-bottom',
|
||||
name: 'link-point-bottom',
|
||||
|
@ -33,7 +33,7 @@ Shape.registerNode(
|
||||
bottom: false,
|
||||
left: false,
|
||||
// circle的大小
|
||||
size: 3,
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#72CC4A',
|
||||
stroke: '#72CC4A',
|
||||
@ -69,7 +69,7 @@ Shape.registerNode(
|
||||
const { linkPoints: defaultLinkPoints } = this.options as ModelConfig;
|
||||
const linkPoints = mix({}, defaultLinkPoints, cfg.linkPoints);
|
||||
|
||||
const { top, left, right, bottom, size: markSize, ...markStyle } = linkPoints;
|
||||
const { top, left, right, bottom, size: markSize, r: markR, ...markStyle } = linkPoints;
|
||||
const size = (this as ShapeOptions).getSize!(cfg);
|
||||
const width = size[0];
|
||||
const height = size[1];
|
||||
@ -81,7 +81,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: -width / 2,
|
||||
y: 0,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-left',
|
||||
name: 'link-point-left',
|
||||
@ -96,7 +96,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: width / 2,
|
||||
y: 0,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-right',
|
||||
name: 'link-point-right',
|
||||
@ -111,7 +111,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: 0,
|
||||
y: -height / 2,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-top',
|
||||
name: 'link-point-top',
|
||||
@ -126,7 +126,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: 0,
|
||||
y: height / 2,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-bottom',
|
||||
name: 'link-point-bottom',
|
||||
|
@ -32,7 +32,7 @@ Shape.registerNode(
|
||||
leftBottom: false,
|
||||
rightBottom: false,
|
||||
// circle的大小
|
||||
size: 3,
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#fff',
|
||||
stroke: '#72CC4A',
|
||||
@ -97,6 +97,7 @@ Shape.registerNode(
|
||||
leftBottom,
|
||||
rightBottom,
|
||||
size: markSize,
|
||||
r: markR,
|
||||
...markStyle
|
||||
} = linkPoints;
|
||||
const size = (this as ShapeOptions).getSize!(cfg);
|
||||
@ -113,7 +114,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: x1,
|
||||
y: -y1,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-right',
|
||||
name: 'link-point-right',
|
||||
@ -131,7 +132,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: x1,
|
||||
y: -y1,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-top',
|
||||
name: 'link-point-top',
|
||||
@ -149,7 +150,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: x1,
|
||||
y: -y1,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-left',
|
||||
name: 'link-point-left',
|
||||
@ -167,7 +168,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: x1,
|
||||
y: -y1,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-left-bottom',
|
||||
name: 'link-point-left-bottom',
|
||||
@ -185,7 +186,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: x1,
|
||||
y: -y1,
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-right-bottom',
|
||||
name: 'link-point-right-bottom',
|
||||
@ -277,17 +278,17 @@ Shape.registerNode(
|
||||
const linkPoints = mix({}, currentLinkPoints, cfg.linkPoints);
|
||||
|
||||
const { fill: markFill, stroke: markStroke, lineWidth: borderWidth } = linkPoints;
|
||||
let markSize = linkPoints.size;
|
||||
let markSize = linkPoints.size / 2;
|
||||
if (!markSize) markSize = linkPoints.r;
|
||||
const { left, right, top, leftBottom, rightBottom } = cfg.linkPoints
|
||||
? cfg.linkPoints
|
||||
: {
|
||||
left: undefined,
|
||||
right: undefined,
|
||||
top: undefined,
|
||||
leftBottom: undefined,
|
||||
rightBottom: undefined,
|
||||
};
|
||||
left: undefined,
|
||||
right: undefined,
|
||||
top: undefined,
|
||||
leftBottom: undefined,
|
||||
rightBottom: undefined,
|
||||
};
|
||||
|
||||
const size = (this as ShapeOptions).getSize!(cfg);
|
||||
const outerR = size[0];
|
||||
|
@ -33,7 +33,7 @@ Shape.registerNode(
|
||||
bottom: false,
|
||||
left: false,
|
||||
// circle的大小
|
||||
size: 5,
|
||||
size: 10,
|
||||
lineWidth: 1,
|
||||
fill: '#fff',
|
||||
stroke: '#72CC4A',
|
||||
@ -105,7 +105,7 @@ Shape.registerNode(
|
||||
|
||||
const direction = cfg.direction || defaultDirection;
|
||||
|
||||
const { top, left, right, bottom, size: markSize, ...markStyle } = linkPoints;
|
||||
const { top, left, right, bottom, size: markSize, r: markR, ...markStyle } = linkPoints;
|
||||
|
||||
const size = (this as ShapeOptions).getSize!(cfg);
|
||||
const len = size[0];
|
||||
@ -130,7 +130,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: leftPos[0],
|
||||
y: leftPos[1],
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-left',
|
||||
name: 'link-point-left',
|
||||
@ -158,7 +158,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: rightPos[0],
|
||||
y: rightPos[1],
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-right',
|
||||
name: 'link-point-right',
|
||||
@ -186,7 +186,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: topPos[0],
|
||||
y: topPos[1],
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-top',
|
||||
name: 'link-point-top',
|
||||
@ -214,7 +214,7 @@ Shape.registerNode(
|
||||
...markStyle,
|
||||
x: bottomPos[0],
|
||||
y: bottomPos[1],
|
||||
r: markSize,
|
||||
r: markSize / 2 || markR || 5,
|
||||
},
|
||||
className: 'link-point-bottom',
|
||||
name: 'link-point-bottom',
|
||||
@ -320,7 +320,7 @@ Shape.registerNode(
|
||||
const linkPoints = mix({}, currentLinkPoints, cfg.linkPoints);
|
||||
|
||||
const { fill: markFill, stroke: markStroke, lineWidth: borderWidth } = linkPoints;
|
||||
let markSize = linkPoints.size;
|
||||
let markSize = linkPoints.size / 2;
|
||||
if (!markSize) markSize = linkPoints.r;
|
||||
const { left, right, top, bottom } = cfg.linkPoints
|
||||
? cfg.linkPoints
|
||||
|
@ -419,7 +419,7 @@ export const getLetterWidth = (letter, fontSize) => {
|
||||
*/
|
||||
export const getTextSize = (text, fontSize) => {
|
||||
let width = 0;
|
||||
const pattern = new RegExp("[\u4E00-\u9FA5]+");
|
||||
const pattern = new RegExp("[\u{4E00}-\u{9FA5}]+");
|
||||
text.split('').forEach(letter => {
|
||||
if (pattern.test(letter)) {
|
||||
// 中文字符
|
||||
|
@ -142,7 +142,7 @@ describe('circle test', () => {
|
||||
bottom: true,
|
||||
left: true,
|
||||
fill: '#fff',
|
||||
size: 5,
|
||||
size: 10,
|
||||
},
|
||||
},
|
||||
};
|
||||
|
@ -139,7 +139,7 @@ describe('diamond test', () => {
|
||||
left: true,
|
||||
right: true,
|
||||
fill: '#fff',
|
||||
size: 5,
|
||||
size: 10,
|
||||
},
|
||||
},
|
||||
};
|
||||
|
@ -180,7 +180,7 @@ describe('ellipse test', () => {
|
||||
return g.get('className') === 'link-point-top';
|
||||
});
|
||||
expect(markTop).not.toBe(null);
|
||||
expect(markTop.attr('r')).toEqual(5);
|
||||
expect(markTop.attr('r')).toEqual(2.5);
|
||||
expect(markTop.attr('fill')).toEqual('#fff');
|
||||
|
||||
const markBottom = group.find(g => {
|
||||
|
@ -459,7 +459,7 @@ describe('model rect test', () => {
|
||||
return g.get('className') === 'link-point-top';
|
||||
});
|
||||
expect(markTop).not.toBe(null);
|
||||
expect(markTop.attr('r')).toEqual(3);
|
||||
expect(markTop.attr('r')).toEqual(5);
|
||||
expect(markTop.attr('y')).toEqual(-35);
|
||||
|
||||
const markBottom = group.find(g => {
|
||||
@ -506,7 +506,7 @@ describe('model rect test', () => {
|
||||
return g.get('className') === 'link-point-left';
|
||||
});
|
||||
expect(markLeft).not.toBe(null);
|
||||
expect(markLeft.attr('r')).toEqual(3);
|
||||
expect(markLeft.attr('r')).toEqual(5);
|
||||
expect(markLeft.attr('y')).toEqual(0);
|
||||
|
||||
const markTop = group.find(g => {
|
||||
|
@ -89,7 +89,7 @@ describe('rect test', () => {
|
||||
left: true,
|
||||
right: true,
|
||||
fill: '#fff',
|
||||
size: 5,
|
||||
size: 10,
|
||||
},
|
||||
},
|
||||
};
|
||||
|
@ -214,7 +214,7 @@ describe('star test', () => {
|
||||
return g.get('className') === 'link-point-right';
|
||||
});
|
||||
expect(rightPoint).not.toBe(null);
|
||||
expect(rightPoint.attr('r')).toBe(10);
|
||||
expect(rightPoint.attr('r')).toBe(5);
|
||||
expect(rightPoint.attr('fill')).toBe('#f00');
|
||||
expect(rightPoint.attr('stroke')).toBe('#0f0');
|
||||
expect(rightPoint.attr('lineWidth')).toBe(2);
|
||||
@ -227,7 +227,7 @@ describe('star test', () => {
|
||||
linkPoints: {
|
||||
left: false,
|
||||
top: true,
|
||||
size: 10,
|
||||
size: 20,
|
||||
fill: '#f00',
|
||||
stroke: '#0f0',
|
||||
lineWidth: 2,
|
||||
|
@ -289,7 +289,7 @@ describe('triangle test', () => {
|
||||
return g.get('className') === 'link-point-right';
|
||||
});
|
||||
expect(rightPoint).not.toBe(null);
|
||||
expect(rightPoint.attr('r')).toBe(10);
|
||||
expect(rightPoint.attr('r')).toBe(5);
|
||||
expect(rightPoint.attr('fill')).toBe('#f00');
|
||||
expect(rightPoint.attr('stroke')).toBe('#0f0');
|
||||
expect(rightPoint.attr('lineWidth')).toBe(2);
|
||||
|
Loading…
Reference in New Issue
Block a user