开发者

Backbone.js detecting scroll event

I have a following view

var FullWindow = Backbone.View.extend({
  initialize: function() {
    _.bindAll(this, 'detect_scroll');
  },

  // bind the events
  events : {
    "scroll" : "detect_scroll"
  },

  detect_scroll: function() {
    console.log('detected');
  }
});

and I initialize it via

var full_window = new FullWindow({el:$('body')});

But I don't think 开发者_开发知识库it's working.

When I change the events to

events : {
  "click" : "detect_scroll"
},

It's fine.

What's wrong?


I don't think that the body element will fire a scroll event unless you explicitly give it a scrollbar by setting set its overflow property to scroll in CSS. From the jQuery docs:

The scroll event is sent to an element when the user scrolls to a different place in the element. It applies to window objects, but also to scrollable frames and elements with the overflow CSS property set to scroll (or auto when the element's explicit height or width is less than the height or width of its contents).

Assuming that you aren't explicitly giving the body element a scrollbar with overflow:scroll and/or a fixed height, the scroll event you want to listen for is probably being fired by the window object, not the body.

I think the best approach here is to drop the Backbone event binding (which is really just a shorthand, and only works on events within the view.el element) and bind directly to the window in initialize():

initialize: function() {
    _.bindAll(this, 'detect_scroll');
    // bind to window
    $(window).scroll(this.detect_scroll);
}


I think the problem is that Backbone uses event delegation to capture events, that is it attaches listeners to the this.$el, and that the scroll event does not bubble up by definition. So, if the scroll event occurs for a child (or descendant) of this.$el, then this event can not be observed at this.$el.

The reason it works for click, is just because click bubbles up.


The scroll bars for body and window are different and you have to make sure you aren't scrolling on the window object. Here is a jsfiddle that illustrates the issue you are probably encountering.

jsfiddle

I'm not for sure if you can change the 'el' to the document.window object, but I don't think that would be a good solution anyway. I would say your best bet is to either use CSS like I've done to help you with the body element or to create a div inside the body and reference that verse the body tag.

Good luck.


I had same issue and this is how I implemented it

var MyView = Backbone.View.extend({
el: $('body'),
initialize: function() {
    $(window).scroll(function() {
        if ($(window).scrollTop()!=0 && $(window).scrollTop() == $(document).height() - $(window).height()) {
            if (mpListModel.get('next')) {
                var res = confirm('Next page?');
                if (res==true) {
                    myView.fetch()
                }
            }
        }
    });
},
events: {},
fetch: function() {
    //fetch stuff
}

}); var myView = MyView();


afterRender: function() {
    // <div id="page-content" class="page-content"> la class qui contiens le scroll
    var $scrollable = this.$el.find('.page-content'); 
    $scrollable.scroll(function() {
           alert("event scroll ");
    });
},
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜