我有一个Carddiv,如果内容超过其高度,它应该显示滚动。我曾经overflow-y: auto这样做过。我正在尝试使用Select其中的 a ,并且选择菜单应该显示在卡的前面。菜单位置是absolute。
问题是,即使使用position: absolute,菜单也会占用卡内的空间。使其可滚动。
如果我从卡中删除溢出部分,它工作正常,但内容超出了它。我为它创建了一个沙箱:
https://codesandbox.io/s/position-absolute-inside-overflow-y-9kppcy?file=/src/App.js
显示SelectMenu门户内部。
从卡片中删除溢出,将其添加到CardBody元素中,并将选择保留在其外部。
这可能是一个常见问题,但我找不到解决方案。
我认为您使用 React Portal 的解决方案实际上很有意义,但您只需要更多一点技巧来定位元素。
{showMenu &&
createPortal(
<div className="SelectMenu" style={menuStyle}>
I'm the menu.
</div>,
PORTAL_HOST_NODE
)}
Run Code Online (Sandbox Code Playgroud)
它menuStyle只是一个由 返回的计算值useMemo,它只是我们需要应用来定位菜单的 CSS 样式。您想要的是要使用的菜单position: fixed,然后只需使用触发元素(在本例中为“打开选择”按钮)的、 和top属性left来定位该元素。widthheight
为了确保在视口滚动时更新位置,您还需要跟踪该window.scrollY值:
const [scrollY, setScrollY] = useState(window.scrollY);
useEffect(() => {
const onScroll = () => setScrollY(window.scrollY);
window.addEventListener("scroll", onScroll);
return () => {
window.removeEventListener("scroll", onScroll);
};
}, []);
Run Code Online (Sandbox Code Playgroud)
我发现您有一个手动0.5rem偏移量,您希望选择菜单远离其触发元素。我们可以将其存储为 CSS 变量:
{showMenu &&
createPortal(
<div className="SelectMenu" style={menuStyle}>
I'm the menu.
</div>,
PORTAL_HOST_NODE
)}
Run Code Online (Sandbox Code Playgroud)
然后,就像前面提到的那样设置其他代码。一些注意事项:
const [menuTriggerElementRect, setMenuTriggerElementRect] = useState(null);
const toggleMenu = useCallback((e) => {
setShowMenu((old) => !old);
setMenuTriggerElementRect(e.currentTarget.getBoundingClientRect());
}, []);
const menuStyle = useMemo(() => {
if (menuTriggerElementRect === null) return {};
const { top, left, width, height } = menuTriggerElementRect;
return {
transform: `translate(${left}px, calc(${
top + height - scrollY
}px + var(--top-offset)))`,
width: `${width}px`
};
}, [menuTriggerElementRect, scrollY]);
Run Code Online (Sandbox Code Playgroud)
请在此处查看更新的 CodeSandbox 示例:
| 归档时间: |
|
| 查看次数: |
353 次 |
| 最近记录: |