尝试在打字稿

时间:2020-05-30 11:10:31

标签: javascript reactjs typescript

使用React和Typescript,我正在构建一个tabs组件,您可以在其中通过顶部溢出从左到右滚动选项卡链接:滚动集。这可以与触控板一起使用,但是我需要为鼠标用户实现一种方法,以便他们可以像在此Codepen中一样单击和滚动:https://codepen.io/thenutz/full/VwYeYEE 到目前为止,我对位于“内容”标签上方的“链接”标签的代码如下:

<div className='container'>
  <div className='flex-row'
    sx={{ overflow: 'scroll',
    '::-webkit-scrollbar': { display: 'none' },
    display: flex,
    flexDirection: 'row',
    flexWrap: 'no-wrap' }}>
    <div className='tabLinks'
       sx={{display: 'flex', flexDirection: 'row', flexWrap: 'no-wrap'}}>
      {React.Children.map(children, (child, index) => ( //LOOPS THROUGH TAB LINKS HERE ))}
    </div>
  </div>
</div>

tabLinks div是需要同时用触控板和鼠标(单击和拖动)水平滚动的div

我这样做的第一次尝试是使用react useRef为具有ClassName'tabLinks'的div创建一个ref

const ref = React.useRef<HTMLDivElement>(null)

此引用随后传递给tabLinks div,我尝试按照codepen示例实现onMouseDown事件,但在下面遇到此错误:

Property 'offsetLeft' does not exist on type 'RefObject<HTMLDivElement>'

任何帮助将不胜感激。

编辑:

这是我到目前为止尝试过的:

const ref = React.useRef<HTMLDivElement>(null)
  let startX
  let scrollLeft

<div className='container'>
  <div className='flex-row'
    sx={{ overflow: 'scroll',
    '::-webkit-scrollbar': { display: 'none' },
    display: flex,
    flexDirection: 'row',
    flexWrap: 'no-wrap' }}>
        <div
          className='items'
          sx={{
            display: 'flex', 
            flexDirection: 'row',
            flexWrap: 'no-wrap'
           }}
          ref={ref}
          onMouseDown={e => {
            isDown= true
            const offset = ref.current?.offsetLeft || 0
            startX = e.pageX - offset
            scrollLeft = ref.current?.scrollLeft
          }}
          onMouseUp={e => {
            isDown = false;
          }}
          onMouseLeave={e => {
            isDown = false
          }}
          onMouseMove={e => {
            if(!isDown) return;
            e.preventDefault();
            const x = e.pageX - (ref.current?.offsetLeft ?? 0)
            const walk = (x - startX) * 3; //scroll-fast
            ref.scrollLeft = scrollLeft - walk
            console.log(walk)
          }}
        >
      {React.Children.map(children, (child, index) => ( //LOOPS THROUGH TAB LINKS HERE ))}
    </div>
  </div>
</div>

我现在收到此错误

Uncaught TypeError: Cannot add property scrollLeft, object is not extensible
    at onMouseMove (index.tsx:102)
    at HTMLUnknownElement.callCallback (react-dom.development.js:149)
    at Object.invokeGuardedCallbackDev (react-dom.development.js:199)
    at invokeGuardedCallback (react-dom.development.js:256)
    at invokeGuardedCallbackAndCatchFirstError (react-dom.development.js:270)
    at executeDispatch (react-dom.development.js:561)
    at executeDispatchesInOrder (react-dom.development.js:583)
    at executeDispatchesAndRelease (react-dom.development.js:680)
    at executeDispatchesAndReleaseTopLevel (react-dom.development.js:688)
    at forEachAccumulated (react-dom.development.js:662)

1 个答案:

答案 0 :(得分:0)

const offset = ref.current?.offsetLeft ?? 0;

与以下内容相同:

scrollLeft = ref.current?.scrollLeft ?? 0;

当当前引用为空时,这确保两个变量都具有数字值。

您将需要null合并运算符。如果没有可用的,请使用:

const offset = ref.current?.offsetLeft || 0; scrollLeft = ref.current?.scrollLeft || 0;