1.概述
SVG 是一种基于 XML 语法的图像格式,全称是可缩放矢量图(Scalable Vector Graphics)。其他图像格式都是基于像素处理的,SVG 则是属于对图像的形状描述,所以它本质上是文本文件,体积较小,且不管放大多少倍都不会失真。SVG 文件可以直接插入网页,成为 DOM 的一部分,然后用 JavaScript 和 CSS 进行操作。
2.入门
可以查看阮一峰这篇文章
www.ruanyifeng.com/blog/2018/0…
3.实现效果(1对M,M对1的关系)
4. 实现原理
- 贝塞尔曲线绘制:对称的曲线需要四个点foreignObject来绘制,第一个点为起点的(X,Y),第四个点为终点(EX, EY),第二第三个点可以根据起点和终点计算得出,第二个点为(X, (Y+EY)/2),第三个点为(EX, (Y+EY)/2)。这样就可以绘制出对称平滑的曲线。** parentRowlen 父级行的盒子个数,**
数据格式定义:relationLine: [
{ from: 0, to: 1 },
{ from: 0, to: 2 },
{ from: 0, to: 3 },
{ from: 1, to: 4 },
{ from: 1, to: 5 },
{ from: 2, to: 6 },
{ from: 3, to: 6 },
],
startX =halfSize -(parentRowlen - 1) * 0.5 * (boxW + boxSpace) +parentSort * (boxSpace + boxW) -
0.5 * boxW +0.5 * boxW;
startY = parentLevel * topSpace + boxH * parentLevel + topH;
- 盒子的绘制:在svg插入DOM元素需要使用 foreignObject 标签。
最重要是盒子位置的计算,从上图可以看出,盒子的布局是左右对称的,所以我们应该考虑从对称点中点出发,rowlen为当前行的个数, topSpace 是每行的间距,level 表示第几行,从1开始
数据格式定义:key为盒子的ID, relationNode: {
1: { level: 1, sort: 0 },
2: { level: 1, sort: 1 },
3: { level: 1, sort: 2 },
4: { level: 2, sort: 0 },
5: { level: 2, sort: 1 },
6: { level: 2, sort: 2 },
},
startX = halfSize -(rowlen - 1) * 0.5 * (boxW + boxSpace) +sort * (boxSpace + boxW) -0.5 * boxW;
startY = level * topSpace + boxH * (level - 1) + topH;