如何滚动一个div在ReactJS中可见? [英] How can I scroll a div to be visible in ReactJS?

查看:226
本文介绍了如何滚动一个div在ReactJS中可见?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个弹出列表,它是一个 div ,包含子 div 的垂直列表。我已经添加了向上/向下键盘导航来更改当前高亮显示的子项。

I have a popup list which is a div that contains a vertical list of child divs. I have added up/down keyboard navigation to change which child is currently highlighted.

现在,如果我按下向下键足够多次,突出显示的项目不再可见。

Right now, if I press the down key enough times, the highlighted item is no longer visible. The same thing also occurs with the up key if the view is scrolled.

React自动滚动子对象的正确方法 div into view?

What is the right way in React to automatically scroll a child div into view?

推荐答案

我假设你有某种列表组件和某种类型的组件。我在一个项目中执行的方式是让项目知道它是否处于活动状态;如果需要,项目将要求列表将其滚动到视图。考虑下面的伪代码:

I assume that you have some sort of List component and some sort of Item component. The way I did it in one project was to let the item know if it was active or not; the item would ask the list to scroll it into view if necessary. Consider the following pseudocode:

class List extends React.Component {
  render() {
    return <div>{this.props.items.map(this.renderItem)}</div>;
  }

  renderItem(item) {
    return <Item key={item.id} item={item}
                 active={item.id === this.props.activeId}
                 scrollIntoView={this.scrollElementIntoViewIfNeeded} />
  }

  scrollElementIntoViewIfNeeded(domNode) {
    var containerDomNode = React.findDOMNode(this);
    // Determine if `domNode` fully fits inside `containerDomNode`.
    // If not, set the container's scrollTop appropriately.
  }
}

class Item extends React.Component {
  render() {
    return <div>something...</div>;
  }

  componentDidMount() {
    this.ensureVisible();
  }

  componentDidUpdate() {
    this.ensureVisible();
  }

  ensureVisible() {
    if (this.props.active) {
      this.props.scrollIntoView(React.findDOMNode(this));
    }
  }
}

使列表负责将项目滚动到视图中(没有项目意识到它甚至在列表中)。要这样做,您可以添加 ref 属性到某个项目,并找到它:

A better solution is probably to make the list responsible for scrolling the item into view (without the item being aware that it's even in a list). To do so, you could add a ref attribute to a certain item and find it with that:

class List extends React.Component {
  render() {
    return <div>{this.props.items.map(this.renderItem)}</div>;
  }

  renderItem(item) {
    var active = item.id === this.props.activeId;
    var props = {
      key: item.id,
      item: item,
      active: active
    };
    if (active) {
      props.ref = "activeItem";
    }
    return <Item {...props} />
  }

  componentDidUpdate(prevProps) {
    // only scroll into view if the active item changed last render
    if (this.props.activeId !== prevProps.activeId) {
      this.ensureActiveItemVisible();
    }
  }

  ensureActiveItemVisible() {
    var itemComponent = this.refs.activeItem;
    if (itemComponent) {
      var domNode = React.findDOMNode(itemComponent);
      this.scrollElementIntoViewIfNeeded(domNode);
    }
  }

  scrollElementIntoViewIfNeeded(domNode) {
    var containerDomNode = React.findDOMNode(this);
    // Determine if `domNode` fully fits inside `containerDomNode`.
    // If not, set the container's scrollTop appropriately.
  }
}

如果你不想做数学确定该项目是否在列表节点中可见,则可以使用 DOM方法 scrollIntoView() 或Webkit特定 scrollIntoViewIfNeeded ,其中有一个polyfill可用,因此您可以在非Webkit浏览器中使用它。

If you don't want to do the math to determine if the item is visible inside the list node, you could use the DOM method scrollIntoView() or the Webkit-specific scrollIntoViewIfNeeded, which has a polyfill available so you can use it in non-Webkit browsers.

这篇关于如何滚动一个div在ReactJS中可见?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆