【问题标题】:Check if element is in view with React [duplicate]使用 React 检查元素是否在视图中 [重复]
【发布时间】:2018-11-21 21:19:27
【问题描述】:

请不要标记为重复。它与其他问题类似,但有所不同,因为我问的是哪里将代码放在哪里,而不是如何编写。

我有这段代码,想检测哪个部分在视图中:

export default class Home extends React.Component {
    render() {
        return (
            <React.Fragment>
                <div className="col_first">
                    <Scrollspy id="menu_section"
                               items={['section_1', 'section_2', 'section_3', 'section_4', 'section_5']}
                               currentClassName="is-current" className="c_nav_menu" style={{marginTop: 100}}>
                        <li className="c_nav_menu_item"><a href="#section_1">1</a></li>
                        <li className="c_nav_menu_item"><a href="#section_2">2</a></li>
                        <li className="c_nav_menu_item"><a href="#section_3">3</a></li>
                        <li className="c_nav_menu_item"><a href="#section_4">4</a></li>
                        <li className="c_nav_menu_item"><a href="#section_5">5</a></li>
                    </Scrollspy>

                    <div>
                        <li className="lines_between_1"></li>
                        <li className="lines_between_2"></li>
                        <li className="lines_between_3"></li>
                        <li className="lines_between_4"></li>
                    </div>
                </div>
                <section className="row bg_double">
                    <div className="col-lg-1">
                    </div>
                    <div className="col-lg-11  s_anim">
                        <div className="full_screen" id="section_1">
                            <div className="row full_size">
                                <div className="col-lg-12 center_in_s1">
                                    <h1 className="text_s1 gradient_text">ZdajTo</h1>
                                    <p>korepetycje on-line</p>
                                </div>
                            </div>
                            <div className="icon_border_round">
                                <a href="#section_2"><img src={"/assets/images/ic_arrow_down_gradient.png"}/></a>
                            </div>
                        </div>

                        <div className="full_screen" id="section_2">
                            <div className="row full_size">
                                <div className="col-lg-6 center_in">
                                    <h1> elo elo 320 </h1>
                                </div>
                                <div className="col-lg-6 center_in">
                                    <h1>Przykładowy tekst</h1>
                                </div>
                            </div>
                            <div className="icon_border_round">
                                <a href="#section_3"><img src={"/assets/images/ic_arrow_down_gradient.png"}/></a>
                            </div>
                        </div>

                        <div className="full_screen" id="section_3">
                            <div className="row full_size">
                                <div className="col-lg-6 center_in">
                                    <h1> elo elo 320 </h1>
                                </div>
                                <div className="col-lg-6 center_in">
                                    <h1>Przykładowy tekst</h1>
                                </div>
                            </div>
                            <div className="icon_border_round">
                                <a href="#section_4"><img src={"/assets/images/ic_arrow_down_gradient.png"}/></a>
                            </div>
                        </div>

                        <div className="full_screen" id="section_4">
                            <div className="row full_size">
                                <div className="col-lg-6 center_in">
                                    <h1> elo elo 320 </h1>
                                </div>
                                <div className="col-lg-6 center_in">
                                    <h1>Przykładowy tekst</h1>
                                </div>
                            </div>

                            <div className="icon_border_round">
                                <a href="#section_5"><img src={"/assets/images/ic_arrow_down_gradient.png"}/></a>
                            </div>

                        </div>


                        <div className="full_screen" id="section_5">
                            <div className="row full_size">
                                <div className="col-lg-6 center_in">
                                    <h1> elo elo 320 </h1>
                                </div>
                                <div className="col-lg-6 center_in">
                                    <h1>Przykładowy tekst</h1>
                                </div>
                            </div>

                            <div className="icon_border_round">
                                <a href="#section_1"><img src={"/assets/images/ic_arrow_up_gradient.png"}/></a>
                            </div>
                        </div>
                    </div>
                </section>
            </React.Fragment>
        )
    }
};

我或多或少知道该怎么做。

我发现了这个问题:Check if element is visible on screen

它有一个很好的答案,指向这个小提琴:http://jsfiddle.net/t2L274ty/1/

答案中的代码

window.onscroll = function() {
  wrapper.style.backgroundColor = checkVisible(tester) ? '#4f4' : '#f44';
};

function checkVisible(elm) {
  var rect = elm.getBoundingClientRect();
  var viewHeight = Math.max(document.documentElement.clientHeight, window.innerHeight);
  return !(rect.bottom < 0 || rect.top - viewHeight >= 0);
}

所以我的问题是我应该把这种代码放在哪里?在componentDidMount()render()? React 的做事方式是什么?

【问题讨论】:

  • stackoverflow.com/questions/29725828/…我会以类似于这个问题的答案的方式检查
  • render() 可能会触发多次,而componentDidMount 只会触发一次,所以 Joe 的链接应该对您有所帮助。
  • 虽然,你可能想用 Rx.js 之类的东西来限制滚动事件
  • @Joe,只是出于好奇,您是如何找到链接的问题的?虽然它确实回答了我的问题,但它询问的是不同的东西,我从没想过要像这样搜索它。
  • 我不久前在 knockoutjs 中实现了类似的东西。我搜索“React onscroll”或类似的东西。

标签: javascript reactjs


【解决方案1】:

您可以将您的事件代码放在 componentDidMount 和 componentWillUnmount 中。

componentDidMount() {
   window.addEventListener('scroll', this.onWindowScroll);
}

componentWillUnmount() {
  window.removeEventListener('scroll, this.onWindowScroll);
}

onWindowScroll = debounce(() => { // assuming you're using https://babeljs.io/docs/plugins/transform-class-properties/
  console.log('Debounced scroll event');
}, 100)

如果您只想听一次滚动事件并且您拥有多个此类组件,您可以更聪明一点,但不确定您的用例。

【讨论】:

  • 编辑:没关系有人链接到具有基本相同答案的东西
  • 我仍然会选择最好的,因为问题完全不同。它恰好可以通过相同的答案来解决。
  • 谢谢@alex.iron ;)
猜你喜欢
  • 2014-01-14
  • 2011-06-15
  • 2011-07-12
  • 1970-01-01
  • 2020-04-06
  • 2011-06-03
  • 2014-02-17
相关资源
最近更新 更多