@cdc/chart 4.25.3-6 → 4.25.5-1

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.
Files changed (84) hide show
  1. package/dist/cdcchart-1a1724a1.es.js +4886 -0
  2. package/dist/cdcchart.js +50347 -75521
  3. package/index.html +1 -0
  4. package/package.json +22 -27
  5. package/src/CdcChart.tsx +1 -22
  6. package/src/CdcChartComponent.tsx +35 -21
  7. package/src/_stories/Chart.CI.stories.tsx +43 -0
  8. package/src/_stories/Chart.DynamicSeries.stories.tsx +68 -49
  9. package/src/_stories/Chart.Legend.Gradient.stories.tsx +6 -0
  10. package/src/_stories/Chart.stories.tsx +7 -16
  11. package/src/_stories/_mock/bar_chart_ci_labels.json +620 -0
  12. package/src/_stories/_mock/barchart_labels.mock.json +612 -0
  13. package/src/_stories/_mock/dynamic_series_bar_config.json +1 -1
  14. package/src/_stories/_mock/dynamic_series_suppression_mock.json +610 -0
  15. package/{examples/private/line-issue.json → src/_stories/_mock/legend_groupBy_mock.json} +46 -69
  16. package/src/components/Annotations/components/AnnotationDropdown.tsx +2 -2
  17. package/src/components/AreaChart/components/AreaChart.jsx +33 -5
  18. package/src/components/Axis/Categorical.Axis.tsx +2 -2
  19. package/src/components/BarChart/components/BarChart.Horizontal.tsx +51 -41
  20. package/src/components/BarChart/components/BarChart.StackedHorizontal.tsx +19 -9
  21. package/src/components/BarChart/components/BarChart.StackedVertical.tsx +20 -9
  22. package/src/components/BarChart/components/BarChart.Vertical.tsx +48 -31
  23. package/src/components/BarChart/components/{BarChart.jsx → BarChart.tsx} +23 -5
  24. package/src/components/BarChart/components/context.tsx +20 -2
  25. package/src/components/BarChart/helpers/getBarHeights.ts +47 -0
  26. package/src/components/BarChart/helpers/index.ts +5 -2
  27. package/src/components/BarChart/helpers/tests/getBarHeights.test.ts +83 -0
  28. package/src/{hooks → components/BarChart/helpers}/useBarChart.ts +11 -47
  29. package/src/components/BoxPlot/BoxPlot.tsx +2 -1
  30. package/src/components/DeviationBar.jsx +2 -1
  31. package/src/components/EditorPanel/EditorPanel.tsx +60 -24
  32. package/src/components/EditorPanel/components/Panels/Panel.General.tsx +34 -34
  33. package/src/components/EditorPanel/components/Panels/Panel.Series.tsx +51 -25
  34. package/src/components/EditorPanel/components/Panels/Panel.Visual.tsx +10 -3
  35. package/src/components/EditorPanel/helpers/updateFieldRankByValue.ts +4 -3
  36. package/src/components/EditorPanel/useEditorPermissions.ts +1 -4
  37. package/src/components/ForestPlot/ForestPlot.tsx +2 -2
  38. package/src/components/Legend/Legend.Component.tsx +69 -58
  39. package/src/components/Legend/Legend.Suppression.tsx +12 -22
  40. package/src/components/Legend/Legend.tsx +3 -1
  41. package/src/components/Legend/LegendGroup/LegendGroup.styles.css +40 -0
  42. package/src/components/Legend/LegendGroup/LegendGroup.tsx +103 -0
  43. package/src/components/Legend/LegendGroup/index.tsx +3 -0
  44. package/src/components/Legend/helpers/createFormatLabels.tsx +28 -0
  45. package/src/components/LineChart/LineChartProps.ts +3 -1
  46. package/src/components/LineChart/components/LineChart.Circle.tsx +77 -119
  47. package/src/components/LineChart/helpers.ts +133 -56
  48. package/src/components/LineChart/index.tsx +125 -60
  49. package/src/components/LinearChart.tsx +74 -115
  50. package/src/components/PairedBarChart.jsx +3 -2
  51. package/src/components/PieChart/PieChart.tsx +71 -91
  52. package/src/components/ScatterPlot/ScatterPlot.jsx +5 -0
  53. package/src/components/Sparkline/components/SparkLine.tsx +80 -18
  54. package/src/components/ZoomBrush.tsx +4 -4
  55. package/src/data/initial-state.js +4 -2
  56. package/src/helpers/countNumOfTicks.ts +1 -1
  57. package/src/helpers/dataHelpers.ts +31 -0
  58. package/src/helpers/sizeHelpers.ts +23 -0
  59. package/src/hooks/useMinMax.ts +21 -28
  60. package/src/hooks/useRightAxis.ts +4 -2
  61. package/src/hooks/useScales.ts +12 -14
  62. package/src/hooks/useTooltip.tsx +204 -203
  63. package/src/index.jsx +2 -2
  64. package/src/scss/main.scss +13 -6
  65. package/src/store/chart.actions.ts +1 -1
  66. package/src/types/ChartConfig.ts +7 -1
  67. package/LICENSE +0 -201
  68. package/examples/private/DEV-8850-2.json +0 -493
  69. package/examples/private/DEV-9822.json +0 -574
  70. package/examples/private/DEV-9840.json +0 -553
  71. package/examples/private/DEV-9850-3.json +0 -461
  72. package/examples/private/chart.json +0 -1084
  73. package/examples/private/ci_formatted.json +0 -202
  74. package/examples/private/ci_issue.json +0 -3016
  75. package/examples/private/completed.json +0 -634
  76. package/examples/private/dem-data-long.csv +0 -20
  77. package/examples/private/dem-data-long.json +0 -36
  78. package/examples/private/demographic_data.csv +0 -157
  79. package/examples/private/demographic_data.json +0 -2654
  80. package/examples/private/demographic_dynamic.json +0 -443
  81. package/examples/private/demographic_standard.json +0 -560
  82. package/examples/private/ehdi.json +0 -29939
  83. package/examples/private/not-loading.json +0 -360
  84. package/examples/private/test.json +0 -493
@@ -17,7 +17,8 @@ const Legend = forwardRef((props, ref) => {
17
17
  transformedData: data,
18
18
  currentViewport,
19
19
  dimensions,
20
- getTextWidth
20
+ getTextWidth,
21
+ transformedData
21
22
  } = useContext(ConfigContext)
22
23
  if (!config.legend) return null
23
24
  // create fn to reverse labels while legend is Bottom. Legend-right , legend-left works by default.
@@ -30,6 +31,7 @@ const Legend = forwardRef((props, ref) => {
30
31
  getTextWidth={getTextWidth}
31
32
  dimensions={dimensions}
32
33
  ref={ref}
34
+ transformedData={transformedData}
33
35
  skipId={props.skipId || 'legend'}
34
36
  config={config}
35
37
  colorScale={colorScale}
@@ -0,0 +1,40 @@
1
+ .legend-container {
2
+ .legend-group {
3
+ font-size: 1rem;
4
+
5
+ line-height: 18px;
6
+ margin-bottom: 0.5rem;
7
+
8
+ .group-item .visx-legend-label {
9
+ font-weight: 400;
10
+ font-size: 0.889rem;
11
+ margin-bottom: 0.5rem;
12
+ }
13
+ .group-label {
14
+ font-weight: 500;
15
+ font-family: Nunito, sans-serif;
16
+ font-size: 1rem;
17
+ }
18
+ }
19
+
20
+ .legend-group.top,
21
+ .legend-group.bottom {
22
+ grid-gap: 10px;
23
+
24
+ &.group-item {
25
+ display: flex;
26
+ flex-direction: column;
27
+ align-items: flex-start;
28
+ }
29
+
30
+ & .inactive {
31
+ opacity: 0.5;
32
+ transition: 0.2s all;
33
+ }
34
+ & .highlighted {
35
+ outline: 1px solid #005ea2;
36
+ outline-offset: 5px;
37
+ border-radius: 1px;
38
+ }
39
+ }
40
+ }
@@ -0,0 +1,103 @@
1
+ import React, { useContext } from 'react'
2
+ import { LegendOrdinal, LegendItem, LegendLabel } from '@visx/legend'
3
+ import LegendShape from '@cdc/core/components/LegendShape'
4
+ import ConfigContext from '../../../ConfigContext'
5
+ import _ from 'lodash'
6
+ import './LegendGroup.styles.css'
7
+
8
+ interface LegendGroup {
9
+ formatLabels: Function
10
+ }
11
+ const LegendGroup = ({ formatLabels }) => {
12
+ const {
13
+ highlight,
14
+ seriesHighlight,
15
+ colorScale,
16
+ transformedData: data,
17
+ config,
18
+ currentViewport
19
+ } = useContext(ConfigContext)
20
+
21
+ const getSubGroups = (data, key: string | undefined) => {
22
+ const uniqueGroups = new Set()
23
+ data.forEach(d => {
24
+ config.series.forEach(series => {
25
+ if (d[key] && d[series.dataKey]) {
26
+ uniqueGroups.add(d[key])
27
+ }
28
+ })
29
+ })
30
+ return Array.from(uniqueGroups) as string[]
31
+ }
32
+
33
+ const groups: string[] = getSubGroups(data, config.legend.groupBy)
34
+
35
+ const classNames = ['legend-group', 'container', config.legend.position, currentViewport, 'row']
36
+
37
+ const gridCol =
38
+ currentViewport === 'xs'
39
+ ? 'col-12'
40
+ : currentViewport === 'sm'
41
+ ? 'col-6'
42
+ : currentViewport === 'md'
43
+ ? 'col-4'
44
+ : 'col-3'
45
+
46
+ const isSigleCol = config.legend.position === 'bottom' || config.legend.position === 'top' ? gridCol : 'col-12'
47
+
48
+ let classNameItem = ['legend-group group-item', isSigleCol]
49
+
50
+ return (
51
+ <div className={classNames.join(' ')}>
52
+ {groups.map(group => {
53
+ return (
54
+ <div className={classNameItem.join(' ')} key={group}>
55
+ <div>
56
+ <p className='legend-group group-label'>{group}</p>
57
+ </div>
58
+ <LegendOrdinal scale={colorScale} itemDirection='row' labelMargin='0 20px 0 0' shapeMargin='0 10px 0'>
59
+ {labels =>
60
+ formatLabels(labels)
61
+ .filter(label => {
62
+ const groupBy = config.legend.groupBy || ''
63
+ return data.some(d => d[groupBy] === group && d[label.text] !== undefined && d[label.text] !== 'NA')
64
+ })
65
+
66
+ .map((label, i) => {
67
+ let className = ['legend-group', 'group-item']
68
+ if (seriesHighlight.length) {
69
+ if (!seriesHighlight.includes(label.datum)) {
70
+ className.push('inactive')
71
+ } else {
72
+ className.push('highlighted')
73
+ }
74
+ }
75
+
76
+ return (
77
+ <LegendItem
78
+ alignItems='start'
79
+ className={className.join(' ')}
80
+ onClick={e => {
81
+ e.preventDefault()
82
+ highlight(label)
83
+ }}
84
+ key={`legend-item-${i}`}
85
+ tabIndex={0}
86
+ >
87
+ <LegendShape shape={config.legend.style === 'boxes' ? 'square' : 'circle'} fill={label.value} />
88
+ <LegendLabel align='left' margin='0'>
89
+ {label.text}
90
+ </LegendLabel>
91
+ </LegendItem>
92
+ )
93
+ })
94
+ }
95
+ </LegendOrdinal>
96
+ </div>
97
+ )
98
+ })}
99
+ </div>
100
+ )
101
+ }
102
+
103
+ export default LegendGroup
@@ -0,0 +1,3 @@
1
+ import LegendGroup from './LegendGroup'
2
+
3
+ export default LegendGroup
@@ -17,8 +17,36 @@ export const createFormatLabels =
17
17
  })
18
18
  : labels
19
19
  const reverseLabels = labels => {
20
+ if (config.series.some(series => series.dynamicCategory)) {
21
+ return orderDynamicLabels(labels)
22
+ }
23
+
20
24
  return config.legend.reverseLabelOrder ? sortVertical(labels).reverse() : sortVertical(labels)
21
25
  }
26
+
27
+ const orderDynamicLabels = labels => {
28
+ // Handle different ordering configurations
29
+ switch (config.legend.order) {
30
+ case 'dataColumn':
31
+ return labels
32
+ case 'asc':
33
+ case 'desc':
34
+ return labels.sort((a, b) => {
35
+ const valA = a.datum || a.text
36
+ const valB = b.datum || b.text
37
+ const numA = parseFloat(valA)
38
+ const numB = parseFloat(valB)
39
+ if (!isNaN(numA) && !isNaN(numB)) {
40
+ return config.legend.order === 'asc' ? numA - numB : numB - numA
41
+ } else {
42
+ return config.legend.order === 'asc' ? valA.localeCompare(valB) : valB.localeCompare(valA)
43
+ }
44
+ })
45
+
46
+ default:
47
+ return labels // Default case to handle any unexpected config.legend.order values
48
+ }
49
+ }
22
50
  const colorCode = config.legend?.colorCode
23
51
  if (visualizationType === 'Deviation Bar') {
24
52
  const [belowColor, aboveColor] = twoColorPalette[config.twoColor.palette]
@@ -29,9 +29,11 @@ export interface StyleProps {
29
29
  handleLineType: Function
30
30
  lineType: string
31
31
  preliminaryData: PreliminaryDataItem[]
32
- seriesKey: 'string'
32
+ seriesKey: string
33
33
  stroke: string
34
34
  strokeWidth: number
35
+ dynamicCategory: string
36
+ originalSeriesKey: string
35
37
  }
36
38
  export interface Style {
37
39
  stroke: string
@@ -1,22 +1,15 @@
1
- import React from 'react'
2
1
  import chroma from 'chroma-js'
3
- import { type ChartConfig } from '../../../types/ChartConfig'
2
+ import { LineChartConfig, type ChartConfig } from '../../../types/ChartConfig'
4
3
  import { GlyphDiamond, GlyphCircle, GlyphSquare, GlyphTriangle, GlyphCross, Glyph as CustomGlyph } from '@visx/glyph'
5
4
  import { Text } from '@visx/text'
6
5
 
7
6
  type LineChartCircleProps = {
8
- circleData: object[]
9
7
  config: ChartConfig
10
8
  data: object[]
11
9
  tableData: object[]
12
10
  d?: Object
13
11
  displayArea: boolean
14
12
  seriesKey: string
15
- tooltipData: {
16
- data: []
17
- tooltipDataX: number
18
- tooltipDataY: number
19
- }
20
13
  xScale: any
21
14
  yScale: any
22
15
  yScaleRight: any
@@ -25,7 +18,14 @@ type LineChartCircleProps = {
25
18
  seriesAxis: string
26
19
  dataIndex: number
27
20
  seriesIndex: number
28
- mode: 'ISOLATED_POINTS' | 'HOVER_POINTS' | 'ALWAYS_SHOW_POINTS'
21
+ mode: 'ISOLATED_POINTS' | 'HOVER_POINTS' | 'ALWAYS_SHOW_POINTS' | 'TOOLTIP_POINTS'
22
+ tooltipPoint: {
23
+ xValue: string | number
24
+ yValue: string | number
25
+ color: string
26
+ }
27
+ handleTooltipMouseOver?: Function
28
+ handleTooltipMouseOff?: Function
29
29
  }
30
30
  const Glyphs = [
31
31
  GlyphCircle,
@@ -46,146 +46,80 @@ const Glyphs = [
46
46
  const LineChartCircle = (props: LineChartCircleProps) => {
47
47
  const {
48
48
  config,
49
- d,
50
- tableData,
49
+ d: pointData,
51
50
  displayArea,
52
51
  seriesKey,
53
- tooltipData,
54
52
  xScale,
55
53
  yScale,
56
54
  colorScale,
57
55
  parseDate,
58
56
  yScaleRight,
59
57
  data,
60
- circleData,
58
+ tooltipPoint,
61
59
  dataIndex,
62
60
  mode,
63
- seriesIndex
61
+ seriesIndex,
62
+ handleTooltipMouseOver,
63
+ handleTooltipMouseOff
64
64
  } = props
65
- const { lineDatapointStyle, visual } = config
65
+ const { isolatedDotsSameSize, lineDatapointStyle, visual } = config as LineChartConfig
66
66
  const filtered = config?.series.filter(s => s.dataKey === seriesKey)?.[0]
67
67
  const Shape =
68
68
  Glyphs[
69
69
  config.visual.lineDatapointSymbol === 'standard' && seriesIndex < visual.maximumShapeAmount ? seriesIndex : 0
70
70
  ]
71
71
  const isReversedTriangle = seriesIndex === 4
72
- const transformShape = (top, left) => `translate(${left}, ${top})${isReversedTriangle ? ' rotate(180)' : ''}`
72
+ const LARGE_DOT_SIZE = 124
73
+ const REGULAR_DOT_SIZE = 55
74
+ const dotSize = isolatedDotsSameSize ? REGULAR_DOT_SIZE : LARGE_DOT_SIZE
73
75
 
74
- // If we're not showing the circle, simply return
75
- const getColor = (
76
- displayArea: boolean,
77
- colorScale: Function,
78
- config: ChartConfig,
79
- hoveredKey: string,
80
- seriesKey: string
81
- ) => {
82
- const seriesLabels = config.runtime.seriesLabels || []
83
- const seriesLabelsAll = config.runtime.seriesLabelsAll || []
84
- let color = displayArea ? colorScale(seriesLabels[hoveredKey] || seriesLabelsAll[seriesIndex]) : ' transparent'
85
- if (config.lineDatapointColor === 'Lighter than Line' && color !== 'transparent' && color) {
86
- color = chroma(color).brighten(1)
87
- }
88
- return color
89
- }
90
76
  const getXPos = hoveredXValue => {
91
77
  return (
92
78
  (config.xAxis.type === 'categorical' ? xScale(hoveredXValue) : xScale(parseDate(hoveredXValue))) +
93
79
  (xScale.bandwidth ? xScale.bandwidth() / 2 : 0)
94
80
  )
95
81
  }
96
- if (mode === 'ALWAYS_SHOW_POINTS' && lineDatapointStyle !== 'hidden') {
97
- if (lineDatapointStyle === 'always show') {
98
- const isMatch = circleData?.some(
99
- cd => cd[config.xAxis.dataKey] === d[config.xAxis.dataKey] && cd[seriesKey] === d[seriesKey]
100
- )
101
82
 
102
- if (
103
- isMatch ||
104
- !filtered ||
105
- (visual.maximumShapeAmount === seriesIndex && visual.lineDatapointSymbol === 'standard')
106
- )
107
- return <></>
108
- const positionLeft = getXPos(d[config.xAxis.dataKey])
109
- const positionTop = filtered.axis === 'Right' ? yScaleRight(d[filtered.dataKey]) : yScale(d[filtered.dataKey])
83
+ const transformShape = (xValue, yValue) => {
84
+ const positionLeft = getXPos(xValue)
85
+ const positionTop = filtered?.axis === 'Right' ? yScaleRight(yValue) : yScale(yValue)
110
86
 
111
- return (
112
- <g transform={transformShape(positionTop, positionLeft)}>
113
- <Shape
114
- opacity={d[seriesKey] ? 1 : 0}
115
- fillOpacity={1}
116
- fill={getColor(displayArea, colorScale, config, seriesKey, seriesKey)}
117
- style={{ filter: 'unset', opacity: 1 }}
118
- />
119
- </g>
120
- )
121
- }
87
+ return `translate(${positionLeft}, ${positionTop})${isReversedTriangle ? ' rotate(180)' : ''}`
122
88
  }
123
89
 
124
- if (mode === 'HOVER_POINTS') {
125
- if (lineDatapointStyle === 'hover') {
126
- if (!tooltipData) return
127
- if (!seriesKey) return
128
- if (!tooltipData.data) return
129
- let hoveredXValue = tooltipData?.data?.[0]?.[1]
130
- if (!hoveredXValue) return
131
-
132
- let hoveredSeriesValue
133
- let hoveredSeriesData = tooltipData.data.filter(d => d[0] === seriesKey)
134
- let hoveredSeriesKey = hoveredSeriesData?.[0]?.[0]
135
- let hoveredSeriesAxis = hoveredSeriesData?.[0]?.[2]
136
- const dynamicSeriesConfig = config.runtime.series.find(s => s.dynamicCategory)
137
- const originalDataKey = dynamicSeriesConfig?.originalDataKey ?? seriesKey
138
-
139
- if (!hoveredSeriesKey) return
140
- hoveredSeriesValue = tableData?.find(d => {
141
- const dynamicCategory = dynamicSeriesConfig?.dynamicCategory
142
- const matchingXValue = d[config.xAxis.dataKey] === hoveredXValue
143
- if (!matchingXValue) return false
144
- if (dynamicCategory) {
145
- const match = d[dynamicCategory] === hoveredSeriesKey
146
- return match
147
- }
148
- return true
149
- })?.[originalDataKey]
150
-
151
- // hoveredSeriesValue = extractNumber(hoveredSeriesValue)
152
- return tooltipData?.data.map((tooltipItem, index) => {
153
- if (isNaN(hoveredSeriesValue)) return <></>
154
- const isMatch = circleData?.some(cd => cd[config.xAxis.dataKey] === hoveredXValue)
155
-
156
- if (
157
- isMatch ||
158
- !hoveredSeriesValue ||
159
- (visual.maximumShapeAmount === seriesIndex && visual.lineDatapointSymbol === 'standard')
160
- ) {
161
- return <></>
162
- }
163
-
164
- const positionTop = hoveredSeriesAxis === 'right' ? yScaleRight(hoveredSeriesValue) : yScale(hoveredSeriesValue)
165
- const positionLeft = getXPos(hoveredXValue)
166
- return (
167
- <g transform={transformShape(positionTop, positionLeft)}>
168
- <Shape
169
- size={55}
170
- opacity={1}
171
- fillOpacity={1}
172
- fill={getColor(displayArea, colorScale, config, hoveredSeriesKey, seriesKey)}
173
- style={{ filter: 'unset', opacity: 1 }}
174
- />
175
- </g>
176
- )
177
- })
90
+ // If we're not showing the circle, simply return
91
+ const getColor = (displayArea: boolean, colorScale: Function, config: ChartConfig, hoveredKey: string) => {
92
+ const seriesLabels = config.runtime.seriesLabels || []
93
+ const seriesLabelsAll = config.runtime.seriesLabelsAll || []
94
+ let color = displayArea ? colorScale(seriesLabels[hoveredKey] || seriesLabelsAll[seriesIndex]) : 'transparent'
95
+ if (config.lineDatapointColor === 'Lighter than Line' && color !== 'transparent' && color) {
96
+ color = chroma(color).brighten(1)
178
97
  }
98
+ return color
179
99
  }
100
+
101
+ if (['ALWAYS_SHOW_POINTS', 'HOVER_POINTS'].includes(mode)) {
102
+ if (!filtered || (visual.maximumShapeAmount === seriesIndex && visual.lineDatapointSymbol === 'standard'))
103
+ return <></>
104
+ return (
105
+ <g
106
+ transform={transformShape(pointData[config.xAxis.dataKey], pointData[filtered?.dataKey])}
107
+ className={`visx-glyph-group${displayArea ? '' : '-hidden'}`}
108
+ data-seriesIndex={seriesIndex}
109
+ >
110
+ <Shape
111
+ fillOpacity={mode === 'ALWAYS_SHOW_POINTS' ? 1 : 0}
112
+ fill={getColor(displayArea, colorScale, config, seriesKey)}
113
+ />
114
+ </g>
115
+ )
116
+ }
117
+
180
118
  if (mode === 'ISOLATED_POINTS') {
181
119
  const drawIsolatedPoints = (currentIndex, seriesKey) => {
182
120
  const currentPoint = data[currentIndex]
183
121
  const previousPoint = data[currentIndex - 1] || {}
184
122
  const nextPoint = data[currentIndex + 1] || {}
185
-
186
- const isMatch = circleData.some(item => item?.data[seriesKey] === currentPoint[seriesKey])
187
- if (isMatch) return false
188
-
189
123
  const isFirstPoint = currentIndex === 0 && !nextPoint[seriesKey]
190
124
  const isLastPoint = currentIndex === data.length - 1 && !previousPoint[seriesKey]
191
125
  const isMiddlePoint =
@@ -197,20 +131,44 @@ const LineChartCircle = (props: LineChartCircleProps) => {
197
131
 
198
132
  return isFirstPoint || isLastPoint || isMiddlePoint
199
133
  }
134
+ const _dataIndex = pointData
135
+ ? data.findIndex(item => item[config.xAxis.dataKey] === pointData[config.xAxis.dataKey])
136
+ : dataIndex
200
137
 
201
- if (drawIsolatedPoints(dataIndex, seriesKey)) {
202
- const positionTop = filtered?.axis === 'Right' ? yScaleRight(d[filtered?.dataKey]) : yScale(d[filtered?.dataKey])
203
- const positionLeft = getXPos(d[config.xAxis?.dataKey])
138
+ if (drawIsolatedPoints(_dataIndex, seriesKey)) {
204
139
  const color = colorScale(config.runtime.seriesLabelsAll[seriesIndex])
205
140
 
206
141
  return (
207
- <g transform={transformShape(positionTop, positionLeft)}>
208
- <Shape size={124} stroke={color} fill={color} />
142
+ <g
143
+ transform={transformShape(pointData[config.xAxis?.dataKey], pointData[filtered?.dataKey])}
144
+ className={`visx-glyph-group${displayArea ? '' : '-hidden'}`}
145
+ data-seriesIndex={seriesIndex}
146
+ >
147
+ <Shape size={dotSize} stroke={color} fill={color} />
209
148
  </g>
210
149
  )
211
150
  }
212
151
  }
213
152
 
153
+ if (mode === 'TOOLTIP_POINTS' && displayArea === true) {
154
+ return (
155
+ <g
156
+ transform={transformShape(tooltipPoint.xValue, tooltipPoint.yValue)}
157
+ className='visx-glyph-circle'
158
+ onMouseOver={e => {
159
+ handleTooltipMouseOver(e)
160
+ if (lineDatapointStyle == 'hover') (e.target as HTMLElement).style.fillOpacity = '1'
161
+ }}
162
+ onMouseOut={e => {
163
+ handleTooltipMouseOff()
164
+ if (lineDatapointStyle == 'hover') (e.target as HTMLElement).style.fillOpacity = '0'
165
+ }}
166
+ >
167
+ <Shape size={55} fill={tooltipPoint.color} fillOpacity={'0'} />
168
+ </g>
169
+ )
170
+ }
171
+
214
172
  return null
215
173
  }
216
174