如何解决如何仅在 React 中的特定组件内侦听事件?
我使用这段代码作为基础在 ReactJS 中创建一个可触摸的滑块,以便用户可以用手指更改滑块,它工作正常,但是我只需要在轮播内触发事件({{ 1}}),这里没有发生什么。在这个例子中,事件是从屏幕的任何部分触发的(你可以在蓝色部分尝试)。
有没有办法做到这一点,让事件侦听器仅在特定组件(这里只是一个 div)内工作?
记住,我使用的是 React,这只是一个例子。
track div
const track = document.querySelector('.track');
let initialPosition = null;
let moving = false;
let transform = 0;
const gestureStart = (e) => {
initialPosition = e.pageX;
moving = true;
const transformMatrix = window.getComputedStyle(track).getPropertyValue('transform');
if (transformMatrix !== 'none') {
transform = parseInt(transformMatrix.split(',')[4].trim());
}
}
const gestureMove = (e) => {
if (moving) {
const currentPosition = e.pageX;
const diff = currentPosition - initialPosition;
track.style.transform = `translateX(${transform + diff}px)`;
}
};
const gestureEnd = (e) => {
moving = false;
}
if (window.PointerEvent) {
window.addEventListener('pointerdown',gestureStart);
window.addEventListener('pointermove',gestureMove);
window.addEventListener('pointerup',gestureEnd);
} else {
window.addEventListener('touchdown',gestureStart);
window.addEventListener('touchmove',gestureMove);
window.addEventListener('touchup',gestureEnd);
window.addEventListener('mousedown',gestureStart);
window.addEventListener('mousemove',gestureMove);
window.addEventListener('mouseup',gestureEnd);
}
body {
margin: 0;
}
.carousel {
width: 100vw;
height: 100vh;
background: blue;
position: relative;
overflow: hidden;
}
.carousel .track {
position: absolute;
top: 50px;
left: 10px;
display: inline-flex;
touch-action: none;
}
.carousel .track .card {
width: 100px;
height: 100px;
background: #fff;
border-radius: 3px;
margin-right: 20px;
}
h2 {
color: white;
text-align: center;
}
解决方法
您可以将事件侦听器添加到任何 dom 元素,而不仅仅是 window
。例如,如果你在这里打开一个控制台,你可以这样做:
document.querySelector('#left-sidebar').addEventListener('mousemove',e => console.log(e))
这将仅记录页面左侧导航上的移动。
对于 react 组件,您可以使用 ref
获取对 dom 元素的引用,并使用 useEffect
附加侦听器。示例:
import { useEffect,useRef } from "react";
export default function App() {
const ref = useRef();
useEffect(() => {
ref.current.addEventListener("mousemove",(e) => {
console.log("moving in the blue box",e.x,e.y);
});
},[]);
return (
<div className="App">
<div ref={ref} style={blueBox} />
<div style={orangeBox} />
</div>
);
}
const box = { minWidth: "300px",minHeight: "300px" };
const blueBox = { ...box,backgroundColor: "cornflowerblue" };
const orangeBox = { ...box,backgroundColor: "coral" };
,
在 React 中将事件侦听器附加到特定 DOM 元素的首选和最安全的方法是使用 JSX 专用属性,即 // Find a randomDate between $startDate and $endDate
function randomDate($startDate,$endDate)
{
// Convert to timetamps
$min = strtotime($startDate);
$max = strtotime($endDate);
// Generate random number using above bounds
$val = rand($min,$max);
// Convert back to date
return Carbon::createFromTimestamp($val);
}
dd($this->randomDate('2014-12-10',Carbon::now()->toString()));
、onMouseDown
、onMouseMove
。在您的情况下,React 组件必须如下所示:
onMouseUp
,
您正在将事件添加到窗口,这就是将它们添加到仅跟踪的全部内容
xport default function App() {
const track = React.useRef();
/**
* This is where you must define your listeners:
* onMouseDown,gestureMove,gestureEnd
*
*/
React.useEffect(()=>{
if (window.PointerEvent && track.current) {
track.current.addEventListener('pointerdown',gestureStart);
track.current.addEventListener('pointermove',gestureMove);
track.addEventListener('pointerup',gestureEnd);
} else {
track.addEventListener('touchdown',gestureStart);
track.addEventListener('touchmove',gestureMove);
track.addEventListener('touchup',gestureEnd);
track.addEventListener('mousedown',gestureStart);
track.addEventListener('mousemove',gestureMove);
track.addEventListener('mouseup',gestureEnd);
}
},[]);
return (
<div className="container">
<div className="carousel">
<h2>It shouldn't work here outside of the carousel</h2>
<div
ref={track}
>
<div className="card"></div>
<div className="card"></div>
<div className="card"></div>
<div className="card"></div>
<div className="card"></div>
<div className="card"></div>
<div className="card"></div>
<div className="card"></div>
<div className="card"></div>
<div className="card"></div>
</div>
</div>
</div>
);
}
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。