Intégration Laravel

Guide complet pour utiliser TailwindUI PHP avec Laravel

Installation

Étape 1 : Copier les fichiers

Copiez le dossier UI/ dans app/ :

laravel-project/
├── app/
├── UI/
├── Component.php
├── Button.php
├── Card.php
├── ...
├── Http/
├── Models/
└── Providers/

Important : Modifiez le namespace de TailwindUI dans chaque fichier PHP.

Étape 2 : Mettre à jour les namespaces

Dans chaque fichier du dossier UI, changez le namespace :

<?php
// Avant
namespace TailwindUI;

// Aucun changement nécessaire si vous utilisez TailwindUI dans Laravel !
// Le namespace App\ est déjà configuré par défaut.
?>

Étape 3 : Configurer Tailwind CSS

Si vous n'avez pas encore Tailwind CSS dans votre projet Laravel :

npm install -D tailwindcss postcss autoprefixer
npx tailwindcss init -p

Ou utilisez le CDN dans votre layout Blade :

<!-- resources/views/layouts/app.blade.php -->
<!DOCTYPE html>
<html lang="fr">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>@yield('title', 'Mon Application')</title>

    <!-- Tailwind CSS CDN -->
    <script src="https://cdn.tailwindcss.com"></script>

    <!-- Font Awesome -->
    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.0/css/all.min.css">

    @stack('styles')
</head>
<body class="bg-gray-50">
    @yield('content')

    @stack('scripts')
</body>
</html>

Utilisation dans Blade

Méthode 1 : Utilisation directe

{{-- resources/views/dashboard.blade.php --}}

@extends('layouts.app')

@section('title', 'Dashboard')

@section('content')
<div class="max-w-7xl mx-auto py-8 px-4">
    <h1 class="text-3xl font-bold mb-8">Tableau de bord</h1>

    {{-- Alertes --}}
    @if(session('success'))
        {!! \TailwindUI\Alert::success(session('success')) !!}
    @endif

    @if(session('error'))
        {!! \TailwindUI\Alert::error(session('error')) !!}
    @endif

    {{-- Statistiques --}}
    <div class="grid grid-cols-1 md:grid-cols-4 gap-6 mb-8">
        {!! \TailwindUI\Card::stat('Projets', $projectCount, 'fas fa-folder', 'blue') !!}
        {!! \TailwindUI\Card::stat('Tâches', $taskCount, 'fas fa-tasks', 'green') !!}
        {!! \TailwindUI\Card::stat('Terminées', $completedCount, 'fas fa-check-circle', 'purple') !!}
        {!! \TailwindUI\Card::stat('En retard', $overdueCount, 'fas fa-exclamation-triangle', 'red') !!}
    </div>

    {{-- Tableau --}}
    @php
        $headers = ['Titre', 'Statut', 'Priorité', 'Actions'];
        $rows = [];
        foreach($tasks as $task) {
            $rows[] = [
                e($task->title),
                \TailwindUI\Table::statusCell($task->status),
                \TailwindUI\Table::priorityCell($task->priority),
                \TailwindUI\Table::actionsCell([
                    \TailwindUI\Table::actionButton(route('tasks.edit', $task), 'fas fa-edit', 'Modifier', 'blue'),
                    \TailwindUI\Table::actionButton(route('tasks.destroy', $task), 'fas fa-trash', 'Supprimer', 'red')
                ])
            ];
        }
    @endphp

    {!! \TailwindUI\Table::full($headers, $rows) !!}
</div>
@endsection

Méthode 2 : Avec imports use

{{-- resources/views/projects/create.blade.php --}}

@php
    use TailwindUI\Form;
    use TailwindUI\Button;
    use TailwindUI\Card;
@endphp

@extends('layouts.app')

@section('content')
<div class="max-w-2xl mx-auto py-8">
    {!! Card::withHeader(
        'Nouveau Projet',
        '
        <form method="POST" action="' . route('projects.store') . '">
            ' . csrf_field() . '
            ' . Form::input('title', 'Titre du projet', [
                'required' => true,
                'value' => old('title')
            ], $errors->first('title')) . '

            ' . Form::textarea('description', 'Description', [
                'rows' => 4,
                'value' => old('description')
            ], $errors->first('description')) . '

            ' . Form::grid([
                Form::select('priority', 'Priorité', [
                    'low' => 'Basse',
                    'medium' => 'Moyenne',
                    'high' => 'Haute'
                ], old('priority', 'medium')),
                Form::datetime('deadline', 'Date limite', 'date', [
                    'value' => old('deadline')
                ])
            ], 2) . '

            <div class="flex justify-end space-x-4 pt-6 border-t">
                ' . Button::secondary('Annuler', ['onclick' => 'history.back()']) . '
                ' . Button::withIcon('Créer', 'fas fa-save', 'primary', ['type' => 'submit']) . '
            </div>
        </form>
        '
    ) !!}
</div>
@endsection

Créer une Facade (Optionnel)

Helper Class UI

Créez une classe helper pour un accès plus simple :

<?php
// app/Helpers/UI.php

namespace App\Helpers;

use TailwindUI\Button;
use TailwindUI\Card;
use TailwindUI\Form;
use TailwindUI\Alert;
use TailwindUI\Badge;
use TailwindUI\Table;
use TailwindUI\Navigation;

class UI
{
    // Button shortcuts
    public static function button(...$args) { return Button::primary(...$args); }
    public static function buttonPrimary(...$args) { return Button::primary(...$args); }
    public static function buttonSecondary(...$args) { return Button::secondary(...$args); }
    public static function buttonSuccess(...$args) { return Button::success(...$args); }
    public static function buttonDanger(...$args) { return Button::danger(...$args); }
    public static function buttonWithIcon(...$args) { return Button::withIcon(...$args); }

    // Card shortcuts
    public static function card(...$args) { return Card::basic(...$args); }
    public static function cardWithHeader(...$args) { return Card::withHeader(...$args); }
    public static function stat(...$args) { return Card::stat(...$args); }
    public static function emptyState(...$args) { return Card::empty(...$args); }

    // Form shortcuts
    public static function input(...$args) { return Form::input(...$args); }
    public static function textarea(...$args) { return Form::textarea(...$args); }
    public static function select(...$args) { return Form::select(...$args); }
    public static function checkbox(...$args) { return Form::checkbox(...$args); }

    // Alert shortcuts
    public static function alertSuccess(...$args) { return Alert::success(...$args); }
    public static function alertError(...$args) { return Alert::error(...$args); }
    public static function alertWarning(...$args) { return Alert::warning(...$args); }
    public static function alertInfo(...$args) { return Alert::info(...$args); }

    // Badge shortcuts
    public static function badge(...$args) { return Badge::primary(...$args); }
    public static function status(...$args) { return Badge::status(...$args); }
    public static function priority(...$args) { return Badge::priority(...$args); }

    // Table shortcuts
    public static function table(...$args) { return Table::full(...$args); }
    public static function pagination(...$args) { return Table::pagination(...$args); }

    // Navigation shortcuts
    public static function breadcrumb(...$args) { return Navigation::breadcrumb(...$args); }
    public static function tabs(...$args) { return Navigation::tabs(...$args); }
}
?>

Enregistrez-le dans composer.json :

{
    "autoload": {
        "files": [
            "app/Helpers/UI.php"
        ]
    }
}

Utilisation simplifiée

{{-- Dans vos vues Blade --}}

@php use App\Helpers\UI; @endphp

{!! UI::stat('Projets', '12', 'fas fa-folder', 'blue') !!}

{!! UI::input('email', 'Email', ['required' => true]) !!}

{!! UI::buttonWithIcon('Enregistrer', 'fas fa-save', 'primary') !!}

{!! UI::status('active') !!}

{!! UI::alertSuccess('Opération réussie !') !!}

Composants Blade (Avancé)

Créer des composants Blade

Pour une syntaxe encore plus propre, créez des composants Blade :

<?php
// app/View/Components/UIButton.php

namespace App\View\Components;

use Illuminate\View\Component;
use TailwindUI\Button;

class UIButton extends Component
{
    public string $text;
    public string $variant;
    public string $size;
    public array $attributes;

    public function __construct(
        string $text,
        string $variant = 'primary',
        string $size = 'md',
        array $attributes = []
    ) {
        $this->text = $text;
        $this->variant = $variant;
        $this->size = $size;
        $this->attributes = $attributes;
    }

    public function render()
    {
        $method = $this->variant;
        return Button::$method($this->text, $this->attributes, $this->size);
    }
}
?>

Utilisation dans Blade :

<!-- Utilisation avec composant Blade -->
<x-u-i-button text="Enregistrer" variant="primary" />
<x-u-i-button text="Annuler" variant="secondary" />
<x-u-i-button text="Supprimer" variant="danger" />

Exemple de Controller

ProjectController.php

<?php

namespace App\Http\Controllers;

use App\Models\Project;
use Illuminate\Http\Request;

class ProjectController extends Controller
{
    public function index()
    {
        $projects = Project::with('tasks')
            ->where('user_id', auth()->id())
            ->latest()
            ->paginate(10);

        // Stats pour les cartes
        $stats = [
            'total' => Project::where('user_id', auth()->id())->count(),
            'active' => Project::where('user_id', auth()->id())
                ->where('status', 'active')->count(),
            'completed' => Project::where('user_id', auth()->id())
                ->where('status', 'completed')->count(),
        ];

        return view('projects.index', compact('projects', 'stats'));
    }

    public function store(Request $request)
    {
        $validated = $request->validate([
            'title' => 'required|string|max:255',
            'description' => 'nullable|string',
            'priority' => 'required|in:low,medium,high',
            'deadline' => 'nullable|date',
        ]);

        $project = auth()->user()->projects()->create($validated);

        return redirect()
            ->route('projects.show', $project)
            ->with('success', 'Projet créé avec succès !');
    }

    public function destroy(Project $project)
    {
        $this->authorize('delete', $project);

        $project->delete();

        return redirect()
            ->route('projects.index')
            ->with('success', 'Projet supprimé avec succès.');
    }
}
?>

Conseils et Astuces

Validation des erreurs

Utilisez $errors->first('field') pour afficher les erreurs Laravel dans les champs Form :

Form::input('email', 'Email', [], $errors->first('email'))

Old input

Conservez les anciennes valeurs avec old() :

Form::input('title', 'Titre', ['value' => old('title')])

Flash messages

Créez un partial pour les messages flash dans votre layout :

@if(session('success'))
    {!! \TailwindUI\Alert::success(session('success')) !!}
@endif

Routes nommées

Utilisez route() pour les URLs dans les boutons :

Button::primary('Voir', ['onclick' => 'window.location="' . route('projects.show', $project) . '"'])