React:使用可滚动元素更改状态和范围输入值

React: change state and range input value using a scrollable element

这里我有一个包含范围输入值的状态:

const [currentRange, setCurrentRange = useState({currentValue: 0})
<input
 type="range"
 id="scroll-range"
 value={currentRange.currentValue}
 onChange={dragHandler}
 ></input>

这里我有一个水平滚动的可滚动元素:

import ScrollContainer from "react-indiana-drag-scroll"; 
// I'm using this library to implement scroll on drag

const Slider = () => {
return(
<ScrollContainer
      id="scrolling-container"
      vertical={false}
      style={{
        display: "grid",
        gridTemplateColumns: "repeat(100, 0.25em)",
        width: "4em",
        height: "50%",
        alignItems: "center",
        cursor: "grab",
        marginBottom: "1rem",
      }}
    >
    <div>1</div>
    <div>2</div>
    <div>3</div>
    <div>4</div>
    <div>5</div>
    <div>6</div>
   
    </ScrollContainer>
  );
};

我想要的是在滚动 ScrollContainer 时更改范围输入值。我该如何实施?

<ScrollContainer /> 组件有一个 onScroll 道具,您可以向其添加一个 handleScroll 函数,该函数将使用 scrollHeightscrollTop 元素属性计算它滚动了多少。

  1. 使用 useRef 挂钩获取对组件的引用。

  2. 将 onScroll 属性添加到 ScrollContainer 并附加一个处理函数,您将在其中进行计算。

  3. handleScroll 函数将进行主要计算。它首先必须确定 ScrollContainer 相对于其 scrollHeight.

    滚动了多少
  4. 确保 <input/>minmax 值设置为 0100

...
  const dragScrollElement = useRef(null); // 1.

  // 3. 
  const handleScroll = () => {
    const scrollableHeight =
    dragScrollElement.current.container.current.scrollHeight -
    dragScrollElement.current.container.current.offsetHeight;
    const amountScrolled = dragScrollElement.current.scrollTop;
    const rangeValue = (amountScrolled / scrollableHeight) * 100; // To make the value between 0 and 100.
    setCurrentRange({ currentValue: rangeValue });
  };

  return(
    ...
    <ScrollContainer
      ref={dragScrollElement}
      onScroll={handleScroll} // 2.
      id="scrolling-container"
      vertical={false}
      style={{
        display: "grid",
        gridTemplateColumns: "repeat(100, 0.25em)",
        width: "4em",
        height: "50%",
        alignItems: "center",
        cursor: "grab",
        marginBottom: "1rem",
      }}
    >
    ...
  );
...

<!-- 5. -->
<input
 type="range"
 id="scroll-range"
 value={currentRange.currentValue}
 min={0}
 max={100}
 readOnly 
 ></input>

实际工作示例来自沙箱,因此请根据需要随意更改。

Codesandbox