【问题标题】:Can't get scroll position using `window.scrollY` or `window.pageYOffset`无法使用“window.scrollY”或“window.pageYOffset”获取滚动位置
【发布时间】:2019-07-17 21:08:11
【问题描述】:

问题

我需要获取滚动位置,以便我可以根据它切换工具提示位置。

这是我的工具提示的外观:

但是当我向下滚动时,我希望它向下切换,但现在没有发生期望:向上切换

解决问题的方法

我尝试使用window.scrollYwindow.pageYOffset 来获取滚动位置,但无论我滚动多少,它都会将其记录为0

可能的解决方案

我尝试参考this question 但删除 height: 100% 属性对我不起作用。

代码

import React, { Component } from 'react'
import ReactMarkdown from 'react-markdown'
import styled from 'styled-components'

import glossary from '../Documentation/glossary'

class Tooltip extends Component {
  state = {
    hover: false,
    timeout: null,
    width: 400,
    margin: -70,
    pointMargin: -15
  }

  tooltipWidthEval = () => {
    const markdownBody = document.getElementsByClassName('markdown-body')[0]
    const maxWidth = markdownBody.offsetLeft + markdownBody.clientWidth
    const container = document.getElementsByClassName('tooltip-container')[0]
    const tooltipWidth = container.offsetLeft + this.state.width
    if (tooltipWidth > maxWidth) {
      this.setState({
        margin: -340,
        pointMargin: 260
      })
    } else {
      this.setState({
        margin: -70,
        pointMargin: -15
      })
    }
  }

  hoverIn = () => {
    console.log(window.scrollY)
    if (this.state.interval) {
      clearTimeout(this.state.interval)
      this.setState(
        {
          interval: null,
          hover: true
        },
        this.tooltipWidthEval
      )
    } else {
      this.setState(
        {
          hover: true
        },
        this.tooltipWidthEval
      )
    }
  }

  hoverOut = () => {
    this.setState({
      interval: setTimeout(() => {
        this.setState({
          hover: false
        })
      }, 100)
    })
  }

  render() {
    const { text } = this.props
    let header = ''
    let description = ''
    glossary.contents.forEach(glossaryItem => {
      if (glossaryItem.match.includes(text)) {
        header = glossaryItem.name
        description = glossaryItem.desc
      }
    })
    return (
      <>
        <HighlightedText
          onMouseOver={this.hoverIn}
          onMouseLeave={this.hoverOut}
        >
          {text}
        </HighlightedText>
        {this.state.hover && (
          <TooltipContainer
            className="tooltip-container"
            onMouseOver={this.hoverIn}
            onMouseLeave={this.hoverOut}
          >
            <TooltipText
              margin={this.state.margin}
              width={this.state.width}
              pointMargin={this.state.pointMargin}
            >
              <div className="header">{header}</div>
              <ReactMarkdown source={description} />
            </TooltipText>
          </TooltipContainer>
        )}
      </>
    )
  }
}

const HighlightedText = styled.span`
  border-bottom: 1px black dotted;
`

const TooltipContainer = styled.div`
  position: absolute;
  display: inline-block;
  z-index: 300000000;
  background-color: white;
`

const TooltipText = styled.div`
  padding: 8px 10px;
  border: 1px solid #d1d5da;
  border-radius: 3px;
  background-color: white;
  position: absolute;
  z-index: 1;
  bottom: 90%;
  margin-left: ${props => props.margin || -70}px;
  width: ${props => props.width || 400}px;

  &:after,
  &:before {
    content: '';
    position: absolute;
    top: 100%;
    border-style: solid;
    margin-left: ${props => props.pointMargin || -15}px;
  }

  &:after {
    left: 10%;
    border-width: 10px;
    border-color: white transparent transparent transparent;
  }
  &:before {
    left: 10%;
    border-width: 11px;
    border-color: #d1d5da transparent transparent transparent;
  }

  .header {
    font-size: 1.3em;
    font-weight: bold;
  }
`

export default Tooltip

附:我想如果仅使用 javascript 解决问题,因为该项目不使用jQuery

【问题讨论】:

  • scrollTop 怎么样
  • @super scrollTop 对我也不起作用。
  • scrollTop 应该可以解决问题
  • 如何以及何时在脚本中调用window.scrollY?没有代码就无能为力。另外scrollTop 不是任何规范的一部分(与window.scrollY 不同),所以我完全不建议使用它。
  • 您的屏幕截图表明您实际上并没有滚动整个页面,而是在某处应用了overflow:scroll(或自动)的固定高度元素。因此,您需要读取该元素的滚动偏移量,而不是窗口。

标签: javascript reactjs


【解决方案1】:

如果我做对了,您实际上是在滚动一个容器(例如 div 或类似的东西)而不是页面本身。在这种情况下,您可以使用 scrollTop 获取滚动偏移量,如之前的 cmets 中所述。

但是您需要为正在滚动的元素获取该属性(NOT window.scrollTop)。因此,如果您的内容在 div 中,则需要从该元素中获取 scrollTop 属性。这是一个工作示例,我从元素中获取滚动位置:

const container = document.getElementById('container');

container.addEventListener('scroll', () => {
	console.log(container.scrollTop);
});
#container {
  height: 300px;
  border: 1px solid lightgray;
  overflow-y: auto;
  padding: 10px;
}
#content {
  background: linear-gradient(0deg, rgba(2,0,36,1) 0%, rgba(9,9,121,1) 35%, rgba(0,212,255,1) 100%);
  height: 1000px;
}
<div id="container">
  <div id="content">
  
  </div>
</div>

【讨论】:

  • 感谢您的回答!所以我有一个 div,它有一个名为markdown-body 的类。当我登录document.getElementsByClassName('markdown-body')[0].scrollHeight 时,它显示2855。但是当我滚动它并记录document.getElementsByClassName('markdown-body')[0].scrollTop时,它的值仍然为0。这就是我正在谈论的页面:dvc.org/doc/commands-reference/version
  • 好的,我想通了。我使用document.getElementById('bodybag').scrollTop 来获取滚动位置并且它有效!但我不知道为什么。
  • 好吧,因为window.scrollY 是 body 元素的滚动条(afaik,不要引用我的话)。 [element].scrollTop 为您提供到顶部的滚动偏移量。仅供您参考scrollHeight 为您提供可以滚动的完整高度。如果我的回答是正确的,请接受它:) 否则问我,我会尽力帮助你。顺便说一句漂​​亮的网站
猜你喜欢
  • 1970-01-01
  • 2013-11-06
  • 2021-06-01
  • 1970-01-01
  • 1970-01-01
  • 2019-04-09
  • 1970-01-01
  • 2023-01-22
  • 1970-01-01
相关资源
最近更新 更多