1
votes

I know I can fire any made up event I like using $('#x').trigger('y') but I want create a new event type that can be bound to any DOM element and won't be triggered unless it's listened on.

For example, I want to create:

$('#mydiv').on('wheel', function(e) {
   // do something with e
});

Where "wheel" is my custom event. As soon as "wheel" is bound, it should bind the real event:

$(???).on('mousewheel DOMMouseScroll', function(e) {
    e.delta = null;
    if (e.originalEvent) {
        if (e.originalEvent.wheelDelta) e.delta = e.originalEvent.wheelDelta / -40;
        if (e.originalEvent.deltaY) e.delta = e.originalEvent.deltaY;
        if (e.originalEvent.detail) e.delta = e.originalEvent.detail;
    }
    $(this).trigger('wheel', e);
});

Is there a way to do this?

Note: I don't want to listen on $(document) for any wheel events; it should listen just on the chosen element(s), and only when the event is bound.

1
I don't think you can customize how jQuery interprets the event argument. You should write a plugin that allows you to write $('#mydiv').wheel(), and have this bind both your custom wheel event and the standard mousewheel and DOMMouseScroll events. - Barmar
@Joe: I addressed exactly that in the latest paragraph. Further, I wouldn't need to trigger it on all elements; I could get the target element, but it's still listening on everything, and it could get blocked when it shouldn't have by preventing bubbling. - mpen

1 Answers

1
votes

Here is short plugin which achieves the functionality you want (thanks to Barmar for the idea):

$.fn.wheel = function (callback) {
    return this.each(function () {
        $(this).on('mousewheel DOMMouseScroll', function (e) {
            e.delta = null;
            if (e.originalEvent) {
                if (e.originalEvent.wheelDelta) e.delta = e.originalEvent.wheelDelta / -40;
                if (e.originalEvent.deltaY) e.delta = e.originalEvent.deltaY;
                if (e.originalEvent.detail) e.delta = e.originalEvent.detail;
            }

            if (typeof callback == 'function') {
                callback.call(this, e);
            }
        });
    });
};

$('body').wheel(function (e) {
    console.log(e);
});

It's pretty self explanatory but it basically just binds the mousewheel DOMMouseScroll to every element it's called on. It also passes on the event object as a callback argument.

Here it is working: http://jsfiddle.net/uTbGp/2/ (Mark's fiddle with his improved version of the plugin)