Tipps und Tricks Filter

getTemplateGroup ab Contao 2.9

Mit der Methode getTemplateGroup ist es in einem Modul möglich, dem Nutzer im Backend die Auswahl von Templates zu ermöglichen, die im Frontend dann verwendet werden sollen. Damit ist es auch möglich, eigene Templates zu erstellen und zu verwenden.

Bis Contao 2.8.4 wurden die Templates im Verzeichnis templates des Moduls gesucht und anschließend im Verzeichnis TL_ROOT/templates.

Ab Contao 2.9 wurde auf Grund des Theme-Managers diese Methode erweitert, damit diese nun auch im Template Verzeichnis des Themes gesucht werden.

 

Ab Contao 2.9 ist es möglich in der Theme Konfiguration ein eigenes Template Verzeichnis zu definieren. Technisch gesehen ist es ein Unterverzeichnis von TL_ROOT/templates. Da diese Templates sich auf das Theme beziehen, muss auch die Auswahl innerhalb eines ermittelbaren Themes erfolgen. Am einfachsten gehts das direkt im Frontend Modul. (Diese werden ja nun innerhalb eines Themes angelegt)

Beispiele sind aus dem Modul Banner entnommen.

Tabellen Angaben

Hierzu braucht nur im Modul ein Feld angelegt werden.

-- 
-- Table `tl_module`
-- 
CREATE TABLE `tl_module` (
  `banner_template` varchar(32) NOT NULL default '',
) ENGINE=MyISAM DEFAULT CHARSET=utf8; 

DCA Angaben

In der DCA, hier "tl_module.php", erfolgte nun im Abschnitt "fields" dieser Teil:

$GLOBALS['TL_DCA']['tl_module']['fields']['banner_template'] = array
(
    'label'                   => &$GLOBALS['TL_LANG']['tl_module']['banner_template'],
    'default'                 => 'mod_banner_list_all',
    'exclude'                 => true,
    'inputType'               => 'select',
    //'options'                 => $this->getTemplateGroup('mod_banner_list_'), // Das wäre die alte Variante
    'options_callback'        => array('tl_module_banner', 'getBannerTemplates')
);

Die alte Variante (hier auskommentiert) ist hier auch dargestellt, welche nach der alten Variante funktionieren würde.
Bei der neuen Variante ist zu sehen, dass ein "options_callback" nötig ist. Grund ist, dass die Methode "getTemplateGroup" einen optionalen zweiten Parameter neuerdings versteht. Dieser Parameter ist die Theme-ID. Da diese aber hier nicht zur Verfügung steht, holt man sich diese per callback:

// mit in der dca Datei
class tl_module_banner	extends Backend 
{
	/**
	 * Template over theme id
	 */
	public function getBannerTemplates(DataContainer $dc)
	{
            if (version_compare(VERSION.BUILD, '2.9.0', '>=')) {
	        return $this->getTemplateGroup('mod_banner_list_', $dc->activeRecord->pid);
            } else {
                return $this->getTemplateGroup('mod_banner_list_');
            }
	}  
}

Hier wieder zu sehen, beginnt die Suche nach Templates mit "mod_banner_list_". Hier wird nun in folgender Reihenfolge gesucht:

  1. Verzeichnis templates des Moduls
  2. Verzeichnis TL_ROOT/templates (nicht rekursiv!)
  3. Im Template Verzeichnis des Themes, z.b. TL_ROOT/templates/mein_theme/meine_templates

Im obigen Beispiel wurde noch ein Versionsvergleich eingebaut. Somit arbeitet diese Methode sowohl in Contao 2.8 als auch in Contao 2.9.

Frontend Modul

Das Frontend Modul bekommt hier durch das Framework die Felder aus tl_module automatisch, dazu braucht es also keine SQL Abfrage. Daher verkürzt sich die Sache sehr. Hier mal kurze Code Sequenzen, die das Ganze etwas deutlicher machen sollten.

class ModuleBanner extends Module
{
  /**
   * Template
   * @var string
   */
  protected $strTemplate = 'mod_banner_list_all';  // Default wie in DCA definiert

  /**
   * Generate module
   */
  protected function compile()
  {
  ....
     if (($this->banner_template != $this->strTemplate) && ($this->banner_template != '')) 
     {
        $this->strTemplate = $this->banner_template;
        $this->Template = new FrontendTemplate($this->strTemplate);
     }
  ....
  }
}

Content Element

Bei Content Elementen in Artikel sieht das Ganze wieder komplizierter aus. Das Grundprinzip ist aber das gleiche. Es wird über Artikel und Seitenstruktur ermittelt, in welchem Theme sich dieses CE befindet und mit der Theme ID wird dann wie bei der Modul Variante wieder nach Templates gesucht.

Hier beispielsweise ein Auszug aus dem DCA der Contao-internen Galerie:

public function getGalleryTemplates(DataContainer $dc)
{
  // Ermitteln der Seiten ID
  $objArticle = $this->Database->prepare("SELECT pid FROM tl_article WHERE id=?")
                 ->limit(1)
                 ->execute($dc->activeRecord->pid);
 
  // Vererbung der Seiteneigenschaften
  $objPage = $this->getPageDetails($objArticle->pid);
 
  // Ermitteln der Theme ID
  $objLayout = $this->Database->prepare("SELECT pid FROM tl_layout WHERE id=?")
                ->limit(1)
                ->execute($objPage->layout);
 
  // Alle verfügbaren Galerie-Templates anzeigen
  return $this->getTemplateGroup('gallery_', $objLayout->pid);
}

getTemplateGroup in TYPOlight 2.8

Wie das ganze in TYPOlight 2.8 funktioniert, also die alte Variante, kann im Wiki nachgelesen werden.