jan 23
Réaliser un panel à onglet simple avec Mootools
Objectifs
Je souhaitais réaliser un système de panel à onglet (ou tab panel in english) pour un site sur lequel je travaille. Le but est d’avoir peu de code, que ce soit facilement utilisable et implémentable mais également compatible avec la majorité des navigateurs. Sachant que je bosse avec le framework javascript Mootools, je vais l’utiliser pour me faciliter tout ça. Je souhaite également pouvoir mettre sur la même page plusieurs panels à onglets. Par contre, je tiens à ce que ça reste très simple, donc pas d’animation inutiles ou de fonctionnalités de-la-mort-qui-tue-mais-qui-servent-pas-à-grand-chose.
Le plus rapide aurait été de reprendre un code existant sur le net, mais c’est pas drôle. Alors amusé à le faire tout seul comme un grand.
Résultat
On commence par la démo disponible à cette adresse : http://delistage.net/tutos/tab-panel-simple-mootools/.
Et on passe maintenant au détail des différents fichiers et scripts nécessaires :
index.html
<div class="panel">
<ul class="panel-header">
<li class="panel-active"><a href="#" rel="panel-content-1">Content 1</a></li>
<li><a href="#" rel="panel-content-2">Content 2</a></li>
<li><a href="#" rel="panel-content-3">Content 3</a></li>
</ul>
<div id="panel-content-1" class="panel-content panel-display">
panel-content-1
</div><!-- #panel-content-1 -->
<div id="panel-content-2" class="panel-content">
panel-content-2
</div><!-- #panel-content-2 -->
<div id="panel-content-3" class="panel-content">
panel-content-3
</div><!-- #panel-content-3 -->
</div><!-- Panel 1 -->
Conteneur : un div ayant la classe panel, à ne pas changer.
La liste des onglets (ul) sans contrainte au niveau du nom de la classe. Chaque onglet est contenu dans une ligne (li) dont celui à sélectionner par défaut doit avoir la classe panel-active. On a ensuite l’onglet en lui-même sous forme de lien. L’attribut rel de cette balise doit contenir l’id de la div de contenu correspondant.
Différentes DIV de contenu doivent posséder un id (identique à celui rentré dans la balise rel de l’onglet) et la classe panel-content. Si vous souhaitez afficher un des panels par défaut, il suffit de lui ajouter la classe panel-display.
panels.js
Ce fichier contient la fonction en charge de la gestion des différents panels. Pas besoin de plus de commentaires que ceux qui sont dans le code je pense.
panelManager = function(panelClass) {
// On parcourt chaque panel
$$('.panel').each(function(panelElt) {
// On récupère les onglets ...
var tabs = panelElt.getFirst('ul').getElements('a');
// Et on les parcourt à leur tour
tabs.each(function(tab) {
/*
* Ajout de l'évèment click
*/
tab.addEvent('click', function() {
// On regarde si le panel-content lié à cet onglet existe
var contentDiv = $(this.rel);
if(contentDiv != null) {
// Si c'est le cas, on masque les panel-content
panelElt.getElements('div').removeClass('panel-display');
// On déselectionne tous les onglets
panelElt.getFirst('ul').getElements('li').removeClass('panel-active');
// On affiche le panel-content sélectionné
contentDiv.addClass('panel-display');
// On sélectionne l'onglet
this.getParent().addClass('panel-active');
}
// Etant donné que notre onglet est un lien (a),
// on retourne faux pour annuler son action
return false;
});
});
});
}
Sur les pages contenant un ou plusieurs panels, il vous suffit d’appeler cette fonction très simplement :
<script type="text/javascript" src="panels.js"></script>
<script type="text/javascript">
window.addEvent('domready', function() {
panelManager();
});
</script>
panels.css
.panel { margin-bottom: 15px; }
.panel-header { border-bottom: 1px solid #333333; height: 30px; }
.panel-header li {
float: left;
height: 24px;
margin-right: 10px;
padding: 0 10px;
padding-top: 5px;
border: 1px solid #666666;
border-bottom: 1px solid #333333;
background-color: #fafafa;
}
.panel-header li a { color: #555555; text-decoration: none; }
.panel-header li:first-child { margin-left: 5px; }
.panel-header li.panel-active {
background-color: #eeeeee;
border: 1px solid #333333;
border-bottom: 1px dashed #333333;
color: #333333;
}
.panel-header li.panel-active a {
color: #333333;
text-decoration: none;
font-weight: bold;
}
.panel-content {
clear: both;
background-color: #eeeeee;
border: 1px solid #333333;
border-top: 0;
padding: 5px;
display: none;
}
.panel-display { display: block; }
Conclusion
Et voilà, vous avez là une petite fonction qui s’occupe d’afficher de la gestion des panels très simplement. Ça fonctionne avec Firefox 3.5, IE8 et Chrome 3.0 pour ceux que j’ai testé, mais étant donné que ça utilise Mootools, c’est censé être compatible avec la majorité des navigateurs. En cas de bugs ou de choses pas claires, les commentaires sont ouverts.

janvier 23rd, 2010 à 13:39
Pas besoin de Mootools pour ça : http://javascript.internet.com/css/tab-view.html
Même sans JS c’est possible en 100% CSS : http://www.cssplay.co.uk/menu/one_page
janvier 23rd, 2010 à 14:13
Bien sûr que c’est possible de le faire sans Mootools voir même sans JS, c’est pour ça que j’ai précisé « avec Mootools ». :D Tout dépend après de l’utilisation et ce que tu utilises déjà sur le reste du site.
Par exemple la version par CSS que tu proposes ne présente pas le même comportement : les panels passent au dessus du texte, même si je suis sûr que ça doit être modifiable.
Par contre la version JS, ça serait dommage pour moi d’utiliser une librairie JS (en l’occurence Mootools dans mon cas) un peu partout sur le site et de pondre un code 100% JS natif/pur/sans librairie pour les panels. C’est facilement faisable, mais autant faire quelque chose d’un minimum cohérent pour faciliter les mises à jours en cas de besoin et utiliser les fonctionnalités proposées par le framework (comme la fonction Element.each() qui fait gagner pas mal de temps). Sans compter également que mon code fait un peu plus de 15 lignes sans commentaires, là où la solution que t’as linké en fait près du double. ;)
Et puis si un jour j’ai envie de rajouter un peu d’animation, c’est juste quelques petites lignes supplémentaires à rajouter. :)