Skip to content

Commit 136eed6

Browse files
committed
#RI-3722 - No tooltip on hovering on small value chart
1 parent ab19568 commit 136eed6

File tree

2 files changed

+46
-28
lines changed

2 files changed

+46
-28
lines changed

redisinsight/ui/src/components/charts/bar-chart/BarChart.spec.tsx

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,12 @@
1-
import { last } from 'lodash'
1+
import { isEmpty, last, min as minBy, reject } from 'lodash'
22
import React from 'react'
33
import { render, screen, fireEvent, waitFor } from 'uiSrc/utils/test-utils'
44

55
import BarChart, { BarChartData, BarChartDataType } from './BarChart'
66

77
const mockData: BarChartData[] = [
88
{ x: 1, y: 0, xlabel: '', ylabel: '' },
9-
{ x: 5, y: 10, xlabel: '', ylabel: '' },
9+
{ x: 5, y: 0.1, xlabel: '', ylabel: '' },
1010
{ x: 10, y: 20, xlabel: '', ylabel: '' },
1111
{ x: 2, y: 30, xlabel: '', ylabel: '' },
1212
{ x: 30, y: 40, xlabel: '', ylabel: '' },
@@ -39,6 +39,18 @@ describe('BarChart', () => {
3939
})
4040
})
4141

42+
it('should render smallest bar with min height', () => {
43+
const minBarHeight = 5
44+
const smallestBar = minBy(
45+
reject([...mockData], ({ y }) => !y),
46+
({ y }, i) => y,
47+
) ?? { x: 0, y: 0 }
48+
49+
render(<BarChart data={mockData} minBarHeight={minBarHeight} />)
50+
expect(screen.getByTestId(`bar-${smallestBar.x}-${smallestBar.y}`)).toBeInTheDocument()
51+
expect(screen.getByTestId(`bar-${smallestBar.x}-${smallestBar.y}`)).toHaveAttribute('height', `${minBarHeight}`)
52+
})
53+
4254
it('should render tooltip and content inside', async () => {
4355
render(<BarChart data={mockData} name="test" />)
4456

redisinsight/ui/src/components/charts/bar-chart/BarChart.tsx

Lines changed: 32 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@ interface IProps {
2626
data?: BarChartData[]
2727
dataType?: BarChartDataType
2828
barWidth?: number
29+
minBarHeight?: number
2930
width?: number
3031
height?: number
3132
yCountTicks?: number
@@ -45,6 +46,7 @@ interface IProps {
4546
export const DEFAULT_MULTIPLIER_GRID = 5
4647
export const DEFAULT_Y_TICKS = 8
4748
export const DEFAULT_BAR_WIDTH = 40
49+
export const MIN_BAR_HEIGHT = 3
4850
let cleanedData: IDatum[] = []
4951

5052
const BarChart = (props: IProps) => {
@@ -55,6 +57,7 @@ const BarChart = (props: IProps) => {
5557
height: propHeight = 0,
5658
barWidth = DEFAULT_BAR_WIDTH,
5759
yCountTicks = DEFAULT_Y_TICKS,
60+
minBarHeight = MIN_BAR_HEIGHT,
5861
dataType,
5962
classNames,
6063
divideLastColumn,
@@ -135,32 +138,6 @@ const BarChart = (props: IProps) => {
135138
.domain([0, maxY || 0])
136139
.range([height, 0])
137140

138-
// bars
139-
svg
140-
.selectAll('.bar')
141-
.data(cleanedData)
142-
.enter()
143-
.append('rect')
144-
.attr('class', cx(styles.bar, classNames?.bar))
145-
.attr('x', (d) => xAxis(d.index))
146-
.attr('width', barWidth)
147-
.attr('y', (d) => yAxis(d.y))
148-
.attr('height', (d) => height - yAxis(d.y))
149-
.attr('data-testid', (d) => `bar-${d.x}-${d.y}`)
150-
.on('mousemove mouseenter', (event, d) => {
151-
tooltip.transition()
152-
.duration(200)
153-
.style('opacity', 1)
154-
tooltip.html(tooltipValidation(d.y, d.index))
155-
.style('left', `${event.pageX + 16}px`)
156-
.style('top', `${event.pageY + 16}px`)
157-
.attr('data-testid', 'bar-tooltip')
158-
})
159-
.on('mouseout', () => {
160-
tooltip.transition()
161-
.style('opacity', 0)
162-
})
163-
164141
// divider for last column
165142
if (divideLastColumn) {
166143
svg.append('line')
@@ -210,6 +187,35 @@ const BarChart = (props: IProps) => {
210187
yTicks.selectAll('text')
211188
.attr('x', -10)
212189

190+
// bars
191+
svg
192+
.selectAll('.bar')
193+
.data(cleanedData)
194+
.enter()
195+
.append('rect')
196+
.attr('class', cx(styles.bar, classNames?.bar))
197+
.attr('x', (d) => xAxis(d.index))
198+
.attr('width', barWidth)
199+
// set minimal height for Bar
200+
.attr('y', (d) => (d.y && height - yAxis(d.y) < minBarHeight ? height - minBarHeight : yAxis(d.y)))
201+
.attr('height', (d) => {
202+
const initialHeight = height - yAxis(d.y)
203+
return initialHeight && initialHeight < minBarHeight ? minBarHeight : initialHeight
204+
})
205+
.attr('data-testid', (d) => `bar-${d.x}-${d.y}`)
206+
.on('mouseenter mousemove', (event, d) => {
207+
tooltip
208+
.style('opacity', 1)
209+
tooltip.html(tooltipValidation(d.y, d.index))
210+
.style('left', `${event.pageX + 16}px`)
211+
.style('top', `${event.pageY + 16}px`)
212+
.attr('data-testid', 'bar-tooltip')
213+
})
214+
.on('mouseleave', () => {
215+
tooltip
216+
.style('opacity', 0)
217+
})
218+
213219
return () => {
214220
tooltip.remove()
215221
}

0 commit comments

Comments
 (0)