@visactor/vrender-components 0.13.9-alpha.5 → 0.13.9-alpha.6
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/cjs/brush/brush.d.ts +5 -3
- package/cjs/brush/brush.js +23 -16
- package/cjs/brush/brush.js.map +1 -1
- package/cjs/brush/type.d.ts +10 -1
- package/cjs/brush/type.js +7 -1
- package/cjs/brush/type.js.map +1 -1
- package/cjs/index.d.ts +1 -1
- package/cjs/index.js +1 -1
- package/cjs/index.js.map +1 -1
- package/cjs/label/base.d.ts +1 -2
- package/cjs/label/base.js +22 -61
- package/cjs/label/base.js.map +1 -1
- package/cjs/label/dataLabel.js +2 -3
- package/cjs/label/dataLabel.js.map +1 -1
- package/cjs/label/index.d.ts +0 -1
- package/cjs/label/index.js +1 -2
- package/cjs/label/index.js.map +1 -1
- package/cjs/label/overlap/bitmap.d.ts +1 -1
- package/cjs/label/overlap/bitmap.js +2 -0
- package/cjs/label/overlap/bitmap.js.map +1 -1
- package/cjs/label/type.d.ts +1 -41
- package/cjs/label/type.js.map +1 -1
- package/cjs/link-path/type.js +2 -1
- package/cjs/marker/base.js +1 -2
- package/cjs/pager/index.js +1 -1
- package/cjs/pager/pager.js +1 -1
- package/cjs/tooltip/util.js.map +1 -1
- package/dist/index.js +72 -864
- package/dist/index.min.js +1 -1
- package/es/brush/brush.d.ts +5 -3
- package/es/brush/brush.js +22 -13
- package/es/brush/brush.js.map +1 -1
- package/es/brush/type.d.ts +10 -1
- package/es/brush/type.js +7 -1
- package/es/brush/type.js.map +1 -1
- package/es/index.d.ts +1 -1
- package/es/index.js +1 -1
- package/es/index.js.map +1 -1
- package/es/label/base.d.ts +1 -2
- package/es/label/base.js +22 -61
- package/es/label/base.js.map +1 -1
- package/es/label/dataLabel.js +1 -4
- package/es/label/dataLabel.js.map +1 -1
- package/es/label/index.d.ts +0 -1
- package/es/label/index.js +0 -2
- package/es/label/index.js.map +1 -1
- package/es/label/overlap/bitmap.d.ts +1 -1
- package/es/label/overlap/bitmap.js +2 -0
- package/es/label/overlap/bitmap.js.map +1 -1
- package/es/label/type.d.ts +1 -41
- package/es/label/type.js.map +1 -1
- package/es/link-path/type.js +2 -1
- package/es/marker/base.js +1 -2
- package/es/pager/index.js +1 -1
- package/es/pager/pager.js +1 -1
- package/es/tooltip/util.js.map +1 -1
- package/package.json +4 -4
- package/cjs/label/arc.d.ts +0 -69
- package/cjs/label/arc.js +0 -397
- package/cjs/label/arc.js.map +0 -1
- package/cjs/label/util.d.ts +0 -12
- package/cjs/label/util.js +0 -113
- package/cjs/label/util.js.map +0 -1
- package/es/label/arc.d.ts +0 -69
- package/es/label/arc.js +0 -387
- package/es/label/arc.js.map +0 -1
- package/es/label/util.d.ts +0 -12
- package/es/label/util.js +0 -99
- package/es/label/util.js.map +0 -1
package/dist/index.js
CHANGED
|
@@ -1311,6 +1311,9 @@
|
|
|
1311
1311
|
_clear(index >>> DIV, ~(1 << (index & MOD)));
|
|
1312
1312
|
},
|
|
1313
1313
|
getRange: ({ x1, y1, x2, y2 }) => {
|
|
1314
|
+
if (x2 < 0 || y2 < 0 || x1 > w || y1 > h) {
|
|
1315
|
+
return true;
|
|
1316
|
+
}
|
|
1314
1317
|
let r = y2;
|
|
1315
1318
|
let start;
|
|
1316
1319
|
let end;
|
|
@@ -1343,6 +1346,9 @@
|
|
|
1343
1346
|
return false;
|
|
1344
1347
|
},
|
|
1345
1348
|
setRange: ({ x1, y1, x2, y2 }) => {
|
|
1349
|
+
if (x2 < 0 || y2 < 0 || x1 > w || y1 > h) {
|
|
1350
|
+
return;
|
|
1351
|
+
}
|
|
1346
1352
|
let start;
|
|
1347
1353
|
let end;
|
|
1348
1354
|
let indexStart;
|
|
@@ -1592,10 +1598,6 @@
|
|
|
1592
1598
|
_lastHover;
|
|
1593
1599
|
_lastSelect;
|
|
1594
1600
|
_enableAnimation;
|
|
1595
|
-
layoutArcLabels(position, attribute, currentMarks) {
|
|
1596
|
-
const arcs = [];
|
|
1597
|
-
return arcs;
|
|
1598
|
-
}
|
|
1599
1601
|
render() {
|
|
1600
1602
|
this._prepare();
|
|
1601
1603
|
const { overlap, smartInvert, dataFilter, customLayoutFunc, customOverlapFunc } = this.attribute;
|
|
@@ -1609,14 +1611,12 @@
|
|
|
1609
1611
|
}
|
|
1610
1612
|
else {
|
|
1611
1613
|
labels = this.layout(data);
|
|
1612
|
-
if (
|
|
1613
|
-
|
|
1614
|
-
|
|
1615
|
-
|
|
1616
|
-
|
|
1617
|
-
|
|
1618
|
-
labels = this._overlapping(labels);
|
|
1619
|
-
}
|
|
1614
|
+
if (vutils.isFunction(customOverlapFunc)) {
|
|
1615
|
+
labels = customOverlapFunc(labels, (d) => this._idToGraphic.get(d.id));
|
|
1616
|
+
}
|
|
1617
|
+
else {
|
|
1618
|
+
if (overlap !== false) {
|
|
1619
|
+
labels = this._overlapping(labels);
|
|
1620
1620
|
}
|
|
1621
1621
|
}
|
|
1622
1622
|
}
|
|
@@ -1737,47 +1737,20 @@
|
|
|
1737
1737
|
const textData = data[i];
|
|
1738
1738
|
const baseMark = this._idToGraphic.get(textData.id);
|
|
1739
1739
|
const labelAttribute = {
|
|
1740
|
-
fill: baseMark.attribute.fill,
|
|
1741
1740
|
...textStyle,
|
|
1742
1741
|
...textData
|
|
1743
1742
|
};
|
|
1744
1743
|
const text = this._createLabelText(labelAttribute);
|
|
1745
1744
|
const textBounds = this.getGraphicBounds(text);
|
|
1746
1745
|
const graphicBounds = this.getGraphicBounds(baseMark, { x: textData.x, y: textData.y });
|
|
1747
|
-
|
|
1748
|
-
|
|
1749
|
-
|
|
1750
|
-
this.labeling(textBounds, graphicBounds, vutils.isFunction(position) ? position(textData) : position, offset, graphicAttributes, textData, width, height, this.attribute);
|
|
1751
|
-
labels.push(text);
|
|
1752
|
-
}
|
|
1753
|
-
else {
|
|
1754
|
-
const textLocation = this.labeling(textBounds, graphicBounds, vutils.isFunction(position) ? position(textData) : position, offset);
|
|
1755
|
-
if (!textLocation) {
|
|
1756
|
-
continue;
|
|
1757
|
-
}
|
|
1758
|
-
labelAttribute.x = textLocation.x;
|
|
1759
|
-
labelAttribute.y = textLocation.y;
|
|
1760
|
-
text.setAttributes(textLocation);
|
|
1761
|
-
labels.push(text);
|
|
1762
|
-
}
|
|
1763
|
-
}
|
|
1764
|
-
if (this.attribute.type === 'arc') {
|
|
1765
|
-
const arcs = this.layoutArcLabels(position, this.attribute, Array.from(this._idToGraphic.values()));
|
|
1766
|
-
for (let i = 0; i < data.length; i++) {
|
|
1767
|
-
const textData = data[i];
|
|
1768
|
-
const basedArc = arcs.find(arc => arc.labelText === textData.text);
|
|
1769
|
-
const labelAttribute = {
|
|
1770
|
-
x: basedArc.labelPosition.x,
|
|
1771
|
-
y: basedArc.labelPosition.y,
|
|
1772
|
-
textAlign: this.attribute.textAlign ?? basedArc.textAlign,
|
|
1773
|
-
textBaseline: this.attribute.textBaseline ?? basedArc.textBaseline,
|
|
1774
|
-
angle: this.attribute.angle ?? basedArc.angle
|
|
1775
|
-
};
|
|
1776
|
-
labels[i].setAttributes(labelAttribute);
|
|
1777
|
-
labels[i].pointA = basedArc.pointA;
|
|
1778
|
-
labels[i].pointB = basedArc.pointB;
|
|
1779
|
-
labels[i].pointC = basedArc.pointC;
|
|
1746
|
+
const textLocation = this.labeling(textBounds, graphicBounds, vutils.isFunction(position) ? position(textData) : position, offset);
|
|
1747
|
+
if (!textLocation) {
|
|
1748
|
+
continue;
|
|
1780
1749
|
}
|
|
1750
|
+
labelAttribute.x = textLocation.x;
|
|
1751
|
+
labelAttribute.y = textLocation.y;
|
|
1752
|
+
text.setAttributes(textLocation);
|
|
1753
|
+
labels.push(text);
|
|
1781
1754
|
}
|
|
1782
1755
|
return labels;
|
|
1783
1756
|
}
|
|
@@ -1823,6 +1796,15 @@
|
|
|
1823
1796
|
continue;
|
|
1824
1797
|
}
|
|
1825
1798
|
}
|
|
1799
|
+
let hasPlace = false;
|
|
1800
|
+
for (let j = 0; j < strategy.length; j++) {
|
|
1801
|
+
hasPlace = place(bmpTool, bitmap, strategy[j], this.attribute, text, this.getGraphicBounds(baseMark, labels[i]), this.labeling);
|
|
1802
|
+
if (hasPlace !== false) {
|
|
1803
|
+
text.setAttributes({ x: hasPlace.x, y: hasPlace.y });
|
|
1804
|
+
result.push(text);
|
|
1805
|
+
break;
|
|
1806
|
+
}
|
|
1807
|
+
}
|
|
1826
1808
|
if (clampForce) {
|
|
1827
1809
|
const { dx = 0, dy = 0 } = clampText(text, bmpTool.width, bmpTool.height);
|
|
1828
1810
|
if (!(dx === 0 && dy === 0) &&
|
|
@@ -1833,19 +1815,11 @@
|
|
|
1833
1815
|
y2: text.AABBBounds.y2 + dy
|
|
1834
1816
|
})) {
|
|
1835
1817
|
text.setAttributes({ x: text.attribute.x + dx, y: text.attribute.y + dy });
|
|
1818
|
+
bitmap.setRange(boundToRange(bmpTool, text.AABBBounds, true));
|
|
1836
1819
|
result.push(text);
|
|
1837
1820
|
continue;
|
|
1838
1821
|
}
|
|
1839
1822
|
}
|
|
1840
|
-
let hasPlace = false;
|
|
1841
|
-
for (let j = 0; j < strategy.length; j++) {
|
|
1842
|
-
hasPlace = place(bmpTool, bitmap, strategy[j], this.attribute, text, this.getGraphicBounds(baseMark, labels[i]), this.labeling);
|
|
1843
|
-
if (hasPlace !== false) {
|
|
1844
|
-
text.setAttributes({ x: hasPlace.x, y: hasPlace.y });
|
|
1845
|
-
result.push(text);
|
|
1846
|
-
break;
|
|
1847
|
-
}
|
|
1848
|
-
}
|
|
1849
1823
|
!hasPlace && !hideOnHit && result.push(text);
|
|
1850
1824
|
}
|
|
1851
1825
|
if (vutils.isFunction(this.onAfterLabelOverlap)) {
|
|
@@ -1887,29 +1861,14 @@
|
|
|
1887
1861
|
const prevTextMap = this._graphicToText || new Map();
|
|
1888
1862
|
const texts = [];
|
|
1889
1863
|
labels.forEach((text, index) => {
|
|
1890
|
-
let labelLine;
|
|
1891
|
-
if (this.attribute.type === 'arc' && this.attribute.position === 'outside') {
|
|
1892
|
-
labelLine = vrender.createPath({
|
|
1893
|
-
visible: text.attribute?.visible ?? true,
|
|
1894
|
-
stroke: text.attribute?.line?.stroke ?? text.attribute?.fill,
|
|
1895
|
-
lineWidth: 1,
|
|
1896
|
-
path: `M${Math.round(text.pointA.x)},${Math.round(text.pointA.y)}` +
|
|
1897
|
-
` L${Math.round(text.pointB.x)},${Math.round(text.pointB.y)}` +
|
|
1898
|
-
` L${Math.round(text.pointC.x)},${Math.round(text.pointC.y)}`
|
|
1899
|
-
});
|
|
1900
|
-
}
|
|
1901
1864
|
const relatedGraphic = this._idToGraphic.get(text.attribute.id);
|
|
1902
1865
|
const state = prevTextMap?.get(relatedGraphic) ? 'update' : 'enter';
|
|
1903
1866
|
if (state === 'enter') {
|
|
1904
1867
|
texts.push(text);
|
|
1905
|
-
if (this.attribute.type === 'arc' && this.attribute.position === 'outside') ;
|
|
1906
1868
|
currentTextMap.set(relatedGraphic, text);
|
|
1907
1869
|
if (!disableAnimation && relatedGraphic) {
|
|
1908
1870
|
const { from, to } = getAnimationAttributes(text.attribute, 'fadeIn');
|
|
1909
1871
|
this.add(text);
|
|
1910
|
-
if (this.attribute.type === 'arc' && this.attribute.position === 'outside') {
|
|
1911
|
-
this.add(labelLine);
|
|
1912
|
-
}
|
|
1913
1872
|
relatedGraphic.onAnimateBind = () => {
|
|
1914
1873
|
text.setAttributes(from);
|
|
1915
1874
|
const listener = this._afterRelatedGraphicAttributeUpdate(text, texts, index, relatedGraphic, {
|
|
@@ -2017,15 +1976,7 @@
|
|
|
2017
1976
|
continue;
|
|
2018
1977
|
}
|
|
2019
1978
|
const baseMark = this._idToGraphic.get(label.attribute.id);
|
|
2020
|
-
|
|
2021
|
-
if (this.attribute.type === 'arc') {
|
|
2022
|
-
if (this.attribute.position === 'inside') {
|
|
2023
|
-
isInside = true;
|
|
2024
|
-
}
|
|
2025
|
-
else {
|
|
2026
|
-
isInside = false;
|
|
2027
|
-
}
|
|
2028
|
-
}
|
|
1979
|
+
const isInside = canPlaceInside(label.AABBBounds, baseMark?.AABBBounds);
|
|
2029
1980
|
if (label.attribute.stroke && label.attribute.lineWidth > 0) {
|
|
2030
1981
|
label.setAttributes({
|
|
2031
1982
|
fill: labelSmartInvert(label.attribute.fill, label.attribute.stroke, textType, contrastRatiosThreshold, alternativeColors)
|
|
@@ -2252,769 +2203,9 @@
|
|
|
2252
2203
|
}
|
|
2253
2204
|
}
|
|
2254
2205
|
|
|
2255
|
-
function polarToCartesian(point) {
|
|
2256
|
-
if (!point.radius) {
|
|
2257
|
-
return { x: 0, y: 0 };
|
|
2258
|
-
}
|
|
2259
|
-
return {
|
|
2260
|
-
x: Math.cos(point.angle) * point.radius,
|
|
2261
|
-
y: Math.sin(point.angle) * point.radius
|
|
2262
|
-
};
|
|
2263
|
-
}
|
|
2264
|
-
function circlePoint(x0, y0, radius, radian) {
|
|
2265
|
-
const offset = polarToCartesian({
|
|
2266
|
-
radius,
|
|
2267
|
-
angle: radian
|
|
2268
|
-
});
|
|
2269
|
-
return {
|
|
2270
|
-
x: x0 + offset.x,
|
|
2271
|
-
y: y0 + offset.y
|
|
2272
|
-
};
|
|
2273
|
-
}
|
|
2274
|
-
function computeQuadrant(angle) {
|
|
2275
|
-
angle = normalizeAngle(angle);
|
|
2276
|
-
if (angle > 0 && angle <= Math.PI / 2) {
|
|
2277
|
-
return 2;
|
|
2278
|
-
}
|
|
2279
|
-
else if (angle > Math.PI / 2 && angle <= Math.PI) {
|
|
2280
|
-
return 3;
|
|
2281
|
-
}
|
|
2282
|
-
else if (angle > Math.PI && angle <= (3 * Math.PI) / 2) {
|
|
2283
|
-
return 4;
|
|
2284
|
-
}
|
|
2285
|
-
return 1;
|
|
2286
|
-
}
|
|
2287
|
-
function normalizeAngle(angle) {
|
|
2288
|
-
while (angle < 0) {
|
|
2289
|
-
angle += Math.PI * 2;
|
|
2290
|
-
}
|
|
2291
|
-
while (angle >= Math.PI * 2) {
|
|
2292
|
-
angle -= Math.PI * 2;
|
|
2293
|
-
}
|
|
2294
|
-
return angle;
|
|
2295
|
-
}
|
|
2296
|
-
function isQuadrantLeft(quadrant) {
|
|
2297
|
-
return quadrant === 3 || quadrant === 4;
|
|
2298
|
-
}
|
|
2299
|
-
function isQuadrantRight(quadrant) {
|
|
2300
|
-
return quadrant === 1 || quadrant === 2;
|
|
2301
|
-
}
|
|
2302
|
-
function lineCirclePoints(a, b, c, x0, y0, r) {
|
|
2303
|
-
if ((a === 0 && b === 0) || r <= 0) {
|
|
2304
|
-
return [];
|
|
2305
|
-
}
|
|
2306
|
-
if (a === 0) {
|
|
2307
|
-
const y1 = -c / b;
|
|
2308
|
-
const fy = (y1 - y0) ** 2;
|
|
2309
|
-
const fd = r ** 2 - fy;
|
|
2310
|
-
if (fd < 0) {
|
|
2311
|
-
return [];
|
|
2312
|
-
}
|
|
2313
|
-
else if (fd === 0) {
|
|
2314
|
-
return [{ x: x0, y: y1 }];
|
|
2315
|
-
}
|
|
2316
|
-
const x1 = Math.sqrt(fd) + x0;
|
|
2317
|
-
const x2 = -Math.sqrt(fd) + x0;
|
|
2318
|
-
return [
|
|
2319
|
-
{ x: x1, y: y1 },
|
|
2320
|
-
{ x: x2, y: y1 }
|
|
2321
|
-
];
|
|
2322
|
-
}
|
|
2323
|
-
else if (b === 0) {
|
|
2324
|
-
const x1 = -c / a;
|
|
2325
|
-
const fx = (x1 - x0) ** 2;
|
|
2326
|
-
const fd = r ** 2 - fx;
|
|
2327
|
-
if (fd < 0) {
|
|
2328
|
-
return [];
|
|
2329
|
-
}
|
|
2330
|
-
else if (fd === 0) {
|
|
2331
|
-
return [{ x: x1, y: y0 }];
|
|
2332
|
-
}
|
|
2333
|
-
const y1 = Math.sqrt(fd) + y0;
|
|
2334
|
-
const y2 = -Math.sqrt(fd) + y0;
|
|
2335
|
-
return [
|
|
2336
|
-
{ x: x1, y: y1 },
|
|
2337
|
-
{ x: x1, y: y2 }
|
|
2338
|
-
];
|
|
2339
|
-
}
|
|
2340
|
-
const fa = (b / a) ** 2 + 1;
|
|
2341
|
-
const fb = 2 * ((c / a + x0) * (b / a) - y0);
|
|
2342
|
-
const fc = (c / a + x0) ** 2 + y0 ** 2 - r ** 2;
|
|
2343
|
-
const fd = fb ** 2 - 4 * fa * fc;
|
|
2344
|
-
if (fd < 0) {
|
|
2345
|
-
return [];
|
|
2346
|
-
}
|
|
2347
|
-
const y1 = (-fb + Math.sqrt(fd)) / (2 * fa);
|
|
2348
|
-
const y2 = (-fb - Math.sqrt(fd)) / (2 * fa);
|
|
2349
|
-
const x1 = -(b * y1 + c) / a;
|
|
2350
|
-
const x2 = -(b * y2 + c) / a;
|
|
2351
|
-
if (fd === 0) {
|
|
2352
|
-
return [{ x: x1, y: y1 }];
|
|
2353
|
-
}
|
|
2354
|
-
return [
|
|
2355
|
-
{ x: x1, y: y1 },
|
|
2356
|
-
{ x: x2, y: y2 }
|
|
2357
|
-
];
|
|
2358
|
-
}
|
|
2359
|
-
function connectLineRadian(radius, length) {
|
|
2360
|
-
if (length > radius * 2) {
|
|
2361
|
-
return NaN;
|
|
2362
|
-
}
|
|
2363
|
-
return Math.asin(length / 2 / radius) * 2;
|
|
2364
|
-
}
|
|
2365
|
-
function checkBoundsOverlap(boundsA, boundsB) {
|
|
2366
|
-
const { x1: ax1, y1: ay1, x2: ax2, y2: ay2 } = boundsA;
|
|
2367
|
-
const { x1: bx1, y1: by1, x2: bx2, y2: by2 } = boundsB;
|
|
2368
|
-
return !((ax1 <= bx1 && ax2 <= bx1) ||
|
|
2369
|
-
(ax1 >= bx2 && ax2 >= bx2) ||
|
|
2370
|
-
(ay1 <= by1 && ay2 <= by1) ||
|
|
2371
|
-
(ay1 >= by2 && ay2 >= by2));
|
|
2372
|
-
}
|
|
2373
|
-
|
|
2374
|
-
class ArcInfo {
|
|
2375
|
-
key;
|
|
2376
|
-
refDatum;
|
|
2377
|
-
center;
|
|
2378
|
-
outerCenter;
|
|
2379
|
-
labelSize;
|
|
2380
|
-
labelPosition;
|
|
2381
|
-
labelLimit;
|
|
2382
|
-
labelVisible;
|
|
2383
|
-
lastLabelY;
|
|
2384
|
-
labelYRange;
|
|
2385
|
-
labelText;
|
|
2386
|
-
pointA;
|
|
2387
|
-
pointB;
|
|
2388
|
-
pointC;
|
|
2389
|
-
quadrant;
|
|
2390
|
-
radian;
|
|
2391
|
-
middleAngle;
|
|
2392
|
-
k;
|
|
2393
|
-
textAlign;
|
|
2394
|
-
textBaseline;
|
|
2395
|
-
angle;
|
|
2396
|
-
constructor(refDatum, center, outerCenter, quadrant, radian, middleAngle) {
|
|
2397
|
-
this.refDatum = refDatum;
|
|
2398
|
-
this.center = center;
|
|
2399
|
-
this.outerCenter = outerCenter;
|
|
2400
|
-
this.quadrant = quadrant;
|
|
2401
|
-
this.radian = radian;
|
|
2402
|
-
this.middleAngle = middleAngle;
|
|
2403
|
-
this.labelVisible = true;
|
|
2404
|
-
this.labelLimit = 0;
|
|
2405
|
-
}
|
|
2406
|
-
getLabelBounds() {
|
|
2407
|
-
if (!this.labelPosition || !this.labelSize) {
|
|
2408
|
-
return { x1: 0, x2: 0, y1: 0, y2: 0 };
|
|
2409
|
-
}
|
|
2410
|
-
return {
|
|
2411
|
-
x1: this.labelPosition.x - this.labelSize.width / 2,
|
|
2412
|
-
y1: this.labelPosition.y - this.labelSize.height / 2,
|
|
2413
|
-
x2: this.labelPosition.x + this.labelSize.width / 2,
|
|
2414
|
-
y2: this.labelPosition.y + this.labelSize.height / 2
|
|
2415
|
-
};
|
|
2416
|
-
}
|
|
2417
|
-
}
|
|
2418
|
-
class ArcLabel extends LabelBase {
|
|
2419
|
-
name = 'arc-label';
|
|
2420
|
-
static defaultAttributes = {
|
|
2421
|
-
coverEnable: false,
|
|
2422
|
-
spaceWidth: 5,
|
|
2423
|
-
layoutArcGap: 6,
|
|
2424
|
-
textStyle: {
|
|
2425
|
-
visible: true,
|
|
2426
|
-
fontSize: 14,
|
|
2427
|
-
fontWeight: 'normal',
|
|
2428
|
-
fillOpacity: 1
|
|
2429
|
-
},
|
|
2430
|
-
position: 'outside',
|
|
2431
|
-
offset: 0,
|
|
2432
|
-
line: {
|
|
2433
|
-
visible: true,
|
|
2434
|
-
line1MinLength: 20,
|
|
2435
|
-
line2MinLength: 10
|
|
2436
|
-
},
|
|
2437
|
-
layout: {
|
|
2438
|
-
align: 'arc',
|
|
2439
|
-
strategy: 'priority',
|
|
2440
|
-
tangentConstraint: true
|
|
2441
|
-
}
|
|
2442
|
-
};
|
|
2443
|
-
_ellipsisWidth = 0;
|
|
2444
|
-
_arcLeft = new Map();
|
|
2445
|
-
_arcRight = new Map();
|
|
2446
|
-
constructor(attributes) {
|
|
2447
|
-
super(vutils.merge({}, ArcLabel.defaultAttributes, attributes));
|
|
2448
|
-
}
|
|
2449
|
-
labeling(textBounds, graphicBounds, position = 'outside', offset = 0, graphicAttributes, textData, width, height, attribute) {
|
|
2450
|
-
if (!textBounds || !graphicBounds) {
|
|
2451
|
-
return;
|
|
2452
|
-
}
|
|
2453
|
-
const radiusRatio = this.computeLayoutOuterRadius(graphicAttributes.outerRadius, width, height);
|
|
2454
|
-
const radius = this.computeRadius(radiusRatio, width, height);
|
|
2455
|
-
const center = { x: graphicAttributes?.x ?? 0, y: graphicAttributes?.y ?? 0 };
|
|
2456
|
-
const item = textData;
|
|
2457
|
-
const arcMiddleAngle = (graphicAttributes.startAngle + graphicAttributes.endAngle) / 2;
|
|
2458
|
-
const intervalAngle = graphicAttributes.endAngle - graphicAttributes.startAngle;
|
|
2459
|
-
const arcQuadrant = computeQuadrant(graphicAttributes.endAngle - intervalAngle / 2);
|
|
2460
|
-
const arcMiddle = circlePoint(center.x, center.y, graphicAttributes.outerRadius, arcMiddleAngle);
|
|
2461
|
-
const outerArcMiddle = circlePoint(center.x, center.y, radius + attribute.line.line1MinLength, arcMiddleAngle);
|
|
2462
|
-
const arc = new ArcInfo(item, arcMiddle, outerArcMiddle, arcQuadrant, intervalAngle, arcMiddleAngle);
|
|
2463
|
-
arc.pointA = circlePoint(center.x, center.y, this.computeDatumRadius(center.x * 2, center.y * 2, graphicAttributes.outerRadius), arc.middleAngle);
|
|
2464
|
-
arc.labelSize = {
|
|
2465
|
-
width: textBounds.x2 - textBounds.x1,
|
|
2466
|
-
height: textBounds.y2 - textBounds.y1
|
|
2467
|
-
};
|
|
2468
|
-
if (isQuadrantRight(arc.quadrant)) {
|
|
2469
|
-
arc.textAlign = 'left';
|
|
2470
|
-
arc.textBaseline = 'middle';
|
|
2471
|
-
this._arcRight.set(arc.refDatum, arc);
|
|
2472
|
-
}
|
|
2473
|
-
else if (isQuadrantLeft(arc.quadrant)) {
|
|
2474
|
-
arc.textAlign = 'right';
|
|
2475
|
-
arc.textBaseline = 'middle';
|
|
2476
|
-
this._arcLeft.set(arc.refDatum, arc);
|
|
2477
|
-
}
|
|
2478
|
-
}
|
|
2479
|
-
layoutArcLabels(position, attribute, currentMarks) {
|
|
2480
|
-
const leftArcs = Array.from(this._arcLeft.values());
|
|
2481
|
-
const rightArcs = Array.from(this._arcRight.values());
|
|
2482
|
-
const arcs = [];
|
|
2483
|
-
if (position === 'inside') {
|
|
2484
|
-
arcs.push(...this._layoutInsideLabels(rightArcs, attribute, currentMarks));
|
|
2485
|
-
arcs.push(...this._layoutInsideLabels(leftArcs, attribute, currentMarks));
|
|
2486
|
-
}
|
|
2487
|
-
else {
|
|
2488
|
-
arcs.push(...this._layoutOutsideLabels(rightArcs, attribute, currentMarks));
|
|
2489
|
-
arcs.push(...this._layoutOutsideLabels(leftArcs, attribute, currentMarks));
|
|
2490
|
-
}
|
|
2491
|
-
return arcs;
|
|
2492
|
-
}
|
|
2493
|
-
_layoutInsideLabels(arcs, attribute, currentMarks) {
|
|
2494
|
-
const center = { x: currentMarks[0].attribute?.x ?? 0, y: currentMarks[0].attribute?.y ?? 0 };
|
|
2495
|
-
const innerRadiusRatio = this.computeLayoutOuterRadius(currentMarks[0].attribute.innerRadius, attribute.width, attribute.height);
|
|
2496
|
-
const outerRadiusRatio = this.computeLayoutOuterRadius(currentMarks[0].attribute.outerRadius, attribute.width, attribute.height);
|
|
2497
|
-
const labelConfig = attribute;
|
|
2498
|
-
const spaceWidth = labelConfig.spaceWidth;
|
|
2499
|
-
arcs.forEach((arc) => {
|
|
2500
|
-
const { labelSize, radian } = arc;
|
|
2501
|
-
const innerRadius = this.computeRadius(innerRadiusRatio, attribute.width, attribute.height, 1);
|
|
2502
|
-
const outerRadius = this.computeRadius(outerRadiusRatio, attribute.width, attribute.height, 1);
|
|
2503
|
-
const minRadian = connectLineRadian(outerRadius, labelSize.height);
|
|
2504
|
-
let limit;
|
|
2505
|
-
if (radian < minRadian) {
|
|
2506
|
-
limit = 0;
|
|
2507
|
-
}
|
|
2508
|
-
else {
|
|
2509
|
-
let minRadius;
|
|
2510
|
-
if (radian >= Math.PI) {
|
|
2511
|
-
minRadius = innerRadius;
|
|
2512
|
-
}
|
|
2513
|
-
else {
|
|
2514
|
-
minRadius = Math.max(innerRadius, labelSize.height / 2 / Math.tan(radian / 2));
|
|
2515
|
-
}
|
|
2516
|
-
limit = outerRadius - minRadius - spaceWidth;
|
|
2517
|
-
}
|
|
2518
|
-
if (labelConfig?.rotate !== true) {
|
|
2519
|
-
limit = outerRadius - spaceWidth;
|
|
2520
|
-
}
|
|
2521
|
-
const text = this._getFormatLabelText(arc.refDatum, limit);
|
|
2522
|
-
arc.labelText = text;
|
|
2523
|
-
const labelWidth = Math.min(limit, arc.labelSize.width);
|
|
2524
|
-
const align = this._computeAlign(arc, attribute);
|
|
2525
|
-
const alignOffset = align === 'left' ? labelWidth : align === 'right' ? 0 : labelWidth / 2;
|
|
2526
|
-
const labelRadius = outerRadius - spaceWidth - alignOffset;
|
|
2527
|
-
arc.labelPosition = circlePoint(center.x, center.y, labelRadius, arc.middleAngle);
|
|
2528
|
-
arc.labelLimit = labelWidth;
|
|
2529
|
-
if (!vutils.isGreater(labelWidth, 0)) {
|
|
2530
|
-
arc.labelVisible = false;
|
|
2531
|
-
}
|
|
2532
|
-
(arc.textAlign = 'center'), (arc.textBaseline = 'middle');
|
|
2533
|
-
arc.angle = arc.middleAngle;
|
|
2534
|
-
});
|
|
2535
|
-
return arcs;
|
|
2536
|
-
}
|
|
2537
|
-
_layoutOutsideLabels(arcs, attribute, currentMarks) {
|
|
2538
|
-
const center = { x: currentMarks[0].attribute?.x ?? 0, y: currentMarks[0].attribute?.y ?? 0 };
|
|
2539
|
-
const height = center.y * 2;
|
|
2540
|
-
const line2MinLength = attribute.line.line2MinLength;
|
|
2541
|
-
const labelLayout = attribute.layout;
|
|
2542
|
-
const spaceWidth = attribute.spaceWidth;
|
|
2543
|
-
arcs.forEach(arc => {
|
|
2544
|
-
const direction = isQuadrantLeft(arc.quadrant) ? -1 : 1;
|
|
2545
|
-
arc.labelPosition = {
|
|
2546
|
-
x: arc.outerCenter.x + direction * (arc.labelSize.width / 2 + line2MinLength + spaceWidth),
|
|
2547
|
-
y: arc.outerCenter.y
|
|
2548
|
-
};
|
|
2549
|
-
});
|
|
2550
|
-
arcs.sort((a, b) => {
|
|
2551
|
-
return a.labelPosition.y - b.labelPosition.y;
|
|
2552
|
-
});
|
|
2553
|
-
if (attribute.coverEnable !== false || labelLayout.strategy === 'none') {
|
|
2554
|
-
for (const arc of arcs) {
|
|
2555
|
-
const { labelPosition, labelSize } = arc;
|
|
2556
|
-
arc.labelLimit = labelSize.width;
|
|
2557
|
-
arc.pointB = isQuadrantLeft(arc.quadrant)
|
|
2558
|
-
? {
|
|
2559
|
-
x: labelPosition.x + labelSize.width / 2 + line2MinLength + spaceWidth,
|
|
2560
|
-
y: labelPosition.y
|
|
2561
|
-
}
|
|
2562
|
-
: {
|
|
2563
|
-
x: labelPosition.x - labelSize.width / 2 - line2MinLength - spaceWidth,
|
|
2564
|
-
y: labelPosition.y
|
|
2565
|
-
};
|
|
2566
|
-
this._computeX(arc, attribute, currentMarks);
|
|
2567
|
-
}
|
|
2568
|
-
if (attribute.coverEnable === false && labelLayout.strategy === 'none') {
|
|
2569
|
-
this._coverLabels(arcs);
|
|
2570
|
-
}
|
|
2571
|
-
}
|
|
2572
|
-
else {
|
|
2573
|
-
const maxLabels = height / (attribute.textStyle?.fontSize || 16);
|
|
2574
|
-
this._adjustY(arcs, maxLabels, attribute, currentMarks);
|
|
2575
|
-
const { minY, maxY } = arcs.reduce((yInfo, arc) => {
|
|
2576
|
-
const { y1, y2 } = arc.getLabelBounds();
|
|
2577
|
-
yInfo.minY = Math.max(0, Math.min(y1, yInfo.minY));
|
|
2578
|
-
yInfo.maxY = Math.min(height, Math.max(y2, yInfo.maxY));
|
|
2579
|
-
return yInfo;
|
|
2580
|
-
}, { minY: Infinity, maxY: -Infinity });
|
|
2581
|
-
const halfY = Math.max(Math.abs(height / 2 - minY), Math.abs(maxY - height / 2));
|
|
2582
|
-
const r = this._computeLayoutRadius(halfY, attribute, currentMarks);
|
|
2583
|
-
for (const arc of arcs) {
|
|
2584
|
-
this._computePointB(arc, r, attribute, currentMarks);
|
|
2585
|
-
this._computeX(arc, attribute, currentMarks);
|
|
2586
|
-
}
|
|
2587
|
-
}
|
|
2588
|
-
const width = center.x * 2;
|
|
2589
|
-
arcs.forEach(arc => {
|
|
2590
|
-
if (arc.labelVisible &&
|
|
2591
|
-
(vutils.isLess(arc.pointB.x, line2MinLength + spaceWidth) ||
|
|
2592
|
-
vutils.isGreater(arc.pointB.x, width - line2MinLength - spaceWidth))) {
|
|
2593
|
-
arc.labelVisible = false;
|
|
2594
|
-
}
|
|
2595
|
-
arc.angle = 0;
|
|
2596
|
-
});
|
|
2597
|
-
return arcs;
|
|
2598
|
-
}
|
|
2599
|
-
_computeX(arc, attribute, currentMarks) {
|
|
2600
|
-
const center = { x: currentMarks[0].attribute?.x ?? 0, y: currentMarks[0].attribute?.y ?? 0 };
|
|
2601
|
-
const plotLayout = { width: center.x * 2, height: center.y * 2 };
|
|
2602
|
-
const radiusRatio = this.computeLayoutOuterRadius(currentMarks[0].attribute.outerRadius, attribute.width, attribute.height);
|
|
2603
|
-
const line1MinLength = attribute.line.line1MinLength;
|
|
2604
|
-
const line2MinLength = attribute.line.line2MinLength;
|
|
2605
|
-
const labelLayoutAlign = attribute.layout?.align;
|
|
2606
|
-
const spaceWidth = attribute.spaceWidth;
|
|
2607
|
-
const align = this._computeAlign(arc, attribute);
|
|
2608
|
-
const { labelPosition, quadrant, pointB } = arc;
|
|
2609
|
-
if (!vutils.isValidNumber(pointB.x * pointB.y)) {
|
|
2610
|
-
arc.pointC = { x: NaN, y: NaN };
|
|
2611
|
-
labelPosition.x = NaN;
|
|
2612
|
-
arc.labelLimit = 0;
|
|
2613
|
-
}
|
|
2614
|
-
const radius = this.computeRadius(radiusRatio, attribute.width, attribute.height);
|
|
2615
|
-
const flag = isQuadrantLeft(quadrant) ? -1 : 1;
|
|
2616
|
-
let cx = 0;
|
|
2617
|
-
const restWidth = flag > 0 ? plotLayout.width - pointB.x : pointB.x;
|
|
2618
|
-
let limit = restWidth - line2MinLength - spaceWidth;
|
|
2619
|
-
if (labelLayoutAlign === 'labelLine') {
|
|
2620
|
-
cx = (radius + line1MinLength + line2MinLength) * flag + center.x;
|
|
2621
|
-
limit = (flag > 0 ? plotLayout.width - cx : cx) - spaceWidth;
|
|
2622
|
-
}
|
|
2623
|
-
const text = this._getFormatLabelText(arc.refDatum, limit);
|
|
2624
|
-
arc.labelText = text;
|
|
2625
|
-
let labelWidth = Math.min(limit, arc.labelSize.width);
|
|
2626
|
-
switch (labelLayoutAlign) {
|
|
2627
|
-
case 'labelLine':
|
|
2628
|
-
break;
|
|
2629
|
-
case 'edge':
|
|
2630
|
-
cx = flag > 0 ? plotLayout.width - labelWidth - spaceWidth : labelWidth + spaceWidth;
|
|
2631
|
-
break;
|
|
2632
|
-
case 'arc':
|
|
2633
|
-
default:
|
|
2634
|
-
cx = pointB.x + flag * line2MinLength;
|
|
2635
|
-
break;
|
|
2636
|
-
}
|
|
2637
|
-
labelWidth = Math.max(this._ellipsisWidth, labelWidth);
|
|
2638
|
-
arc.pointC = { x: cx, y: labelPosition.y };
|
|
2639
|
-
if (labelLayoutAlign === 'edge') {
|
|
2640
|
-
const alignOffset = this._computeAlignOffset(align, labelWidth, -flag);
|
|
2641
|
-
labelPosition.x = flag > 0 ? plotLayout.width + alignOffset : alignOffset;
|
|
2642
|
-
}
|
|
2643
|
-
else {
|
|
2644
|
-
const alignOffset = this._computeAlignOffset(align, labelWidth, flag);
|
|
2645
|
-
labelPosition.x = cx + alignOffset + flag * spaceWidth;
|
|
2646
|
-
}
|
|
2647
|
-
arc.labelLimit = labelWidth;
|
|
2648
|
-
}
|
|
2649
|
-
_computeAlignOffset(align, labelWidth, alignFlag) {
|
|
2650
|
-
switch (align) {
|
|
2651
|
-
case 'left':
|
|
2652
|
-
return alignFlag < 0 ? -labelWidth : 0;
|
|
2653
|
-
case 'right':
|
|
2654
|
-
return alignFlag < 0 ? 0 : labelWidth;
|
|
2655
|
-
case 'center':
|
|
2656
|
-
default:
|
|
2657
|
-
return (labelWidth / 2) * alignFlag;
|
|
2658
|
-
}
|
|
2659
|
-
}
|
|
2660
|
-
_computeAlign(arc, attribute) {
|
|
2661
|
-
const labelConfig = attribute;
|
|
2662
|
-
const textAlign = labelConfig.textStyle?.textAlign ?? labelConfig.textStyle?.align;
|
|
2663
|
-
const layoutAlign = labelConfig.layout?.textAlign ?? labelConfig.layout?.align;
|
|
2664
|
-
if (labelConfig.position !== 'inside') {
|
|
2665
|
-
if (vutils.isNil(textAlign) || textAlign === 'auto') {
|
|
2666
|
-
if (layoutAlign === 'edge') {
|
|
2667
|
-
return isQuadrantLeft(arc.quadrant) ? 'left' : 'right';
|
|
2668
|
-
}
|
|
2669
|
-
return isQuadrantLeft(arc.quadrant) ? 'right' : 'left';
|
|
2670
|
-
}
|
|
2671
|
-
return textAlign;
|
|
2672
|
-
}
|
|
2673
|
-
return vutils.isNil(textAlign) || textAlign === 'auto' ? 'center' : textAlign;
|
|
2674
|
-
}
|
|
2675
|
-
_getFormatLabelText(value, limit) {
|
|
2676
|
-
return value.text;
|
|
2677
|
-
}
|
|
2678
|
-
_adjustY(arcs, maxLabels, attribute, currentMarks) {
|
|
2679
|
-
const center = { x: currentMarks[0].attribute?.x ?? 0, y: currentMarks[0].attribute?.y ?? 0 };
|
|
2680
|
-
const plotRect = { width: center.x * 2, height: center.y * 2 };
|
|
2681
|
-
const labelLayout = attribute.layout;
|
|
2682
|
-
if (labelLayout.strategy === 'vertical') {
|
|
2683
|
-
let lastY = 0;
|
|
2684
|
-
let delta;
|
|
2685
|
-
const len = arcs.length;
|
|
2686
|
-
if (len <= 0) {
|
|
2687
|
-
return;
|
|
2688
|
-
}
|
|
2689
|
-
for (let i = 0; i < len; i++) {
|
|
2690
|
-
const { y1 } = arcs[i].getLabelBounds();
|
|
2691
|
-
delta = y1 - lastY;
|
|
2692
|
-
if (vutils.isLess(delta, 0)) {
|
|
2693
|
-
const index = this._shiftY(arcs, i, len - 1, -delta);
|
|
2694
|
-
this._shiftY(arcs, index, 0, delta / 2);
|
|
2695
|
-
}
|
|
2696
|
-
const { y2 } = arcs[i].getLabelBounds();
|
|
2697
|
-
lastY = y2;
|
|
2698
|
-
}
|
|
2699
|
-
const { y1: firstY1 } = arcs[0].getLabelBounds();
|
|
2700
|
-
delta = firstY1 - 0;
|
|
2701
|
-
if (vutils.isLess(delta, 0)) {
|
|
2702
|
-
this._shiftY(arcs, 0, len - 1, -delta);
|
|
2703
|
-
}
|
|
2704
|
-
for (let i = arcs.length - 1; i >= 0; i--) {
|
|
2705
|
-
if (arcs[i].getLabelBounds().y2 > plotRect.height) {
|
|
2706
|
-
arcs[i].labelVisible = false;
|
|
2707
|
-
}
|
|
2708
|
-
else {
|
|
2709
|
-
break;
|
|
2710
|
-
}
|
|
2711
|
-
}
|
|
2712
|
-
}
|
|
2713
|
-
else if (labelLayout.strategy !== 'none') {
|
|
2714
|
-
const priorityArcs = arcs.map((arc, i) => {
|
|
2715
|
-
return {
|
|
2716
|
-
arc,
|
|
2717
|
-
originIndex: i,
|
|
2718
|
-
priorityIndex: 0
|
|
2719
|
-
};
|
|
2720
|
-
});
|
|
2721
|
-
priorityArcs.sort((a, b) => {
|
|
2722
|
-
return b.arc.radian - a.arc.radian;
|
|
2723
|
-
});
|
|
2724
|
-
priorityArcs.forEach((priorityArc, i) => {
|
|
2725
|
-
priorityArc.priorityIndex = i;
|
|
2726
|
-
priorityArc.arc.labelVisible = false;
|
|
2727
|
-
});
|
|
2728
|
-
let topLabelIndex = Infinity;
|
|
2729
|
-
let bottomLabelIndex = -Infinity;
|
|
2730
|
-
for (let i = 0; i < maxLabels && i < arcs.length; i++) {
|
|
2731
|
-
this._storeY(arcs);
|
|
2732
|
-
const arc = priorityArcs[i].arc;
|
|
2733
|
-
this._computeYRange(arc, attribute, currentMarks);
|
|
2734
|
-
arc.labelVisible = true;
|
|
2735
|
-
const curY = arc.labelPosition.y;
|
|
2736
|
-
const { lastIndex, nextIndex } = this._findNeighborIndex(arcs, priorityArcs[i]);
|
|
2737
|
-
const lastArc = arcs[lastIndex];
|
|
2738
|
-
const nextArc = arcs[nextIndex];
|
|
2739
|
-
if (lastIndex === -1 && nextIndex !== -1) {
|
|
2740
|
-
const nextY = nextArc.labelPosition.y;
|
|
2741
|
-
if (curY > nextY) {
|
|
2742
|
-
arc.labelPosition.y = nextY - nextArc.labelSize.height / 2 - arc.labelSize.height / 2;
|
|
2743
|
-
}
|
|
2744
|
-
else {
|
|
2745
|
-
this._twoWayShift(arcs, arc, nextArc, nextIndex);
|
|
2746
|
-
}
|
|
2747
|
-
}
|
|
2748
|
-
else if (lastIndex !== -1 && nextIndex === -1) {
|
|
2749
|
-
const lastY = lastArc.labelPosition.y;
|
|
2750
|
-
if (curY < lastY) {
|
|
2751
|
-
arc.labelPosition.y = lastY + lastArc.labelSize.height / 2 + arc.labelSize.height / 2;
|
|
2752
|
-
}
|
|
2753
|
-
else {
|
|
2754
|
-
this._twoWayShift(arcs, lastArc, arc, priorityArcs[i].originIndex);
|
|
2755
|
-
}
|
|
2756
|
-
}
|
|
2757
|
-
else if (lastIndex !== -1 && nextIndex !== -1) {
|
|
2758
|
-
const lastY = lastArc.labelPosition.y;
|
|
2759
|
-
const nextY = nextArc.labelPosition.y;
|
|
2760
|
-
if (curY > nextY) {
|
|
2761
|
-
arc.labelPosition.y = nextY - nextArc.labelSize.height / 2 - arc.labelSize.height / 2;
|
|
2762
|
-
this._twoWayShift(arcs, lastArc, arc, priorityArcs[i].originIndex);
|
|
2763
|
-
}
|
|
2764
|
-
else if (curY < lastY) {
|
|
2765
|
-
arc.labelPosition.y = lastY + lastArc.labelSize.height / 2 + arc.labelSize.height / 2;
|
|
2766
|
-
this._twoWayShift(arcs, arc, nextArc, nextIndex);
|
|
2767
|
-
}
|
|
2768
|
-
else {
|
|
2769
|
-
this._twoWayShift(arcs, lastArc, arc, priorityArcs[i].originIndex);
|
|
2770
|
-
this._twoWayShift(arcs, arc, nextArc, nextIndex);
|
|
2771
|
-
}
|
|
2772
|
-
}
|
|
2773
|
-
const nextTopIndex = Math.min(topLabelIndex, priorityArcs[i].originIndex);
|
|
2774
|
-
const nextBottomIndex = Math.max(bottomLabelIndex, priorityArcs[i].originIndex);
|
|
2775
|
-
let delta;
|
|
2776
|
-
delta = arcs[nextBottomIndex].getLabelBounds().y2 - plotRect.height;
|
|
2777
|
-
if (vutils.isGreater(delta, 0)) {
|
|
2778
|
-
this._shiftY(arcs, nextBottomIndex, 0, -delta);
|
|
2779
|
-
}
|
|
2780
|
-
delta = arcs[nextTopIndex].getLabelBounds().y1 - 0;
|
|
2781
|
-
if (vutils.isLess(delta, 0)) {
|
|
2782
|
-
this._shiftY(arcs, nextTopIndex, arcs.length - 1, -delta);
|
|
2783
|
-
}
|
|
2784
|
-
delta = arcs[nextBottomIndex].getLabelBounds().y2 - plotRect.height;
|
|
2785
|
-
if (vutils.isGreater(delta, 0)) {
|
|
2786
|
-
arc.labelVisible = false;
|
|
2787
|
-
this._restoreY(arcs);
|
|
2788
|
-
break;
|
|
2789
|
-
}
|
|
2790
|
-
else if (labelLayout.tangentConstraint && !this._checkYRange(arcs)) {
|
|
2791
|
-
arc.labelVisible = false;
|
|
2792
|
-
this._restoreY(arcs);
|
|
2793
|
-
}
|
|
2794
|
-
else {
|
|
2795
|
-
topLabelIndex = nextTopIndex;
|
|
2796
|
-
bottomLabelIndex = nextBottomIndex;
|
|
2797
|
-
}
|
|
2798
|
-
}
|
|
2799
|
-
}
|
|
2800
|
-
}
|
|
2801
|
-
_shiftY(arcs, start, end, delta) {
|
|
2802
|
-
const direction = start < end ? 1 : -1;
|
|
2803
|
-
let index = start;
|
|
2804
|
-
while (index !== -1) {
|
|
2805
|
-
arcs[index].labelPosition.y += delta;
|
|
2806
|
-
const nextIndex = this._findNextVisibleIndex(arcs, index, end, direction);
|
|
2807
|
-
if (nextIndex >= 0 && nextIndex < arcs.length) {
|
|
2808
|
-
const { y1: curY1, y2: curY2 } = arcs[index].getLabelBounds();
|
|
2809
|
-
const { y1: nextY1, y2: nextY2 } = arcs[nextIndex].getLabelBounds();
|
|
2810
|
-
if ((direction > 0 && curY2 < nextY1) || (direction < 0 && curY1 > nextY2)) {
|
|
2811
|
-
return index;
|
|
2812
|
-
}
|
|
2813
|
-
}
|
|
2814
|
-
index = nextIndex;
|
|
2815
|
-
}
|
|
2816
|
-
return end;
|
|
2817
|
-
}
|
|
2818
|
-
_findNextVisibleIndex(arcs, start, end, direction) {
|
|
2819
|
-
const diff = (end - start) * direction;
|
|
2820
|
-
for (let i = 1; i <= diff; i++) {
|
|
2821
|
-
const index = start + i * direction;
|
|
2822
|
-
if (arcs[index].labelVisible) {
|
|
2823
|
-
return index;
|
|
2824
|
-
}
|
|
2825
|
-
}
|
|
2826
|
-
return -1;
|
|
2827
|
-
}
|
|
2828
|
-
_computePointB(arc, r, attribute, currentMarks) {
|
|
2829
|
-
const labelConfig = attribute;
|
|
2830
|
-
const radiusRatio = this.computeLayoutOuterRadius(currentMarks[0].attribute.outerRadius, attribute.width, attribute.height);
|
|
2831
|
-
const line1MinLength = labelConfig.line.line1MinLength;
|
|
2832
|
-
const labelLayout = labelConfig.layout;
|
|
2833
|
-
if (labelLayout.strategy === 'none') {
|
|
2834
|
-
arc.pointB = {
|
|
2835
|
-
x: arc.outerCenter.x,
|
|
2836
|
-
y: arc.outerCenter.y
|
|
2837
|
-
};
|
|
2838
|
-
}
|
|
2839
|
-
else {
|
|
2840
|
-
const center = { x: currentMarks[0].attribute?.x ?? 0, y: currentMarks[0].attribute?.y ?? 0 };
|
|
2841
|
-
const radius = this.computeRadius(radiusRatio, attribute.width, attribute.height);
|
|
2842
|
-
const { labelPosition, quadrant } = arc;
|
|
2843
|
-
const outerR = Math.max(radius + line1MinLength, currentMarks[0].attribute.outerRadius);
|
|
2844
|
-
const rd = r - outerR;
|
|
2845
|
-
const x = Math.sqrt(r ** 2 - Math.abs(center.y - labelPosition.y) ** 2) - rd;
|
|
2846
|
-
if (vutils.isValidNumber(x)) {
|
|
2847
|
-
arc.pointB = {
|
|
2848
|
-
x: center.x + x * (isQuadrantLeft(quadrant) ? -1 : 1),
|
|
2849
|
-
y: labelPosition.y
|
|
2850
|
-
};
|
|
2851
|
-
}
|
|
2852
|
-
else {
|
|
2853
|
-
arc.pointB = { x: NaN, y: NaN };
|
|
2854
|
-
}
|
|
2855
|
-
}
|
|
2856
|
-
}
|
|
2857
|
-
_storeY(arcs) {
|
|
2858
|
-
for (const arc of arcs) {
|
|
2859
|
-
if (arc.labelVisible) {
|
|
2860
|
-
arc.lastLabelY = arc.labelPosition.y;
|
|
2861
|
-
}
|
|
2862
|
-
}
|
|
2863
|
-
}
|
|
2864
|
-
_computeYRange(arc, attribute, currentMarks) {
|
|
2865
|
-
const center = { x: currentMarks[0].attribute?.x ?? 0, y: currentMarks[0].attribute?.y ?? 0 };
|
|
2866
|
-
const plotRect = { width: center.x * 2, height: center.y * 2 };
|
|
2867
|
-
const radiusRatio = this.computeLayoutOuterRadius(currentMarks[0].attribute.outerRadius, attribute.width, attribute.height);
|
|
2868
|
-
const line1MinLength = attribute.line.line1MinLength;
|
|
2869
|
-
const { width, height } = plotRect;
|
|
2870
|
-
const radius = this.computeRadius(radiusRatio, attribute.width, attribute.height);
|
|
2871
|
-
const r = this._computeLayoutRadius(height / 2, attribute, currentMarks);
|
|
2872
|
-
const cx = Math.abs(arc.center.x - width / 2);
|
|
2873
|
-
const cy = arc.center.y - height / 2;
|
|
2874
|
-
let a;
|
|
2875
|
-
let b;
|
|
2876
|
-
let c;
|
|
2877
|
-
if (vutils.isNumberClose(width / 2, cx)) {
|
|
2878
|
-
a = 0;
|
|
2879
|
-
b = 1;
|
|
2880
|
-
c = -cy;
|
|
2881
|
-
}
|
|
2882
|
-
else if (vutils.isNumberClose(height / 2, cy)) {
|
|
2883
|
-
a = 1;
|
|
2884
|
-
b = 0;
|
|
2885
|
-
c = -cx;
|
|
2886
|
-
}
|
|
2887
|
-
else {
|
|
2888
|
-
const k = -1 / (cy / cx);
|
|
2889
|
-
a = k;
|
|
2890
|
-
b = -1;
|
|
2891
|
-
c = cy - k * cx;
|
|
2892
|
-
}
|
|
2893
|
-
const points = lineCirclePoints(a, b, c, line1MinLength + radius - r, 0, r);
|
|
2894
|
-
if (points.length < 2) {
|
|
2895
|
-
return;
|
|
2896
|
-
}
|
|
2897
|
-
let min;
|
|
2898
|
-
let max;
|
|
2899
|
-
if (points[0].x > points[1].x) {
|
|
2900
|
-
points.reverse();
|
|
2901
|
-
}
|
|
2902
|
-
if (points[0].x < 0) {
|
|
2903
|
-
if (vutils.isNumberClose(points[0].y, points[1].y)) {
|
|
2904
|
-
if (Math.abs(arc.middleAngle) < Math.PI / 2) {
|
|
2905
|
-
min = 0;
|
|
2906
|
-
max = points[1].y + height / 2;
|
|
2907
|
-
}
|
|
2908
|
-
else {
|
|
2909
|
-
min = points[1].y + height / 2;
|
|
2910
|
-
max = height;
|
|
2911
|
-
}
|
|
2912
|
-
}
|
|
2913
|
-
else if (points[0].y < points[1].y) {
|
|
2914
|
-
min = 0;
|
|
2915
|
-
max = points[1].y + height / 2;
|
|
2916
|
-
}
|
|
2917
|
-
else {
|
|
2918
|
-
min = points[1].y + height / 2;
|
|
2919
|
-
max = plotRect.height;
|
|
2920
|
-
}
|
|
2921
|
-
}
|
|
2922
|
-
else {
|
|
2923
|
-
min = Math.min(points[0].y, points[1].y) + height / 2;
|
|
2924
|
-
max = Math.max(points[0].y, points[1].y) + height / 2;
|
|
2925
|
-
}
|
|
2926
|
-
arc.labelYRange = [min, max];
|
|
2927
|
-
}
|
|
2928
|
-
_computeLayoutRadius(halfYLength, attribute, currentMarks) {
|
|
2929
|
-
const labelConfig = attribute;
|
|
2930
|
-
const layoutArcGap = labelConfig.layoutArcGap;
|
|
2931
|
-
const line1MinLength = labelConfig.line.line1MinLength;
|
|
2932
|
-
const radiusRatio = this.computeLayoutOuterRadius(currentMarks[0].attribute.outerRadius, attribute.width, attribute.height);
|
|
2933
|
-
const radius = this.computeRadius(radiusRatio, attribute.width, attribute.height);
|
|
2934
|
-
const outerR = radius + line1MinLength;
|
|
2935
|
-
const a = outerR - layoutArcGap;
|
|
2936
|
-
return Math.max((a ** 2 + halfYLength ** 2) / (2 * a), outerR);
|
|
2937
|
-
}
|
|
2938
|
-
_findNeighborIndex(arcs, priorityArc) {
|
|
2939
|
-
const index = priorityArc.originIndex;
|
|
2940
|
-
let lastIndex = -1;
|
|
2941
|
-
let nextIndex = -1;
|
|
2942
|
-
for (let i = index - 1; i >= 0; i--) {
|
|
2943
|
-
if (arcs[i].labelVisible) {
|
|
2944
|
-
lastIndex = i;
|
|
2945
|
-
break;
|
|
2946
|
-
}
|
|
2947
|
-
}
|
|
2948
|
-
for (let i = index + 1; i < arcs.length; i++) {
|
|
2949
|
-
if (arcs[i].labelVisible) {
|
|
2950
|
-
nextIndex = i;
|
|
2951
|
-
break;
|
|
2952
|
-
}
|
|
2953
|
-
}
|
|
2954
|
-
return {
|
|
2955
|
-
lastIndex,
|
|
2956
|
-
nextIndex
|
|
2957
|
-
};
|
|
2958
|
-
}
|
|
2959
|
-
_twoWayShift(arcs, lastArc, nextArc, nextIndex) {
|
|
2960
|
-
const delta = nextArc.getLabelBounds().y1 - lastArc.getLabelBounds().y2;
|
|
2961
|
-
if (vutils.isLess(delta, 0)) {
|
|
2962
|
-
const i = this._shiftY(arcs, nextIndex, arcs.length - 1, -delta);
|
|
2963
|
-
this._shiftY(arcs, i, 0, delta / 2);
|
|
2964
|
-
}
|
|
2965
|
-
}
|
|
2966
|
-
_restoreY(arcs) {
|
|
2967
|
-
for (const arc of arcs) {
|
|
2968
|
-
if (arc.labelVisible) {
|
|
2969
|
-
arc.labelPosition.y = arc.lastLabelY;
|
|
2970
|
-
}
|
|
2971
|
-
}
|
|
2972
|
-
}
|
|
2973
|
-
_checkYRange(arcs) {
|
|
2974
|
-
for (const arc of arcs) {
|
|
2975
|
-
const { labelYRange, labelPosition } = arc;
|
|
2976
|
-
if (arc.labelVisible &&
|
|
2977
|
-
labelYRange &&
|
|
2978
|
-
(vutils.isLess(labelPosition.y, labelYRange[0]) || vutils.isGreater(labelPosition.y, labelYRange[1]))) {
|
|
2979
|
-
return false;
|
|
2980
|
-
}
|
|
2981
|
-
}
|
|
2982
|
-
return true;
|
|
2983
|
-
}
|
|
2984
|
-
_coverLabels(arcs) {
|
|
2985
|
-
if (arcs.length <= 1) {
|
|
2986
|
-
return;
|
|
2987
|
-
}
|
|
2988
|
-
let lastBounds = arcs[0].getLabelBounds();
|
|
2989
|
-
for (let i = 1; i < arcs.length; i++) {
|
|
2990
|
-
const bounds = arcs[i].getLabelBounds();
|
|
2991
|
-
if (!checkBoundsOverlap(lastBounds, bounds)) {
|
|
2992
|
-
lastBounds = bounds;
|
|
2993
|
-
}
|
|
2994
|
-
else {
|
|
2995
|
-
arcs[i].labelVisible = false;
|
|
2996
|
-
}
|
|
2997
|
-
}
|
|
2998
|
-
}
|
|
2999
|
-
computeRadius(r, width, height, k) {
|
|
3000
|
-
return this.computeLayoutRadius(width ? width : 0, height ? height : 0) * r * (vutils.isNil(k) ? 1 : k);
|
|
3001
|
-
}
|
|
3002
|
-
computeLayoutRadius(width, height) {
|
|
3003
|
-
return Math.min(width / 2, height / 2);
|
|
3004
|
-
}
|
|
3005
|
-
computeLayoutOuterRadius(r, width, height) {
|
|
3006
|
-
return r / (Math.min(width, height) / 2);
|
|
3007
|
-
}
|
|
3008
|
-
computeDatumRadius(width, height, outerRadius) {
|
|
3009
|
-
const outerRadiusRatio = this.computeLayoutOuterRadius(outerRadius, width, height);
|
|
3010
|
-
return this.computeLayoutRadius(width ? width : 0, height ? height : 0) * outerRadiusRatio;
|
|
3011
|
-
}
|
|
3012
|
-
}
|
|
3013
|
-
|
|
3014
2206
|
const labelComponentMap = {
|
|
3015
2207
|
rect: RectLabel,
|
|
3016
|
-
symbol: SymbolLabel
|
|
3017
|
-
arc: ArcLabel
|
|
2208
|
+
symbol: SymbolLabel
|
|
3018
2209
|
};
|
|
3019
2210
|
class DataLabel extends AbstractComponent {
|
|
3020
2211
|
name = 'data-label';
|
|
@@ -9705,6 +8896,17 @@
|
|
|
9705
8896
|
}
|
|
9706
8897
|
}
|
|
9707
8898
|
|
|
8899
|
+
exports.IOperateType = void 0;
|
|
8900
|
+
(function (IOperateType) {
|
|
8901
|
+
IOperateType["drawStart"] = "drawStart";
|
|
8902
|
+
IOperateType["drawEnd"] = "drawEnd";
|
|
8903
|
+
IOperateType["drawing"] = "drawing";
|
|
8904
|
+
IOperateType["moving"] = "moving";
|
|
8905
|
+
IOperateType["moveStart"] = "moveStart";
|
|
8906
|
+
IOperateType["moveEnd"] = "moveEnd";
|
|
8907
|
+
IOperateType["brushClear"] = "brushClear";
|
|
8908
|
+
})(exports.IOperateType || (exports.IOperateType = {}));
|
|
8909
|
+
|
|
9708
8910
|
const DEFAULT_BRUSH_ATTRIBUTES = {
|
|
9709
8911
|
brushMode: 'single',
|
|
9710
8912
|
brushType: 'rect',
|
|
@@ -9736,6 +8938,8 @@
|
|
|
9736
8938
|
_container;
|
|
9737
8939
|
_activeDrawState = false;
|
|
9738
8940
|
_cacheDrawPoints = [];
|
|
8941
|
+
_cacheStartTime;
|
|
8942
|
+
_isDrawedBeforeEnd = false;
|
|
9739
8943
|
_activeMoveState = false;
|
|
9740
8944
|
_operatingMaskMoveDx = 0;
|
|
9741
8945
|
_operatingMaskMoveDy = 0;
|
|
@@ -9791,36 +8995,41 @@
|
|
|
9791
8995
|
this._activeMoveState && this._moving(e);
|
|
9792
8996
|
};
|
|
9793
8997
|
_onBrushEnd = (e) => {
|
|
9794
|
-
|
|
9795
|
-
|
|
8998
|
+
const { removeOnClick } = this.attribute;
|
|
8999
|
+
if (this._activeDrawState && !this._isDrawedBeforeEnd && removeOnClick) {
|
|
9000
|
+
this._container.incrementalClearChild();
|
|
9001
|
+
this._updateDragMaskCallback &&
|
|
9002
|
+
this._updateDragMaskCallback({
|
|
9003
|
+
operateType: exports.IOperateType.brushClear,
|
|
9004
|
+
operateMask: this._operatingMask,
|
|
9005
|
+
operatedMaskAABBBounds: this._brushMaskAABBBoundsDict
|
|
9006
|
+
});
|
|
9007
|
+
}
|
|
9008
|
+
else {
|
|
9009
|
+
this._updateDragMaskCallback &&
|
|
9010
|
+
this._updateDragMaskCallback({
|
|
9011
|
+
operateType: this._activeDrawState ? exports.IOperateType.drawEnd : exports.IOperateType.moveEnd,
|
|
9012
|
+
operateMask: this._operatingMask,
|
|
9013
|
+
operatedMaskAABBBounds: this._brushMaskAABBBoundsDict
|
|
9014
|
+
});
|
|
9796
9015
|
}
|
|
9797
|
-
this._updateDragMaskCallback &&
|
|
9798
|
-
this._updateDragMaskCallback({
|
|
9799
|
-
operateType: this._activeDrawState ? 'brushEnd' : 'brushMaskUp',
|
|
9800
|
-
operateMask: this._operatingMask,
|
|
9801
|
-
operatedMaskAABBBounds: this._brushMaskAABBBoundsDict
|
|
9802
|
-
});
|
|
9803
9016
|
this._activeDrawState = false;
|
|
9804
9017
|
this._activeMoveState = false;
|
|
9018
|
+
this._isDrawedBeforeEnd = false;
|
|
9805
9019
|
this._operatingMask.setAttribute('pickable', false);
|
|
9806
9020
|
};
|
|
9807
9021
|
_initDraw(e) {
|
|
9808
|
-
const { brushMode
|
|
9022
|
+
const { brushMode } = this.attribute;
|
|
9809
9023
|
const pos = this.eventPosToStagePos(e);
|
|
9810
9024
|
this._cacheDrawPoints = [pos];
|
|
9811
|
-
|
|
9812
|
-
|
|
9813
|
-
}
|
|
9814
|
-
if (brushMode === 'single' && removeOnClick) {
|
|
9025
|
+
this._isDrawedBeforeEnd = false;
|
|
9026
|
+
if (brushMode === 'single') {
|
|
9815
9027
|
this._container.incrementalClearChild();
|
|
9816
|
-
this._addBrushMask();
|
|
9817
|
-
}
|
|
9818
|
-
else if (brushMode === 'multiple') {
|
|
9819
|
-
this._addBrushMask();
|
|
9820
9028
|
}
|
|
9029
|
+
this._addBrushMask();
|
|
9821
9030
|
this._updateDragMaskCallback &&
|
|
9822
9031
|
this._updateDragMaskCallback({
|
|
9823
|
-
operateType:
|
|
9032
|
+
operateType: exports.IOperateType.drawStart,
|
|
9824
9033
|
operateMask: this._operatingMask,
|
|
9825
9034
|
operatedMaskAABBBounds: this._brushMaskAABBBoundsDict
|
|
9826
9035
|
});
|
|
@@ -9841,13 +9050,14 @@
|
|
|
9841
9050
|
this._operatingMask.setAttribute('pickable', true);
|
|
9842
9051
|
this._updateDragMaskCallback &&
|
|
9843
9052
|
this._updateDragMaskCallback({
|
|
9844
|
-
operateType:
|
|
9053
|
+
operateType: exports.IOperateType.moveStart,
|
|
9845
9054
|
operateMask: this._operatingMask,
|
|
9846
9055
|
operatedMaskAABBBounds: this._brushMaskAABBBoundsDict
|
|
9847
9056
|
});
|
|
9848
9057
|
}
|
|
9849
9058
|
_drawing(e) {
|
|
9850
9059
|
const pos = this.eventPosToStagePos(e);
|
|
9060
|
+
this._isDrawedBeforeEnd = true;
|
|
9851
9061
|
if (this._cacheDrawPoints.length > 0) {
|
|
9852
9062
|
const lastPos = this._cacheDrawPoints[this._cacheDrawPoints.length - 1];
|
|
9853
9063
|
if (pos.x === lastPos?.x && pos.y === lastPos?.y) {
|
|
@@ -9860,7 +9070,7 @@
|
|
|
9860
9070
|
this._brushMaskAABBBoundsDict[this._operatingMask.name] = this._operatingMask.AABBBounds;
|
|
9861
9071
|
this._updateDragMaskCallback &&
|
|
9862
9072
|
this._updateDragMaskCallback({
|
|
9863
|
-
operateType:
|
|
9073
|
+
operateType: exports.IOperateType.drawing,
|
|
9864
9074
|
operateMask: this._operatingMask,
|
|
9865
9075
|
operatedMaskAABBBounds: this._brushMaskAABBBoundsDict
|
|
9866
9076
|
});
|
|
@@ -9884,7 +9094,7 @@
|
|
|
9884
9094
|
this._brushMaskAABBBoundsDict[this._operatingMask.name] = this._operatingMask.AABBBounds;
|
|
9885
9095
|
this._updateDragMaskCallback &&
|
|
9886
9096
|
this._updateDragMaskCallback({
|
|
9887
|
-
operateType:
|
|
9097
|
+
operateType: exports.IOperateType.moving,
|
|
9888
9098
|
operateMask: this._operatingMask,
|
|
9889
9099
|
operatedMaskAABBBounds: this._brushMaskAABBBoundsDict
|
|
9890
9100
|
});
|
|
@@ -10411,11 +9621,9 @@
|
|
|
10411
9621
|
}
|
|
10412
9622
|
}
|
|
10413
9623
|
|
|
10414
|
-
const version = "0.13.9-alpha.
|
|
9624
|
+
const version = "0.13.9-alpha.6";
|
|
10415
9625
|
|
|
10416
9626
|
exports.AbstractComponent = AbstractComponent;
|
|
10417
|
-
exports.ArcInfo = ArcInfo;
|
|
10418
|
-
exports.ArcLabel = ArcLabel;
|
|
10419
9627
|
exports.BasePlayer = BasePlayer;
|
|
10420
9628
|
exports.Brush = Brush;
|
|
10421
9629
|
exports.CircleAxis = CircleAxis;
|