Exemple d'implémentation : Un menu hiérarchique

Un article de ReaxiaWiki.

Sommaire

Création de la liste hiérarchique des pages

Lors de la création de votre site, vous serez sûrement amené à créer un menu. Reaxia vous permet de gérer facilement l'organisation des pages et offre la possibilité aux contributeurs d'ajouter, de renommer et de supprimer des pages. Pour cela, nous allons voir comment créer un type Reaxia adapté puis comment afficher un menu permettant de naviguer dans les pages.

Le type Reaxia à créer contiendra une catégorie et un champ paragraphe. Une catégorie est une structure arborescente. Chacun des éléments de la catégorie sera une page du site. Le nom d'un élément sera le titre de la page. Un tel type permet de créer des contenus « multi-pages ».

  1. Dans Reaxia, ouvrir la fenêtre de gestion des types. Dans le menu : Outils d'administration > Créer et gérer les types de contenu du site.
  2. Entrer le nom du type, par exemple, « Pages », et cliquer sur OK.
  3. Cliquer sur le type créé qui est appru dans la liste des types.
  4. Dans l'onglet « Champs », ajouter un champ catégorie. Inscrire par exemple « Menu » comme libellé. Cliquer sur OK.
  5. Les contributeurs pourront ajouter des pages avec le bouton + de la barre d'icône au dessus de la liste des contenus du site.
  6. Ajouter un champ paragraphe, qui contiendra le contenu de la page.
  7. Enregistrer les changements.
  8. Ajouter un contenu en allant dans le menu Outils d'administration > Gérer la structure du site, ajouter un contenu au site. Dans la liste des types, choisir le type « Pages », créé dans les étapes précédentes, et cliquer sur "Ajouter". Lui donner un titre, par exemple "Pages".
  9. Cliquer dans la colonne URL sur le lien "[Changer]". L'URL à indiquer sera de la forme : "index.php?page=$catId". La variable $catId sera remplacée automatiquement par l'identifiant de la catégorie. Cet identifiant est unique pour chaque page.
  10. Sélectionner les pages et éditer leur contenu (voir paragraphe suivant).
  11. Créer une librairie d'affichage pour ce type qui affichera le menu.
  12. Appeler la librairie à l'emplacement voulu pour le menu.

Edition du menu

Dans la liste des contenus, le contenu multi-page apparaît sous forme arborescente en reprenant la hiérarchie du champ Catégorie. En cliquant sur la « page mère », les pages s'affichent sous forme de liste. Pour modifier les données d'une page, double-cliquez sur la ligne correspondante dans la liste de droite ou sélectionnez la page dans l'arbre de gauche.

Il y a deux possibilités pour modifier la structure d'un multi-page :

  • Passer par l'éditeur de type et modifier la hiérarchie associée au champ Catégorie.
  • Cliquer sur un multi-page dans la liste des contenus et utiliser la seconde barre d'outils apparue en haut :
    • Pour ajouter une sous-catégorie, sélectionner la catégorie parente puis cliquer sur la première icône.
    • Pour supprimer une page, cliquer sur la seconde icône.
    • Pour déplacer une branche dans la hiérarchie, utiliser les flèches.
    • Ces actions sont aussi accessibles via le menu contextuel "Contenu multi-page", en faisant en clic droit sur une page dans l'arbre à gauche.

Affichage du menu

Pour afficher le menu, il faut créer une librairie d'affichage. Voici un exemple de librairie qui affiche le menu sous forme d'une simple liste dans une colonne (à enregistrer dans le fichier reaxia_lib/menu/menu.php) :

<?php
class menu extends thread_displayer
{
  /**
   * @param array $thread array with threadname, display_name, categories, PublishedTime
   * @param array $options
   */
  function menu($threadname, &$options)
  {
    // Call the parent's constructor, initializes the class members
    $this->thread_displayer($threadname, $options);

    // Override any of thread_displayer's class members here:
  }

  /**
   * Specify the SQL query who returns blocs
   * @return string the SQL statement that fetches the data
   */
  function GetSQLQuery()
  {
    if ($this->UsePreviewData)
       $rxp = '_rxp';
     else
       $rxp = '';

    // Cette librairie n'a pas besoin du contenu des pages, elle 
    // utilise uniquement les données de la catégorie. La requête 
    // SQL suivante est donc faite pour ne renvoyer aucun résultat. 
    $sql = 'SELECT * FROM `' . $this->threadRef . $rxp . '`';
    $sql .= ' WHERE 0 = 1';  // load only metadata

    return $sql;
  }

  /**
   * Does whatever needs to be done with the selected blocs
   * @return string usually an HTML fragment, but it can be nothing.
   */
  function process_thread_content()
  {
    return menu::get_html_for_menu($this->categories['category_1']);
  }
  
  function get_html_for_menu(&$categories)
  {
    $html = '<ul>' . "\n";
    foreach ($categories as $category)
    {
      $html .= '<li><a href="index.php?page='.$category['id'].'">'.$category['name'].'</a>' . "\n";
      if (!empty($category['children']))
        $html .= menu::get_html_for_menu($category['children']);
      $html .= '</li>' . "\n";
    }  
    $html .= '</ul>' . "\n";
    
    return $html;
  }
}
?>

Cette librairie n'a pas besoin du contenu des pages, elle utilise uniquement les données de la catégorie. La requête SQL retournée par GetSQLQuery() est donc faite pour ne renvoyer aucun résultat. Le texte à afficher est le nom des éléments : $category['name']. L'adresse du lien est construite à partir de l'identifiant de chaque élément : $category['id'].

Ensuite, il suffit d'appeler cette librairie à l'emplacement où doit apparaître le menu :

<?php
  include_once('reaxia_lib/reaxia.php');
  display_thread('pages', 'show_menu');
?>

Affichage d'une page d'un menu

Pour afficher une page d'un menu, il faut créer une librairie d'affichage. Voici un exemple simple qui affiche le titre de la page puis son contenu (à enregistrer dans le fichier reaxia_lib/show_page/show_page.php) :

<?php
class show_page extends thread_displayer
{
  /**
   * @param array $thread array with threadname, display_name, categories, PublishedTime
   * @param array $options
   */
  function show_page($threadname, &$options)
  {
    // Call the parent's constructor, initializes the class members
    $this->thread_displayer($threadname, $options);

    // Override any of thread_displayer's class members here:
  }

  /**
   * Specify the SQL query who returns blocs
   * @return string the SQL statement that fetches the data
   */
  function GetSQLQuery()
  {
    if ($this->UsePreviewData)
       $rxp = '_rxp';
     else
       $rxp = '';

    $sql = 'SELECT * FROM `' . $this->threadRef . $rxp . '`';
    $sql .= " WHERE category_1_id = '".$this->options['page']."'";

    return $sql;
  }

  /**
   * Does whatever needs to be done with the selected blocs
   * @return string usually an HTML fragment, but it can be nothing.
   */
  function process_thread_content()
  {
    $html = '';
    
    $titre = $this->Blocs[0]['category_1_name']; 
    $Texte_de_la_page = $this->Blocs[0]['paragraph_1_text'];
    
    $html .= '<h1>'.$titre.'</h1>'."\n\n";
    $html .= $Texte_de_la_page;
    
    return $html;
  }
?>

Il faut ensuite appeler cette librairie dans chaque page, en lui passant en paramètre l'identifiant de la page à afficher :

<?php
  include_once('reaxia_lib/reaxia.php');
  display_thread('pages', 'show_page', array('page' => $_GET['page']));
?>