【问题标题】:media query for vertical scroll垂直滚动的媒体查询
【发布时间】:2013-05-31 03:18:56
【问题描述】:

有没有办法通过媒体查询检测垂直滚动距离?

似乎媒体查询是围绕检测媒体而设计的(令人震惊的是:P),因此诸如浏览器高度之类的东西是可测试的,但不具体是页面向下滚动了多远。

如果不可能,但您知道 JS(不是 jQuery)中的一种方式,请随时发布!

【问题讨论】:

    标签: css media-queries


    【解决方案1】:

    我不相信 CSS 媒体查询可以做到这一点,但我知道滚动高度可以在 JavaScript 中使用 window.pageYOffset 找到。如果您想在用户每次在页面上向上或向下滚动时通过函数运行此值,您可以执行类似的操作

    window.onscroll = function() {
        scrollFunctionHere(window.pageYOffset);
    };
    

    或者只是:

    window.onscroll = scrollFunctionHere;
    

    如果函数本身检查了window.pageYOffset 的值。

    有关如何在 JavaScript 中高效使用 window.onscroll 的更多建议,请参阅 mynameistechno's answer

    关于效率的重要说明:如果在回调中执行任何非平凡的操作,则每次发出滚动事件时运行一个函数可能会破坏 CPU 周期。相反,最好只允许回调每秒运行这么多次。这被称为“去抖动”。

    下面的简单去抖动滚动事件处理程序代码。注意文本是如何每 250 毫秒在“HELLO”和“WORLD”之间切换的,而不是每帧:

    var outputTo = document.querySelector(".output");
    var timeout_debounce;
    
    window.addEventListener("scroll", debounce);
    
    function debounce(event) {
        if(timeout_debounce) {
            return;
        }
    
        timeout_debounce = setTimeout(clearDebounce, 250);
    // Pass the event to the actual callback.
        actualCallback(event);
    }
    
    function clearDebounce() {
        timeout_debounce = null;
    }
    
    function actualCallback(event) {
    // Perform your logic here with no CPU hogging.
      outputTo.innerText = outputTo.innerText === "HELLO"
        ? "WORLD"
        : "HELLO";
    }
    p {
      padding: 40vh;
      margin: 20vh;
      background: blue;
      color: white;
    }
    <p class="output">Test!</p>

    【讨论】:

    • 我修复了答案中的大写错误,并添加了一些参考您的答案的内容,以获取有关使用 window.onscroll 的更多信息。只是为了记录,我选择不在我的答案中添加更多信息,因为我假设想要使用 JavaScript 技术的开发人员会在 window.onscroll 上进行自己的研究。 @mynameistechno
    【解决方案2】:

    首先,接受的答案不起作用。

    正确的名字是

    window.onscroll
    

    而不是

    window.onScroll
    

    https://developer.mozilla.org/en-US/docs/Web/API/window.onscroll

    其次,这是非常低效的,因为该函数的调用方式超出了它的需要,并且可能使页面在滚动时变得迟缓。来自 John Resig:

    http://ejohn.org/blog/learning-from-twitter/

    最好使用每 150 毫秒左右运行一次的计时器 - 类似于:

    var scrolled = false;
    
    window.onscroll = function() {
      scrolled = true;
    }
    
    setInterval(function(){
      if (scrolled) {
        scrolled = false;
        // scrollFunction()
      }
    }, 150);
    

    【讨论】:

    • 作为对已接受答案的评论,这可能会更好。
    • 计时器是一个非常脆弱和糟糕的想法来实现它。如果您出于某种原因在滚动上进行一些计算量非常大的计算,您会想要使用 Date()、performance.now(),甚至是一个计数器来检查经过的时间。然而.onscroll设计 被覆盖,在滚动上更改一个简单的 CSS 属性根本不会滞后
    • 无论onscroll 是否被设计 覆盖,它都是一个事件处理程序,并且滚动已知 会触发很多事件,因此在处理程序中做很多事情是一个坏主意(而不是因为覆盖的优点)。在相关的说明中,例如,iOS 不会触发 scroll 事件,直到用户 完成 滚动。如果我没记错的话,直到最近的版本。
    • 而不是有一个计时器,正如@Downgoat 所说的那样脆弱,最好使用事件处理程序onscroll 来触发许多事件。解决这些“太多事件”的方法是检查自上次执行 onscroll 函数以来经过了多少毫秒,并且仅当该毫秒值大于某个特定间隔值时才再次执行。
    【解决方案3】:

    在 Jquery 中你有方法 .scrollTop()

    http://api.jquery.com/scrolltop/

    这个例子用窗口滚动来做一个 div 滚动。

    $(window).scroll(function(){            
            $("div").css("margin-top", $(window).scrollTop())   
    });
    

    【讨论】:

      【解决方案4】:

      这是解决方案的一种方法。f https://jsfiddle.net/oravckzx/1/

      $(window).scroll(function(){
          $('.post-sidebar').each(function(){
      var ScrollTopVar = $(window).scrollTop();
           
          var OffsetTopVar = $(this).offset().top;
              var OuterHeightVar = $(this).outerHeight();
               var PositionVar = OffsetTopVar-(OuterHeightVar*1.1);
              if (ScrollTopVar >= PositionVar) {
                  $('.hide') .css('background','green').css('font-size','12px')
                  $('.post-sidebar') .css('background','orange').css('font-size','12px')
                  $('.hide') .css('background','green').css('font-size','12px')
                  $('.post-sidebar') .css('background','gray').css('font-size','12px')
                  document.getElementById("demo3").innerHTML = ScrollTopVar;
                  document.getElementById("demo2").innerHTML = PositionVar;
              
              }else {
              $('.hide') .css('background','yellow').css('background','yellow')
              $('.hide') .css('background','yellow')
              $('.hide') .css('background','yellow')
              document.getElementById("demo").innerHTML = ScrollTopVar;
              document.getElementById("demo12").innerHTML = ScrollTopVar;
              document.getElementById("demo13").innerHTML = ScrollTopVar;
              document.getElementById("demo14").innerHTML = ScrollTopVar;
              document.getElementById("demo2").innerHTML = PositionVar;
              }
          });
      });
      .red {height:100px;
      background:red;margin-bottom:20px;}
      
      .hide {height:50px;background:blue;margin-bottom:20px;}
      
      .post-sidebar {
      height:50px;
      background:yellow;
      margin-bottom:20px;
      box-sizing: border-box;
      display: block;
      font: normal 700 34px Lato, sans-serif;
      padding-right: 20px;
      width: 452px;
      }
      .p {
        font: normal 700 14px Lato, sans-serif;
      }
      <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
      <div class="red"><p id="demo"></div>
      <div class="red"></div><p id="demo12">ok
      <div class="red"><p id="demo13">ok</div>
      
      
      <div class="post-sidebar"><p id="demo2"></p><p>lizard</p></div>
      
      <div class="hide"><p id="demo2">If reaches to chosen class in html, saves value of ScrollTopVar (as distance from top) to separate variable as eventually PositionVar (which is the distance from top to the chosen class in html, - and that specific distance depends of device which is doing it), and then does certain action if ScrollTopVar value matches or exceeds PositionVar value. Else sets it back if needed, if not including Else it remains as it once met the value. <p id="demo3"></div>
      
      
      
      
      <div class="red"><p id="demo14">ok</div>
      <div class="red"><p id="demo"></div>
      <div class="red"><p id="demo"></div>

      【讨论】:

      • fiddle和sn-p完全一样吗?
      猜你喜欢
      • 2023-04-08
      • 2014-06-04
      • 2011-12-30
      • 2019-08-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-11-13
      相关资源
      最近更新 更多