J'ai un menu déroulant. Maintenant, quand il y a plusieurs niveaux, j'aimerais qu'il ajoute un temps d'attente d'environ 2 secondes, avant qu'il ne disparaisse, afin que l'utilisateur puisse revenir, lorsqu'il brise la .hover()
par erreur.
C'est possible?
mon code pour la diapositive:
$('.icon').hover(function() {
$('li.icon > ul').slideDown('fast');
}, function() {
$('li.icon > ul').slideUp('fast');
});
La seconde fonction attendra 2 secondes (2000 millisecondes) avant d’exécuter:
$('.icon').hover(function() {
clearTimeout($(this).data('timeout'));
$('li.icon > ul').slideDown('fast');
}, function() {
var t = setTimeout(function() {
$('li.icon > ul').slideUp('fast');
}, 2000);
$(this).data('timeout', t);
});
Il efface également le délai d'attente lorsque l'utilisateur survole pour éviter un comportement insensé.
Ce n'est cependant pas une façon très élégante de le faire. Vous devriez probablement vérifier le plugin hoverIntent , conçu pour résoudre ce problème particulier.
personnellement, j'aime bien le plugin "hoverIntent":
http://cherne.net/brian/resources/jquery.hoverIntent.html
de la page: hoverIntent est un plug-in qui tente de déterminer l'intention de l'utilisateur ... comme une boule de cristal, uniquement avec le mouvement de la souris! Il fonctionne comme (et a été dérivé de) le survol intégré de jQuery. Toutefois, au lieu d'appeler immédiatement la fonction onMouseOver, il attend que la souris de l'utilisateur ralentisse suffisamment avant de passer l'appel.
Pourquoi? Pour retarder ou empêcher le déclenchement accidentel d'animations ou d'appels ajax. Les délais d'attente simples fonctionnent pour de petites zones, mais si votre zone cible est grande, elle peut s'exécuter quelle que soit l'intention.
var config = {
sensitivity: 3, // number = sensitivity threshold (must be 1 or higher)
interval: 200, // number = milliseconds for onMouseOver polling interval
over: makeTall, // function = onMouseOver callback (REQUIRED)
timeout: 500, // number = milliseconds delay before onMouseOut
out: makeShort // function = onMouseOut callback (REQUIRED)
};
$("#demo3 li").hoverIntent( config )
Options de configuration
sensibilité: Si la souris parcourt moins de ce nombre de pixels entre les intervalles de scrutation, la fonction "over" est appelée. Avec le seuil de sensibilité minimum de 1, la souris ne doit pas se déplacer entre les intervalles de scrutation. Avec des seuils de sensibilité plus élevés, vous êtes plus susceptible de recevoir un faux positif. Sensibilité par défaut: 7
intervalle: Le nombre de millisecondes que hoverIntent attend entre la lecture/comparaison des coordonnées de la souris. Lorsque la souris de l'utilisateur entre pour la première fois dans l'élément, ses coordonnées sont enregistrées. La fonction "over" peut être appelée le plus rapidement possible après un seul intervalle d'interrogation. Si vous définissez un intervalle d'interrogation plus élevé, le délai avant le premier appel "en attente" possible augmente, mais le délai jusqu'au prochain point de comparaison augmente également. Intervalle par défaut: 100
over: Obligatoire. La fonction que vous souhaitez appeler onMouseOver. Votre fonction reçoit les mêmes objets "this" et "event" que ceux de la méthode de survol de jQuery.
timeout: Délai simple, en millisecondes, avant que la fonction "out" ne soit appelée. Si l'utilisateur survole l'élément avant l'expiration du délai imparti, la fonction "out" ne sera pas appelée (la fonction "over" ne sera pas appelée). Cela vise principalement à protéger les utilisateurs contre les trajectoires de souris mouillées/humaines qui enlèvent temporairement (involontairement) l'utilisateur de l'élément cible ... en lui laissant le temps de revenir. Délai d'attente par défaut: 0
out: Obligatoire. La fonction que vous souhaitez appeler onMouseOut. Votre fonction reçoit les mêmes objets "this" et "event" que ceux de la méthode de survol de jQuery. Notez que hoverIntent n'appellera la fonction "out" que si la fonction "over" a été appelée lors de la même exécution.
$('.icon').on("mouseenter mouseleave","li.icon > ul",function(e){
var $this = $(this);
if (e.type === 'mouseenter') {
clearTimeout( $this.data('timeout') );
$this.slideDown('fast');
}else{ // is mouseleave:
$this.data( 'timeout', setTimeout(function(){
$this.slideUp('fast');
},2000) );
}
});
Ce qui suit empêchera le glissement de se déclencher de 2 secondes:
$('.icon').hover(function() {
$('li.icon > ul').delay(2000).slideDown('fast');
}, function() {
$('li.icon > ul').slideUp('fast');
});
ou vous pouvez simplement utiliser transition: tous les 2 s'installent facilement. Assurez-vous d’ajouter -webkit, -moz et -o pour différents navigateurs.
L'idée générale est d'utiliser setTimeout
, comme suit:
$('.icon').hover(function() {
$('li.icon > ul').slideDown('fast');
}, function() {
setTimeout(function() {
$('li.icon > ul').slideUp('fast');
}, 2000);
});
Mais cela peut faire des choses contre-intuitives si l'utilisateur passe la souris hors, puis la souris à nouveau rapidement - cela ne prend pas en compte la suppression du délai d'attente lorsque l'utilisateur la survole à nouveau. Cela nécessiterait un état supplémentaire.
J'aimerais ajouter à Paolo Bergantino que vous pouvez le faire sans l'attribut de données:
var timer;
$('.icon').hover(function() {
clearTimeout(timer);
$('li.icon > ul').slideDown('fast');
}, function() {
timer = setTimeout(function() {
$('li.icon > ul').slideUp('fast');
}, 2000);
});
Je pense que c'est votre code besoin
jQuery( document ).ready( function($) {
var navTimers = [];
$('.icon').hover(function() {
var id = jQuery.data( this );
var $this = $( this );
navTimers[id] = setTimeout( function() {
$this.children( 'ul' ).slideDown('fast');
navTimers[id] = "";
}, 300 );
},
function () {
var id = jQuery.data( this );
if ( navTimers[id] != "" ) {
clearTimeout( navTimers[id] );
} else {
$( this ).children( "ul" ).slideUp('fast');
}
}
);
});
var timer;
var delay = 200;
$('#hoverelement').hover(function() {
on mouse hover, start a timeout
timer = setTimeout(function() {
Do your stuff here
}, delay);
}, function() {
Do mouse leaving function stuff here
clearTimeout(timer);
});
// edit: insérer le code