UNPKG

markdown-it-git-graph

Version:

一个markdown-it插件,用于生成git提交图

128 lines (127 loc) 4.66 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.getSvg = getSvg; exports.newLine = newLine; exports.newMergeLine = newMergeLine; exports.newPoint = newPoint; function newPoint(hash, x, y, color) { return { x, y, color, draw(id, theme) { return `<circle id="p-${id}-${hash}" cx="${this.x}" cy="${this.y}" r="${theme.pointRadius}" fill="${this.color}" />`; }, }; } function newLine(from, to, color) { return { from, to, color, draw() { return `<line x1="${this.from.x}" y1="${this.from.y}" x2="${this.to.x}" y2="${this.to.y}" stroke="${this.color}" stroke-width="2" />`; }, }; } function newMergeLine(from, to, color) { return { from, to, color, draw(_, theme) { const flag = Math.abs(this.to.y - this.from.y) > theme.lineHeight; const x1 = this.from.x; const y1 = this.to.y > this.from.y ? this.to.y - theme.lineHeight : this.to.y + theme.lineHeight; const x2 = this.to.x; const y2 = this.to.y; return `<path d="M ${this.from.x} ${this.from.y}${flag ? ` ${x1} ${y1}` : ''} C ${0.8 * x1 + 0.2 * x2} ${0.2 * y1 + 0.8 * y2} ${0.2 * x1 + 0.8 * x2} ${0.8 * y1 + 0.2 * y2} ${x2} ${y2}" stroke="${this.color}" stroke-width="2" fill="none" />`; }, }; } function addToSvg(commits, svg, theme) { svg.height = commits.length * theme.lineHeight; const padding = { x: theme.lineWidth / 2, y: theme.lineHeight / 2, }; const branchInfoCache = {}; const points = {}; for (let i = 0; i < commits.length; i++) { const commit = commits[i]; if (points[commit.hash]) { svg.errors.push({ draw: () => `commit ${commit.hash} is not uniqued`, }); continue; } let branch = branchInfoCache[commit.branch.id]; if (!branch) { branch = { color: commit.branch.id < theme.colors.length ? theme.colors[commit.branch.id] : randomColor(), x: commit.branch.id * theme.lineWidth + padding.x, }; branchInfoCache[commit.branch.id] = branch; } const point = newPoint(commit.hash, branch.x, i * theme.lineHeight + padding.y, branch.color); points[commit.hash] = point; svg.points.push(point); } svg.width = (Object.keys(branchInfoCache).length) * theme.lineWidth; for (let i = 0; i < commits.length; i++) { const commit = commits[i]; const point = points[commit.hash]; if (commit.base === undefined && commit.merge === undefined) { svg.lines.push(newLine({ x: point.x, y: svg.height - padding.y, }, point, point.color)); continue; } if (commit.base !== undefined) { const basePoint = points[commit.base]; if (!basePoint) { svg.errors.push({ draw: () => `commit ${commit.hash} base ${commit.base} not found`, }); } else { svg.lines.push(newLine(basePoint, point, point.color)); } } if (commit.merge !== undefined) { const mergePoint = points[commit.merge]; if (!mergePoint) { svg.errors.push({ draw: () => `commit ${commit.hash} merge ${commit.merge} not found`, }); } else { svg.mergeLines.push(newMergeLine(mergePoint, point, commit.base ? mergePoint.color : point.color)); } } } } function getSvg(idx, commits, options) { const svg = { id: idx.toString(), width: 0, height: 0, points: [], lines: [], mergeLines: [], errors: [], draw(_, theme) { if (svg.errors.length > 0) { return `<svg width=300 height=100 xmlns='http://www.w3.org/2000/svg'> ${svg.errors.map(e => e.draw(this.id, theme)).join('\n')}</svg>`; } return `<svg width='${this.width}' height='${this.height}' xmlns='http://www.w3.org/2000/svg'>${this.mergeLines.map(e => e.draw(this.id, theme)).join('')}${this.lines.map(e => e.draw(this.id, theme)).join('')}${this.points.map(e => e.draw(this.id, theme)).join('')}</svg>`; }, }; addToSvg(commits, svg, options.theme); return svg; } function randomColor() { return `#${Math.floor(Math.random() * 16777215).toString(16)}`; }