Forum CMS Made Simple Francophone

Aide francophone sur CMS Made Simple

Vous n'êtes pas identifié(e).

Annonce

ATTENTION

  • Prenez le temps de rechercher si quelqu'un n'a pas déjà proposé une solution à votre problème. Sur le forum français et sur le wiki
  • Pensez à mettre à jour votre version de CMS Made Simple. Nous ne faisons de support que sur LA dernière version de CMS Made Simple.
  • Renseignez impérativement le formulaire de nouveau message de manière la plus complète que possible. Dans votre CMS utiliser le menu Administration du site/Informations du système en haut Vue au format texte. Ces informations demandées nous permettent de mieux vous aider
  • Ajoutez [Résolu] au début du titre de votre 1er message lorsqu'une solution a été trouvée.

#1 12/11/2012 19:44:13

Jean le Chauve
Sa Seigneurie le Chauve, Comte du domaine .be
Lieu : Bruxelles
Inscription : 13/12/2007
Messages : 4 693
Site Web

[TUTO] Le gestionnaire de menu : menumanager

Suite au post et aux fréquentes requêtes, j'ai décidé de vous faire un tuto.

Contexte : nous souhaitons un menu ajoutant plusieurs classes et en particulier "last" pour chaque derniers li d'un niveau, "dropdown-menu" pour chaque <ul>, plus "submenu" sur les <ul> à partir du niveau 3, et quelques autres...
Au lieu de vous expliquer comment le coder, je vous explique ce qu'il fait.
Je vous conseille de copier le gabarit suivant dans votre notepad pour bien voir les imbrications des boucles if.
Gabarit :

{if $count > 0}
	<nav class="navbar navbar-fixed-top" id="menutop">
		<div class="navbar-inner">
			<div class="container"><h1 class="brand" >Nom du projet</h1>
			{* 1er niveau de menu ds son ul *}	
				<ul class="nav">
				{foreach $nodelist as $node}
					{capture class assign=class}index{$node->index} lev{$node->depth} prevLev{$node->prevdepth}{/capture}
					{capture title assign=title}{$node->pagetitle}{if $node->titleattribute neq ""}, {$node->titleattribute}{/if}{/capture}
					{if $node->depth > $node->prevdepth}{* on est au moins ul>ul node->depth *}	
						{if $node->depth > 2}
							{repeat string='<ul class="dropdown-menu submenu">' times=$node->depth-$node->prevdepth}
						{else}
							{repeat string='<ul class="dropdown-menu">' times=$node->depth-$node->prevdepth}
						{/if}
					{elseif $node->depth < $node->prevdepth}{* si on descend de niveau *}
					{repeat string='</li></ul>' times=$node->prevdepth-$node->depth}	
					{elseif $node->index > 0}
						</li>{* si on reste sur le même niveau que l'élément précédent}
						{/if}
					{/if}
					{if $node->first == true}{* si on est sur le 1er élément d'un niveau, on concatène $class avec 'first' *}
						{capture class assign=class}{$class|cat:" first"}{/capture}
					{/if}
					{if $node->last == true}{* si on est sur le dernier élément d'un niveau, on concatène $class avec 'last' *}
						{capture class assign=class}{$class|cat:" last"}{/capture}
					{/if}
					{if $node->haschildren == true and $node->type != 'sectionheader' and $node->type != 'separator'}
						{capture class assign=class}{$class|cat:" haschildren dropdown"}{/capture}
						<li class='{$class}'><a rel="tooltip" href="{$node->url}" data-toggle="dropdown" title="{$title}">{$node->menutext}<b></b></a>
					{elseif $node->type == 'sectionheader'}
						<li class='{$class} sectionheader'><span>{$node->menutext}</span>
					{else}
						<li class='{$class}'><a rel="tooltip" href="{$node->url}" title="{$title}">{$node->menutext}</a>
					{/if}
				{/foreach}
						{repeat string="</li></ul>" times=$node->depth-1}
					</li>
				</ul>
			</div>
		</div>
	</nav>
{/if}
Préambule

$count est le nombre de pages actives à afficher. Dans notre exemple, il sera de 3.
L'index commence toujours à 0 (la page par défaut du site).
Le niveau ($node->depth) commence à 1 et augmente de 1 à chaque nouvelle imbrication d'<ul>.

Le foreach

{foreach $nodelist as $node} $node est une tableau comprenant toutes les pages et ses propriétés sauf les inactives si paramètres par défaut. Vous pouvez l'afficher sur le frontend en insérant <pre>{$node|print_r}</pre> juste après.
Voir http://www.smarty.net/docs/en/language. … oreach.tpl

Capture

Ici, nous allons créer une variable $class pour l'utiliser comme valeur pour class="" de vos balises.
{capture class assign=class}index{$node->index} lev{$node->depth} prevLev{$node->prevdepth}{/capture}
En français, ça donne : capture le contenu qui se trouve entre la balise {capture} et sa fermeture {/capture}, crée une variable $class, évalue le contenu (s'il y a des variables comme {$qqchose}) et remplis-la avec ce contenu.
Donc ici, le contenu est index{$node->index} lev{$node->depth} prevLev{$node->prevdepth}.
$class reçoit l'index et le niveau de la page actuellement processée par le manager de menu et le niveau de la page précédemment processée.
Si on est sur le premier élément de la boucle foreach, donc la page d'accueil, $class aura pour valeur : index0 lev1 prevLev1
Voir http://www.smarty.net/docs/en/language. … apture.tpl

{capture title assign=title}{$node->pagetitle}{if $node->titleattribute neq ""}, - {$node->titleattribute}{/if}{/capture} on crée une variable $title comprenant le title de l'élément actuel et on concatène ", {$node->titleattribute}" s'il existe. neq "" est équivalent à !="".
Même principe que pour $class, sauf qu'il y a une sous-condition dans le contenu : y-a-t-il une description ? Si oui, on l'ajoute.

C'est parti

Prenons l'exemple suivant :
1 Accueil
2 Actualités
    2.1 Archives
   
Suivons le cheminement de nos pages dans la boucle foreach, en commençant par la première : l'index 0 (page d'accueil) :
Le moteur PHP écrit <ul class="nav">

Première condition : {if $node->depth > $node->prevdepth}
Si le node actuel est d'un niveau supérieur à celui du node précédent, il est donc son enfant.
Ce n'est pas notre cas, on saute à la condition suivante.

Seconde condition :{elseif $node->depth < $node->prevdepth}
Si le node actuel est d'un niveau inférieur à celui du node précédent. Non, on saute à la condition suivante.

Troisième condition : {elseif $node->index > 0}
L'index de ma page est 0, donc non, on passe à la condition suivante.

Quatrième condition : {if $node->first == true}
Est-ce que je suis le premier node du niveau 1 ? Bin oui, donc on ajoute " first" à $class qui contenait déjà index0 lev1 prevLev1.
{capture class assign=class}{$class|cat:" first"}{/capture} : le modificateur smarty cat (un modificateur est appelé en ajoutant une | juste après la variable à traiter) permet de concaténer une string à une variable.
Voir http://www.smarty.net/docs/en/language.modifier.cat.tpl

Cinquième condition : {if $node->last == true}
Est-ce que je suis le dernier node du niveau 1 ? Oui, on ajoute " last" à $class qui contenait déjà index0 lev1 prevLev1 first.

Sixième condition : {if $node->haschildren == true and $node->type != 'sectionheader' and $node->type != 'separator'}
Ai-je des enfants ET ne suis pas un sectionheader ET ne suis pas un separator ? Non, je n'ai pas d'enfant, on saute à la condition suivante.

Septième condition SI on a dit non à la condition 6 : {elseif $node->type == 'sectionheader'}
Est-ce que je suis un sectionheader ? Non, on passe à la condition suivante.

Huitième et dernière condition SI on a dit non aux conditions 6 et 7 : {else}
C'est le cas, le moteur php écrit <li class='{$class}'><a rel="tooltip" href="{$node->url}" title="{$titel}">{$node->menutext}</a> dans le gabarit.
Ce qui donne après que smarty a évalué le gabarit :
<ul class="nav">
    <li class='index0 lev1 prevLev1 first last'><a rel="tooltip" href="http://www.mondomaine.com/accueil" title="Accueil, bienvenue sur mon site">Accueil</a>
   
Fin de l'évaluation du premier node. Vous remarquez que nous n'avons pas encore fermé le <li>.

On passe au node page 2 qui a un enfant et pas de frère

Les variables et title sont réassignées avec les nouvelles valeurs : index1 lev1 prevLev1.

Première condition : {if $node->depth > $node->prevdepth}
Non, je suis au même niveau que la page d'accueil, on saute à la condition suivante.

Seconde condition :{elseif $node->depth < $node->prevdepth}
Non, on saute à la condition suivante.

Troisième condition : {elseif $node->index > 0}
L'index de ma page est 1, donc oui. On peut fermer le li de la page précédente : </li>
Nous avons donc maintenant :
<ul class="nav">
    <li class='index0 lev1 prevLev1 first last'><a rel="tooltip" href="http://www.mondomaine.com/accueil" title="Accueil, bienvenue sur mon site">Accueil</a></li>

Quatrième condition : {if $node->first == true}
Oui, on ajoute " last" à $class qui contenait déjà index1 lev1 prevLev1.

Cinquième condition : {if $node->last == true}
Est-ce que je suis le dernier node du niveau 1 ? Oui, on ajoute " last" à $class qui contenait déjà index1 lev1 prevLev1 first.

Sixième condition : {if $node->haschildren == true and $node->type != 'sectionheader' and $node->type != 'separator'}
Ai-je des enfants ET ne suis pas un sectionheader ET ne suit pas un separator ? Oui, on ajoute haschildren et dropdown à la variable $class.
PHP écrit <li class='{$class}'><a rel="tooltip" href="{$node->url}" data-toggle="dropdown" title="{$title}">{$node->menutext}<b></b></a>
Ce qui donne après que smarty a évalué le gabarit :
<ul class="nav">
    <li class='index0 lev1 prevLev1 first last'><a rel="tooltip" href="http://www.mondomaine.com/accueil" title="Accueil, bienvenue sur mon site">Accueil</a></li>
    <li class='index1 lev1 prevLev1 first last haschildren dropdown'><a rel="tooltip" href="http://www.mondomaine.com/accueil" title="Actualités, toutes les news et événements du mois">Actualités</a>
Et on sort de la boucle foreach puisque la condition 6 empêche 7 et 8.

On passe au node page 3, les archives

Les variables et title sont réassignées avec les nouvelles valeurs : index2 lev2 prevLev1.

Première condition : {if $node->depth > $node->prevdepth}
Oui, on continue.

Sous-condition 1 : {if $node->depth > 2}
Non, on passe à la suivante

Seconde condition : {elseif $node->depth < $node->prevdepth}
Non, on passe dans le {else} :
{repeat string='<ul class="dropdown-menu">' times=$node->depth-$node->prevdepth}
Ah, ça c'est du chinois LOL
Meuh non, décryptons tout ça :
repeat string='<ul class="dropdown-menu">' veux dire "écris plusieurs fois '<ul class="dropdown-menu">'
Combien de fois ? times = $node->depth - $node->prevdepth
Donc 2 - 1 = 1
PHP écrit <ul class="dropdown-menu">' 1 seule fois.
Ce qui donne après que smarty a évalué le gabarit :
<ul class="nav">
    <li class='index0 lev1 prevLev1 first last'><a rel="tooltip" href="http://www.mondomaine.com/accueil" title="Accueil, bienvenue sur mon site">Accueil</a></li>
    <li class='index1 lev1 prevLev1 first last haschildren dropdown'><a rel="tooltip" href="http://www.mondomaine.com/accueil" title="Actualités, toutes les news et événements du mois">Actualités</a>
        <ul class="dropdown-menu">
Comme nous avons réalisé la condition 1, on saute les elseif.

Quatrième condition : {if $node->first == true}
Oui, on ajoute " last" à $class qui contenait déjà index2 lev2 prevLev1.

Cinquième condition : {if $node->last == true}
Est-ce que je suis le dernier node du niveau 1 ? Oui, on ajoute " last" à $class qui contenait déjà index2 lev2 prevLev1 first.

Sixième condition : {if $node->haschildren == true and $node->type != 'sectionheader' and $node->type != 'separator'}
Ai-je des enfants ET ne suis pas un sectionheader ET ne suit pas un separator ? Non, on passe.

Septième condition SI on a dit non à la condition 6 : {elseif $node->type == 'sectionheader'}
Est-ce que je suis un sectionheader ? Non, on passe à la condition suivante.

Huitième et dernière condition SI on a dit non aux conditions 6 et 7 : {else}
C'est le cas, le moteur php écrit <li class='{$class}'><a rel="tooltip" href="{$node->url}" title="{$titel}">{$node->menutext}</a> dans le gabarit.
Ce qui donne après que smarty a évalué le gabarit :
<ul class="nav">
    <li class='index0 lev1 prevLev1 first last'><a rel="tooltip" href="http://www.mondomaine.com/accueil" title="Accueil, bienvenue sur mon site">Accueil</a></li>
    <li class='index1 lev1 prevLev1 first last haschildren dropdown'><a rel="tooltip" href="http://www.mondomaine.com/actualites" title="Actualités, toutes les news et événements du mois">Actualités</a>
        <ul class="dropdown-menu">
            <li class='index2 lev2 prevLev1 first last'><a rel="tooltip" href="http://www.mondomaine.com/actualites/archives" title="Archives, retrouvez toutes les news et événements archivées">Actualités</a>
   
Fin de l'évaluation du troisième et dernier node. Vous remarquez qu'il manque des fermetures de balises.

On sort du foreach et de nouveau du chinois wink

{repeat string="</li></ul>" times=$node->depth-1}
Ici, de nouveau, times vaut 2 - 1 = 1 et PHP écrit </li></ul> et suit par </li></ul> et les fermetures des balises <div> et <nav>.
Notre code est devenu :

<nav class="navbar navbar-fixed-top" id="menutop">
	<div class="navbar-inner">
		<div class="container"><h1 class="brand" >Nom du projet</h1>
		{* 1er niveau de menu ds son ul *}	
			<ul class="nav">
				<li class='index0 lev1 prevLev1 first last'><a rel="tooltip" href="http://www.mondomaine.com/accueil" title="Accueil, bienvenue sur mon site">Accueil</a>
				</li>
				<li class='index1 lev1 prevLev1 first last haschildren dropdown'><a rel="tooltip" href="http://www.mondomaine.com/actualites" title="Actualités, toutes les news et événements du mois">Actualités</a>
					<ul class="dropdown-menu">
						<li class='index2 lev2 prevLev1 first last'><a rel="tooltip" href="http://www.mondomaine.com/actualites/archives" title="Archives, retrouvez toutes les news et événements archivées">Actualités</a>
						</li>
					</ul>
				</li>
			</ul>
		</div>
	</div>
</nav>

Vous ne voyez pas de $node->parent ou current, je vous laisse le plaisir de le découvrir dans les gabarits par défaut et l'aide du module.
Mais, attention, $node->parent n'est true QUE pour la page parentles pages parent du $node en cours. Donc, il y a zéro ou une page répondant à la condition {if $node->parent == true}.

Enjoy smile

Dernière modification par Jean le Chauve (12/07/2013 09:55:17)

Hors ligne

#2 12/11/2012 20:11:21

bess
Administrateur
Lieu : Rennes
Inscription : 16/12/2008
Messages : 6 094
Site Web

Re : [TUTO] Le gestionnaire de menu : menumanager

Aouch... le pavé  lol

en tout cas merci, ça servira de référence à lire en cas de nouvelle question  smile

Hors ligne

#3 12/11/2012 20:22:19

Jean le Chauve
Sa Seigneurie le Chauve, Comte du domaine .be
Lieu : Bruxelles
Inscription : 13/12/2007
Messages : 4 693
Site Web

Re : [TUTO] Le gestionnaire de menu : menumanager

Tu as raison, je l'ai un peu agrémenté  tongue

Hors ligne

#4 13/11/2012 11:45:59

Ouik
Modérateur
Lieu : Bourgogne
Inscription : 08/01/2008
Messages : 1 080
Site Web

Re : [TUTO] Le gestionnaire de menu : menumanager

Merci !!!  cool

Hors ligne

#5 14/07/2013 12:29:58

lakpo
Membre
Lieu : Clermont-ferrand
Inscription : 11/05/2009
Messages : 128

Re : [TUTO] Le gestionnaire de menu : menumanager

merci ! ^^


Des chercheurs qui cherchent on en trouve mais des chercheurs qui trouvent on en cherche!!!!

Hors ligne

Pied de page des forums