You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@echarts.apache.org by sh...@apache.org on 2021/08/22 06:39:37 UTC

[echarts] 01/01: fix(bar): optimize label distance when using round cap

This is an automated email from the ASF dual-hosted git repository.

shenyi pushed a commit to branch fix-sausage-label-distance
in repository https://gitbox.apache.org/repos/asf/echarts.git

commit 8ee3fed524f6562cda9399688f58a4872bb9629b
Author: pissang <bm...@gmail.com>
AuthorDate: Sun Aug 22 14:38:38 2021 +0800

    fix(bar): optimize label distance when using round cap
---
 src/chart/bar/BarView.ts  |  8 ++++--
 src/label/sectorLabel.ts  | 72 ++++++++++++++++++++++++++++-------------------
 test/bar-polar-label.html |  5 +++-
 3 files changed, 53 insertions(+), 32 deletions(-)

diff --git a/src/chart/bar/BarView.ts b/src/chart/bar/BarView.ts
index b948582..faa4adb 100644
--- a/src/chart/bar/BarView.ts
+++ b/src/chart/bar/BarView.ts
@@ -755,14 +755,18 @@ const elementCreator: {
         const ShapeClass = (!isRadial && roundCap) ? Sausage : Sector;
 
         const sector = new ShapeClass({
-            shape: defaults({clockwise: clockwise}, layout),
+            shape: defaults({
+                clockwise: clockwise
+            }, layout),
             z2: 1
         });
 
         sector.name = 'item';
 
         const positionMap = createPolarPositionMapping(isRadial);
-        sector.calculateTextPosition = createSectorCalculateTextPosition<PolarBarLabelPosition>(positionMap);
+        sector.calculateTextPosition = createSectorCalculateTextPosition(positionMap, {
+            isRoundCap: ShapeClass === Sausage
+        });
 
         // Animation
         if (animationModel) {
diff --git a/src/label/sectorLabel.ts b/src/label/sectorLabel.ts
index ba75e03..6ed74d2 100644
--- a/src/label/sectorLabel.ts
+++ b/src/label/sectorLabel.ts
@@ -24,8 +24,18 @@ export type SectorLike = {
 };
 
 export function createSectorCalculateTextPosition<T extends (string | (number | string)[])>(
-    positionMapping: (seriesLabelPosition: T) => SectorTextPosition
+    positionMapping: (seriesLabelPosition: T) => SectorTextPosition,
+    opts?: {
+        /**
+         * If has round cap on two ends. If so, label should have an extra offset
+         */
+        isRoundCap?: boolean
+    }
 ): ElementCalculateTextPosition {
+
+    opts = opts || {};
+    const isRoundCap = opts.isRoundCap;
+
     return function (
         this: Sector,
         out: TextPositionCalculationResult,
@@ -57,82 +67,86 @@ export function createSectorCalculateTextPosition<T extends (string | (number |
         const startAngle = sector.startAngle;
         const endAngle = sector.endAngle;
         const middleAngle = (startAngle + endAngle) / 2;
+        const extraDist = isRoundCap ? Math.abs(r - r0) / 2 : 0;
+
+        const mathCos = Math.cos;
+        const mathSin = Math.sin;
 
         // base position: top-left
-        let x = cx + r * Math.cos(startAngle);
-        let y = cy + r * Math.sin(startAngle);
+        let x = cx + r * mathCos(startAngle);
+        let y = cy + r * mathSin(startAngle);
 
         let textAlign: TextAlign = 'left';
         let textVerticalAlign: TextVerticalAlign = 'top';
 
         switch (mappedSectorPosition) {
             case 'startArc':
-                x = cx + (r0 - distance) * Math.cos(middleAngle);
-                y = cy + (r0 - distance) * Math.sin(middleAngle);
+                x = cx + (r0 - distance) * mathCos(middleAngle);
+                y = cy + (r0 - distance) * mathSin(middleAngle);
                 textAlign = 'center';
                 textVerticalAlign = 'top';
                 break;
 
             case 'insideStartArc':
-                x = cx + (r0 + distance) * Math.cos(middleAngle);
-                y = cy + (r0 + distance) * Math.sin(middleAngle);
+                x = cx + (r0 + distance) * mathCos(middleAngle);
+                y = cy + (r0 + distance) * mathSin(middleAngle);
                 textAlign = 'center';
                 textVerticalAlign = 'bottom';
                 break;
 
             case 'startAngle':
-                x = cx + middleR * Math.cos(startAngle)
-                    + adjustAngleDistanceX(startAngle, distance, false);
-                y = cy + middleR * Math.sin(startAngle)
-                    + adjustAngleDistanceY(startAngle, distance, false);
+                x = cx + middleR * mathCos(startAngle)
+                    + adjustAngleDistanceX(startAngle, distance + extraDist, false);
+                y = cy + middleR * mathSin(startAngle)
+                    + adjustAngleDistanceY(startAngle, distance + extraDist, false);
                 textAlign = 'right';
                 textVerticalAlign = 'middle';
                 break;
 
             case 'insideStartAngle':
-                x = cx + middleR * Math.cos(startAngle)
-                    + adjustAngleDistanceX(startAngle, -distance, false);
-                y = cy + middleR * Math.sin(startAngle)
-                    + adjustAngleDistanceY(startAngle, -distance, false);
+                x = cx + middleR * mathCos(startAngle)
+                    + adjustAngleDistanceX(startAngle, -distance + extraDist, false);
+                y = cy + middleR * mathSin(startAngle)
+                    + adjustAngleDistanceY(startAngle, -distance + extraDist, false);
                 textAlign = 'left';
                 textVerticalAlign = 'middle';
                 break;
 
             case 'middle':
-                x = cx + middleR * Math.cos(middleAngle);
-                y = cy + middleR * Math.sin(middleAngle);
+                x = cx + middleR * mathCos(middleAngle);
+                y = cy + middleR * mathSin(middleAngle);
                 textAlign = 'center';
                 textVerticalAlign = 'middle';
                 break;
 
             case 'endArc':
-                x = cx + (r + distance) * Math.cos(middleAngle);
-                y = cy + (r + distance) * Math.sin(middleAngle);
+                x = cx + (r + distance) * mathCos(middleAngle);
+                y = cy + (r + distance) * mathSin(middleAngle);
                 textAlign = 'center';
                 textVerticalAlign = 'bottom';
                 break;
 
             case 'insideEndArc':
-                x = cx + (r - distance) * Math.cos(middleAngle);
-                y = cy + (r - distance) * Math.sin(middleAngle);
+                x = cx + (r - distance) * mathCos(middleAngle);
+                y = cy + (r - distance) * mathSin(middleAngle);
                 textAlign = 'center';
                 textVerticalAlign = 'top';
                 break;
 
             case 'endAngle':
-                x = cx + middleR * Math.cos(endAngle)
-                    + adjustAngleDistanceX(endAngle, distance, true);
-                y = cy + middleR * Math.sin(endAngle)
-                    + adjustAngleDistanceY(endAngle, distance, true);
+                x = cx + middleR * mathCos(endAngle)
+                    + adjustAngleDistanceX(endAngle, distance + extraDist, true);
+                y = cy + middleR * mathSin(endAngle)
+                    + adjustAngleDistanceY(endAngle, distance + extraDist, true);
                 textAlign = 'left';
                 textVerticalAlign = 'middle';
                 break;
 
             case 'insideEndAngle':
-                x = cx + middleR * Math.cos(endAngle)
-                    + adjustAngleDistanceX(endAngle, -distance, true);
-                y = cy + middleR * Math.sin(endAngle)
-                    + adjustAngleDistanceY(endAngle, -distance, true);
+                x = cx + middleR * mathCos(endAngle)
+                    + adjustAngleDistanceX(endAngle, -distance + extraDist, true);
+                y = cy + middleR * mathSin(endAngle)
+                    + adjustAngleDistanceY(endAngle, -distance + extraDist, true);
                 textAlign = 'right';
                 textVerticalAlign = 'middle';
                 break;
diff --git a/test/bar-polar-label.html b/test/bar-polar-label.html
index 85b4f9e..0f6a1c5 100644
--- a/test/bar-polar-label.html
+++ b/test/bar-polar-label.html
@@ -27,7 +27,7 @@ under the License.
     </head>
     <body>
         <style>
-            #main0, #main1 {
+            #main0, #main1, #main2 {
                 width: 100%;
                 height: 1200px;
                 margin: 20px 0;
@@ -36,6 +36,7 @@ under the License.
         <h3>Polar bar series label positions</h3>
         <div id="main0"></div>
         <div id="main1"></div>
+        <div id="main2"></div>
         <script>
 
             require(['echarts'], function (echarts) {
@@ -93,6 +94,7 @@ under the License.
                                 ],
                                 coordinateSystem: 'polar',
                                 polarIndex: id,
+                                roundCap: chartIndex === 2,
                                 label: {
                                     show: true,
                                     position: positions[id],
@@ -125,6 +127,7 @@ under the License.
 
                 setChart(0);
                 setChart(1);
+                setChart(2);
             });
         </script>
     </body>

---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@echarts.apache.org
For additional commands, e-mail: commits-help@echarts.apache.org