11548 sujets

JavaScript, DOM et API Web HTML5

Bonjour,

J'ai repris l'exemple du précedent post en simplifiant :


function showmenu() {
if (!document.getElementsByTagName) return false;
var dls = document.getElementsByTagName("dl");
for (var a=0;a<dls.length;a++) {
  var dds = dls[a].getElementsByTagName("dd");
  for (var b=0;b<dds.length;b++) {
      dds[b].style.display='none';
      if (dds[b].previousSibling.tagName == "dt"){
        dds[b].previousSibling.addEventListener('click', function() {dds[b].style.display='block';}, false);
      }
    }
  }
}
window.onload=showmenu;


Jusqu'à display:none; c'est ok par contre comment passer les dd en display:block; quand on clique sur l'élément dt ?

Pour rappel code html :


<dl id="menu">

		<dt><a href="#">Menu 1</a></dt>
			
		<dt >Menu 2</dt>
			<dd>
				<ul>
					<li><a href="#">Sous-Menu 2.1</a></li>
					<li><a href="#">Sous-Menu 2.2</a></li>

					<li><a href="#">Sous-Menu 2.3</a></li>
				</ul>
			</dd>	

		<dt>Menu 3</dt>
			<dd>
				<ul>
					<li><a href="#">Sous-Menu 3.1</a></li>
					<li><a href="#">Sous-Menu 3.1</a></li>

					<li><a href="#">Sous-Menu 3.1</a></li>
					<li><a href="#">Sous-Menu 3.1</a></li>
					<li><a href="#">Sous-Menu 3.1</a></li>
					<li><a href="#">Sous-Menu 3.1</a></li>
				</ul>
			</dd>
  <dt>Menu 4</dt>
			<dd>
				<ul>
					<li><a href="#">Sous-Menu 4.1</a></li>
					<li><a href="#">Sous-Menu 4.1</a></li>
				</ul>
			</dd>

	
</dl>
[/b][/b][/b][/b]
Modifié par EricLB (09 Sep 2006 - 00:22)
Modérateur
Salut,

Désolé, je manque un peu de temps pour me plonger sur ton code mais si çà t'intéresse, tu peux faire çà en repartant de la structure de ce menu (une fois le code JS supprimé de la partie XHTML) :

var alsa =
{
	addLoadEvent: function(func)
	{
		var oldonload = window.onload;
		if( typeof window.onload != 'function' )
		{
			window.onload = func;
		}
		else
		{
			window.onload = function()
			{
				oldonload();
				func();
			}
		}
	},
	display: function()
	{
		if( !document.getElementById || !document.getElementsByTagName ) return false;
		var oDl = document.getElementById('menu').getElementsByTagName('dl'),
			oList = document.getElementById('menu').getElementsByTagName('dd'),
			iI = oDl.length - 1,
			iJ = oList.length - 1;
		for( iJ; iJ>=0; iJ-- )
		{
			oList[iJ].style.display = 'none';
		}
		for( iI; iI>=0; iI-- )
		{
			if( oDl[iI].getElementsByTagName('dd')[0] )
			{
				oDl[iI].onmouseover = function()
				{
					this.getElementsByTagName('dd')[0].style.display = 'block';
				}
				oDl[iI].onmouseout = function()
				{
					this.getElementsByTagName('dd')[0].style.display = 'none';
				}
			}
		}
		return true;
	}
};
alsa.addLoadEvent(alsa.display);

Si tu ne veux pas la div supplémentaire, je te laisse adapter le code et si tu n'as pas l'habitude du modèle objet, je t'invite à lire ceci.

@+
Merci pour ta réponse Koala,

Mais je cherche plus à comprendre comment fonctionne javascript avec le dom, selon les navigateurs, qu'à trouver une solution toute faite.

par exemple pourquoi il faut mettre :

previousSibling

avec IE, alors que dans les autres navigateurs c'est :

previousSibling.previousSibling
Bonjour,
a écrit :

par exemple pourquoi il faut mettre :
previousSibling
avec IE, alors que dans les autres navigateurs c'est :
previousSibling.previousSibling

Et bien cela dépend du contexte, c'est-à-dire de la structure même du document et de ce que tu veux faire, mais je suppose que tu parles de
ce code ci
Pour ce cas précis, je reprends ton html :

<dl id="menu">
		<dt id="menu1"><a href="#">Menu 1</a></dt>
		<dt id="menu2">Menu 2</dt>
			<dd id="smenu1">
				<ul>
					<li><a href="#">Sous-Menu 2.1</a></li>
					<li><a href="#">Sous-Menu 2.2</a></li>
					<li><a href="#">Sous-Menu 2.3</a></li>
				</ul>
			</dd>
		<dt id="menu3">Menu 3</dt>
			<dd id="smenu2">
				<ul>
					<li><a href="#">Sous-Menu 3.1</a></li>
					<li><a href="#">Sous-Menu 3.1</a></li>
					<li><a href="#">Sous-Menu 3.1</a></li>
					<li><a href="#">Sous-Menu 3.1</a></li>
					<li><a href="#">Sous-Menu 3.1</a></li>
					<li><a href="#">Sous-Menu 3.1</a></li>
				</ul>
			</dd>
</dl>

En examinant ce code, on voit qu'il existe un espace entre un "</dt>" et le "<dd>" qui suit (qui n'est pas rendu dans le navigateur). Pour un navigateur comme Mozilla qui est conforme au W3C DOM, cet espace existe et est représenté dans l'arbre DOM comme étant un noeud texte vide. L'arbre DOM de IE, lui ne le voit pas comme un noeud.

Tu peux vérifier cela en supprimant cet espace sur un des dt ex:

<dt id="menu3">Menu 3</dt><dd id="smenu2">

si tu regardes ton arbre DOM dans l'inspecteur DOM de Mozilla tu verras que pour ce cas, il n'y a plus de noeud text entre le dt et le dd.

J'espère avoir été clair Smiley cligne

Si tu veux en apprendre plus sur le DOM et JS, je te conseille d'aller voir ce sujet épinglé ou bien les liens sur le tuto de koala si tu n'aimes pas les livres Smiley cligne

a+
Modifié par dunjl (07 Sep 2006 - 00:58)
EricLB a écrit :
Merci pour ta réponse Koala,

Mais je cherche plus à comprendre comment fonctionne javascript avec le dom, selon les navigateurs, qu'à trouver une solution toute faite.

par exemple pourquoi il faut mettre :

previousSibling

avec IE, alors que dans les autres navigateurs c'est :

previousSibling.previousSibling


Pour ça, tu peux regarder du côté de "nodeType" il me semble

Genre :

while (machin.previousSibling.nodeType != 1) {
machin.previousSibling.previousSibling;
}


La condition du while n'est pas bonne du tout, je te dis ça à l'arrache, mais il me semble que ça vient du fait que les sauts de ligne sont pris en compte par certains et pas par d'autre en tant que "frère" (sibling). Le nodeType permet de tester si on a bien à faire à une balise.

Pour les codes résultant de nodeType, regarder sur google ça se trouve tout seul.

Je suis pas certain que ça règle la question de la différence entre IE et firefox pour le previousSibling, mais je pense. (pas testé)
Modifié par Olivier (07 Sep 2006 - 01:03)