iPhone 上滚动事件内的 SetInterval - 为什么此代码不起作用?

发布于 2024-11-27 01:38:09 字数 901 浏览 1 评论 0原文

请看一下这段代码(顺便说一句,我正在使用 Zepto http://zeptojs.com/)。 正如您所看到的,

var timer = false;

$(window).bind('touchstart touchmove scroll', function (e) {
    if (timer === false) {
        timer = setInterval(function () {
            $('footer').css('top', (this.pageYOffset + this.innerHeight - 40) + 'px');
            console.log('Adjusted...');
        }, 100);
    }
}).bind('touchend', function () {
    clearInterval(timer);
    timer = false;
    console.log('Cleaned it up...');
});

我试图将一个页脚元素固定在 iPhone 屏幕的底部。我知道有一些库可以帮助我们轻松实现这一点,例如 iScroll 4 http://cubiq.org/iscroll-4 ,但我想看看是否可以让它变得更简单。

事实证明,上面的代码不能正常工作。当我实际滚动页面时,由于某种原因 setInterval 不执行,而是似乎堆积在后台以同时运行每个调用。

最后它没有做我想要它做的事情,即为页脚“设置动画”并在滚动期间将其放置在适当的位置,而不仅仅是在滚动之后。有谁知道如何以类似的方式实现这种效果?

谢谢!

Please, take a look at this code (I'm using Zepto http://zeptojs.com/ BTW)...

var timer = false;

$(window).bind('touchstart touchmove scroll', function (e) {
    if (timer === false) {
        timer = setInterval(function () {
            $('footer').css('top', (this.pageYOffset + this.innerHeight - 40) + 'px');
            console.log('Adjusted...');
        }, 100);
    }
}).bind('touchend', function () {
    clearInterval(timer);
    timer = false;
    console.log('Cleaned it up...');
});

As you can see, I have a footer element that I'm trying to keep fixed on the bottom of the iPhone screen. I know that there are libraries that helps us make this quite easily like iScroll 4 http://cubiq.org/iscroll-4, but I was trying to see if I could make it simpler.

It turns out that the code above doesn't work properly. While I'm actually scrolling the page, for some reason setInterval doesn't execute but instead seems to pile up on the background to run every call at the same time.

At the end it doesn't do what I wanted it to do, which is to "animate" the footer and have it in place during scroll not only after. Does anyone has any idea on how such effect could be achieved on some similar manner?

Thanks!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

青春有你 2024-12-04 01:38:09

当您将一个方法传递给 setInterval() (或任何其他函数)时,它将使用错误的 this 值来调用。 JavaScript 参考中详细解释了此问题。

MDC 文档

When you pass a method to setInterval() (or any other function, for that matter), it will be invoked with a wrong this value. This problem is explained in detail in the JavaScript reference.

MDC docs

七分※倦醒 2024-12-04 01:38:09

在外部回调中,this 将是您关心的 DOM 元素,但在 setInterval 回调中,this 将是 window< /代码>。请记住,this 是一个关键字,而不是一个变量,并且它是高度上下文敏感的。

通常的方法是捕获变量中 this 的值,然后使用该变量代替 this

if(timer === false) {
    var self = this; // "_that" is also a common name for the variable.
    timer = setInterval(function () {
        $('footer').css('top', (self.pageYOffset + self.innerHeight - 40) + 'px');
        console.log('Adjusted...');
    }, 100);
}

类似的问题适用于 JavaScript 中的所有回调,请始终确保您了解this 是什么,获取它的值,并在它不是您想要的值时构建一个闭包。

Inside your outer callback, this will be the DOM element you care about, but inside the setInterval callback, this will be window. Keep in mind that this is a keyword, not a variable, and that it is highly context sensitive.

The usual approach is to capture the value of this in a variable and then use that variable instead of this:

if(timer === false) {
    var self = this; // "_that" is also a common name for the variable.
    timer = setInterval(function () {
        $('footer').css('top', (self.pageYOffset + self.innerHeight - 40) + 'px');
        console.log('Adjusted...');
    }, 100);
}

Similar issues apply to all callbacks in JavaScript, always make sure you know what this is and grab its value and build a closure over that value when it won't be what you want.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文