@antv/gpt-vis 1.0.0-beta.1 → 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +223 -47
- package/README.zh-CN.md +227 -51
- package/dist/cjs/gpt-vis/index.d.ts +8 -1
- package/dist/cjs/gpt-vis/index.js +43 -20
- package/dist/cjs/index.d.ts +15 -2
- package/dist/cjs/index.js +22 -2
- package/dist/cjs/syntax/parser.d.ts +17 -2
- package/dist/cjs/syntax/parser.js +151 -38
- package/dist/cjs/util/container.d.ts +5 -0
- package/dist/cjs/util/container.js +43 -0
- package/dist/cjs/util/theme.d.ts +5 -0
- package/dist/cjs/util/theme.js +9 -2
- package/dist/cjs/vis/area/index.js +2 -1
- package/dist/cjs/vis/bar/index.js +5 -4
- package/dist/cjs/vis/boxplot/index.js +7 -2
- package/dist/cjs/vis/column/index.js +5 -4
- package/dist/cjs/vis/dual-axes/index.js +3 -3
- package/dist/cjs/vis/fishbone-diagram/index.d.ts +35 -0
- package/dist/cjs/vis/fishbone-diagram/index.js +191 -0
- package/dist/cjs/vis/flow-diagram/index.d.ts +27 -0
- package/dist/cjs/vis/flow-diagram/index.js +287 -0
- package/dist/cjs/vis/funnel/index.js +2 -1
- package/dist/cjs/vis/histogram/index.js +3 -7
- package/dist/cjs/vis/indented-tree/index.d.ts +40 -0
- package/dist/cjs/vis/indented-tree/index.js +385 -0
- package/dist/cjs/vis/line/index.js +2 -1
- package/dist/cjs/vis/liquid/index.js +2 -1
- package/dist/cjs/vis/mindmap/index.d.ts +32 -0
- package/dist/cjs/vis/mindmap/index.js +222 -0
- package/dist/cjs/vis/network-graph/index.d.ts +59 -0
- package/dist/cjs/vis/network-graph/index.js +175 -0
- package/dist/cjs/vis/organization-chart/index.d.ts +64 -0
- package/dist/cjs/vis/organization-chart/index.js +200 -0
- package/dist/cjs/vis/pie/index.js +3 -3
- package/dist/cjs/vis/radar/index.d.ts +1 -0
- package/dist/cjs/vis/radar/index.js +10 -9
- package/dist/cjs/vis/sankey/index.js +2 -1
- package/dist/cjs/vis/scatter/index.d.ts +2 -0
- package/dist/cjs/vis/scatter/index.js +9 -4
- package/dist/cjs/vis/summary/index.js +17 -3
- package/dist/cjs/vis/table/index.d.ts +1 -0
- package/dist/cjs/vis/table/index.js +37 -1
- package/dist/cjs/vis/treemap/index.js +2 -1
- package/dist/cjs/vis/venn/index.d.ts +2 -1
- package/dist/cjs/vis/venn/index.js +18 -3
- package/dist/cjs/vis/violin/index.js +2 -1
- package/dist/cjs/vis/waterfall/index.d.ts +6 -9
- package/dist/cjs/vis/waterfall/index.js +29 -6
- package/dist/cjs/vis/word-cloud/index.js +2 -1
- package/dist/cjs/vis-wrapper/icons.js +2 -2
- package/dist/cjs/vis-wrapper/index.d.ts +1 -0
- package/dist/cjs/vis-wrapper/index.js +27 -16
- package/dist/cjs/vis-wrapper/styles.d.ts +1 -1
- package/dist/cjs/vis-wrapper/styles.js +8 -1
- package/dist/esm/gpt-vis/index.d.ts +8 -1
- package/dist/esm/gpt-vis/index.js +47 -26
- package/dist/esm/index.d.ts +15 -2
- package/dist/esm/index.js +7 -1
- package/dist/esm/syntax/parser.d.ts +17 -2
- package/dist/esm/syntax/parser.js +248 -90
- package/dist/esm/util/container.d.ts +5 -0
- package/dist/esm/util/container.js +20 -0
- package/dist/esm/util/theme.d.ts +5 -0
- package/dist/esm/util/theme.js +9 -0
- package/dist/esm/vis/area/index.js +3 -2
- package/dist/esm/vis/bar/index.js +7 -6
- package/dist/esm/vis/boxplot/index.js +17 -4
- package/dist/esm/vis/column/index.js +7 -6
- package/dist/esm/vis/dual-axes/index.js +13 -5
- package/dist/esm/vis/fishbone-diagram/index.d.ts +35 -0
- package/dist/esm/vis/fishbone-diagram/index.js +219 -0
- package/dist/esm/vis/flow-diagram/index.d.ts +27 -0
- package/dist/esm/vis/flow-diagram/index.js +349 -0
- package/dist/esm/vis/funnel/index.js +3 -2
- package/dist/esm/vis/histogram/index.js +6 -7
- package/dist/esm/vis/indented-tree/index.d.ts +40 -0
- package/dist/esm/vis/indented-tree/index.js +569 -0
- package/dist/esm/vis/line/index.js +3 -2
- package/dist/esm/vis/liquid/index.js +3 -2
- package/dist/esm/vis/mindmap/index.d.ts +32 -0
- package/dist/esm/vis/mindmap/index.js +316 -0
- package/dist/esm/vis/network-graph/index.d.ts +59 -0
- package/dist/esm/vis/network-graph/index.js +242 -0
- package/dist/esm/vis/organization-chart/index.d.ts +64 -0
- package/dist/esm/vis/organization-chart/index.js +271 -0
- package/dist/esm/vis/pie/index.js +4 -8
- package/dist/esm/vis/radar/index.d.ts +1 -0
- package/dist/esm/vis/radar/index.js +20 -4
- package/dist/esm/vis/sankey/index.js +3 -2
- package/dist/esm/vis/scatter/index.d.ts +2 -0
- package/dist/esm/vis/scatter/index.js +15 -4
- package/dist/esm/vis/summary/index.js +25 -4
- package/dist/esm/vis/table/index.d.ts +1 -0
- package/dist/esm/vis/table/index.js +9 -2
- package/dist/esm/vis/treemap/index.js +3 -2
- package/dist/esm/vis/venn/index.d.ts +2 -1
- package/dist/esm/vis/venn/index.js +29 -4
- package/dist/esm/vis/violin/index.js +3 -2
- package/dist/esm/vis/waterfall/index.d.ts +6 -9
- package/dist/esm/vis/waterfall/index.js +33 -13
- package/dist/esm/vis/word-cloud/index.js +3 -2
- package/dist/esm/vis-wrapper/icons.js +2 -2
- package/dist/esm/vis-wrapper/index.d.ts +1 -0
- package/dist/esm/vis-wrapper/index.js +15 -10
- package/dist/esm/vis-wrapper/styles.d.ts +1 -1
- package/dist/esm/vis-wrapper/styles.js +1 -1
- package/dist/umd/index.min.js +1 -1
- package/package.json +17 -21
- package/src/gpt-vis/index.ts +0 -283
- package/src/index.ts +0 -44
- package/src/readme.md +0 -37
- package/src/syntax/index.ts +0 -2
- package/src/syntax/parser.ts +0 -411
- package/src/types/index.ts +0 -29
- package/src/util/theme.ts +0 -167
- package/src/vis/area/README.md +0 -143
- package/src/vis/area/index.ts +0 -212
- package/src/vis/bar/README.md +0 -158
- package/src/vis/bar/index.ts +0 -186
- package/src/vis/boxplot/README.md +0 -168
- package/src/vis/boxplot/index.ts +0 -162
- package/src/vis/column/README.md +0 -158
- package/src/vis/column/index.ts +0 -185
- package/src/vis/dual-axes/README.md +0 -191
- package/src/vis/dual-axes/index.ts +0 -218
- package/src/vis/funnel/README.md +0 -143
- package/src/vis/funnel/index.ts +0 -238
- package/src/vis/histogram/README.md +0 -130
- package/src/vis/histogram/index.ts +0 -153
- package/src/vis/line/README.md +0 -138
- package/src/vis/line/index.ts +0 -159
- package/src/vis/liquid/README.md +0 -150
- package/src/vis/liquid/index.ts +0 -130
- package/src/vis/pie/README.md +0 -127
- package/src/vis/pie/index.ts +0 -163
- package/src/vis/radar/README.md +0 -184
- package/src/vis/radar/index.ts +0 -214
- package/src/vis/sankey/README.md +0 -144
- package/src/vis/sankey/index.ts +0 -144
- package/src/vis/scatter/README.md +0 -145
- package/src/vis/scatter/index.ts +0 -147
- package/src/vis/summary/README.md +0 -272
- package/src/vis/summary/index.ts +0 -91
- package/src/vis/table/README.md +0 -174
- package/src/vis/table/index.ts +0 -241
- package/src/vis/treemap/README.md +0 -199
- package/src/vis/treemap/index.ts +0 -167
- package/src/vis/venn/README.md +0 -153
- package/src/vis/venn/index.ts +0 -149
- package/src/vis/violin/README.md +0 -168
- package/src/vis/violin/index.ts +0 -216
- package/src/vis/waterfall/README.md +0 -178
- package/src/vis/waterfall/index.ts +0 -258
- package/src/vis/word-cloud/README.md +0 -137
- package/src/vis/word-cloud/index.ts +0 -137
- package/src/vis-wrapper/README.md +0 -159
- package/src/vis-wrapper/icons.ts +0 -35
- package/src/vis-wrapper/index.ts +0 -276
- package/src/vis-wrapper/styles.ts +0 -195
|
@@ -23,6 +23,7 @@ __export(summary_exports, {
|
|
|
23
23
|
});
|
|
24
24
|
module.exports = __toCommonJS(summary_exports);
|
|
25
25
|
var import_t8 = require("@antv/t8");
|
|
26
|
+
var import_theme = require("../../util/theme");
|
|
26
27
|
var Summary = (options) => {
|
|
27
28
|
let { theme = "light" } = options;
|
|
28
29
|
if (theme === "academy" || theme === "default")
|
|
@@ -31,20 +32,33 @@ var Summary = (options) => {
|
|
|
31
32
|
if (!container) {
|
|
32
33
|
throw new Error("Container not found");
|
|
33
34
|
}
|
|
35
|
+
const wrapper = document.createElement("div");
|
|
36
|
+
wrapper.className = "gpt-vis-summary";
|
|
37
|
+
container.appendChild(wrapper);
|
|
34
38
|
let text = null;
|
|
35
39
|
const render = (syntax) => {
|
|
36
40
|
if (text) {
|
|
37
41
|
text.unmount();
|
|
38
42
|
}
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
43
|
+
let activeTheme = theme;
|
|
44
|
+
const cleanedSyntax = syntax.replace(/^theme\s+(light|dark)\s*$/im, (_, t) => {
|
|
45
|
+
activeTheme = t;
|
|
46
|
+
return "";
|
|
47
|
+
});
|
|
48
|
+
text = new import_t8.Text(wrapper);
|
|
49
|
+
wrapper.style.backgroundColor = activeTheme === "dark" ? (0, import_theme.getBackgroundColor)("dark") : "";
|
|
50
|
+
wrapper.style.padding = "16px";
|
|
51
|
+
text.theme(activeTheme);
|
|
52
|
+
text.render(cleanedSyntax.trim());
|
|
42
53
|
};
|
|
43
54
|
const destroy = () => {
|
|
44
55
|
if (text) {
|
|
45
56
|
text.unmount();
|
|
46
57
|
text = null;
|
|
47
58
|
}
|
|
59
|
+
if (wrapper.parentNode) {
|
|
60
|
+
wrapper.parentNode.removeChild(wrapper);
|
|
61
|
+
}
|
|
48
62
|
};
|
|
49
63
|
return {
|
|
50
64
|
render,
|
|
@@ -33,6 +33,7 @@ var TABLE_STYLES = `
|
|
|
33
33
|
font-family: ${FONT_FAMILY};
|
|
34
34
|
overflow: auto;
|
|
35
35
|
height: 100%;
|
|
36
|
+
padding: 16px;
|
|
36
37
|
}
|
|
37
38
|
|
|
38
39
|
.${SCOPE_ID} .table-title {
|
|
@@ -85,6 +86,37 @@ var TABLE_STYLES = `
|
|
|
85
86
|
background: #f5f5f5;
|
|
86
87
|
cursor: pointer;
|
|
87
88
|
}
|
|
89
|
+
|
|
90
|
+
.${SCOPE_ID}[data-theme="dark"] {
|
|
91
|
+
background: #000;
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
.${SCOPE_ID}[data-theme="dark"] .table-title {
|
|
95
|
+
color: #ffffffd9;
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
.${SCOPE_ID}[data-theme="dark"] table {
|
|
99
|
+
background: #141414;
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
.${SCOPE_ID}[data-theme="dark"] th,
|
|
103
|
+
.${SCOPE_ID}[data-theme="dark"] td {
|
|
104
|
+
border-bottom: 1px solid #303030;
|
|
105
|
+
color: #ffffffd9;
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
.${SCOPE_ID}[data-theme="dark"] th {
|
|
109
|
+
background: #1f1f1f;
|
|
110
|
+
color: #ffffffa6;
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
.${SCOPE_ID}[data-theme="dark"] th:not(:last-child)::after {
|
|
114
|
+
background: #303030;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
.${SCOPE_ID}[data-theme="dark"] tbody tr:hover {
|
|
118
|
+
background: #1f1f1f;
|
|
119
|
+
}
|
|
88
120
|
`;
|
|
89
121
|
var calculateTableMinWidth = (data, columns) => {
|
|
90
122
|
let maxRowWidth = 0;
|
|
@@ -118,19 +150,23 @@ var injectStyles = () => {
|
|
|
118
150
|
document.head.appendChild(styleElement);
|
|
119
151
|
};
|
|
120
152
|
var Table = (options) => {
|
|
153
|
+
const { theme: chartTheme = "default" } = options;
|
|
121
154
|
const container = typeof options.container === "string" ? document.querySelector(options.container) : options.container;
|
|
122
155
|
if (!container) {
|
|
123
156
|
throw new Error("Container not found");
|
|
124
157
|
}
|
|
125
158
|
let tableWrapper = null;
|
|
126
159
|
const render = (config) => {
|
|
127
|
-
const { data = [], title } = config;
|
|
160
|
+
const { data = [], title, theme = chartTheme } = config;
|
|
128
161
|
injectStyles();
|
|
129
162
|
if (tableWrapper) {
|
|
130
163
|
tableWrapper.remove();
|
|
131
164
|
}
|
|
132
165
|
tableWrapper = document.createElement("div");
|
|
133
166
|
tableWrapper.className = SCOPE_ID;
|
|
167
|
+
if (theme === "dark") {
|
|
168
|
+
tableWrapper.setAttribute("data-theme", "dark");
|
|
169
|
+
}
|
|
134
170
|
if (data.length === 0) {
|
|
135
171
|
tableWrapper.innerHTML = `
|
|
136
172
|
${title ? `<div class="table-title">${title}</div>` : ""}
|
|
@@ -32,7 +32,7 @@ var Treemap = (options) => {
|
|
|
32
32
|
if (chart) {
|
|
33
33
|
chart.destroy();
|
|
34
34
|
}
|
|
35
|
-
const colors =
|
|
35
|
+
const colors = (0, import_theme.normalizePalette)(style.palette, theme);
|
|
36
36
|
const backgroundColor = style.backgroundColor || (0, import_theme.getBackgroundColor)(theme);
|
|
37
37
|
chart = new import_g2.Chart({
|
|
38
38
|
container,
|
|
@@ -41,6 +41,7 @@ var Treemap = (options) => {
|
|
|
41
41
|
autoFit: true
|
|
42
42
|
});
|
|
43
43
|
const chartOptions = {
|
|
44
|
+
animate: false,
|
|
44
45
|
type: "treemap",
|
|
45
46
|
data: {
|
|
46
47
|
type: "inline",
|
|
@@ -3,7 +3,8 @@ import type { VisualizationOptions } from '../../types';
|
|
|
3
3
|
* VennDataItem is the type for each data item in the venn chart.
|
|
4
4
|
*/
|
|
5
5
|
export type VennDataItem = {
|
|
6
|
-
|
|
6
|
+
/** Parser / DSL often yields a comma-separated string; G2 venn transform expects string[]. */
|
|
7
|
+
sets: string[] | string;
|
|
7
8
|
value: number;
|
|
8
9
|
label?: string;
|
|
9
10
|
};
|
|
@@ -24,6 +24,16 @@ __export(venn_exports, {
|
|
|
24
24
|
module.exports = __toCommonJS(venn_exports);
|
|
25
25
|
var import_g2 = require("@antv/g2");
|
|
26
26
|
var import_theme = require("../../util/theme");
|
|
27
|
+
function normalizeVennSets(sets) {
|
|
28
|
+
if (Array.isArray(sets))
|
|
29
|
+
return sets.map((s) => String(s));
|
|
30
|
+
if (typeof sets === "string") {
|
|
31
|
+
return sets.split(",").map((s) => s.trim()).filter(Boolean);
|
|
32
|
+
}
|
|
33
|
+
if (sets == null)
|
|
34
|
+
return [];
|
|
35
|
+
return [String(sets)];
|
|
36
|
+
}
|
|
27
37
|
var Venn = (options) => {
|
|
28
38
|
const { container, width, height, theme: chartTheme = "default" } = options;
|
|
29
39
|
let chart = null;
|
|
@@ -32,8 +42,12 @@ var Venn = (options) => {
|
|
|
32
42
|
if (chart) {
|
|
33
43
|
chart.destroy();
|
|
34
44
|
}
|
|
35
|
-
const colors =
|
|
45
|
+
const colors = (0, import_theme.normalizePalette)(style.palette, theme);
|
|
36
46
|
const backgroundColor = style.backgroundColor || (0, import_theme.getBackgroundColor)(theme);
|
|
47
|
+
const normalizedData = data.map((d) => ({
|
|
48
|
+
...d,
|
|
49
|
+
sets: normalizeVennSets(d.sets)
|
|
50
|
+
}));
|
|
37
51
|
chart = new import_g2.Chart({
|
|
38
52
|
container,
|
|
39
53
|
width,
|
|
@@ -41,9 +55,10 @@ var Venn = (options) => {
|
|
|
41
55
|
autoFit: true
|
|
42
56
|
});
|
|
43
57
|
const chartOptions = {
|
|
58
|
+
animate: false,
|
|
44
59
|
type: "path",
|
|
45
60
|
data: {
|
|
46
|
-
value:
|
|
61
|
+
value: normalizedData,
|
|
47
62
|
transform: [
|
|
48
63
|
{
|
|
49
64
|
type: "venn",
|
|
@@ -61,7 +76,7 @@ var Venn = (options) => {
|
|
|
61
76
|
},
|
|
62
77
|
style: {
|
|
63
78
|
// Set opacity: intersections (sets.length > 1) are nearly transparent, single sets are more opaque
|
|
64
|
-
opacity: (d) => d.sets.length > 1 ? 1e-3 : 0.65
|
|
79
|
+
opacity: (d) => normalizeVennSets(d.sets).length > 1 ? 1e-3 : 0.65
|
|
65
80
|
},
|
|
66
81
|
labels: [
|
|
67
82
|
{
|
|
@@ -33,7 +33,7 @@ var Violin = (options) => {
|
|
|
33
33
|
if (chart) {
|
|
34
34
|
chart.destroy();
|
|
35
35
|
}
|
|
36
|
-
const colors =
|
|
36
|
+
const colors = (0, import_theme.normalizePalette)(style.palette, theme);
|
|
37
37
|
const backgroundColor = style.backgroundColor || (0, import_theme.getBackgroundColor)(theme);
|
|
38
38
|
const startAtZero = style.startAtZero || false;
|
|
39
39
|
const hasGroupField = ((_a = (data || [])[0]) == null ? void 0 : _a.group) !== void 0;
|
|
@@ -114,6 +114,7 @@ var Violin = (options) => {
|
|
|
114
114
|
];
|
|
115
115
|
}
|
|
116
116
|
const chartOptions = {
|
|
117
|
+
animate: false,
|
|
117
118
|
type: "view",
|
|
118
119
|
data,
|
|
119
120
|
title: title ?? "",
|
|
@@ -8,14 +8,6 @@ export type WaterfallDataItem = {
|
|
|
8
8
|
isIntermediateTotal?: boolean;
|
|
9
9
|
isTotal?: boolean;
|
|
10
10
|
};
|
|
11
|
-
/**
|
|
12
|
-
* WaterfallPalette defines custom colors for positive, negative, total bars.
|
|
13
|
-
*/
|
|
14
|
-
export interface WaterfallPalette {
|
|
15
|
-
positiveColor?: string;
|
|
16
|
-
negativeColor?: string;
|
|
17
|
-
totalColor?: string;
|
|
18
|
-
}
|
|
19
11
|
/**
|
|
20
12
|
* WaterfallConfig defines the configuration for rendering the waterfall chart.
|
|
21
13
|
*/
|
|
@@ -28,7 +20,12 @@ export interface WaterfallConfig {
|
|
|
28
20
|
axisYTitle?: string;
|
|
29
21
|
style?: {
|
|
30
22
|
backgroundColor?: string;
|
|
31
|
-
|
|
23
|
+
/**
|
|
24
|
+
* Custom color palette for waterfall bars.
|
|
25
|
+
* Array order: [0] positive color, [1] negative color, [2] total/intermediate-total color.
|
|
26
|
+
* Defaults: ['#FF4D4F', '#2EBB59', '#1783FF']
|
|
27
|
+
*/
|
|
28
|
+
palette?: string[];
|
|
32
29
|
};
|
|
33
30
|
}
|
|
34
31
|
/**
|
|
@@ -77,10 +77,10 @@ var Waterfall = (options) => {
|
|
|
77
77
|
chart.destroy();
|
|
78
78
|
}
|
|
79
79
|
const backgroundColor = style.backgroundColor || (0, import_theme.getBackgroundColor)(theme);
|
|
80
|
-
const palette = style.palette ||
|
|
81
|
-
const positiveColor = palette
|
|
82
|
-
const negativeColor = palette
|
|
83
|
-
const totalColor = palette
|
|
80
|
+
const palette = style.palette || [];
|
|
81
|
+
const positiveColor = palette[0] || DEFAULT_POSITIVE_COLOR;
|
|
82
|
+
const negativeColor = palette[1] || DEFAULT_NEGATIVE_COLOR;
|
|
83
|
+
const totalColor = palette[2] || DEFAULT_TOTAL_COLOR;
|
|
84
84
|
const transformedData = transformWaterfallData(data);
|
|
85
85
|
const linkData = generateLinkData(transformedData);
|
|
86
86
|
chart = new import_g2.Chart({
|
|
@@ -90,6 +90,7 @@ var Waterfall = (options) => {
|
|
|
90
90
|
autoFit: true
|
|
91
91
|
});
|
|
92
92
|
const chartOptions = {
|
|
93
|
+
animate: false,
|
|
93
94
|
type: "view",
|
|
94
95
|
data: transformedData,
|
|
95
96
|
title: title ?? "",
|
|
@@ -109,12 +110,13 @@ var Waterfall = (options) => {
|
|
|
109
110
|
children: [
|
|
110
111
|
{
|
|
111
112
|
type: "interval",
|
|
113
|
+
animate: false,
|
|
112
114
|
data: transformedData,
|
|
113
115
|
encode: { x: "category", y: ["__start__", "__end__"], color: "category" },
|
|
114
116
|
style: {
|
|
115
117
|
maxWidth: 60,
|
|
116
118
|
stroke: "#666",
|
|
117
|
-
radius: 4,
|
|
119
|
+
...theme !== "academy" ? { radius: 4 } : {},
|
|
118
120
|
fill: (d) => {
|
|
119
121
|
return d.isTotal || d.isIntermediateTotal ? totalColor : d.__value__ > 0 ? positiveColor : negativeColor;
|
|
120
122
|
}
|
|
@@ -130,10 +132,31 @@ var Waterfall = (options) => {
|
|
|
130
132
|
fontWeight: 600,
|
|
131
133
|
stroke: "#fff"
|
|
132
134
|
}
|
|
133
|
-
]
|
|
135
|
+
],
|
|
136
|
+
tooltip: {
|
|
137
|
+
title: (d) => d.category,
|
|
138
|
+
items: [
|
|
139
|
+
{
|
|
140
|
+
field: "__value__",
|
|
141
|
+
name: "数值",
|
|
142
|
+
valueFormatter: "~s"
|
|
143
|
+
},
|
|
144
|
+
{
|
|
145
|
+
field: "__start__",
|
|
146
|
+
name: "起始",
|
|
147
|
+
valueFormatter: "~s"
|
|
148
|
+
},
|
|
149
|
+
{
|
|
150
|
+
field: "__end__",
|
|
151
|
+
name: "结束",
|
|
152
|
+
valueFormatter: "~s"
|
|
153
|
+
}
|
|
154
|
+
]
|
|
155
|
+
}
|
|
134
156
|
},
|
|
135
157
|
{
|
|
136
158
|
type: "link",
|
|
159
|
+
animate: false,
|
|
137
160
|
data: linkData,
|
|
138
161
|
encode: {
|
|
139
162
|
x: "x",
|
|
@@ -32,7 +32,7 @@ var WordCloud = (options) => {
|
|
|
32
32
|
if (chart) {
|
|
33
33
|
chart.destroy();
|
|
34
34
|
}
|
|
35
|
-
const colors =
|
|
35
|
+
const colors = (0, import_theme.normalizePalette)(style.palette, theme);
|
|
36
36
|
const backgroundColor = style.backgroundColor || (0, import_theme.getBackgroundColor)(theme);
|
|
37
37
|
chart = new import_g2.Chart({
|
|
38
38
|
container,
|
|
@@ -41,6 +41,7 @@ var WordCloud = (options) => {
|
|
|
41
41
|
autoFit: true
|
|
42
42
|
});
|
|
43
43
|
const chartOptions = {
|
|
44
|
+
animate: false,
|
|
44
45
|
type: "wordCloud",
|
|
45
46
|
data,
|
|
46
47
|
title: title ?? "",
|
|
@@ -44,13 +44,13 @@ function createDownloadIcon(size = 14, fill = "#707070") {
|
|
|
44
44
|
function createZoomInIcon(size = 18, fill = "#707070") {
|
|
45
45
|
return `<svg viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" width="${size}" height="${size}" fill="${fill}">
|
|
46
46
|
<path d="M889.5 852.7l-220-219.9c45-53.4 72.1-122.3 72.1-197.5 0-169.4-137.8-307.3-307.3-307.3S127.1 265.8 127.1 435.3s137.8 307.3 307.3 307.3c76.1 0 145.7-27.8 199.4-73.8l219.8 219.8c4.9 5 11.4 7.4 17.9 7.4s13-2.5 17.9-7.4c10-9.9 10-26 0.1-35.9zM434.4 691.8c-141.4 0-256.5-115.1-256.5-256.5 0-141.5 115.1-256.5 256.5-256.5s256.5 115.1 256.5 256.5-115.1 256.5-256.5 256.5z"></path>
|
|
47
|
-
<path d="M555 418.
|
|
47
|
+
<path d="M555 418.3h-99.8v-99.8c0-14-11.4-25.4-25.4-25.4s-25.4 11.4-25.4 25.4v99.8h-99.8c-14 0-25.4 11.4-25.4 25.4s11.4 25.4 25.4 25.4h99.8v99.8c0 14 11.4 25.4 25.4 25.4s25.4-11.4 25.4-25.4v-99.8H555c14 0 25.4-11.4 25.4-25.4S569 418.3 555 418.3z"></path>
|
|
48
48
|
</svg>`;
|
|
49
49
|
}
|
|
50
50
|
function createZoomOutIcon(size = 18, fill = "#707070") {
|
|
51
51
|
return `<svg viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" width="${size}" height="${size}" fill="${fill}">
|
|
52
52
|
<path d="M889.5 852.7l-220-219.9c45-53.4 72.1-122.3 72.1-197.5 0-169.4-137.8-307.3-307.3-307.3S127.1 265.8 127.1 435.3s137.8 307.3 307.3 307.3c76.1 0 145.7-27.8 199.4-73.8l219.8 219.8c4.9 5 11.4 7.4 17.9 7.4s13-2.5 17.9-7.4c10-9.9 10-26 0.1-35.9zM434.4 691.8c-141.4 0-256.5-115.1-256.5-256.5 0-141.5 115.1-256.5 256.5-256.5s256.5 115.1 256.5 256.5-115.1 256.5-256.5 256.5z"></path>
|
|
53
|
-
<path d="M555 418.
|
|
53
|
+
<path d="M555 418.3H304.7c-14 0-25.4 11.4-25.4 25.4s11.4 25.4 25.4 25.4H555c14 0 25.4-11.4 25.4-25.4S569 418.3 555 418.3z"></path>
|
|
54
54
|
</svg>`;
|
|
55
55
|
}
|
|
56
56
|
// Annotate the CommonJS export names for ESM import in node:
|
|
@@ -41,7 +41,6 @@ var DEFAULT_LABELS = {
|
|
|
41
41
|
copied: "Copied"
|
|
42
42
|
}
|
|
43
43
|
};
|
|
44
|
-
var G6_CHART_TYPES = [];
|
|
45
44
|
function createVisWrapper(container, config = {}) {
|
|
46
45
|
(0, import_styles.injectWrapperStyles)();
|
|
47
46
|
const containerElement = typeof container === "string" ? document.querySelector(container) : container;
|
|
@@ -51,24 +50,23 @@ function createVisWrapper(container, config = {}) {
|
|
|
51
50
|
const { chartType = "", syntax = "", locale = "zh-CN" } = config;
|
|
52
51
|
const syntaxString = typeof syntax === "string" ? syntax : JSON.stringify(syntax, null, 2);
|
|
53
52
|
const labels = DEFAULT_LABELS[locale] || DEFAULT_LABELS["en-US"];
|
|
54
|
-
const isG6Chart = G6_CHART_TYPES.includes(chartType);
|
|
55
53
|
let chartRef = null;
|
|
56
54
|
let copyTimeout;
|
|
57
|
-
const zoomButtonsHTML =
|
|
58
|
-
<button class="gpt-vis-wrapper-text-button gpt-vis-wrapper-zoom-button"
|
|
59
|
-
data-action="zoom-
|
|
60
|
-
aria-label="Zoom
|
|
61
|
-
title="Zoom in">
|
|
62
|
-
${(0, import_icons.createZoomInIcon)(18)}
|
|
63
|
-
</button>
|
|
64
|
-
<button class="gpt-vis-wrapper-text-button gpt-vis-wrapper-zoom-button"
|
|
65
|
-
data-action="zoom-out"
|
|
66
|
-
aria-label="Zoom out"
|
|
55
|
+
const zoomButtonsHTML = `
|
|
56
|
+
<button class="gpt-vis-wrapper-text-button gpt-vis-wrapper-zoom-button gpt-vis-wrapper-tab-hide"
|
|
57
|
+
data-action="zoom-out"
|
|
58
|
+
aria-label="Zoom out"
|
|
67
59
|
title="Zoom out">
|
|
68
60
|
${(0, import_icons.createZoomOutIcon)(18)}
|
|
69
61
|
</button>
|
|
70
|
-
<
|
|
71
|
-
|
|
62
|
+
<button class="gpt-vis-wrapper-text-button gpt-vis-wrapper-zoom-button gpt-vis-wrapper-tab-hide"
|
|
63
|
+
data-action="zoom-in"
|
|
64
|
+
aria-label="Zoom in"
|
|
65
|
+
title="Zoom in">
|
|
66
|
+
${(0, import_icons.createZoomInIcon)(18)}
|
|
67
|
+
</button>
|
|
68
|
+
<div class="gpt-vis-wrapper-divider gpt-vis-wrapper-tab-hide"></div>
|
|
69
|
+
`;
|
|
72
70
|
const wrapperHTML = `
|
|
73
71
|
<div class="gpt-vis-wrapper-container">
|
|
74
72
|
<div class="gpt-vis-wrapper-header">
|
|
@@ -131,6 +129,7 @@ function createVisWrapper(container, config = {}) {
|
|
|
131
129
|
);
|
|
132
130
|
const divider = wrapperContainer.querySelector(".gpt-vis-wrapper-divider");
|
|
133
131
|
function switchTab(tab) {
|
|
132
|
+
const hasZoomSupport = chartRef && typeof chartRef.zoomTo === "function";
|
|
134
133
|
if (tab === "chart") {
|
|
135
134
|
chartTabButton.classList.add("active");
|
|
136
135
|
chartTabButton.setAttribute("aria-selected", "true");
|
|
@@ -140,7 +139,7 @@ function createVisWrapper(container, config = {}) {
|
|
|
140
139
|
codeContainer.classList.add("gpt-vis-wrapper-tab-hide");
|
|
141
140
|
downloadButton.classList.remove("gpt-vis-wrapper-tab-hide");
|
|
142
141
|
copyButton.classList.add("gpt-vis-wrapper-tab-hide");
|
|
143
|
-
if (
|
|
142
|
+
if (hasZoomSupport && zoomInButton && zoomOutButton && divider) {
|
|
144
143
|
zoomInButton.classList.remove("gpt-vis-wrapper-tab-hide");
|
|
145
144
|
zoomOutButton.classList.remove("gpt-vis-wrapper-tab-hide");
|
|
146
145
|
divider.classList.remove("gpt-vis-wrapper-tab-hide");
|
|
@@ -154,7 +153,7 @@ function createVisWrapper(container, config = {}) {
|
|
|
154
153
|
codeContainer.classList.remove("gpt-vis-wrapper-tab-hide");
|
|
155
154
|
downloadButton.classList.add("gpt-vis-wrapper-tab-hide");
|
|
156
155
|
copyButton.classList.remove("gpt-vis-wrapper-tab-hide");
|
|
157
|
-
if (
|
|
156
|
+
if (hasZoomSupport && zoomInButton && zoomOutButton && divider) {
|
|
158
157
|
zoomInButton.classList.add("gpt-vis-wrapper-tab-hide");
|
|
159
158
|
zoomOutButton.classList.add("gpt-vis-wrapper-tab-hide");
|
|
160
159
|
divider.classList.add("gpt-vis-wrapper-tab-hide");
|
|
@@ -214,8 +213,20 @@ function createVisWrapper(container, config = {}) {
|
|
|
214
213
|
zoomOutButton.onclick = handleZoomOut;
|
|
215
214
|
return {
|
|
216
215
|
chartContainer,
|
|
216
|
+
update: (newSyntax) => {
|
|
217
|
+
const newSyntaxString = typeof newSyntax === "string" ? newSyntax : JSON.stringify(newSyntax, null, 2);
|
|
218
|
+
codeContainer.textContent = newSyntaxString;
|
|
219
|
+
},
|
|
217
220
|
setChartRef: (chart) => {
|
|
218
221
|
chartRef = chart;
|
|
222
|
+
if (chart && typeof chart.zoomTo === "function") {
|
|
223
|
+
if (zoomInButton)
|
|
224
|
+
zoomInButton.classList.remove("gpt-vis-wrapper-tab-hide");
|
|
225
|
+
if (zoomOutButton)
|
|
226
|
+
zoomOutButton.classList.remove("gpt-vis-wrapper-tab-hide");
|
|
227
|
+
if (divider)
|
|
228
|
+
divider.classList.remove("gpt-vis-wrapper-tab-hide");
|
|
229
|
+
}
|
|
219
230
|
},
|
|
220
231
|
destroy: () => {
|
|
221
232
|
if (copyTimeout) {
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* CSS styles for the wrapper component
|
|
3
3
|
*/
|
|
4
|
-
export declare const wrapperStyles = "\n.gpt-vis-wrapper-container {\n border-radius: 8px;\n overflow: hidden;\n}\n\n.gpt-vis-wrapper-header {\n display: flex;\n justify-content: space-between;\n align-items: center;\n background: #f5f5f5;\n padding: 6px 14px 6px 6px;\n gap: 2px;\n position: relative;\n z-index: 10;\n}\n\n.gpt-vis-wrapper-tab-left {\n display: flex;\n gap: 2px;\n}\n\n.gpt-vis-wrapper-tab-right {\n display: flex;\n gap: 4px;\n align-items: center;\n}\n\n.gpt-vis-wrapper-tab-button {\n border: none;\n box-shadow: none;\n background: transparent;\n color: #494949;\n border-radius: 8px;\n height: 26px;\n width: 52px;\n font-size: 12px;\n transition: all 0.2s cubic-bezier(0.645, 0.045, 0.355, 1);\n transform: scale(1);\n cursor: pointer;\n outline: none;\n font-family: inherit;\n display: inline-flex;\n align-items: center;\n justify-content: center;\n}\n\n.gpt-vis-wrapper-tab-button.active {\n background: #fff;\n box-shadow: 0 2px 4px rgba(0, 0, 0, 0.08);\n}\n\n.gpt-vis-wrapper-tab-button:hover,\n.gpt-vis-wrapper-tab-button:focus {\n color: #494949;\n transform: scale(1.02);\n}\n\n.gpt-vis-wrapper-tab-button:not(.active):hover,\n.gpt-vis-wrapper-tab-button:not(.active):focus {\n background: #f0f0f0;\n box-shadow: 0 1px 3px rgba(0, 0, 0, 0.06);\n}\n\n.gpt-vis-wrapper-tab-button.active:hover,\n.gpt-vis-wrapper-tab-button.active:focus {\n background: #fff;\n box-shadow: 0 2px 6px rgba(0, 0, 0, 0.12);\n}\n\n.gpt-vis-wrapper-tab-button:active {\n transform: scale(0.96);\n transition: all 0.1s cubic-bezier(0.645, 0.045, 0.355, 1);\n}\n\n.gpt-vis-wrapper-tab-button.active:active {\n background: #fff;\n box-shadow: 0 1px 2px rgba(0, 0, 0, 0.1);\n}\n\n.gpt-vis-wrapper-tab-button:not(.active):active {\n background: #e8e8e8;\n box-shadow: 0 1px 2px rgba(0, 0, 0, 0.04);\n}\n\n.gpt-vis-wrapper-text-button {\n border: none;\n box-shadow: none;\n background: transparent;\n color: #494949;\n height: 26px;\n padding: 0 8px;\n font-size: 12px;\n transition: all 0.2s cubic-bezier(0.645, 0.045, 0.355, 1);\n transform: scale(1);\n border-radius: 8px;\n display: inline-flex;\n align-items: center;\n justify-content: center;\n gap: 4px;\n cursor: pointer;\n outline: none;\n font-family: inherit;\n}\n\n.gpt-vis-wrapper-text-button:hover,\n.gpt-vis-wrapper-text-button:focus {\n color: #666;\n background: #e8e8e8;\n transform: scale(1.02);\n}\n\n.gpt-vis-wrapper-text-button:active {\n background: #e8e8e8;\n transform: scale(0.98);\n}\n\n.gpt-vis-wrapper-zoom-button {\n width: 24px;\n height: 24px;\n padding: 0;\n}\n\n.gpt-vis-wrapper-divider {\n width: 1px;\n height: 16px;\n background-color: #d9d9d9;\n margin: 0 8px;\n flex-shrink: 0;\n}\n\n.gpt-vis-wrapper-content {\n overflow: hidden;\n position: relative;\n background: #fafafa;\n}\n\n.gpt-vis-wrapper-chart {\n min-width: 300px;\n max-width: 100%;\n overflow: hidden;\n position: relative;\n
|
|
4
|
+
export declare const wrapperStyles = "\n.gpt-vis-wrapper-container {\n border-radius: 8px;\n overflow: hidden;\n}\n\n.gpt-vis-wrapper-header {\n display: flex;\n justify-content: space-between;\n align-items: center;\n background: #f5f5f5;\n padding: 6px 14px 6px 6px;\n gap: 2px;\n position: relative;\n z-index: 10;\n}\n\n.gpt-vis-wrapper-tab-left {\n display: flex;\n gap: 2px;\n}\n\n.gpt-vis-wrapper-tab-right {\n display: flex;\n gap: 4px;\n align-items: center;\n}\n\n.gpt-vis-wrapper-tab-button {\n border: none;\n box-shadow: none;\n background: transparent;\n color: #494949;\n border-radius: 8px;\n height: 26px;\n width: 52px;\n font-size: 12px;\n transition: all 0.2s cubic-bezier(0.645, 0.045, 0.355, 1);\n transform: scale(1);\n cursor: pointer;\n outline: none;\n font-family: inherit;\n display: inline-flex;\n align-items: center;\n justify-content: center;\n}\n\n.gpt-vis-wrapper-tab-button.active {\n background: #fff;\n box-shadow: 0 2px 4px rgba(0, 0, 0, 0.08);\n}\n\n.gpt-vis-wrapper-tab-button:hover,\n.gpt-vis-wrapper-tab-button:focus {\n color: #494949;\n transform: scale(1.02);\n}\n\n.gpt-vis-wrapper-tab-button:not(.active):hover,\n.gpt-vis-wrapper-tab-button:not(.active):focus {\n background: #f0f0f0;\n box-shadow: 0 1px 3px rgba(0, 0, 0, 0.06);\n}\n\n.gpt-vis-wrapper-tab-button.active:hover,\n.gpt-vis-wrapper-tab-button.active:focus {\n background: #fff;\n box-shadow: 0 2px 6px rgba(0, 0, 0, 0.12);\n}\n\n.gpt-vis-wrapper-tab-button:active {\n transform: scale(0.96);\n transition: all 0.1s cubic-bezier(0.645, 0.045, 0.355, 1);\n}\n\n.gpt-vis-wrapper-tab-button.active:active {\n background: #fff;\n box-shadow: 0 1px 2px rgba(0, 0, 0, 0.1);\n}\n\n.gpt-vis-wrapper-tab-button:not(.active):active {\n background: #e8e8e8;\n box-shadow: 0 1px 2px rgba(0, 0, 0, 0.04);\n}\n\n.gpt-vis-wrapper-text-button {\n border: none;\n box-shadow: none;\n background: transparent;\n color: #494949;\n height: 26px;\n padding: 0 8px;\n font-size: 12px;\n transition: all 0.2s cubic-bezier(0.645, 0.045, 0.355, 1);\n transform: scale(1);\n border-radius: 8px;\n display: inline-flex;\n align-items: center;\n justify-content: center;\n gap: 4px;\n cursor: pointer;\n outline: none;\n font-family: inherit;\n}\n\n.gpt-vis-wrapper-text-button:hover,\n.gpt-vis-wrapper-text-button:focus {\n color: #666;\n background: #e8e8e8;\n transform: scale(1.02);\n}\n\n.gpt-vis-wrapper-text-button:active {\n background: #e8e8e8;\n transform: scale(0.98);\n}\n\n.gpt-vis-wrapper-zoom-button {\n width: 24px;\n height: 24px;\n padding: 0;\n}\n\n.gpt-vis-wrapper-divider {\n width: 1px;\n height: 16px;\n background-color: #d9d9d9;\n margin: 0 8px;\n flex-shrink: 0;\n}\n\n.gpt-vis-wrapper-content {\n overflow: hidden;\n position: relative;\n background: #fafafa;\n}\n\n.gpt-vis-wrapper-chart {\n min-width: 300px;\n max-width: 100%;\n overflow: hidden;\n position: relative;\n}\n\n.gpt-vis-wrapper-chart--g6 {\n min-height: 400px;\n}\n\n.gpt-vis-wrapper-chart-container {\n width: 100%;\n height: 100%;\n overflow: auto;\n scrollbar-width: none;\n -ms-overflow-style: none;\n}\n\n.gpt-vis-wrapper-chart--g6 .gpt-vis-wrapper-chart-container {\n min-height: 360px;\n}\n\n.gpt-vis-wrapper-chart-container::-webkit-scrollbar {\n display: none;\n}\n\n.gpt-vis-wrapper-code {\n max-height: 500px;\n overflow: auto;\n padding: 16px;\n font-family: 'Monaco', 'Menlo', 'Ubuntu Mono', 'Consolas', 'source-code-pro', monospace;\n font-size: 12px;\n line-height: 1.6;\n color: #333;\n background: #fafafa;\n white-space: pre-wrap;\n word-wrap: break-word;\n}\n\n.gpt-vis-wrapper-tab-hide {\n display: none;\n}\n";
|
|
5
5
|
/**
|
|
6
6
|
* Inject styles into the document head
|
|
7
7
|
*/
|
|
@@ -165,7 +165,10 @@ var wrapperStyles = `
|
|
|
165
165
|
max-width: 100%;
|
|
166
166
|
overflow: hidden;
|
|
167
167
|
position: relative;
|
|
168
|
-
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
.gpt-vis-wrapper-chart--g6 {
|
|
171
|
+
min-height: 400px;
|
|
169
172
|
}
|
|
170
173
|
|
|
171
174
|
.gpt-vis-wrapper-chart-container {
|
|
@@ -176,6 +179,10 @@ var wrapperStyles = `
|
|
|
176
179
|
-ms-overflow-style: none;
|
|
177
180
|
}
|
|
178
181
|
|
|
182
|
+
.gpt-vis-wrapper-chart--g6 .gpt-vis-wrapper-chart-container {
|
|
183
|
+
min-height: 360px;
|
|
184
|
+
}
|
|
185
|
+
|
|
179
186
|
.gpt-vis-wrapper-chart-container::-webkit-scrollbar {
|
|
180
187
|
display: none;
|
|
181
188
|
}
|
|
@@ -4,10 +4,16 @@ import type { BarConfig } from '../vis/bar';
|
|
|
4
4
|
import type { BoxplotConfig } from '../vis/boxplot';
|
|
5
5
|
import type { ColumnConfig } from '../vis/column';
|
|
6
6
|
import type { DualAxesConfig } from '../vis/dual-axes';
|
|
7
|
+
import type { FishboneDiagramConfig } from '../vis/fishbone-diagram';
|
|
8
|
+
import type { FlowDiagramConfig } from '../vis/flow-diagram';
|
|
7
9
|
import type { FunnelConfig } from '../vis/funnel';
|
|
8
10
|
import type { HistogramConfig } from '../vis/histogram';
|
|
11
|
+
import type { IndentedTreeConfig } from '../vis/indented-tree';
|
|
9
12
|
import type { LineConfig } from '../vis/line';
|
|
10
13
|
import type { LiquidConfig } from '../vis/liquid';
|
|
14
|
+
import type { MindmapConfig } from '../vis/mindmap';
|
|
15
|
+
import type { NetworkGraphConfig } from '../vis/network-graph';
|
|
16
|
+
import type { OrganizationChartConfig } from '../vis/organization-chart';
|
|
11
17
|
import type { PieConfig } from '../vis/pie';
|
|
12
18
|
import type { RadarConfig } from '../vis/radar';
|
|
13
19
|
import type { SankeyConfig } from '../vis/sankey';
|
|
@@ -22,7 +28,7 @@ import type { WordCloudConfig } from '../vis/word-cloud';
|
|
|
22
28
|
/**
|
|
23
29
|
* Union type for all supported chart configurations
|
|
24
30
|
*/
|
|
25
|
-
export type GPTVisConfig = AreaConfig | BarConfig | BoxplotConfig | ColumnConfig | DualAxesConfig | FunnelConfig | HistogramConfig | LineConfig | LiquidConfig | PieConfig | RadarConfig | SankeyConfig | ScatterConfig | SummaryConfig | TableConfig | TreemapConfig | VennConfig | ViolinConfig | WaterfallConfig | WordCloudConfig;
|
|
31
|
+
export type GPTVisConfig = AreaConfig | BarConfig | BoxplotConfig | ColumnConfig | DualAxesConfig | FlowDiagramConfig | FunnelConfig | HistogramConfig | IndentedTreeConfig | LineConfig | LiquidConfig | MindmapConfig | NetworkGraphConfig | OrganizationChartConfig | PieConfig | RadarConfig | SankeyConfig | ScatterConfig | SummaryConfig | TableConfig | TreemapConfig | VennConfig | ViolinConfig | WaterfallConfig | WordCloudConfig | FishboneDiagramConfig;
|
|
26
32
|
/**
|
|
27
33
|
* GPTVis is the unified API for all chart types.
|
|
28
34
|
* It provides a simple interface to render different types of visualizations.
|
|
@@ -66,6 +72,7 @@ export type GPTVisConfig = AreaConfig | BarConfig | BoxplotConfig | ColumnConfig
|
|
|
66
72
|
export declare class GPTVis {
|
|
67
73
|
private options;
|
|
68
74
|
private currentChart;
|
|
75
|
+
private currentChartType;
|
|
69
76
|
private wrapperInstance;
|
|
70
77
|
/**
|
|
71
78
|
* Chart type registry mapping type strings to factory functions
|