views:

162

answers:

1

I've been struggling with this for a little while now.. I am using this code to monitor the mousewheel so it can be used for scrolling with a slider that I have.. however, it has an issue where the actions queue up so if you scroll with the mousewheel fast (like anyone would do normally) they build up and it causes buggy behavior.. I know about handling this sort of issue with animation, but not with a mousewheel monitor..

I want to do something like unbind the mousewheel at the start of the action (in this case, to scroll the scrollbar after mousewheel is moved) then rebind it after this, so if user does too many scrolls too fast it just ignores until the initial scroll is completed.. I tried the code below but its not rebinding so I'm not sure what I am doing wrong, any advice is appreciated.

        $("#wavetextcontainer").bind("mousewheel", function(event, delta) {

   //HERE IS WHERE EVENT IS UNBOUND:
     $("#wavetextcontainer").unbind("mousewheel");

        var speed = 10;
        var mySlider = $("#slider");
        var sliderVal = mySlider.slider("option", "value");

        sliderVal += (delta*speed);

        if (sliderVal > mySlider.slider("option", "max")) sliderVal = mySlider.slider("option", "max");
        else if (sliderVal < mySlider.slider("option", "min")) sliderVal = mySlider.slider("option", "min");

        $("#slider").slider("value", sliderVal);

        event.preventDefault();

      // HERE I WANT TO REBIND THE EVENT:
     $("#wavetextcontainer").bind("mousewheel");

});
+3  A: 

You need to store the function were you can reference it, like this:

function myHandler(event, delta) {
     $("#wavetextcontainer").unbind("mousewheel", myHandler);

        var speed = 10;
        var mySlider = $("#slider");
        var sliderVal = mySlider.slider("option", "value");

        sliderVal += (delta*speed);

        if (sliderVal > mySlider.slider("option", "max")) sliderVal = mySlider.slider("option", "max");
        else if (sliderVal < mySlider.slider("option", "min")) sliderVal = mySlider.slider("option", "min");

        $("#slider").slider("value", sliderVal);

        event.preventDefault();

      // HERE I WANT TO REBIND THE EVENT:
     $("#wavetextcontainer").bind("mousewheel", myHandler);    
};

$("#wavetextcontainer").bind("mousewheel", myHandler);

By doing this you can call .bind() later to the same function (you can't reference an anonymous one). You're currently trying to call .bind() without a function to handle anything, which doesn't work. This also has the added advantage of being able to pass that same function reference to .unbind() so it unbinds only that handler, not any mousewheel handler.


Alternatively, do this without un/re-binding, like this:

$("#wavetextcontainer").bind("mousewheel", function (event, delta) {
  event.preventDefault();
  if($.data(this, 'processing')) return; //we're processing, ignore event

  $.data(this, 'processing', true);
  var speed = 10;
  var mySlider = $("#slider");
  var sliderVal = mySlider.slider("option", "value");

  sliderVal += (delta*speed);

  if (sliderVal > mySlider.slider("option", "max")) sliderVal = mySlider.slider("option", "max");
  else if (sliderVal < mySlider.slider("option", "min")) sliderVal = mySlider.slider("option", "min");

  $("#slider").slider("value", sliderVal);
  $.data(this, 'processing', false);
});

This just uses $.data() to store a "we're working" data entry with the element, if anything hits this handler while it's true, it just returns and ignores the event.

Nick Craver
Thank you for the quick answer, will try that..
Rick
I see now.. the anonymous functions are something that I have struggled with a bit since it doesn't exist in the other languages I have used previously.. this helps clear it up for me, thanks
Rick
@Rick - Welcome :) I added another alternative that may simplify things even further for you, give it a try.
Nick Craver
I think the 2nd answer may work better since the unbinding works, as far as the unbind / rebind, but its still giving some weirdness with what seems like a queing of the event
Rick