This is an automated email from the ASF dual-hosted git repository. ovilia pushed a commit to branch main in repository https://gitbox.apache.org/repos/asf/echarts-custom-series.git
commit 6b4128bb8eed8c6909ce24734f04f5598b49e80b Author: Ovilia <[email protected]> AuthorDate: Wed Mar 12 16:12:16 2025 +0800 feat(segmentedDoughnut): render item and bg --- custom-series/segmentedDoughnut/src/index.ts | 105 ++++++++++++++++++++++++++- 1 file changed, 102 insertions(+), 3 deletions(-) diff --git a/custom-series/segmentedDoughnut/src/index.ts b/custom-series/segmentedDoughnut/src/index.ts index cb11088..db3f76b 100644 --- a/custom-series/segmentedDoughnut/src/index.ts +++ b/custom-series/segmentedDoughnut/src/index.ts @@ -17,15 +17,30 @@ * under the License. */ -import echarts from 'echarts'; +import echarts, { zrUtil, number } from 'echarts'; import type { CustomRootElementOption, CustomSeriesRenderItem, } from 'echarts/types/src/chart/custom/CustomSeries.d.ts'; import type { EChartsExtensionInstallRegisters } from 'echarts/src/extension.ts'; +import type { CustomElementOption } from 'echarts/src/chart/custom/CustomSeries.ts'; type SegmentedDoughnutItemPayload = { - + center?: [number | string, number | string]; + radius?: [number | string, number | string]; + segmentCount?: number; + padAngle?: number; + backgroundStyle?: { + color?: string; + borderColor?: string; + borderWidth?: number; + borderType?: string; + opacity?: number; + shadowBlur?: number; + shadowColor?: string; + shadowOffsetX?: number; + shadowOffsetY?: number; + } }; const renderItem = ( @@ -37,10 +52,94 @@ const renderItem = ( const cnt = params.dataInsideLength; if (params.dataIndex === cnt - 1) { } + console.log(params, itemPayload); + + const segmentCount = Math.max(1, itemPayload.segmentCount || 1); + const value = Math.min(segmentCount, api.value(0) as number || 0); + + const center = itemPayload.center || ['50%', '50%']; + const radius = itemPayload.radius || ['50%', '60%']; + const width = api.getWidth(); + const height = api.getHeight(); + const size = Math.min(width, height); + const cx = number.parsePercent(center[0], api.getWidth()); + const cy = number.parsePercent(center[1], api.getHeight()); + const r = number.parsePercent(radius[1], size / 2); + const r0 = number.parsePercent(radius[0], size / 2); + + const padAngle = (zrUtil.retrieve2( + itemPayload.padAngle, + 2 + ) || 0) * Math.PI / 180; + const pieceAngle = (Math.PI * 2 - padAngle * segmentCount) / segmentCount; + + const backgroundGroup = { + type: 'group', + children: [] as CustomElementOption[], + }; + const bgStyle = itemPayload.backgroundStyle || {}; + const backgroundStyle = { + fill: bgStyle.color || 'rgba(180, 180, 180, 0.2)', + stroke: bgStyle.borderColor || 'none', + lineWidth: bgStyle.borderWidth || 0, + lineType: bgStyle.borderType || 'solid', + opacity: bgStyle.opacity || 1, + shadowBlur: bgStyle.shadowBlur || 0, + shadowColor: bgStyle.shadowColor || 'rgba(0, 0, 0, 0)', + shadowOffsetX: bgStyle.shadowOffsetX || 0, + shadowOffsetY: bgStyle.shadowOffsetY || 0, + } + + const itemGroup = { + type: 'group', + children: [] as CustomElementOption[], + }; + const itemStyle = api.style(); + const itemStyleEmphasis = api.styleEmphasis(); + + const startAngle = -Math.PI / 2; + const cornerRadius = (r - r0) / 2; + for (let i = 0; i < segmentCount; ++i) { + const sAngle = startAngle + (pieceAngle + padAngle) * i; + const eAngle = startAngle + (pieceAngle + padAngle) * i + pieceAngle; + backgroundGroup.children.push({ + type: 'sector', + shape: { + cx, + cy, + r0, + r, + cornerRadius, + startAngle: sAngle, + endAngle: eAngle, + clockwise: true, + }, + style: backgroundStyle, + silent: true + }); + + if (i < value) { + itemGroup.children.push({ + type: 'sector', + shape: { + cx, + cy, + r0, + r, + cornerRadius, + startAngle: sAngle, + endAngle: eAngle, + clockwise: true, + }, + style: itemStyle, + styleEmphasis: itemStyleEmphasis + }); + } + } return { type: 'group', - children: [], + children: [backgroundGroup, itemGroup], } as CustomRootElementOption; }; --------------------------------------------------------------------- To unsubscribe, e-mail: [email protected] For additional commands, e-mail: [email protected]
