简体   繁体   English

基于滚动更改内容 position

[英]Changing content based on scroll position

I am trying to build a Showcase component, similar to the one seen here , where the user cycles through different content as they scroll:我正在尝试构建一个Showcase组件,类似于此处看到的组件,用户在滚动时循环浏览不同的内容:

在此处输入图像描述

I'm making the section fixed by using some CSS:我正在使用一些 CSS 修复该部分:

.sticky {
  position: sticky;
}

.top-0 {
  top: 0;
}

Applied to my HTML:应用于我的 HTML:

  <section
    ref={(r) => this.ref = r}
    className={`vh-500 bg-near-white z-max pv6-ns pv3 bg-near-white min-vh-100
    ...
    `}>
    <div className='sticky top-0 vh-100'>

Using the ref on my HTML element, I work out the area where the Showcase component is sticky by seeing the scrollY is relation to the top and bottom of the component itself:使用我的 HTML 元素上的ref ,我通过查看scrollY与组件本身的顶部和底部的关系来计算Showcase组件的粘性区域:

  componentDidMount() {
    if (this.ref) {
      this.setState(
        {
          firstThreshold: this.ref.getBoundingClientRect().top,
          secondThreshold: window.innerHeight * amount
        },
        // tslint:disable-next-line:no-console
        () => console.log(this.state, "state")
      );
    }
    window.addEventListener("scroll", this.handleScroll);
  }

Then in my handleScroll() function I detect when we're scrolling through the Showcase component:然后在我的handleScroll() function 中,我检测到我们何时滚动Showcase组件:

// if we're scrolling through the Showcase component
if (scrollY >= firstThreshold && scrollY <= secondThreshold) {
...
}

Now here's the bit I'm lost with:现在这是我迷失的一点:

I get the height of the Component by multiplying the viewport height with the amount of chapters of a story I want to display in my component:我通过将视口高度乘以要在组件中显示的故事的章节数量来获得组件的高度:

const chapters = [
  {
    content: 'Signs up',
    title: '',
  },
  {
    content: 'Receives request',
    title: '',
  },
  {
    content: 'Gets a shit, rude requests from a person with 0 rating',
    title: '',
  },
  {
    content: 'Blocks them',
    title: '',
  },
  {
    content: 'Gets a nice request from a person who’s rated 5 stars',
    title: '',
  },
  {
    content: 'They agree on terms and accept the request',
    title: '',
  },
  {
    content: 'Time elapses',
    title: '',
  },
  {
    content: 'Thanks them for the time, gives them 5 stars',
    title: '',
  },
]

const amount = chapters.length

And in my handleScroll() function I'm trying to work out which chapter to show as the user scrolls, but I'm not sure how to get there.在我的handleScroll() function 中,我试图确定在用户滚动时显示哪一章,但我不知道如何到达那里。 Here's what I have right now:这是我现在拥有的:

  for (let i = 0; i < amount; i++) {
    // tslint:disable-next-line:no-console
    console.log(i, "i");
    if (scrollY >= (firstThreshold + sectionThreshold) * i) {
      // tslint:disable-next-line:no-console
      console.log(sectionThreshold * i, "sectionThreshold * i");
      this.setState({ currentChapter: i }, () => {
        // tslint:disable-next-line:no-console
        console.log(
          `scrolling inside section: ${this.state.currentChapter}`
        );
      });
    }
  }

What I am trying to achieve:我想要达到的目标:

  • Display each chapter as the user scrolls through the page在用户滚动页面时显示每一章

How do I do this?我该怎么做呢?

Codesandbox代码沙盒

So I managed to figure it out, I think I was just overthinking it before.所以我设法弄清楚了,我想我之前只是想多了。 Basically inside of the handleScroll(e) you get the height of each section:基本上在handleScroll(e)内部,您可以获得每个部分的高度:

First, get the height of the chapters by dividing the chapterAmount by the componentHeight and push the results into an array:首先,通过将chapterAmount除以componentHeight来获取章节的高度,并将结果推送到数组中:

const chapterHeights = [];
for (let index = 0; index < chapters.length; index++) {
  const chapterHeight = componentHeight / chapterAmount;
  chapterHeights.push(chapterHeight * index);
}

Then loop through chapterHeights array and compare it to the scroll position, then set the state of the title and content which will be rendered in the view.然后循环遍历chapterHeights数组并与滚动条 position 进行比较,然后设置将在视图中呈现的titlecontent的 state。

for (let index = 0; index < chapterHeights.length; index++) {
  // console.log(chapterHeights[index], "chapterHeights[index]");
  const chapterLength = chapterHeights[index];

  if (scrollY >= chapterLength) {
    this.setState({
      title: chapters[index].title,
      content: chapters[index].content,
    })
  }
}

Codesandbox here代码沙盒在这里

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM