Javascript 在react中滚动到视图

Javascript 在react中滚动到视图,javascript,reactjs,scroll,Javascript,Reactjs,Scroll,我正在制作一个简单的react应用程序,其中有两个不同的div 一个带有选择输入和选择列表 <div id="container"> <div className="_2iA8p44d0WZ"> <span className="chip _7ahQImy">Item One</span> <span className="chip _7

我正在制作一个简单的react应用程序,其中有两个不同的
div

一个带有选择输入和选择列表

  <div id="container">
    <div className="_2iA8p44d0WZ">
      <span className="chip _7ahQImy">Item One</span>
      <span className="chip _7ahQImy">Item Two</span>
      <span className="chip _7ahQImy">Item Three</span>
      <span className="chip _7ahQImy">Item Four</span>
      <span className="chip _7ahQImy">Item Five</span>
      <input
        type="text"
        className="searchBox"
        id="search_input"
        placeholder="Select"
        autoComplete="off"
        value=""
      />
    </div>
  </div>
基于,我已将
createRef
添加到所选元素,如

<div key={i} className="selected-element" ref={scrollDiv}>
</div>
将click事件侦听器添加到所有元素,如

  const chipsArray = document.querySelectorAll("#container > div > .chip");
  chipsArray.forEach((elem, index) => {
    elem.addEventListener("click", scrollSmoothHandler);
  });
然后
scrollSmoothHandler
like

const scrollDiv = createRef();

  const scrollSmoothHandler = () => {
    console.log(scrollDiv.current);
    if (scrollDiv.current) {
      scrollDiv.current.scrollIntoView({ behavior: "smooth" });
    }
  };
但这并不像预期的那样有效

要求:

单击
第一个div
中的任何项,则其相关字段集需要在另一个div中平滑滚动

例如: 如果用户单击下面的元素
项目4
。。。第四项

然后,需要将相关字段集滚动到。此处是带有图例的字段集,如
项目4

我认为在react上使用JSDOM查询方法似乎不是一种react实现方式。请任何人帮助我实现在点击所选项目时滚动到相关字段集的结果

问题
  • React.createRef实际上仅在基于类的组件中有效。如果在功能组件主体中使用,则将在每个渲染周期重新创建ref
  • 不要使用DOM查询选择器将
    onClick
    侦听器附加到DOM元素。这些活动在外部进行反应,您需要记住清理它们(即移除它们),以避免内存泄漏。使用React的
    onClick
    prop
  • 映射
    selectedElements
    时,您会将相同的引用附加到每个元素,因此最后一个集合就是您的UI获得的集合
  • 解决方案
  • 在功能组件主体中使用
    React.useRef
    ,存储要附加到要滚动到视图中的每个元素的React ref数组
  • 将scrollSmoothHandler直接连接到每个
    span
    onClick
    属性
  • 从1中创建的ref数组中附加每个ref。要滚动到的每个映射字段集
  • 代码


    对不起,我昨天很晚才看到你的消息,直到不久前,我今天大部分时间都很忙。我已经回答了下面的问题,我认为这是解决您的问题的方法。@DrewReese,再次抱歉打扰您,但现在这里的问题不同了,@DrewReese,请告诉我如何处理上面发布的问题。。我接收的数据是一个数组,我将迭代并显示在每一行上,每一行都有一个保存按钮。。我需要将每一行的数据作为一个对象提交,比如,
    {ContactMode:1}
    …非常感谢Reese,请您查看下面的评论。。我无法修改此行
    onClick={scrollSmoothHandler(I)}
    在我的real ap中,因为我正在使用一个库。因此,一般来说,我需要在加载DOM后添加click事件,但我需要动态地添加它,因为它们不是real app中的硬编码jsx。我只需要在第一个div/span标记中得到帮助,因为在第二节中包含fieldset,你可以修改任何东西,而且没有问题。@Undefined啊,我明白了。让我看看我能想出什么。正如我正确理解的那样,您不能修改
    id=“container”
    div中的跨距和
    scrollSmoothHandler
    的附加,ref创建需要基于DOM中查询的内容进行动态?感谢Reese,最终的要求是,如果我单击任何选定的芯片(关闭图标除外)在该库中,则需要滚动选定项的字段集。。因此,我用该库的简单代码关闭了codesandbox,我无法单独修改第一个div代码。。因此,只有我在问题代码沙盒中使用DOM创建了click事件处理程序。。我很抱歉没有提及。。当然,请仔细检查场景,并让我知道更新的解决方案。。
    const scrollDiv = createRef();
    
      const scrollSmoothHandler = () => {
        console.log(scrollDiv.current);
        if (scrollDiv.current) {
          scrollDiv.current.scrollIntoView({ behavior: "smooth" });
        }
      };
    
    import React, { createRef, useRef } from "react";
    import { render } from "react-dom";
    
    const App = () => {
      const selectedElements = [
        "Item One",
        "Item Two",
        "Item Three",
        "Item Four",
        "Item Five"
      ];
    
      // React ref to store array of refs
      const scrollRefs = useRef([]);
    
      // Populate scrollable refs, only create them once
      // if the selectedElements array length is expected to change there is a workaround
      scrollRefs.current = [...Array(selectedElements.length).keys()].map(
        (_, i) => scrollRefs.current[i] ?? createRef()
      );
    
      // Curried handler to take index and return click handler
      const scrollSmoothHandler = (index) => () => {
        scrollRefs.current[index].current.scrollIntoView({ behavior: "smooth" });
      };
    
      return (
        <div>
          <div id="container">
            <div className="_2iA8p44d0WZ">
              {selectedElements.map((el, i) => (
                <span
                  className="chip _7ahQImy"
                  onClick={scrollSmoothHandler(i)} // <-- pass index to curried handler
                >
                  {el}
                </span>
              ))}
              <input
                type="text"
                className="searchBox"
                id="search_input"
                placeholder="Select"
                autoComplete="off"
                value=""
              />
            </div>
          </div>
          <div>
            {selectedElements.map((item, i) => (
              <div
                key={i}
                className="selected-element"
                ref={scrollRefs.current[i]} // <-- pass scroll ref @ index i
              >
                <fieldset>
                  <legend>{item}</legend>
                </fieldset>
              </div>
            ))}
          </div>
        </div>
      );
    };
    
    const App = () => {
      const selectedElements = [
        "Item One",
        "Item Two",
        "Item Three",
        "Item Four",
        "Item Five"
      ];
    
      const [loaded, setLoaded] = useState(false);
      const scrollRefs = useRef([]);
    
      const scrollSmoothHandler = (index) => () => {
        scrollRefs.current[index].current.scrollIntoView({ behavior: "smooth" });
      };
    
      useEffect(() => {
        const chipsArray = document.querySelectorAll("#container > div > .chip");
    
        if (!loaded) {
          scrollRefs.current = [...Array(chipsArray.length).keys()].map(
            (_, i) => scrollRefs.current[i] ?? createRef()
          );
    
          chipsArray.forEach((elem, index) => {
            elem.addEventListener("click", scrollSmoothHandler(index));
          });
          setLoaded(true);
        }
      }, [loaded]);
    
      return (
        <div>
          <div id="container">
            <div className="_2iA8p44d0WZ">
              <span className="chip _7ahQImy">Item One</span>
              <span className="chip _7ahQImy">Item Two</span>
              <span className="chip _7ahQImy">Item Three</span>
              <span className="chip _7ahQImy">Item Four</span>
              <span className="chip _7ahQImy">Item Five</span>
              <input
                type="text"
                className="searchBox"
                id="search_input"
                placeholder="Select"
                autoComplete="off"
                value=""
              />
            </div>
          </div>
          <div>
            {selectedElements.map((item, i) => (
              <div key={i} className="selected-element" ref={scrollRefs.current[i]}>
                <fieldset>
                  <legend>{item}</legend>
                </fieldset>
              </div>
            ))}
          </div>
        </div>
      );
    };