Vue d'ensemble
Le système de thèmes de Larapen vous permet de créer des designs front-end entièrement personnalisés. Chaque thème est un package autonome avec ses propres vues, feuilles de style, JavaScript et configuration. Ce guide vous accompagne dans la création d'un thème de zéro.
Prérequis
- PHP 8.3+ et une installation fonctionnelle de Larapen.
- Node.js 18+ et npm installés (pour la compilation des assets via Vite).
- Connaissances de base en Laravel Blade, Bootstrap 5.3 et SCSS.
- Un éditeur de code (VS Code, PhpStorm, etc.).
Étape 1 : Créer le répertoire du thème
Tous les thèmes se trouvent sous extensions/themes/. Créez un répertoire pour votre thème en utilisant un nom en minuscules :
extensions/themes/mon-theme/
Étape 2 : Créer le manifeste (theme.json)
Créez extensions/themes/mon-theme/theme.json: ce fichier indique à Larapen les informations sur votre thème :
{
"name": "mon-theme",
"display_name": "Mon Thème Personnalisé",
"version": "1.0.0",
"author": "Votre Nom",
"license_type": "free",
"description": "Un thème personnalisé pour mon site web",
"thumbnail": "assets/images/thumbnail.png",
"supports": ["pages", "portfolio", "blog", "shop"],
"settings": {
"primary_color": "#3b82f6",
"layout_style": "wide"
},
"sku": "",
"item_id": "",
"marketplace_item_ids": {
"envato": "",
"gumroad": "",
"shop": ""
}
}
Référence des champs du manifeste
| Champ | Type | Description |
|---|---|---|
name | string | Obligatoire. Nom machine unique: doit correspondre au nom du répertoire. |
display_name | string | Obligatoire. Nom lisible affiché dans le panneau d'administration. |
version | string | Version sémantique (ex. 1.0.0). |
author | string | Nom de l'auteur. |
license_type | string | "free" ou "premium". |
description | string | Description courte pour le panneau d'administration. |
thumbnail | string | Chemin relatif vers une capture d'écran de prévisualisation (recommandé : 1200×900px). |
supports | array | Fonctionnalités supportées : pages, portfolio, blog, shop. |
settings | object | Valeurs par défaut des paramètres (remplacées par config.php). |
sku | string | SKU du produit de licence correspondant sur l'API de licences (ex. larapen-theme-mon-theme) : l'identifiant envoyé en premier lors de la vérification d'un code d'achat. Laisser vide pour les thèmes non vendus. |
marketplace_item_ids | object | Identifiant du thème sur chaque plateforme de vente : envato (ID d'article Envato Market), gumroad (ID de produit Gumroad, ou son permalien court comme abcde ou son permalien personnalisé) et shop (SKU du produit dans la boutique). Un thème qui déclare au moins un identifiant exige un code d'achat valide, acheté sur l'une de ces plateformes, pour être activé. Laisser tout vide pour les thèmes non vendus. |
item_id | string | Ancien ID d'article Envato à plat, conservé pour les anciennes versions du cœur. Le garder identique à marketplace_item_ids.envato. |
Étape 3 : Créer le fichier de paramètres (config.php)
Créez extensions/themes/mon-theme/config.php: ce fichier définit tous les paramètres personnalisables du thème avec leurs valeurs par défaut :
<?php
return [
// Couleurs
'primary_color' => '#3b82f6',
'secondary_color' => '#1e40af',
'accent_color' => '#f59e0b',
'text_color' => '#1e293b',
// Typographie
'heading_font' => 'DM Sans',
'body_font' => 'Inter',
'base_font_size' => '16px',
// Mise en page
'layout_style' => 'wide',
'container_width' => '1320px',
'wide_container_width' => '1250px',
// En-tête : Pages à sections (accueil + pages du constructeur de sections).
// Ces pages s'ouvrent généralement sur un hero : l'en-tête peut donc le recouvrir.
'header_sectioned_wide' => false,
'header_sectioned_style' => 'default',
'header_sectioned_height' => '',
'header_sectioned_bg_color' => '',
'header_sectioned_bg_image' => '',
'header_sectioned_text_color' => '',
// ... autres paramètres header_sectioned_*
// En-tête, Pages standard (pages de contenu + toute page d'accueil
// d'add-on : blog, boutique, forum). Sans hero, l'en-tête est solide.
'header_standard_wide' => false,
'header_standard_style' => 'default',
'header_standard_height' => '',
'header_standard_bg_color' => '',
'header_standard_bg_image' => '',
'header_standard_text_color' => '',
// ... autres paramètres header_standard_*
// Pied de page
'footer_style' => 'default',
'footer_bg_color' => '',
// ... autres paramètres de pied de page
// Comportement de l'interface
'show_back_to_top' => true,
'default_mode' => 'light',
'allow_mode_toggle' => true,
// Code personnalisé
'custom_css' => '',
'custom_js' => '',
];
Ces paramètres sont modifiables par l'administrateur dans Apparence → Paramètres du thème. Vous pouvez ajouter vos propres clés personnalisées: elles seront disponibles dans toutes les vues du thème via le tableau $themeSettings.
header_sectioned_*: appliqué aux pages à sections : l'accueil et toute page construite avec le constructeur de sections. Ces pages s'ouvrent souvent sur un hero, ce jeu permet donc à l'en-tête de le recouvrir (style transparent, par exemple).header_standard_*: appliqué aux pages standard : les pages de contenu et toute page d'accueil d'add-on (blog, boutique, forum, etc.). Sans hero, ce jeu correspond généralement à un en-tête solide.
wide, style, height, bg_color, bg_image, text_color, btn_label_color, btn_bg_color, text_shadow, logo_height, border_bottom_width, border_bottom_color). Les anciennes clés uniques header_* n'existent plus : un thème personnalisé doit lire le jeu correspondant à la page rendue (voir Étape 5).
Étape 4 : Créer la structure de répertoires
Voici la structure de répertoires recommandée pour un thème complet :
extensions/themes/mon-theme/
├── theme.json
├── config.php
├── assets/
│ ├── images/
│ │ └── thumbnail.png
│ ├── scss/
│ │ ├── theme.scss ← Entrée SCSS principale (OBLIGATOIRE)
│ │ └── pages/ ← SCSS spécifique par page (optionnel)
│ │ ├── home.scss
│ │ ├── contact.scss
│ │ └── ...
│ └── js/
│ ├── theme.js ← Entrée JS principale (OBLIGATOIRE)
│ └── pages/ ← JS spécifique par page (optionnel)
│ └── ...
└── views/
├── layouts/
│ └── master.blade.php ← Layout principal (OBLIGATOIRE)
├── partials/
│ ├── header.blade.php
│ ├── footer.blade.php
│ └── seo.blade.php
├── sections/ ← Templates de sections (constructeur de pages)
├── components/ ← Composants Blade réutilisables
└── pages/ ← Vues de pages complètes
├── home.blade.php
├── page.blade.php
├── contact.blade.php
└── ...
theme.json, assets/scss/theme.scss, assets/js/theme.js et views/layouts/master.blade.php. Sans ces fichiers, le thème ne peut pas être activé.
Étape 5 : Créer le layout principal
Le layout principal (views/layouts/master.blade.php) est le squelette HTML de chaque page. Consultez la version anglaise de cet article pour le code complet du layout de démarrage.
Résoudre le jeu de paramètres d'en-tête
Comme l'en-tête est configuré par deux jeux indépendants (header_sectioned_* et header_standard_* : voir Étape 3), le layout principal doit choisir le bon pour la page rendue et l'exposer sous forme d'un unique tableau $headerSettings à clés courtes (sans préfixe). Ajoutez ce bloc @php dans le <head> du layout :
@php
// Détermine quel jeu de paramètres d'en-tête s'applique à la page.
// Les pages à sections (pages/sectioned.blade.php) déclarent
// @section('headerVariant', 'sectioned') ; toute autre page, pages de
// contenu et pages d'accueil d'add-on, retombe sur 'standard'.
$headerVariant = trim($__env->yieldContent('headerVariant')) === 'sectioned' ? 'sectioned' : 'standard';
$headerPrefix = 'header_' . $headerVariant . '_';
$headerSettings = collect([
'wide', 'style', 'height', 'bg_color', 'bg_image', 'text_color',
'btn_label_color', 'btn_bg_color', 'text_shadow', 'logo_height',
'border_bottom_width', 'border_bottom_color',
])->mapWithKeys(fn ($key) => [$key => $themeSettings[$headerPrefix . $key] ?? null])->all();
@endphp
Votre vue de page à sections (views/pages/sectioned.blade.php : l'accueil et les pages du constructeur de sections) doit donc déclarer @section('headerVariant', 'sectioned') pour recevoir le jeu header_sectioned_* :
@extends('layouts.master')
{{-- Opte pour le jeu de paramètres header_sectioned_* --}}
@section('headerVariant', 'sectioned')
@section('content')
{{-- hero + sections dynamiques --}}
@endsection
Toutes les autres vues (pages de contenu, et toute page d'accueil d'add-on comme blog ou boutique) omettent cette section et reçoivent automatiquement le jeu header_standard_*. Votre partials/header.blade.php consomme alors le tableau résolu par ses clés courtes, par exemple $headerSettings['style'] ou $headerSettings['bg_color'], et non plus les anciennes clés header_*.
Variables disponibles dans toutes les vues
| Variable | Type | Description |
|---|---|---|
$themeSettings | array | Tous les paramètres du thème (valeurs par défaut de config.php + remplacements admin). |
$headerSettings | array | Le jeu d'en-tête résolu pour la page courante (clés courtes : style, bg_color, …), issu de header_sectioned_* ou header_standard_*. Résolu dans master.blade.php (voir ci-dessus). |
$activeTheme | string | Nom du thème actuellement actif. |
$isPreviewMode | bool | true lors de l'utilisation du paramètre de requête ?theme=. |
$currentLocale | string | Code de la langue actuelle (ex. en, fr). |
$availableLocales | Collection | Toutes les langues disponibles pour le sélecteur de langue. |
Étape 6 : Créer le fichier SCSS principal
Créez assets/scss/theme.scss: c'est le point d'entrée principal des styles. Importez Bootstrap, Bootstrap Icons, puis ajoutez vos styles personnalisés.
Étape 7 : Créer le fichier JavaScript principal
Créez assets/js/theme.js: importez Bootstrap JS et les utilitaires partagés du cœur, puis ajoutez vos initialisations personnalisées.
Étape 8 : Créer les vues de pages
Les vues de pages vont dans views/pages/ et étendent le layout principal avec @extends('layouts.master'). Utilisez @section('content') pour le contenu et @push('styles') pour les CSS spécifiques à la page.
Étape 9 : Remplacer les vues des modules
Votre thème peut remplacer les vues de n'importe quel add-on en plaçant des fichiers au chemin correspondant :
extensions/themes/mon-theme/views/pages/blog/index.blade.php
extensions/themes/mon-theme/views/pages/shop/index.blade.php
L'ordre de résolution des vues est :
- Thème actif :
extensions/themes/{thème-actif}/views/{vue} - Thème par défaut (repli) :
extensions/themes/default/views/{vue} - Laravel standard :
resources/views/{vue}
Étape 10 : Compiler les assets avec Vite
La configuration Vite de Larapen découvre automatiquement les assets des thèmes. Après avoir créé vos fichiers SCSS et JS, compilez-les :
# Compiler tous les assets des thèmes
npx vite build
# Ou utiliser la commande Artisan pour un thème spécifique
php artisan theme:build mon-theme
npx vite build après avoir créé de nouveaux fichiers SCSS ou JS. Le manifeste Vite doit être reconstruit pour que les directives @vite() résolvent les assets de votre thème.
Étape 11 : Activer votre thème
- Allez dans Apparence → Thèmes dans le panneau d'administration.
- Cliquez sur « Synchroniser » pour découvrir les nouveaux thèmes.
- Votre thème devrait apparaître dans la liste.
- Cliquez sur « Activer » pour basculer vers votre thème.
Commandes Artisan utiles
| Commande | Description |
|---|---|
php artisan theme:status | Affiche tous les thèmes avec leur statut de compilation. |
php artisan theme:build {nom} | Compile les assets d'un thème spécifique via Vite. |
php artisan theme:publish {nom} | Publie les assets statiques vers public/themes/. |
Utiliser l'IA pour créer des thèmes
Larapen inclut un serveur MCP (Model Context Protocol) qui permet aux assistants IA de comprendre le système de thèmes et de générer des fichiers de thème valides. Au lieu de créer les fichiers manuellement, vous pouvez décrire votre thème en langage naturel et l'IA générera tous les fichiers nécessaires en respectant les conventions Larapen. Consultez l'article « Utiliser l'IA pour créer des thèmes » pour les instructions de configuration détaillées et les flux de travail.
Conseils pour des thèmes de qualité
- Responsive d'abord: Concevez en mobile-first avec la grille responsive de Bootstrap.
- Propriétés CSS personnalisées: Définissez toutes les couleurs et polices comme variables
:root. - Utilitaires Bootstrap: Minimisez le CSS personnalisé en utilisant les utilitaires Bootstrap.
- Accessibilité: Suivez les directives WCAG AA.
- Mode sombre: Utilisez l'attribut
data-bs-theme="dark"de Bootstrap. - Chaînes traduisibles: Jamais de texte en dur. Utilisez toujours
{{ __('clé') }}.