0

We have a React Virtualized Table with a header row.

One (or more) of the header cells will contain a drop down Componentallowing you to select values to filter the column by.

We have created the Component, and the ValuePanel has position: absolute; to make it float above the other elements on the page.

We included it in the header and it mostly works, except that the HeaderRow has overflow:none; on it.

<div
    class="ReactVirtualized__Table__headerRow table-toplevel-row table-toplevel-header"
    role="row"
    style="height: 100px;overflow: hidden;padding-right: 17px;width: 1920px;"
>

This "chops off" the bottom of the panel showing the values.

Reading up on overflow: none; and position: absolute; it seems that the ValuePanel must have a (positional) parent outside of the HeaderRow.

This can be achieved by either:

  1. Moving the ValuePanel element so it's no longer an ancestor of the HeaderRow.

  2. Having the nearest ancestor of the ValuePanel element with a position of absolute or relative (i.e. it's positional parent) outside of the HeaderRow.

The problem with 1, is that the Component is supposed to be a self-contained and reusable anywhere, so it shouldn't require part of it's HTML to exist outside of itself ... that violates the "self-contained" bit.

The problems with 2 are that we won't always be able to guarantee where the positional parent is in the hierarchy above the ValuePanel unless the positional parent is inside the Component. And the ValuePanel gets it's width from it's positional parent, so if the positional parent is outside of the Component then the width could well be wrong.

We very much want to avoid having to specify a fixed width for the component and/or the ValuePanel. And we want to keep the Component self-contained.

The thought occurred to remove overflow: none; from the HeaderRow, but it's obviously there for a reason. I haven't tested, but I assume getting rid of that would cause issues with header content that, well, overflows. We could replace it with overflow-y: none;overflow-x: hidden;, but again this seems like it's likely to cause issues under certain circumstances.

I had a search around, but I couldn't find any results for it.

Has anyone achieved this before and can provide some insight? Or otherwise has some ideas/advice?

  • I don't have enough time to leave a thorough answer so I'm going to just leave a comment. Essentially I recommend using portals for this. eg check out github.com/tajo/react-portal. Portals allow you to break drop-downs out of the z-index stack so they don't get clipped. – bvaughn Nov 10 '17 at 16:59
  • Thanks for the reply! –  Nov 10 '17 at 17:35

1 Answers1

0

Slightly longer answer now that I'm back at my computer: Check out react-portal.

It lifts content out of the z-index stack (and so avoids clipping problems) while maintaining the visual position of it (top/left), allowing it to render outside of the clipping rect/box of its parent. It's perfect for things like drop-down menus within List or Table.

bvaughn
  • 13,300
  • 45
  • 46
  • I returned to this today and ... I really don't like CSS and it's bloody quirks, like [this](https://stackoverflow.com/q/6421966/310988). But my opinion of CSS won't get the issue fixed! Using an element with an independent parent definitely seems like the correct way to handle this situation, but I'm slightly ashamed to say I went for the easy option, removing "overflow:none;" from the header. We tested that it still renders correctly, which it does, for now. I've added lots of comments and a link to this issue, and I hope to fix it "properly" in the future. –  Nov 13 '17 at 15:46
  • How does exactly maintain the visual position? If I render content in a portal and cell changes position when scrolling, the content does not moves with the cell. – rekans Feb 20 '18 at 23:02
  • I think what you're asking is more of a `react-portal` question. RV gives you hooks to do what is needed- render a cell with a portal, and react to "scroll" events. – bvaughn Feb 21 '18 at 03:47