graph-svg-js
v1.1.39
Published
> 一个基于 TypeScript 的 SVG 图形绘制库,提供面向对象的 API 和命令式 DSL 两种使用方式。
Readme
graph-svg-js
一个基于 TypeScript 的 SVG 图形绘制库,提供面向对象的 API 和命令式 DSL 两种使用方式。
简介
graph-svg-js 是一个轻量级的 SVG 图形绘制工具库,支持在浏览器或 Node.js 环境中创建和操作 SVG 图形。提供了丰富的基本图形元素(圆、椭圆、矩形、多边形、三角形、星星等)、高级图表组件(饼图、环形图、雷达图、柱状图)、文本处理、路径操作、动画效果以及命令式 DSL 系统。
特性
- 完整的图形支持:圆形、椭圆、矩形、多边形、三角形、星星、扇形、圆环等
- 图表组件:饼图、环形图、坐标系、柱状图、雷达图
- 文本处理:普通文本、路径文本、垂直文本、超链接文本
- 高级功能:渐变、遮罩、标记、图案填充、Symbol 引用、裁剪路径
- 动画系统:基础动画、颜色动画、路径动画、变换动画
- 命令 DSL:支持字符串命令解析,快速创建图形
- 画笔模式:支持链式调用的画笔操作
- 环境兼容:同时支持浏览器环境和 Node.js 环境
安装
npm install graph-svg-js快速开始
基础用法
import Svg from 'graph-svg-js';
// 创建 SVG 画布
const svg = new Svg({ width: 900, height: 900 });
// 绘制直线
svg.line({ x: 10, y: 10 }, { x: 30, y: 10 }, { width: 1, color: '#000000' });
// 绘制圆形
svg.circle({ x: 100, y: 100 }, 50, { color: '#446688' });
// 绘制矩形
svg.rect({ x: 200, y: 200 }, 100, 80, { color: '#EEE', border: { width: 2, color: '#333' } });
// 绘制扇形
svg.sector({ x: 300, y: 300 }, 80, { start: 0, end: 120, color: '#446688' });
// 绘制文本
svg.text({ x: 100, y: 50 }, 'Hello SVG', { size: 16, color: '#333' });
// 渲染到页面
document.body.append(svg.draw());命令 DSL 模式
import Svg from 'graph-svg-js';
const svg = new Svg({ width: 900, height: 900 });
// 使用命令绘制
svg.exec('line 10,10 30,10 --border 1 #000000');
svg.exec('sector 100,450 50 0 360 #EEEEEE 20');
svg.exec('circle 300,600 100 --fill #FFF --border 20 #000');
svg.exec('triangle 400,200 200,400 500,500 --fill red');
svg.exec("text '文本内容' 100,50 #000000 --offset 10 15");
// 批量执行命令
svg.commands(
'sector 200,200 100 0 120 #446688 20 --attr id id1',
'sector 200,200 100 120 240 #887731 20 --attr id id2',
'sector 200,200 100 240 360 #431a88 20 --attr id id3'
);
// 查看命令帮助
svg.commandHelp();画笔模式
import Svg from 'graph-svg-js';
const svg = new Svg({ width: 800, height: 600 });
const painter = svg.painter({ x: 50, y: 50 });
// 链式调用绘制
painter
.circle(30, { color: 'red' })
.move({ x: 100, y: 50 })
.rect(60, 40, { color: 'blue' })
.move({ x: 200, y: 50 })
.text('画笔模式', { size: 14, color: '#333' });API 文档
Svg 主类
创建 SVG 画布的统一入口。
构造函数
new Svg(options?: SvgOptions)SvgOptions 配置项:
| 属性 | 类型 | 说明 | |------|------|------| | viewBox | ViewBox | string | 视图盒模型 | | preserveAspectRatio | string | 元素缩放属性 | | width | string | number | 画布宽度 | | height | string | number | 画布高度 | | style | string | Style | 样式定义 | | desc | string | SVG 描述文本 |
主要方法
| 方法 | 说明 |
|------|------|
| circle(o, r, options?) | 绘制圆形 |
| ellipse(o, rx, ry, color?) | 绘制椭圆 |
| sector(o, r, options?) | 绘制扇形或圆环 |
| line(start, end, border?) | 绘制直线 |
| rect(point, width, height, options?) | 绘制矩形 |
| text(point, content, options?) | 添加文本 |
| polygon(points?) | 绘制多边形 |
| triangle(p1, p2, p3?) | 绘制三角形 |
| star(o, minR, maxR, size?) | 绘制星星 |
| pie(o, r, ratios, optional?) | 绘制饼图 |
| image(point, src, options?) | 添加图片 |
| path(point, commands, attrs?) | 绘制路径 |
| use(href, point, options?) | 引用 Symbol |
| symbol(id, options) | 定义 Symbol |
| coordinate(o, width, height, color?) | 绘制坐标系 |
| lineto(points, options?) | 绘制连续线段 |
| html(html, options?) | 嵌入 HTML 片段 |
| def(def?) | 创建 Defs 容器 |
| painter(point?) | 创建画笔 |
| command(command) | 执行单个命令 |
| commands(...commands) | 批量执行命令 |
| commandHelp() | 查看命令帮助 |
| append(...graphs) | 添加图形元素 |
| css(css, cssValue?) | 设置样式 |
| attr(name, value) | 设置属性 |
| draw() | 渲染 SVG 元素 |
| toString() | 输出 SVG 字符串 |
| clear() | 清空画布 |
图形元素详细 API
所有图形元素均继承自 Graph 基类,提供通用的操作方法。
Graph 基类方法
| 方法 | 说明 |
|------|------|
| fill(color, opacity?) | 设置填充色 |
| border(border) | 设置边框 |
| transparent() | 设置为透明 |
| font(options) | 设置字体样式 |
| attr(name, value) | 设置属性 |
| translate(x, y?) | 平移变换 |
| rotate(angle, point?) | 旋转变换 |
| scale(x, y?) | 缩放变换 |
| skewX(angle) / skewY(angle) | 斜切变换 |
| matrix(a, b, c, d, e, f) | 变换矩阵 |
| clipPath(id) | 引用裁剪路径 |
| setClass(className) | 设置 CSS 类 |
| setId(id) | 设置 ID |
| style(css) | 设置内联样式 |
| addEventListener(type, listener) | 添加事件监听 |
| removeEventListener(type, listener) | 移除事件监听 |
Circle - 圆形
import { Circle } from 'graph-svg-js';
const circle = new Circle({ x: 100, y: 100 }, 50);
// 获取圆上某点的坐标(以垂直方向为0°,顺时针)
const point = circle.getPoint(45);
// 批量绘制圆(工厂方法)
const paintFn = Circle.paint(50, { x: 100, y: 100 }, { x: 200, y: 100 });
const elements = paintFn({ fill: 'red' });Sector - 扇形/圆环
import { Sector } from 'graph-svg-js';
// 绘制扇形
const sector = Sector.sector(
{ x: 100, y: 100 }, // 圆心
80, // 半径
0, // 起始角度
120, // 终止角度
'#446688', // 填充色
0.8 // 透明度(可选)
);
// 绘制圆环
const annulus = Sector.annulus(
{ x: 100, y: 100 }, // 圆心
80, // 外半径
20, // 环宽度
'#446688', // 填充色
0, // 起始角度
360, // 终止角度
0.8 // 透明度(可选)
);
// 绘制实心圆
const circle = Sector.circle(
{ x: 100, y: 100 },
50,
'red',
0.5
);Ellipse - 椭圆
import { Ellipse } from 'graph-svg-js';
const ellipse = new Ellipse(
{ x: 100, y: 100 }, // 中心点
80, // 横向半径
50 // 纵向半径(不设置则为正圆)
);Polygon - 多边形
import Polygon from 'graph-svg-js';
// 基于顶点坐标创建
const polygon = new Polygon([
{ x: 100, y: 100 },
{ x: 200, y: 150 },
{ x: 150, y: 250 }
]);
// 创建正多边形
const hexagon = new Polygon().equilateral(
{ x: 150, y: 150 }, // 中心点
80, // 半径(中心到顶点距离)
6, // 边数(至少为3)
0 // 起始偏移角度(可选,默认0)
);
// 基于分值创建(用于雷达图等)
const radar = new Polygon().score(
{ x: 150, y: 150 }, // 中心点
100, // 满分对应的半径
100, // 满分分值
[80, 60, 90, 70, 85], // 各维度分值(从垂直方向顺时针)
0 // 起始偏移角度(可选)
);
// 设置顶点连接样式
polygon.linejoin('round'); // 'miter' | 'round' | 'bevel'
// 设置圆角半径
polygon.radius(5);Triangle - 三角形
import { Triangle } from 'graph-svg-js';
// 基于三个顶点创建
const triangle = new Triangle(
{ x: 100, y: 50 },
{ x: 50, y: 150 },
{ x: 150, y: 150 }
);
// 创建正等边三角形
const equilateral = Triangle.equilateral(
{ x: 100, y: 100 }, // 中心位置
60, // 中心到顶点距离
0 // 偏移角度(可选)
);
// 创建等腰三角形(已知顶点和夹角)
const isosceles = Triangle.isosceles(
{ x: 100, y: 50 }, // 顶点坐标
100, // 顶点到对边中心点的距离
60, // 顶点两条边的夹角(度)
false // 是否反向(可选)
);
// 创建特殊的正三角形(基于原点到顶点的距离)
const regular = Triangle.regular({
o: { x: 100, y: 100 }, // 圆心坐标
vr: 60, // 圆心到上顶点距离
lr: 50, // 圆心到左下顶点距离
rr: 50 // 圆心到右下顶点距离
});Rectangle - 矩形
import { Rectangle } from 'graph-svg-js';
const rect = new Rectangle(
{ x: 50, y: 50 }, // 左上角坐标
200, // 宽度
100 // 高度(不设置则为正方形)
);
// 设置圆角
rect.radius(10); // 统一圆角
rect.radius(10, 20); // rx=10, ry=20
// 获取中心点
const center = rect.getCenter();
// 获取四个顶点
const points = rect.getPoints();
// 返回: { lt, rt, lb, rb } 分别代表左上、右上、左下、右下Star - 星星
import { Star } from 'graph-svg-js';
const star = new Star({
size: 5, // 几角星(至少3角)
minR: 30, // 内角半径(内角到圆心距离)
maxR: 60, // 顶角半径(顶角到圆心距离)
o: { x: 100, y: 100 } // 圆心坐标
});Line - 直线
import { Line, Polyline } from 'graph-svg-js';
// 两点创建直线
const line = Line.build(
{ x: 10, y: 10 },
{ x: 200, y: 200 }
);
// 水平线
const horizontal = Line.horizontal(
{ x: 10, y: 50 },
200 // 长度
);
// 垂直线
const vertical = Line.vertical(
{ x: 100, y: 10 },
150 // 长度
);
// 斜线(已知起点、长度、角度)
const slash = Line.slash(
{ x: 50, y: 50 },
100, // 长度
45 // 角度(度)
);
// 设置虚线
line.dash('5,5'); // 虚线模式
line.dash('10,5,2,5', 3); // 虚线模式+偏移量
// 多段线
const polyline = new Polyline([
{ x: 10, y: 10 },
{ x: 100, y: 50 },
{ x: 200, y: 100 }
]);
// 添加点
polyline.point({ x: 300, y: 150 });
polyline.point(400, 200);
// 在顶点处绘制圆
const circles = polyline.acme(
5, // 圆半径
'red', // 圆填充色
{ stroke: '#000' } // 圆属性(可选)
);Path - 路径
Path 提供 SVG 路径命令的完整支持,支持绝对定位(大写)和相对定位(小写)。
import Path from 'graph-svg-js';
const path = new Path({ x: 10, y: 10 });
// M/m - 移动到指定点
path.moveto({ x: 50, y: 50 });
path.moveto({ x: 10, y: 10 }, true); // 相对定位
// L/l - 连线到指定点
path.lineto({ x: 100, y: 100 });
path.lineto({ x: 20, y: 20 }, true); // 相对定位
// H/h - 水平移动
path.horizontal(150);
path.horizontal(-30, true); // 相对定位
// V/v - 垂直移动
path.vertical(200);
path.vertical(50, true); // 相对定位
// A/a - 圆弧
path.arc({
rx: 50, // 椭圆x轴半径
ry: 50, // 椭圆y轴半径
xr: 0, // 椭圆长轴角度
laf: 0, // 是否选择长弧 (0或1)
sf: 0, // 是否逆时针 (0或1)
point: { x: 150, y: 50 } // 终止点
});
// C/c - 三次贝塞尔曲线
// 当前点为起点,end为终点,point1和point2为控制点
path.curveto(
{ x: 50, y: 0 }, // 控制点1
{ x: 100, y: 100 }, // 控制点2
{ x: 150, y: 50 } // 终点
);
// S/s - 简化贝塞尔曲线(C的简化版)
// 第一个控制点自动计算为前一个控制点的对称点
path.smoothCurveto(
{ x: 100, y: 100 }, // 控制点
{ x: 150, y: 50 } // 终点
);
// Q/q - 二次贝塞尔曲线
// 只需要一个控制点
path.quadratic(
{ x: 75, y: 0 }, // 控制点
{ x: 150, y: 50 } // 终点
);
// T/t - 简化二次贝塞尔(Q的简写)
// 自动推断控制点
path.smoothQuadratic(
{ x: 100, y: 100 }, // 推断的控制点
{ x: 150, y: 50 } // 终点
);
// 设置虚线
path.dash('5,5'); // 虚线模式
path.dash('10,5,2,5', 3); // 虚线模式+偏移
// 手动添加路径命令字符串
path.push('M 10 10 L 100 100 Z');
// 注意:Path 最终会自动添加 'Z' 命令闭合路径Text - 文本
import { Text, Tspan } from 'graph-svg-js';
// 基础文本
const text = new Text({
content: 'Hello SVG',
point: { x: 100, y: 100 }
});
// 设置字体样式
text.font({
size: 16,
weight: 'bold',
family: 'Arial',
color: '#333333'
});
// 设置文本偏移
text.offset(10, 5); // dx=10, dy=5
text.offsetX(15); // 仅x偏移
text.offsetY(10); // 仅y偏移
// 文本对齐
text.anchor('middle'); // 'start' | 'middle' | 'end'
text.middle(); // 快捷方法,等同于 anchor('middle')
// 垂直显示文字
text.vertical(1); // 每行1个字符
text.vertical(2, 3); // 每行2个字符,行间距3px
// 添加 Tspan
text.tspan('高亮文字', { fill: 'red', fontWeight: 'bold' });
text.tspan(new Tspan('自定义Tspan'));
// 添加多行文本
text.text(['第一行', '第二行', '第三行']);
text.text('追加内容');
// 路径文本(文字沿着路径显示)
// 首先需要定义一个 path 并设置 id
const textPath = new Text({
content: '沿着曲线显示的文字',
point: { x: 0, y: 0 }
});
textPath.href('pathId'); // 引用 path 的 id
// 或者使用 href 参数一步到位
const text2 = new Text({
content: '路径文本',
point: { x: 0, y: 0 },
href: 'pathId' // 直接关联到 path
});Image - 图片
import { Image } from 'graph-svg-js';
const image = new Image({
src: '/path/to/image.png',
point: { x: 100, y: 100 },
width: 200,
height: 150
});Pie - 饼图
import { Pie } from 'graph-svg-js';
const pie = new Pie({
o: { x: 200, y: 200 }, // 饼图中心
r: 100, // 半径
ratios: [
{ value: 25, color: '#446688', name: 'A' },
{ value: 35, color: '#887731', name: 'B' },
{ value: 40, color: '#431a88', name: 'C' }
],
optional: {
width: 2, // 边框宽度
attrs: { stroke: '#FFF' }, // 扇形属性
font: { color: '#333', size: 12 }, // 标签字体
anchor: 'middle' // 标签对齐方式
}
});
// 快捷创建(自动分配颜色)
const pie2 = Pie.build(
{ x: 200, y: 200 },
100,
[25, 35, 40] // 仅提供数值
);Ring - 环形图
import { Ring } from 'graph-svg-js';
const ring = new Ring({
o: { x: 200, y: 200 }, // 中心点
r: 100, // 半径
width: 30, // 环宽度
items: [
{ value: 30, color: '#446688', label: 'A' },
{ value: 70, color: '#887731', label: 'B' }
],
colors: ['#FF0000', '#00FF00', '#0000FF'], // 自定义颜色序列(可选)
render: (graph, item, index) => {
// 自定义渲染回调(可选)
if (graph instanceof Sector) {
graph.attr('opacity', 0.8);
}
}
});
// 动态添加项
ring.addItem({ value: 50, label: 'C' });
ring.addItem(25); // 仅数值Coordinate - 坐标系
import Coordinate from 'graph-svg-js';
const coordinate = new Coordinate({
o: { x: 100, y: 300 }, // 坐标系原点
width: 400, // 宽度(x轴)
height: -250, // 高度(y轴,负数表示向上)
color: '#333333' // 轴线颜色
});Radar - 雷达图
雷达图(蛛网图)用于显示多变量数据的可视化图表。维度数量和最大值会自动从数据中推导。
import { Radar } from 'graph-svg-js';
const radar = new Radar({
center: { x: 300, y: 300 }, // 雷达图中心坐标
radius: 150, // 雷达图半径
gridLevels: 5, // 网格层数(可选,默认5)
style: { // 样式配置(可选)
gridColor: '#CCCCCC', // 网格线颜色
gridWidth: 1, // 网格线宽度
gridOpacity: 0.5, // 网格透明度
axisColor: '#999999', // 轴线颜色
axisWidth: 1, // 轴线宽度
axisOpacity: 0.5, // 轴线透明度
labelOffset: 20, // 标签距离顶点的偏移量
labelFont: { // 标签字体配置
size: '12',
color: '#333333',
family: 'Arial'
}
},
datasets: [
{
data: [
{ label: '攻击力', value: 80 },
{ label: '防御力', value: 60 },
{ label: '速度', value: 90 },
{ label: '力量', value: 70 },
{ label: '技巧', value: 85 },
{ label: '耐力', value: 75 }
],
fillColor: '#446688', // 填充色
fillOpacity: 0.3, // 填充透明度
strokeColor: '#446688', // 描边颜色
strokeWidth: 2, // 描边宽度
pointStyle: { // 数据点样式
r: 4, // 点半径
fill: '#446688', // 填充色
stroke: '#FFF', // 边框色
strokeWidth: 1 // 边框宽度
}
}
]
});
svg.append(radar);多数据集对比示例:
import { Radar } from 'graph-svg-js';
const radar = new Radar({
center: { x: 300, y: 300 },
radius: 150,
datasets: [
{
data: [
{ label: '维度A', value: 80 },
{ label: '维度B', value: 60 },
{ label: '维度C', value: 90 },
{ label: '维度D', value: 70 },
{ label: '维度E', value: 85 }
],
fillColor: '#446688',
fillOpacity: 0.3,
strokeColor: '#446688'
},
{
data: [
{ label: '维度A', value: 65 },
{ label: '维度B', value: 75 },
{ label: '维度C', value: 70 },
{ label: '维度D', value: 90 },
{ label: '维度E', value: 60 }
],
fillColor: '#FF6666',
fillOpacity: 0.3,
strokeColor: '#FF6666'
}
]
});
svg.append(radar);动态操作数据集:
// 添加新数据集
radar.addDataset({
data: [
{ label: '维度A', value: 50 },
{ label: '维度B', value: 80 },
{ label: '维度C', value: 60 },
{ label: '维度D', value: 75 },
{ label: '维度E', value: 90 }
],
fillColor: '#66CC66',
fillOpacity: 0.3,
strokeColor: '#66CC66'
});
// 更新数据集
radar.updateDataset(0, {
data: [
{ label: '维度A', value: 90 },
// ...
],
fillColor: '#446688'
});
// 清空所有数据集
radar.clearDatasets();Defs 定义元素
Defs - 定义容器
import { Defs, LinearGradient, RadialGradient, Pattern, ClipPath, Marker, Mask, Symbol, Use } from 'graph-svg-js';
const defs = new Defs();
// 线性渐变
const linearGrad = new LinearGradient('grad1', {
start: { x: 0, y: 0 },
end: { x: 1, y: 0 }
});
linearGrad.stop({ offset: '0%', stopColor: '#8cffa0' });
linearGrad.stop({ offset: '100%', stopColor: '#8ca0ff' });
defs.def(linearGrad);
// 径向渐变
const radialGrad = new RadialGradient('grad2', {
o: { x: 0.5, y: 0.5 },
r: '50%',
focus: { x: 0.3, y: 0.3 }
});
radialGrad.stop({ offset: '0%', stopColor: 'white' });
radialGrad.stop({ offset: '100%', stopColor: 'black' });
defs.def(radialGrad);
// 图案填充
const pattern = new Pattern({
id: 'pattern1',
x: 0, y: 0,
width: 20, height: 20
});
// 可以往 pattern 里添加图形
defs.def(pattern);
// 剪切路径
const clipPath = new ClipPath('myClip');
clipPath.append(new Circle({ x: 30, y: 30 }, 20));
defs.def(clipPath);
// 标记(用于箭头等)
const marker = Marker.build('arrow', {
viewBox: { point: { x: 0, y: 0 }, width: 10, height: 10 },
markerWidth: 6,
markerHeight: 6,
orient: 'auto',
refX: 1,
refY: 5
});
// 往 marker 里添加路径等
defs.def(marker);
// 遮罩
const mask = new Mask({
id: 'myMask',
maskUnits: 'objectBoundingBox',
x: '-10%',
y: '-10%',
width: '120%',
height: '120%'
});
// 往 mask 里添加图形定义遮罩
defs.def(mask);
// Symbol 定义
const symbol = new Symbol({
id: 'mySymbol',
viewBox: '0 0 1024 1024'
});
// 往 symbol 里添加内容
defs.def(symbol);
// Use 引用
const use = Use.link('mySymbol', {
point: { x: 100, y: 100 },
width: 50,
height: 50
});
use.mask('myMask'); // 应用遮罩动画系统
Animate - 基础动画
import { Animate, AnimateColor, AnimateMotion, AnimateTransform } from 'graph-svg-js';
// 基础属性动画
const animate = new Animate({
attributeName: 'opacity',
from: '0',
to: '1',
dur: '2s',
repeatCount: 'indefinite'
});
// 颜色动画
const animateColor = new AnimateColor({
attributeName: 'fill',
from: 'red',
to: 'blue',
dur: '3s',
repeatCount: 3
});
// 路径动画(元素沿路径移动)
const animateMotion = new AnimateMotion({
dur: '6s',
repeatCount: 'indefinite',
path: new Path({ x: 10, y: 110 }), // 运动路径
calcMode: 'linear',
rotate: 'auto' // 自动旋转朝向路径
});
// 或者引用已有的 path
const animateMotion2 = new AnimateMotion({
dur: '6s',
repeatCount: 'indefinite',
'xlink:href': '#theMotionPath' // 引用 path 的 id
});
// 变换动画
const animateTransform = new AnimateTransform({
type: 'rotate', // 'translate' | 'scale' | 'rotate' | 'skewX' | 'skewY'
from: '0 100 100',
to: '360 100 100',
dur: '10s',
repeatCount: 'indefinite'
});
// 高级选项
const advancedAnimate = new Animate({
attributeName: 'x',
from: '0',
to: '100',
dur: '5s',
repeatCount: 'indefinite',
values: '0;50;100;50;0', // 多个变化值
by: '10', // 相对结束值
begin: '3s', // 延迟开始
end: '10s', // 结束时间
attributeType: 'XML' // 'CSS' | 'XML' | 'auto'
});支持的 DSL 命令
| 命令 | 说明 | 示例 |
|------|------|------|
| circle | 绘制圆形 | circle 100,100 50 --border 2 #333 |
| ellipse | 绘制椭圆 | ellipse 100,100 50 30 |
| sector | 绘制扇形/圆环 | sector 100,100 50 0 180 red |
| line | 绘制直线 | line 10,10 100,100 --border 2 blue |
| polyline | 绘制多段线 | polyline 10,10 50,50 100,10 |
| rectangle | 绘制矩形 | rectangle 10,10 100,80 --fill #EEE |
| triangle | 绘制三角形 | triangle 10,10 100,100 50,200 |
| polygon | 绘制多边形 | polygon 10,10 50,50 100,10 |
| text | 添加文本 | text '内容' 100,100 #333 |
| coordinate | 绘制坐标系 | coordinate 100,100 200 200 red |
| defs | 定义容器 | defs |
| symbol | 定义符号 | symbol id1 --viewBox 0 0 100 100 |
| use | 引用符号 | use #id1 50,50 --width 32 --height 32 |
高级组件
饼图 (Pie)
svg.pie(
{ x: 200, y: 200 }, // 中心点
80, // 半径
[
{ color: 'gray', value: 10, name: 'p1' },
{ color: 'green', value: 30, name: 'p2' },
{ color: 'orange', value: 60, name: 'p3' }
],
{
width: 2, // 边框宽度
attrs: { stroke: '#FFF', 'stroke-width': 2 },
font: { color: '#333' }
}
);环形图 (Ring)
import { Ring } from 'graph-svg-js';
const ring = new Ring({
o: { x: 200, y: 200 },
r: 80,
width: 30,
items: [
{ value: 30, color: '#446688', label: 'A' },
{ value: 70, color: '#887731', label: 'B' }
]
});
svg.append(ring);Symbol 与 Use
// 定义 Symbol(可用于 iconfont 图形)
svg.symbol('heart', {
viewBox: '0 0 1024 1024',
content: `<path d="M32 407.584a279.584 279.584 0 0 1 480-194.944..."></path>`
});
// 引用 Symbol
svg.use('heart', { x: 100, y: 100 }, { width: 32, height: 32 })
.attr('fill', 'red');渐变
import { Defs, LinearGradient, GradientStop } from 'graph-svg-js';
const defs = svg.def();
const gradient = new LinearGradient({
id: 'gradient',
x1: '0%', y1: '0%', x2: '100%', y2: '0%'
});
gradient.stop(new GradientStop('0%', '#8cffa0'));
gradient.stop(new GradientStop('100%', '#8ca0ff'));
defs.def(gradient);
svg.circle({ x: 100, y: 100 }, 50).attr('fill', 'url(#gradient)');动画
import { Animate, AnimateColor, AnimateTransform } from 'graph-svg-js';
// 基础动画
const animate = new Animate({
attributeName: 'opacity',
from: '0',
to: '1',
dur: '2s',
repeatCount: 'indefinite'
});
// 颜色动画
const animateColor = new AnimateColor({
attributeName: 'fill',
from: 'red',
to: 'blue',
dur: '3s'
});
// 变换动画
const animateTransform = new AnimateTransform({
type: 'rotate',
from: '0 100 100',
to: '360 100 100',
dur: '5s',
repeatCount: 'indefinite'
});颜色工具
Rgb 颜色类
import { Rgb } from 'graph-svg-js';
const color = new Rgb(255, 0, 0); // RGB 构造
const color2 = new Rgb('#FF0000'); // Hex 字符串构造
const color3 = new Rgb('#FF000080'); // 带透明度
color.setAlpha(0.5); // 调整透明度
color.toHex(); // 转为 Hex 格式
color.toString(); // 输出 rgb(255, 0, 0)Hex 颜色类
import { Hex } from 'graph-svg-js';
const hex = new Hex('#FF0000');
hex.setAlpha(0.8);
hex.toRgb(); // 转为 Rgb 格式
Hex.toRgbString('#FF0000'); // 直接转换项目结构
src/
├── index.ts # 主入口,导出所有模块
├── core.ts # 核心基础类 (Graph, Point, Border 等)
├── circle.ts # 圆形、扇形、椭圆
├── polygon.ts # 多边形、三角形、矩形、星星
├── line.ts # 直线、多段线
├── text.ts # 文本、路径文本、超链接
├── path.ts # SVG 路径操作
├── pie.ts # 饼图
├── ring.ts # 环形图
├── bar.ts # 柱状图
├── radar.ts # 雷达图
├── coordinate.ts # 坐标系
├── defs.ts # SVG 定义元素 (渐变、遮罩、标记等)
├── image.ts # 图片
├── animate.ts # 动画系统
├── style.ts # CSS 样式类型定义
└── command/ # 命令 DSL 系统
├── core.ts # 命令解析与执行基础
├── index.ts # 命令入口
├── circle.ts # 圆形命令
├── line.ts # 线段命令
├── polygon.ts # 多边形命令
├── text.ts # 文本命令
├── defs.ts # 定义命令
├── coordinate.ts # 坐标系命令
└── image.ts # 图片命令构建
# TypeScript 编译
npm run build
# Babel 转换
npm run build-babel
# Webpack 打包
npm run build-webpack
# 生成文档
npm run typedoc技术栈
- TypeScript - 类型安全的 JavaScript 超集
- Babel - JavaScript 编译器
- Webpack - 模块打包工具
- TypeDoc - TypeScript 文档生成器
使用示例
绘制组合图形
import Svg from 'graph-svg-js';
const svg = new Svg({ width: 600, height: 400 });
// 绘制圆环
svg.exec('circle 300,200 100 --fill #FFF --border 20 #333');
// 绘制坐标系
svg.coordinate({ x: 50, y: 350 }, 500, -300, '#666');
// 绘制饼图
svg.pie(
{ x: 450, y: 200 }, 60,
[
{ color: '#446688', value: 25, name: 'A' },
{ color: '#887731', value: 35, name: 'B' },
{ color: '#431a88', value: 40, name: 'C' }
]
);
// 垂直文本
svg.text({ x: 100, y: 50 }, '垂直文本示例', { size: 14, color: '#333' })
.vertical(2);
// 渲染
document.body.append(svg.draw());绘制星星图案
import Svg from 'graph-svg-js';
const svg = new Svg({ width: 400, height: 300 });
// 直接绘制星星
svg.star({ x: 100, y: 150 }, 20, 50);
// 使用 Symbol 复用
svg.symbol('star', {
viewBox: '0 0 256 256',
content: new Star({
size: 5,
minR: 31,
maxR: 80,
o: { x: 128, y: 128 }
})
});
// 多次引用
svg.use('star', { x: 200, y: 100 }, { width: 32, height: 32 }).fill('gold');
svg.use('star', { x: 250, y: 150 }, { width: 32, height: 32 }).fill('gold');
svg.use('star', { x: 300, y: 200 }, { width: 32, height: 32 }).fill('gold');
document.body.append(svg.draw());License
ISC
