You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何将Vanilla JS滚动交互代码转换为React实现?

问题:将鼠标按下滚动交互的Vanilla JS代码转换为React

我需要把一段实现鼠标按下滚动交互的原生JS代码转成React版本。已经知道用React的onMouseDown绑定事件,但不知道怎么实现原生代码里scrollerMiddle.classList.add('scrolling')的DOM类名操作功能。以下是对应的原生代码和我尝试的React片段,原生代码可正常运行,求解决方案:

原生HTML

<div class="middle">
    <img src="images/vr-iootz.jpg" draggable="false"/>
</div>

<div class="scroller scroller-middle">
    <svg class="scroller__thumb" xmlns="http://www.w3.org/2000/svg" width="100" height="100" viewBox="0 0 100 100">
        <polygon points="0 50 37 68 37 32 0 50" style="fill:rgb(24,24,62)"/>
        <polygon points="100 50 64 32 64 68 100 50" style="fill:rgb(24,24,62)"/>
    </svg>
</div>

原生JS代码

scrollerMiddle.addEventListener('mousedown',function(){
  active = "middle";
  scrollerMiddle.classList.add('scrolling');
});

我尝试的React代码片段

<div className="scroller" onMouseDown={ () => {
    active = "middle"
}}>
  <svg
    className="scroller__thumb"
    xmlns="http://www.w3.org/2000/svg"
    width="100"
    height="100"
    viewBox="0 0 100 100"
  >
    <polygon points="0 50 37 68 37 32 0 50" fill="rgb(24,24,62)" />
    <polygon points="100 50 64 32 64 68 100 50" fill="rgb(24,24,62)" />
  </svg>
</div>

解决方案

React不推荐直接操作DOM,而是通过状态管理控制元素类名和交互状态,以下是完整实现思路:

  1. 使用useState钩子管理滚动状态与激活区域
  2. 在onMouseDown事件中更新状态,动态拼接类名
  3. 监听全局mouseup事件,鼠标松开时重置滚动状态(避免一直保留scrolling类)

完整代码示例(函数组件):

import { useState, useEffect } from 'react';

function ScrollSection() {
  // 管理滚动状态:是否处于滚动中
  const [isScrolling, setIsScrolling] = useState(false);
  // 管理激活的区域
  const [activeSection, setActiveSection] = useState('');

  // 鼠标按下事件处理
  const handleMouseDown = () => {
    setActiveSection('middle');
    setIsScrolling(true);
  };

  // 鼠标松开时重置状态
  const handleMouseUp = () => {
    setIsScrolling(false);
  };

  // 全局监听mouseup事件,组件挂载时添加,卸载时移除
  useEffect(() => {
    window.addEventListener('mouseup', handleMouseUp);
    return () => {
      window.removeEventListener('mouseup', handleMouseUp);
    };
  }, []);

  return (
    <>
      <div className="middle">
        <img src="images/vr-iootz.jpg" draggable="false" />
      </div>

      {/* 动态拼接类名:当isScrolling为true时添加scrolling类 */}
      <div 
        className={`scroller scroller-middle ${isScrolling ? 'scrolling' : ''}`}
        onMouseDown={handleMouseDown}
      >
        <svg
          className="scroller__thumb"
          xmlns="http://www.w3.org/2000/svg"
          width="100"
          height="100"
          viewBox="0 0 100 100"
        >
          <polygon points="0 50 37 68 37 32 0 50" fill="rgb(24,24,62)" />
          <polygon points="100 50 64 32 64 68 100 50" fill="rgb(24,24,62)" />
        </svg>
      </div>
    </>
  );
}

export default ScrollSection;

关键说明:

  • 用useState定义isScrolling状态,替代原生classList.add操作,通过模板字符串动态拼接类名
  • 把全局变量active改成组件内状态activeSection,符合React状态管理规范
  • 添加useEffect监听全局mouseup事件,确保鼠标松开后移除scrolling类,还原初始状态

内容的提问来源于stack exchange,提问作者Kiki-ko

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.12 14:22:41