2

I am looking for a way to manage the events. I have a hover function for element A, and click function for element B. I want to disable A`s hover function temporary while the second click of B.

I am looking for a way that not necessary to rewrite the hole function of A inside of B. Something very simply just like "Store and Disable Event, Call Stored Function"

I found some technique like .data('events') and console.log. I tired but failed, or maybe I wrote them in a wrong way.

Please help and advice!

$(A).hover();

$(b).click( 

     if($.hasData($(A)[0])){   // if A has event,
             //STORE all the event A has, and disable
     }else{
            //ENABLE the stored event for A
     }
 );
Brian Tompsett - 汤莱恩
  • 5,753
  • 72
  • 57
  • 129
Micah
  • 4,254
  • 8
  • 30
  • 38
  • Unfortunately I'm afraid that it's not possible to iterate the event handlers of a DOM node from JavaScript. Maybe if you maintain an array where you keep track of the events that you are adding to that node, then you may be able to accomplish this. Is this what you are looking for? – Josep Dec 31 '12 at 02:07
  • Thank you for your reply, so .data('events') is not about this storing event function? – Micah Dec 31 '12 at 02:10
  • I've added a new answer having in consideration the new requirements of this question. – Josep Dec 31 '12 at 03:39

7 Answers7

2

Try this

 var hoverme = function() {
    alert('Hover Event Fired');
};

$('.A').hover(hoverme);

var i = 0;

$('.B').on('click', function(){
    if(i%2 === 0){
        // Unbind event
        $('.A').off('hover');
    }
    else{
        // Else bind the event
        $('.A').hover(hoverme);
    }
    i++;
});

Check Fiddle

Sushanth --
  • 55,259
  • 9
  • 66
  • 105
  • Thank you very much, I have updated my question. I actually want something do not need to install the function again. like call the memory, is it possible? – Micah Dec 31 '12 at 01:51
1

You could try having a variable that is outside the scope of functions a and b, and use that variable to trigger the action to take in function b on function a.

var state;
var a = function() {
    if(!state) {
        state = true; 
        // Add hover action and other prep. I'd create a third function to handle this.
    console.log(state);
};
var b = function() {
    if(state) {
        state = false;
        // Do unbinding of hover code with third function.
    } else {
        state = true;
        // Do whatever else you needed to do
    }
}

Without knowing more about what you're trying to do, I'd try something similar to this.

Jiskiras
  • 84
  • 6
  • thank you very much!, I have updated the code, please help and check. Due to the A function I have is completely separated, I dont want to change the code inside of A. Do I have another solutions? – Micah Dec 31 '12 at 01:42
1

There are provably better ways to do it, but this works fine, on document ready do this:

$("#a")[0].active=false;

$("#b").click(function(){
    $("#a")[0].active = ($("#a")[0].active)==false;
    if($("#a")[0].active){
        $("#a").hover(function(){alert("test")});
    }else{
        $("#a").off('hover');
    }
});

JSFiddle example

Josep
  • 12,926
  • 2
  • 42
  • 45
  • Thank you very much, I have updated my question. I actually want something do not need to install the function again. like call the stored memory, is it possible? – Micah Dec 31 '12 at 01:54
  • Unfortunately I'm afraid that it's not possible to iterate the event handlers of a DOM node from JavaScript. Maybe if you maintain an array where you keep track of the events that you are adding to that node, then you may be able to accomplish this, is this what you are looking for? – Josep Dec 31 '12 at 02:07
  • Thank you for your reply, so .data('events') is not about this storing event function? – Micah Dec 31 '12 at 02:09
1

It sounds like you want to disable the click hover event for A if B is clicked.

$("body").on("hover", "#a", function(){
    alert("hovering");
});

$("#b").click( function(){
    $("body").off("hover", "#a", function() {
        alert("removed hovering");
    });
});

You can use the jQuery off method, have a look at this fiddle. http://jsfiddle.net/nKLwK/1/

sjmdev
  • 159
  • 3
  • Thank you very much, I have updated my question. I actually want something do not need to install the function again. like call the memory, is it possible? – Micah Dec 31 '12 at 01:50
1

Define a function to assign to hover on A element, so in b click, call unbind('hover') for A element and in second click on b element define again a function to hover, like this:

function aHover(eventObject) {
    // Todo when the mouse enter object. You can use $(this) here
}

function aHoverOut(eventObject) {
    // Todo when the mouse leave the object. You can use $(this) here
}

$(A).hover(aHover, aHoverOut);
// ...
$(b).click(function(eventObject) {
    if($.hasData($(A)[0])){   // if A has event,
         $(A).unbind('mouseenter mouseleave'); // This is because not a event hover, jQuery convert the element.hover(hoverIn, hoverOut) in element.bind('mouseenter', hoverIn) and element.bind('mouseleave', hoverOut)
    }else{
        $(A).hover(aHover, aHoverOut);
    }
});
gabrieloliveira
  • 560
  • 3
  • 10
  • Thank you very much, I have updated my question. I actually want something do not need to install the function again. like call the stored memory, is it possible? – Micah Dec 31 '12 at 01:52
1

You can use .off function from jQuery to unbind the hover on your "a" element.

 function hoverA() {
  alert('I\'m on hover');  
}

$('#a').hover( hoverA );

var active = true;

$('#b').on('click', function(){
    if(active){
        $('#a').off('hover');
        active = false;
    } else{
        $('#a').hover(hoverA);
        active = true;
    }
});

Live demo available here : http://codepen.io/joe/pen/wblpC

BenMorel
  • 34,448
  • 50
  • 182
  • 322
Cyril F
  • 1,842
  • 2
  • 19
  • 35
  • Thank you very much, I have updated my question. I actually want something do not need to install the function again. like call the stored memory, is it possible? – Micah Dec 31 '12 at 01:53
1

I think that what you want to do is something like this (example for JQuery 1.7.2):

$("#a").hover(function(){alert("test")});
$("#a")[0].active=true;

$("#b").click(function(){
    if($("#a")[0].active){
        $("#a")[0].storedEvents = [];
        var hoverEvents = $("#a").data("events").mouseover;
        jQuery.each(hoverEvents , function(key,handlerObj) {
            $("#a")[0].storedEvents.push(handlerObj.handler);
        });
        $("#a").off('hover');
    }else{
        for(var i=0;i<$("#a")[0].storedEvents.length;i++){
            $("#a").hover($("#a")[0].storedEvents[i]);
        }
    }
    $("#a")[0].active = ($("#a")[0].active)==false;
});​

JSFiddle Example

But there are a couple of things that you must have in consideration:

  • This will only work if you add the events with JQuery, because JQuery keeps an internal track of the event handlers that have been added.
  • Each version of JQuery handles data("events") differently, that means that this code may not work with other version of JQuery.

I hope that this helps.

EDIT:

data("events") was an internal undocumented data structure used in JQuery 1.6 and JQUery 1.7, but it has been removed in JQuery 1.8. So in JQuery 1.8 the only way to access the events data is through: $._data(element, "events"). But keep in mind the advice from the JQuery documentation: this is not a supported public interface; the actual data structures may change incompatibly from version to version.

Josep
  • 12,926
  • 2
  • 42
  • 45