javascript - 在反应中动态重新定位弹出框时防止闪烁
问题描述
我正在尝试像react-laag文档中显示的示例那样动态地重新定位弹出框。
以下是该示例中发生的情况:滚动时,如果弹出框即将消失,它会移动,以便只要切换弹出框的按钮可见,它就会停留在视口内。
我想使用IntersectionObserverAPI来完成同样的事情,到目前为止,这就是我所做的,
import React, { useState, useEffect, useRef, useLayoutEffect } from "react";
function CustomPopOver(props) {
const menu = useRef(null);
const scrollRef = useRef(null);
const btn = useRef(null);
const [show, setShow] = useState(false);
useEffect(() => {
scrollRef.current.scrollLeft = 300;
scrollRef.current.scrollTop = 300;
}, []);
useLayoutEffect(() => {
if (menu.current) {
createObserver();
}
});
function createObserver() {
let options = {
root: null,
rootMargin: "0px",
threshold: [0.99,0]
};
let observer = new IntersectionObserver(handleIntersect, options);
observer.observe(menu.current);
}
function handleIntersect(entries, observer) {
entries.forEach((entry) => {
if (entry.intersectionRatio < 1) {
if (menu.current) {
const { height: iht, y: iy } = entry.intersectionRect;
const { height: bht, y: by } = entry.boundingClientRect;
if (iht < bht) {
menu.current.style.top =
640 -
(bht + btn.current.getBoundingClientRect().height) -
20 +
"px";
}
if (iy > by) {
menu.current.style.top = 640 + "px";
}
// console.log(entry.intersectionRect, entry.boundingClientRect);
}
}
});
}
return (
<div
ref={scrollRef}
style={{
position: "relative",
height: "600px",
width: "600px",
overflow: "scroll",
backgroundColor: "#f9fafb"
}}
>
<button
ref={btn}
className="btn btn-primary"
style={{
position: "relative",
width: "120px",
top: "600px",
left: "650px"
}}
onClick={() => {
setShow(!show);
}}
>
{!show ? "Show" : "Hide"}
</button>
{show ? (
<ul
ref={menu}
className="menu"
style={{
position: "absolute",
left: "670px",
top: "650px"
}}
>
<li className="popup-list">item 1</li>
<li className="popup-list">item 2</li>
<li className="popup-list">item 3</li>
<li className="popup-list">item 4</li>
</ul>
) : null}
<div style={{ width: "1500px", height: "1500px" }}></div>
</div>
);
}
export default CustomPopOver;
我只介绍了顶部和底部边界的情况。当我在弹出框切换为可见后向上或向下滚动时,它按预期工作。当弹出框到达顶部或底部边界时,它会向上或向下移动。这是我的问题,当在切换弹出框之前向下滚动按钮以使弹出框无法完全显示时,弹出框在从该位置切换时确实会向上移动,但这会产生令人不快的闪烁效果。这可能是因为 intersectionObserver 仅在弹出框位于 DOM 之后才观察到它,因此当弹出框正确定位时闪烁的原因。
我认为这可能是因为我使用了来自useEffect()的观察者,所以我尝试使用useLayoutEffect()进行相同的操作,但结果没有变化。我为上面的代码创建了一个CodeSandBox。我非常感谢有关如何从这里迁移的任何意见。提前致谢!
解决方案
推荐阅读
- javascript - 如何在单击 autocompleteextender 目标搜索文本框时显示所有项目?
- java - 当尝试使用 myBatis 中的单个参数从 View 中检索信息时,结果为 null。使用静态查询时,它可以工作
- java - 无法从共享 Tomcat 类加载器中加载的库中调用本机函数
- ruby-on-rails - 如何排队一个不存在的工人
- mysql - 如何使用 IF 语句为损坏的汽车创建触发器
- matlab - 在 MATLAB 中更改图形的大小以在 LaTeX 中使用它们
- selenium - 如何停止在 Jenkins 上使用 Chrome 插件自动更新 Chrome 驱动程序?
- javascript - 如何从搜索输入中搜索“下一个”字词
- excel - 尝试按自定义顺序排序
- reactjs - 我正在尝试将具有单击功能的组件中的值传递给另一个组件