11521 sujets

JavaScript, DOM et API Web HTML5

Bonjour à tous,

Je suis en train de créer le menu d'un site web que je fais sous WordPress. Le menu que me sort WP est donc fait de blocs qui partagent beaucoup de class communes (dont menu-item) et qui ont chacun un id différent (menu-item-1, menu-item-2, etc).

Le menu est appelé par la fonction WP suivante :

<?php wp_nav_menu( array('menu' => 'Menu', 'before' => '&nbsp;&nbsp;&nbsp;&nbsp;', 'after' => '&nbsp;&nbsp;&nbsp;&nbsp;', 'container' => false )); ?>


Par défaut, chaque élément est affiché avec une opacité de 0.6 :

nav li {
	display: inline;
	opacity: 0.6;
}


Mon but est de passer l'opacité à 1 quand la souris passe dessus, ce que je fais pour l'instant comme ça :

	$("#menu-item-25").mouseenter(function(){
		$("#menu-item-25").fadeTo('fast', 1);
	});
	$("#menu-item-25").mouseleave(function(){
		$("#menu-item-25").fadeTo('fast', 0.6);
	});


Le problèmes, c'est que je suis donc obligé de recopier ce bout de code pour chaque menu-item-xx. Si je désigne dans le JS l'élément de menu de façon plus générique (avec la class menu-item par exemple), tout le menu réagit quand je passe la main sur un seul élément.

Il doit y avoir une façon plus élégante de le faire... Mais laquelle ?

Merci de votre aide.
Modifié par tanpalomino (05 Apr 2015 - 08:40)
Bonjour,

C'est un problème de sélecteurs, et il y a plusieurs façons de procéder dans la sélection sans remettre en cause votre code.

Si j'ai bien compris la structure de votre menu (ce dont je ne suis pas sûr) vous pourriez remplacer vos ids par :
$('nav li')

Mais il vaudrait mieux cibler un id plutôt que 'nav', car cette balise peut être employée ailleurs.

Vous pouvez aussi cibler les id comme vous le faites, mais de manière généraliste, comme ceci :
$('[id^="menu-item-"]')

Ça n'a pas l'air comme ça, mais c'est un sélecteur css2...

Ensuite il faut utiliser $^(this) à l'intérieur de la fonction. Je vous laisse regarder la documentation pour le pourquoi du comment.

Ce qui donne donc, je pense :
$([id^="menu-item-"]").mouseenter(function(){
	$(this).fadeTo('fast', 1);
});
$([id^="menu-item-"]).mouseleave(function(){
	$(this).fadeTo('fast', 0.6);
});

A tester, car je le code en aveugle (sans être sûr de la structure de votre menu).
Modifié par Olivier C (15 Mar 2015 - 07:59)
Bonjour,

Pourquoi ne pas continuer en CSS ce que tu as commencé en CSS, ou n'est-ce pas possible ?

nav li:hover {
        opacity: 1;
}


De plus, est-tu bien sûr de vouloir utiliser la propriété opacity plutôt que des couleurs RGBA ou HSLA ?

L'ennui d'opacity, c'est qu'elle s'applique à tous les éléments descendants de l'élément auquel elle est appliquée, et qu'elle affecte aussi bien le texte de ces éléments que leur background, ce qui n'est peut-être pas souhaitable.

Au lieu d'opacity, tu peux donc utiliser (par exemple) un background-color: rgba(255, 0, 0, 0.6), puis, au survol, un background-color: rgba(255, 0, 0, 1), ou un background-color: hsla(0, 100%, 100%, 0.6) et un background-color: hsla(0, 100%, 100%, 1).

Un lien trouvé en vitesse sur l'intérêt des couleurs HSL/HSLA sur les couleurs RGB/RGBA :

http://iamvdo.me/blog/les-avantages-de-hsl-par-rapport-a-rgb

Bonne continuation.
Modifié par thierry (15 Mar 2015 - 19:46)
thierry a écrit :
Pourquoi ne pas continuer en CSS ce que tu as commencé en CSS, ou n'est-ce pas possible ?

+1.

J'ai tellement foncé tête baissée dans ma réponse que je n'ai même pas pris le temps de considérer l'ensemble du problème. Il vaut bien mieux paramétrer cet effet avec le seul CSS bien sûr, c'est amplement suffisant.
Avec du retard, mes mille mercis. Effectivement, le CSS, c'est plus simple, élégant, léger. Merci pour cette solution.