Créer des onglets (avec AngularJS)

★★★ Avancé - durée : 45 minutes

Dans ce tutoriel, vous allez apprendre à créer des onglets à l’aide d’AngularJS. Ces derniers pourront être entièrement personnalisés et réutilisés dans n’importe quel tableau de bord ou élément de contenu créé avec HTML/CSS sur Opendatasoft.

../_images/module1_final.png

Au cours de ce tutoriel, vous allez apprendre à utiliser 4 directives AngularJS :

  • ng-if
  • ng-click
  • ng-class
  • ng-init

PRÉREQUIS

  • Pour tester ce tutoriel et/ou intégrer les onglets à une page existante, vous avez besoin d’un accès à l’interface d’administration d’un portail Opendatasoft, ainsi que de la permission “Éditer toutes les pages”.

  • Le niveau de difficulté de ce tutoriel étant “Avancé”, nous partons du principe que vous connaissez suffisamment bien HTML et CSS pour reconnaître et comprendre leurs structures et fonctionnements respectifs. Toutefois, d’autres points plus techniques seront expliqués en détail.

Afficher toutes les images

Masquer toutes les images

Créer la structure

1 + Dans ce tutoriel, nous allons créer 3 onglets, chacun comprenant un titre cliquable et un contenu. Dans notre code, nous allons gérer les titres d’onglet d’un côté et les contenus de l’autre. Commençons dès maintenant par la structure de nos titres d’onglet : placez chaque titre d’onglet dans un tag <a>, puis tous les tags <a> dans un tag <div>.

Remarque

Dans le cadre de ce tutoriel, nous avons choisi de placer les titres d’onglet dans des tags <a> à des fins d’accessibilité. Ce tag est aussi pratique, puisqu’il permet d’afficher tous les titres sur la même ligne. Si vous maîtrisez suffisamment HTML/CSS, vous pouvez placer vos titres d’onglet dans un autre tag, mais gardez à l’esprit que vous allez probablement devoir utiliser davantage CSS pour qu’ils ressemblent à l’exemple donné dans ce tutoriel.

Remarque

En fonction de l’environnement (nouvelle page ou tableau de bord existant) dans lequel vous effectuez ce tutoriel, vous pourrez peut-être voir les tags <div class="container"> et <div class="ods-box">. Il s’agit des tags par défaut qui créent le cadre par défaut d’une page Opendatasoft. Si vous souhaitez conserver ce cadre, veillez à ajouter le code du tutoriel entre ces tags par défaut.

<div class="container-fluid">
  <div class="ods-box">

    <div>
      <a>1st tab title</a>
      <a>2nd tab title</a>
      <a>3rd tab title</a>
    </div>

  </div>
</div>
../_images/step112.png

2 + Ajoutons maintenant les contenus d’onglet sous les titres d’onglet. Placez-les dans un tag <div>.

<div class="container-fluid">
  <div class="ods-box">

    <div>
      <a>1st tab title</a>
      <a>2nd tab title</a>
      <a>3rd tab title</a>
    </div>

    <div>
      Content of first tab
    </div>
    <div>
      Content of second tab
    </div>
    <div>
      Content of third tab
    </div>

  </div>
</div>
../_images/step27.png

3 + La base étant créée, nous devons ajouter des éléments CSS pour que nos onglets ressemblent à des onglets dignes de ce nom. Accédez à la section CSS de la page sur laquelle vous travaillez.

../_images/step32.png

4 + Commencez par créer la classe CSS par défaut, qui sera appliquée à tous les titres d’onglet. Nous allons tout particulièrement travailler sur la propriété padding pour nous assurer que les onglets apparaissent comme 3 éléments distincts. En outre, nous allons modifier la couleur du texte.

Remarque

Dans le cadre de ce tutoriel, nous avons ajouté des commentaires dans le code CSS, ainsi que des rappels pour expliquer le rôle de chaque classe ou propriété. Si vous maîtrisez CSS, n’hésitez pas à supprimer ces commentaires. Notez également que le nom de la classe CSS, tab, a été choisi car il est lisible et permet de comprendre à quel élément HTML il va être appliqué. Néanmoins, vous pouvez le renommer si vous le souhaitez.

.tab {
   padding: 10px 20px; /* Gives some space to tab titles */
   color: gray; /* Colors the text in gray */
}
../_images/step42.png

5 + Revenez à la section HTML de la page sur laquelle vous travaillez. Puisque la classe CSS a été créée, nous pouvons l’appliquer aux tags HTML qui contiennent les titres d’onglet.

<div class="container-fluid">
  <div class="ods-box">

    <div>
      <a class="tab">1st tab title</a>
      <a class="tab">2nd tab title</a>
      <a class="tab">3rd tab title</a>
    </div>

    <div>
      Content of first tab
    </div>
    <div>
      Content of second tab
    </div>
    <div>
      Content of third tab
    </div>

  </div>
</div>
../_images/step52.png

6 + Ensuite, nous allons mettre en page les contenus d’onglet. Cette fois, au lieu de créer une toute nouvelle classe CSS, nous allons en utiliser une existante. ods-box est un style CSS Opendatasoft par défaut qui enveloppe les éléments HTML dans une bordure fine. Cela nous permet de donner l’impression que les contenus de notre onglet sont légèrement “en dehors” du reste du contenu de la page. Ajoutez un tag <div> qui enveloppe tous les contenus de l’onglet avec la classe CSS ods-box.

<div class="container-fluid">
  <div class="ods-box">

    <div>
      <a class="tab">1st tab title</a>
      <a class="tab">2nd tab title</a>
      <a class="tab">3rd tab title</a>
    </div>

    <div class="ods-box">
      <div>
        Content of first tab
      </div>
      <div>
        Content of second tab
      </div>
      <div>
        Content of third tab
      </div>
    </div>

  </div>
</div>
../_images/step62.png

7 + Consultez l’aperçu de votre page. C’est fait, nous avons créé la structure de nos onglets !

../_images/step72.png

Ajouter AngularJS

8 + C’est le moment où AngularJS entre en jeu ! Nous allons avoir besoin d’utiliser 4 directives AngularJS pour que nos onglets fonctionnent. Commençons par ng-click, une directive essentiellement utilisée pour indiquer à AngularJS ce qu’il doit faire lorsqu’un utilisateur clique sur un élément HTML. Ici, ng-click va nous permettre de basculer d’un onglet à l’autre.

Commençons déjà par observer la syntaxe pour comprendre comment utiliser la directive ng-click.

ng-click="myvariable = 'myvalue'"

ng-click est la directive AngularJS. Elle est toujours suivie d’un signe égal, =, qui indique que ce qui vient après est une expression. Cette expression sera évaluée par la directive et doit toujours se trouver entre des guillemets doubles ".

Dans l’expression, nous allons attribuer une valeur à une variable. Comme aucune variable ni valeur n’existe à ce stade, nous devons les créer.

  • La variable se trouve au début. Elle constitue le lien entre toutes les directives AngularJS qui seront utilisées au cours de ce tutoriel. Choisissez un nom explicite pour vous assurer que votre code peut être compris par tout le monde. Dans ce tutoriel, nous allons nommer la variable tabselector.

  • Arrive ensuite le signe égal, =, qui sépare la variable de la valeur.

  • Enfin, la valeur ferme la marche. Elle doit toujours être placée entre des guillemets simples '. La valeur joue le rôle d’identifiant d’un onglet ; chaque onglet créé doit avoir un identifiant unique. Une fois encore, veillez à ce que le nom de la valeur soit explicite. Dans ce tutoriel, nous allons avoir 3 valeurs pour les 3 onglets, nommés firsttab, secondtab et thirdtab.

9 + Ajoutez la directive ng-click dans le tag HTML <a> de chaque titre d’onglet. À ce stade, nous avons indiqué à AngularJS que nous avons 3 entités cliquables différentes : nos 3 titres d’onglet.

<div class="container-fluid">
  <div class="ods-box">

    <div>
      <a class="tab" ng-click="tabselector = 'firsttab'">1st tab title</a>
      <a class="tab" ng-click="tabselector = 'secondtab'">2nd tab title</a>
      <a class="tab" ng-click="tabselector = 'thirdtab'">3rd tab title</a>
    </div>

    <div class="ods-box">
      <div>
        Content of first tab
      </div>
      <div>
        Content of second tab
      </div>
      <div>
        Content of third tab
      </div>
    </div>

  </div>
</div>
../_images/step92.png

10 + Passons maintenant à ng-if ! La directive ng-if est une expression conditionnelle qui détermine si un élément HTML doit être affiché ou non. Ici, ng-if nous permet d’afficher le contenu d’onglet approprié lorsque l’utilisateur clique sur un titre d’onglet.

Observons la syntaxe pour comprendre comment utiliser la directive ng-if.

ng-if="myvariable == 'myvalue'"

La structure de la directive ng-if est identique à celle de ng-click. Le nom de la directive est suivi d’un signe égal, =, et l’expression évaluée par la directive ng-if est placée entre des guillemets doubles ".

Toutefois, la syntaxe diffère légèrement. Dans l’expression,

  • La variable est identique à celle créée à l’étape 8.

  • Voici ce qui diffère au niveau de la syntaxe : cette fois, la variable et la valeur doivent être séparées par 2 signes égal, ==. Cela indique qu’il s’agit d’une condition.

  • La valeur (placée entre des guillemets simples ') est identique à celle créée à l’étape 8.

Pour faire simple, la syntaxe ng-if signifie : ” Si myvariable est égal à myvalue, [le contenu de l’élément HTML correspondant à myvalue est affiché`] ”.

11 + Ajoutez la directive ng-if dans le tag HTML <div> de chaque contenu d’onglet. N’oubliez pas d’ajouter les 3 valeurs correspondant aux 3 contenus d’onglet. À ce stade, nous avons indiqué à AngularJS quel contenu d’onglet afficher en fonction du titre d’onglet sélectionné.

<div class="container-fluid">
  <div class="ods-box">

    <div>
      <a class="tab" ng-click="tabselector = 'firsttab'">1st tab title</a>
      <a class="tab" ng-click="tabselector = 'secondtab'">2nd tab title</a>
      <a class="tab" ng-click="tabselector = 'thirdtab'">3rd tab title</a>
    </div>

    <div class="ods-box">
      <div ng-if="tabselector == 'firsttab'">
        Content of first tab
      </div>
      <div ng-if="tabselector == 'secondtab'">
        Content of second tab
      </div>
      <div ng-if="tabselector == 'thirdtab'">
        Content of third tab
      </div>
    </div>

  </div>
</div>
../_images/step113.png

12 + Il est temps de nous intéresser à ng-init ! Cette directive sert à initialiser une variable, c’est-à-dire que quand une page Web est chargée, le code se trouvant derrière la page en question va être lu de la première à la dernière ligne. ng-init indique qu’à partir d’ici, AngularJS est utilisé et spécifie le type de variable appliqué. Ici, ng-init permet également d’indiquer quel contenu d’onglet doit être affiché par défaut.

Observons la syntaxe pour comprendre comment utiliser la directive ng-init.

ng-init="myvariable = 'myvalue'"

La syntaxe de la directive ng-init est en tout point identique à celle de ng-click (cf. étape 8).

Dans l’expression :

  • La variable est identique à celle créée à l’étape 8 et utilisée jusqu’alors.

  • La valeur (placée entre des guillemets simples ') est l’identifiant de l’onglet dont le contenu sera affiché par défaut.

13 + Ajoutez la directive ng-init à un tag HTML qui enveloppe l’ensemble du code des onglets. Dans le cadre de ce tutoriel, puisque nous avons créé une nouvelle page, le code de la page est enveloppé dans 2 tags de cadre par défaut : <div class="container-fluid"> et <div class="ods-box">. Nous allons ensuite placer ng-init dans le tag <div class="ods-box"> par défaut. Nos onglets sont maintenant fonctionnels !

Remarque

Si vous n’avez pas créé de page pour ce tutoriel, et si vous n’avez pas ces tags de cadre par défaut, vous pouvez ajouter un tag <div> normal pour envelopper le code des onglets et ajouter la directive ng-init dans celui-ci.

<div class="container-fluid">
  <div class="ods-box" ng-init="tabselector = 'firsttab'">

    <div>
      <a class="tab" ng-click="tabselector = 'firsttab'">1st tab title</a>
      <a class="tab" ng-click="tabselector = 'secondtab'">2nd tab title</a>
      <a class="tab" ng-click="tabselector = 'thirdtab'">3rd tab title</a>
    </div>

    <div class="ods-box">
      <div ng-if="tabselector == 'firsttab'">
        Content of first tab
      </div>
      <div ng-if="tabselector == 'secondtab'">
        Content of second tab
      </div>
      <div ng-if="tabselector == 'thirdtab'">
        Content of third tab
      </div>
    </div>

  </div>
</div>
../_images/step132.png

14 + Consultez l’aperçu. Même si nos onglets sont entièrement fonctionnels, il manque un petit quelque chose... En effet, rien n’indique quel onglet est sélectionné. Remédions à cela en commençant par créer un style “onglet sélectionné”.

../_images/step142.png

15 + Revenez à la section CSS de la page sur laquelle vous travaillez, puis créez un style distinct qui indique de façon claire l’onglet actuellement sélectionné. Nous allons appeler cette classe CSS activetab, puis jouer avec la couleur du texte et une bordure en gras sous le texte.

.activetab {
   color: black; /* Colors the text in black */
   border-bottom: 3px solid #2d2d2d; /* Underlines the text with a bold dark border */
}
../_images/step152.png

16 + Revenez à la section HTML de la page sur laquelle vous travaillez. Nous allons maintenant appliquer notre style CSS à l’aide de notre quatrième (et dernière !) directive AngularJS : ng-class. Cette directive est une expression conditionnelle qui détermine si une classe CSS va être appliquée à un élément HTML ou non. Ici, ng-class va être utilisée pour appliquer un style particulier au titre d’un onglet quand celui-ci est sélectionné.

Observons la syntaxe pour comprendre comment utiliser la directive ng-class.

ng-class="{'mycssclass' : myvariable == 'myvalue'}"

La structure de la directive ng-class est identique à celle des autres directives : le nom de la directive est directement suivi d’un signe égal, =, et l’expression évaluée par la directive ng-if est placée entre des guillemets doubles ".

Mais voici le format de l’expression pour cette directive :

  • L’expression doit également être placée entre des accolades {}.

  • Dans les accolades {}, le nom de la classe CSS doit figurer en premier et être placé entre des guillemets simples '.

  • Puis, deux-points : doivent être ajoutés.

  • Vient ensuite la partie variable/valeur, qui est exactement identique à l’expression ng-if (cf. étape 10). Nous devons avoir le nom de la variable et le nom de la valeur (placés entre des guillemets simples '). La variable et la valeur doivent être séparées par 2 signes égal, ==.

Pour faire simple, la syntaxe ng-class signifie : ” mycssclass doit être utilisé quand myvariable est égal à myvalue ”.

17 + Ajoutez la directive ng-class dans le tag HTML <a> de chaque titre d’onglet. N’oubliez pas d’ajouter les 3 valeurs qui correspondent aux 3 titres d’onglet.

<div class="container-fluid">
  <div class="ods-box" ng-init="tabselector = 'firsttab'">

    <div>
      <a class="tab" ng-click="tabselector = 'firsttab'" ng-class="{'activetab' : tabselector == 'firsttab'}">1st tab title</a>
      <a class="tab" ng-click="tabselector = 'secondtab'" ng-class="{'activetab' : tabselector == 'secondtab'}">2nd tab title</a>
      <a class="tab" ng-click="tabselector = 'thirdtab'" ng-class="{'activetab' : tabselector == 'thirdtab'}">3rd tab title</a>
    </div>

    <div class="ods-box">
      <div ng-if="tabselector == 'firsttab'">
        Content of first tab
      </div>
      <div ng-if="tabselector == 'secondtab'">
        Content of second tab
      </div>
      <div ng-if="tabselector == 'thirdtab'">
        Content of third tab
      </div>
    </div>

  </div>
</div>
../_images/step172.png

Finaliser les onglets

18 + Notre directive ng-class fonctionne ! Par contre, l’esthétique n’y est pas... Revenons à la section CSS pour apporter la touche finale. Ici, nous allons ajouter plus d’espace entre les titres d’onglet pour éviter que la bordure ne se retrouve dans la zone du contenu de l’onglet. Nous allons également mettre en valeur la sélection possible du titre d’un onglet en créant un style spécifique uniquement visible lorsque la souris survole les titres d’onglet.

.tabs {
   margin: 1em; /* Adds lots of space around the tabs, to avoid the border to fall into the tab content area */
}

/* Only visible when the mouse is on a tab title */
.tab:hover {
   color: black; /* Colors the text in black to highlight the possible selection */
   text-decoration: none; /* Removes the hyperlink underline style */
}
../_images/step182.png

19 + Revenez à la section HTML pour appliquer le tout nouveau style CSS. Notre classe tabs fera parfaitement l’affaire dans le tag div qui enveloppe tous les titres d’onglet. En ce qui concerne tab:hover, puisqu’il repose sur la classe CSS tab principale, il s’applique automatiquement aux éléments HTML avec la classe CSS tab.

<div class="container">
  <div class="ods-box" ng-init="tabselector = 'firsttab'">

    <div class="tabs">
      <a class="tab"
         ng-click="tabselector = 'firsttab'"
         ng-class="{'activetab' : tabselector == 'firsttab'}">1st tab title</a>
      <a class="tab"
         ng-click="tabselector = 'secondtab'"
         ng-class="{'activetab' : tabselector == 'secondtab'}">2nd tab title</a>
      <a class="tab"
         ng-click="tabselector = 'thirdtab'"
         ng-class="{'activetab' : tabselector == 'thirdtab'}">3rd tab title</a>
    </div>

    <div class="ods-box">
      <div ng-if="tabselector == 'firsttab'">
        Content of first tab
      </div>
      <div ng-if="tabselector == 'secondtab'">
        Content of second tab
      </div>
      <div ng-if="tabselector == 'thirdtab'">
        Content of third tab
      </div>
    </div>

  </div>
</div>
../_images/step192.png

20 + Et voilà ! Nous avons créé nos onglets personnalisés ! Il ne nous reste plus qu’à remplacer chaque exemple de texte par du contenu réel.

Vous pouvez choisir les titres d’onglet à votre convenance et ajouter les contenus d’onglet souhaités. Dans le cadre de ce tutoriel, nous allons renseigner les onglets avec le jeu de données Shanghai World University Ranking <https://data.opendatasoft.com/explore/dataset/shanghai-world-university-ranking%40public>. Le premier onglet hébergera la visualisation de tableau, le deuxième, une carte créée avec l’Éditeur de carte et le troisième, une visualisation de graphe. Chaque titre d’onglet indiquera le contenu de l’onglet et sera précédé d’une icône Font Awesome (pour corser un peu les choses).

<ods-dataset-context context="worlduniversityranking"
worlduniversityranking-dataset="shanghai-world-university-ranking@public">

<div class="container">
  <div class="ods-box" ng-init="tabselector = 'firsttab'">

    <div class="tabs">
      <a class="tab"
         ng-click="tabselector = 'firsttab'"
         ng-class="{'activetab' : tabselector == 'firsttab'}"><i class="fa fa-list-ol" aria-hidden="true"></i>
      Full list</a>
      <a class="tab"
         ng-click="tabselector = 'secondtab'"
         ng-class="{'activetab' : tabselector == 'secondtab'}"><i class="fa fa-map" aria-hidden="true"></i>
      World map</a>
      <a class="tab"
         ng-click="tabselector = 'thirdtab'"
         ng-class="{'activetab' : tabselector == 'thirdtab'}"><i class="fa fa-area-chart" aria-hidden="true"></i>
      Top 20 ranking</a>
    </div>

    <div class="ods-box">
      <div ng-if="tabselector == 'firsttab'">
        <h3>
          University list
        </h3>
        <h5>
          Sorted by rank
        </h5>
        <ods-table context="worlduniversityranking"></ods-table>
      </div>
      <div ng-if="tabselector == 'secondtab'">
        <h3>
          University map
        </h3>
        <h5>
          Colored by # of university
        </h5>
        <ods-map no-refit="true"
                 scroll-wheel-zoom="false"
                 display-control="false"
                 search-box="false"
                 toolbar-fullscreen="false"
                 toolbar-geolocation="false"
                 basemap="mapbox.light">
        <ods-map-layer-group>
          <ods-map-layer context="worlduniversityranking"
                         color-numeric-ranges="{'15':'#FFFFFF','50':'#C8CDE3','200':'#929BC8','400':'#5C69AD','2500':'#263892'}"
                         color-undefined="#1B5AA5"
                         color-out-of-bounds="#1BA566"
                         color-numeric-range-min="1"
                         display="choropleth"
                         function="COUNT"
                         expression="total_score"
                         shape-opacity="0.8"
                         point-opacity="1"
                         border-color="#555555"
                         border-opacity="0.8"
                         border-size="1"
                         border-pattern="solid"
                         caption="true"
                         title="Shanghai world university ranking"></ods-map-layer>
        </ods-map-layer-group>
      </ods-map>
    </div>
    <div ng-if="tabselector == 'thirdtab'">
      <h3>
        Top 20 university
      </h3>
      <h5>
        by average score
      </h5>
      <ods-chart single-y-axis="true"
                 single-y-axis-label="University average score"
                 display-legend="false"
                 labels-x-length="35"
                 align-month="true">
      <ods-chart-query context="worlduniversityranking"
                       field-x="university_name"
                       maxpoints="20"
                       sort="serie1-1">
      <ods-chart-serie expression-y="total_score"
                       chart-type="column"
                       function-y="AVG"
                       color="#263892"
                       display-units="false"
                       display-values="true">
    </ods-chart-serie>
  </ods-chart-query>
</ods-chart>
</div>
</div>

</div>
</div>

</ods-dataset-context>
../_images/step202.png

FÉLICITATIONS !

Vous avez terminé ce tutoriel et savez maintenant comment créer des onglets à l’aide d’AngularJS. De plus, vous devez suffisamment maîtriser les directives ng-click, ng-if, ng-init et ng-class pour les utiliser à votre guise !