diff --git a/packages/demo/examples/01-xy-chart/LineSeriesExample.jsx b/packages/demo/examples/01-xy-chart/LineSeriesExample.jsx index dc510b84..18f90dd3 100644 --- a/packages/demo/examples/01-xy-chart/LineSeriesExample.jsx +++ b/packages/demo/examples/01-xy-chart/LineSeriesExample.jsx @@ -91,7 +91,6 @@ class LineSeriesExample extends React.PureComponent { eventTriggerRefs(triggers) { this.triggers = triggers; - this.triggerTooltip(); } triggerTooltip() { diff --git a/packages/xy-chart/src/axis/XAxis.jsx b/packages/xy-chart/src/axis/XAxis.jsx index f3acca01..3d1837b3 100644 --- a/packages/xy-chart/src/axis/XAxis.jsx +++ b/packages/xy-chart/src/axis/XAxis.jsx @@ -59,9 +59,11 @@ export default class XAxis extends React.PureComponent { if (!scale || !innerHeight) return null; const Axis = orientation === 'bottom' ? AxisBottom : AxisTop; - const tickLabelProps = passedTickLabelProps || - (tickStyles.label && tickStyles.label[orientation]) + let tickLabelProps = passedTickLabelProps; + if (!tickLabelProps) { + tickLabelProps = (tickStyles.label && tickStyles.label[orientation]) ? () => tickStyles.label[orientation] : undefined; + } return ( tickStyles.label[orientation] : undefined; + } return ( { if (isSeries(componentName(Child)) && !Child.props.disableMouseEvents) { const { data, seriesKey } = Child.props; + // @TODO data should be sorted, come up with a way to enforce+cache instead of relying on user const datum = findClosestDatum({ data, @@ -39,8 +41,9 @@ export default function findClosestDatums({ const key = seriesKey || childIndex; // fall back to child index series[key] = datum; const deltaY = Math.abs(yScale(getY(datum)) - mouseY); - closestDatum = deltaY < minDelta ? datum : closestDatum; - minDelta = Math.min(deltaY, minDelta); + closestDatum = deltaY < minDeltaY && deltaX <= minDeltaX ? datum : closestDatum; + minDeltaX = closestDatum === datum ? deltaX : minDeltaX; + minDeltaY = closestDatum === datum ? deltaY : minDeltaY; } } }); diff --git a/packages/xy-chart/test/axis/XAxis.test.js b/packages/xy-chart/test/axis/XAxis.test.js index a2f0c813..ab10bc0f 100644 --- a/packages/xy-chart/test/axis/XAxis.test.js +++ b/packages/xy-chart/test/axis/XAxis.test.js @@ -2,6 +2,7 @@ import React from 'react'; import { shallow } from 'enzyme'; import AxisBottom from '@vx/axis/build/axis/AxisBottom'; import AxisTop from '@vx/axis/build/axis/AxisTop'; +import scaleLinear from '@vx/scale/build/scales/linear'; import { XYChart, XAxis, LineSeries } from '../../src/'; describe('', () => { @@ -83,4 +84,70 @@ describe('', () => { const tick = wrapper.render().find('.vx-axis-tick').first(); expect(tick.find('text').text()).toBe(tickFormat()); }); + + test('tickLabelProps should be passed tick value and indexif passed, and tickStyles.label[orientation] if not', () => { + const props = { + scale: scaleLinear({ range: [0, 100], domain: [0, 100] }), + innerHeight: 100, + }; + + const wrapper = shallow( + ({ + fill: i === 0 ? 'pink' : 'blue', + })} + />, + ); + + const label0 = wrapper.find(AxisBottom) + .dive() // Axis + .dive() // Group + .find('.vx-axis-tick') + .first() + .dive() + .find('text'); + + const label1 = wrapper.find(AxisBottom) + .dive() // Axis + .dive() // Group + .find('.vx-axis-tick') + .last() + .dive() + .find('text'); + + expect(label0.prop('fill')).toBe('pink'); + expect(label1.prop('fill')).toBe('blue'); + }); + + test.only('tickStyles.label[orientation] should be used if tickLabelProps is not passed', () => { + const props = { + scale: scaleLinear({ range: [0, 100], domain: [0, 100] }), + innerHeight: 100, + }; + + const wrapper = shallow( + , + ); + + const label0 = wrapper.find(AxisBottom) + .dive() // Axis + .dive() // Group + .find('.vx-axis-tick') + .first() + .dive() + .find('text'); + + expect(label0.prop('fill')).toBe('skyblue'); + }); }); diff --git a/packages/xy-chart/test/axis/YAxis.test.js b/packages/xy-chart/test/axis/YAxis.test.js index 256d48b8..bb868f5b 100644 --- a/packages/xy-chart/test/axis/YAxis.test.js +++ b/packages/xy-chart/test/axis/YAxis.test.js @@ -2,6 +2,7 @@ import React from 'react'; import { shallow } from 'enzyme'; import AxisLeft from '@vx/axis/build/axis/AxisLeft'; import AxisRight from '@vx/axis/build/axis/AxisRight'; +import scaleLinear from '@vx/scale/build/scales/linear'; import { XYChart, YAxis, LineSeries } from '../../src/'; describe('', () => { @@ -83,4 +84,70 @@ describe('', () => { const tick = wrapper.render().find('.vx-axis-tick').first(); expect(tick.find('text').text()).toBe(tickFormat()); }); + + test('tickLabelProps should be passed tick value and indexif passed, and tickStyles.label[orientation] if not', () => { + const props = { + scale: scaleLinear({ range: [100, 0], domain: [0, 100] }), + innerWidth: 100, + }; + + const wrapper = shallow( + ({ + fill: i === 0 ? 'pink' : 'blue', + })} + />, + ); + + const label0 = wrapper.find(AxisRight) + .dive() // Axis + .dive() // Group + .find('.vx-axis-tick') + .first() + .dive() + .find('text'); + + const label1 = wrapper.find(AxisRight) + .dive() // Axis + .dive() // Group + .find('.vx-axis-tick') + .last() + .dive() + .find('text'); + + expect(label0.prop('fill')).toBe('pink'); + expect(label1.prop('fill')).toBe('blue'); + }); + + test('tickStyles.label[orientation] should be used if tickLabelProps is not passed', () => { + const props = { + scale: scaleLinear({ range: [100, 0], domain: [0, 100] }), + innerWidth: 100, + }; + + const wrapper = shallow( + , + ); + + const label0 = wrapper.find(AxisRight) + .dive() // Axis + .dive() // Group + .find('.vx-axis-tick') + .first() + .dive() + .find('text'); + + expect(label0.prop('fill')).toBe('skyblue'); + }); });