victory icon indicating copy to clipboard operation
victory copied to clipboard

Tooltips cut off when using VoronoiContainer

Open tylermassey opened this issue 6 years ago • 14 comments

Checklist

  • [✓] This is not a victory-native specific issue. (Issues that only appear in victory-native should be opened here)

  • [✓] I have read through the FAQ and Guides before asking a question

  • [✓] I am using the latest version of Victory

  • [✓] I've searched open issues to make sure I'm not opening a duplicate issue

The Problem

When trying to display multi-point tooltips with VictoryVoronoiContainer, tooltips are cut off if they overflow the SVG borders even if renderInPortal is set to true for VictoryTooltip and overflow: visible is set for the VictoryChart parent.

Below is a GIF showing the problem. This example is a slightly modified (added styles to highlight the overflow problem) version of the "Mutli-point Tooltips with VictoryVoronoiContainer" section of the Victory docs.

GIF

class VoronoiTest extends React.Component<{}, {}> {
    render() {
        return (
            <div
                style={{
                    marginLeft: 200,
                    marginTop: 200,
                    height: 400,
                    width: 600,
                    border: '1px solid #B4B7BA',
                }}
            >
                <VictoryChart
                    style={{ parent: { overflow: 'visible' } }}
                    containerComponent={
                        <VictoryVoronoiContainer
                            voronoiDimension="x"
                            labels={(d: any) => `y: ${d.y}`}
                            labelComponent={
                                <VictoryTooltip
                                    cornerRadius={0}
                                    flyoutStyle={{
                                        stroke: '#C0AB8E',
                                        fill: '#F0EDE5',
                                    }}
                                    width={400}
                                    renderInPortal={true}
                                />
                            }
                        />
                    }
                >
                    <VictoryAxis />
                    <VictoryLine
                        data={[
                            { x: 1, y: 5, l: 'one' },
                            { x: 1.5, y: 5, l: 'one point five' },
                            { x: 2, y: 4, l: 'two' },
                            { x: 3, y: -2, l: 'three' },
                        ]}
                        style={{
                            data: {
                                stroke: '#E94B3C',
                                strokeWidth: (_d: any, active: boolean) =>
                                    active ? 4 : 2,
                            },
                            labels: { fill: '#E94B3C' },
                        }}
                    />

                    <VictoryLine
                        data={[
                            { x: 1, y: -3, l: 'red' },
                            { x: 2, y: 5, l: 'green' },
                            { x: 3, y: 3, l: 'blue' },
                        ]}
                        style={{
                            data: {
                                stroke: '#6F9FD8',
                                strokeWidth: (_d: any, active: boolean) =>
                                    active ? 4 : 2,
                            },
                            labels: { fill: '#6F9FD8' },
                        }}
                    />

                    <VictoryLine
                        data={[
                            { x: 1, y: 5, l: 'cat' },
                            { x: 2, y: -4, l: 'dog' },
                            { x: 3, y: -2, l: 'bird' },
                        ]}
                        style={{
                            data: {
                                stroke: '#92B558',
                                strokeWidth: (_d: any, active: boolean) =>
                                    active ? 4 : 2,
                            },
                            labels: { fill: '#92B558' },
                        }}
                    />
                </VictoryChart>
            </div>
        );
    }
}

tylermassey avatar Apr 25 '18 21:04 tylermassey

can you make your svg size or viewBox bigger to fix this?

I think this is the only way to solve this

sibelius avatar May 08 '18 20:05 sibelius

@sibelius I was hoping to avoid doing that 😬 . It seems like its possible other ways because Victory tooltips in other scenarios can overflow their SVG and still remain visible (see https://github.com/FormidableLabs/victory-core/pull/243)

tylermassey avatar May 09 '18 21:05 tylermassey

you need to change the parent svg then, not sure how

sibelius avatar May 09 '18 21:05 sibelius

In some cases you need to set overflow: visible on the svg element. Until recently, normalize.css would set overflow: hidden on them.

However, that didn't help in my case. The tooltip is still cut off. What puzzles me is as I changing the code for styling and animation reasons, the tooltip some times doesn't cut off, some times does.

chengyin avatar May 09 '18 22:05 chengyin

New discovery: in Chrome when the Inspector is open and docked in the same browser window as the chart, then tooltip gets cutoff. Otherwise it's shown.

chengyin avatar May 09 '18 22:05 chengyin

How would you do that?

<VictoryChart
    style={{
        svg:{
            overflow: "visible"
        }
    }}

Does not work for me. Editing the <svg> in the Inspector to force overflow:visible fixes the cutoff though.

JarLowrey avatar Aug 29 '18 00:08 JarLowrey

Is it possible to add overflow: "visible" somehow to the SVG element ?

mihalikv avatar Sep 26 '19 10:09 mihalikv

I have added a wrapper element and a CSS rule to add the overflow: visible property to the <svg> element. I know it is a workaround, but it works until there is a proper solution.

Using CSS

JSX-Markup

<div className="chart-wrapper">
  <VictoryChart containerComponent={<VictoryVoronoiContainer />}>
    [...]
  </VictoryChart>
</div>

CSS

.chart-wrapper {
  svg {
    overflow: visible;
  }
}

Using styled components

JSX-Markup

<ChartWrapper>
  <VictoryChart containerComponent={<VictoryVoronoiContainer />}>
    [...]
  </VictoryChart>
</ChartWrapper>

Styled div

const ChartWrapper = styled.div`
  svg {
    overflow: visible;
  }
`

denizkberlin avatar Oct 09 '20 11:10 denizkberlin

Closing for now since there is an easy workaround, but PRs are still welcome!

becca-bailey avatar Feb 15 '22 01:02 becca-bailey

this workaround unfortunately doesn't work for victory-native and the real issue which is the lack of component customization is still present. Could someone please reopen this issue?

arthurgeron-work avatar Apr 07 '22 04:04 arthurgeron-work

How do I hide the border on VictoryToolTip component?

noahNewton avatar Jul 13 '22 20:07 noahNewton

We're using tailwind in React Native, and it's not obvious how to set the svg to overflow:visible. Would rather not include styled components just for this use case.

nikkwong avatar Jan 09 '23 21:01 nikkwong

Is there any solution for this? VictoryBar seems to work fine but line is not working properly. for react native

saurabhg138 avatar Apr 27 '23 14:04 saurabhg138

In React Native, the following works for me:

<VictoryGroup
  containerComponent={
    <VictoryVoronoiContainer
      labelComponent={<VictoryTooltip constrainToVisibleArea />}
    />
  }
>
    <VictoryArea />
</VictoryGroup>

The constrainToVisibleArea prop is what make it work.

davidaik avatar Dec 08 '23 06:12 davidaik