Find first scrollable parent

后端 未结 8 1403
南方客
南方客 2020-12-02 11:53

I have this situation in which I need to scroll an element into the viewport. The problem is that I don\'t know which element is scrollable. For example, in Portrait the bod

8条回答
  •  暗喜
    暗喜 (楼主)
    2020-12-02 12:53

    the answer with most votes doesn't work in all cases scrollHeight > clientHeight can be true even if there is no scrollbar.

    I found this gist solution https://github.com/olahol/scrollparent.js/blob/master/scrollparent.js#L13

    ^ total credit to https://github.com/olahol who wrote the code.

    Refactored it to es6:

    export const getScrollParent = (node) => {
      const regex = /(auto|scroll)/;
      const parents = (_node, ps) => {
        if (_node.parentNode === null) { return ps; }
        return parents(_node.parentNode, ps.concat([_node]));
      };
    
      const style = (_node, prop) => getComputedStyle(_node, null).getPropertyValue(prop);
      const overflow = _node => style(_node, 'overflow') + style(_node, 'overflow-y') + style(_node, 'overflow-x');
      const scroll = _node => regex.test(overflow(_node));
    
      /* eslint-disable consistent-return */
      const scrollParent = (_node) => {
        if (!(_node instanceof HTMLElement || _node instanceof SVGElement)) {
          return;
        }
    
        const ps = parents(_node.parentNode, []);
    
        for (let i = 0; i < ps.length; i += 1) {
          if (scroll(ps[i])) {
            return ps[i];
          }
        }
    
        return document.scrollingElement || document.documentElement;
      };
    
      return scrollParent(node);
      /* eslint-enable consistent-return */
    };
    

    you can use it like:

    const $yourElement = document.querySelector('.your-class-or-selector');
    getScrollParent($yourElement);
    

提交回复
热议问题