/* ==========================================================================
   TUBA PRACTICE HUB - STYLES PUBLICS (FRONT-END)
   ========================================================================== */

/* ==========================================================================
   PALETTE : HÉRITÉE DU SITE, PLUS JAMAIS IMPOSÉE
   --------------------------------------------------------------------------
   Le plugin ne décide plus de son apparence : il lit celle de Tubarama.
   Chaque variable suit une chaîne de repli, de la plus précise à la plus
   générique :

     1. --cp-*                 les tokens de Tubarama (plugin partitions-library)
     2. --wp--preset--color--* les couleurs du thème de blocs
     3. une valeur littérale   l'ancienne palette du plugin, en dernier recours

   Concrètement, sur tubarama.fr le hub reprend désormais tout seul le bleu
   #2C5F8D, le rouge brique #C44536, le texte #2D3748 et le fond #F8F9FA du
   site. Si un jour tu changes de thème ou de palette, le hub suit sans qu'une
   seule ligne de ce fichier soit à retoucher — et s'il manque une variable,
   il retombe proprement sur l'ancienne palette.

   Les noms de variables sont INCHANGÉS : tout le reste de la feuille, et les
   styles en ligne des gabarits, continuent de fonctionner à l'identique.
   ========================================================================== */
:root {
    /* --- Couleurs d'action --- */
    --tph-primary:      var(--cp-primary,    var(--wp--preset--color--accent-3, #3b82f6));
    --tph-accent:       var(--cp-accent,     var(--wp--preset--color--accent-2, #8b5cf6));

    /* Survol : assombrissement calculé à partir de la couleur héritée.
       La première déclaration sert de repli aux navigateurs anciens. */
    --tph-primary-dark: #2563eb;
    --tph-primary-dark: color-mix(in srgb, var(--tph-primary) 82%, #000);

    /* --- Surfaces --- */
    --tph-bg-body:      var(--cp-bg-light,   var(--wp--preset--color--base,   #f8fafc));
    --tph-bg-card:      var(--wp--preset--color--base-2, #ffffff);
    --tph-border:       var(--cp-border,     #e2e8f0);

    /* --- Texte --- */
    --tph-text-main:    var(--cp-text,       var(--wp--preset--color--contrast,   #0f172a));
    --tph-text-muted:   var(--cp-text-light, var(--wp--preset--color--contrast-2, #64748b));

    /* --- Couleurs sémantiques : volontairement NON héritées.
           Un « terminé » doit rester vert et une suppression rouge, quelle que
           soit la charte du site. --- */
    --tph-success:      #10b981;
    --tph-danger:       #ef4444;
    --tph-warning-bg:   #fffbeb;
    --tph-warning-text: #d97706;

    /* --- Typographie : intégralement héritée du site ---
           Le hub imposait « system-ui », ce qui le faisait ressortir comme une
           application collée sur la page. Il reprend maintenant le Roboto
           Condensed du site pour le texte et le Roboto pour les titres. */
    --tph-font:         inherit;
    --tph-font-heading: var(--wp--preset--font-family--roboto, inherit);

    /* --- Formes : arrondis et ombres adoucis ---
           Le site est plat et sobre ; des cartes à 16 px d'arrondi avec de
           grosses ombres portées juraient nettement. */
    --tph-radius-sm: 6px;
    --tph-radius-md: 8px;
    --tph-radius-lg: 10px;

    --tph-shadow-sm:    0 1px 2px rgba(45, 55, 72, 0.06);
    --tph-shadow-md:    0 4px 12px -4px rgba(45, 55, 72, 0.12);
    --tph-shadow-hover: 0 8px 18px -6px rgba(45, 55, 72, 0.16);

    --tph-transition: all 0.2s cubic-bezier(0.4, 0, 0.2, 1);

    /* --- Couleurs des onglets : VOLONTAIREMENT CONSERVÉES ---
           Ce code couleur sert de repère de navigation aux élèves : il ne
           suit PAS la palette du site, et garde exactement les teintes
           d'origine. Les boutons-raccourcis de la playlist vide reprennent
           les mêmes variables, pour que le repère reste cohérent. */
    --tph-tab-seance:     #10b981;
    --tph-tab-exercices:  #3b82f6;
    --tph-tab-etudes:     #4f46e5;
    --tph-tab-programmes: #8b5cf6;
    --tph-tab-generateur: #f59e0b;
    --tph-tab-favoris:    #ec4899;
    --tph-tab-suivi:      #06b6d4;
}

/* --------------------------------------------------------------------------
   1. BOUTONS GÉNÉRAUX
   -------------------------------------------------------------------------- */
.tph-btn {
    background: var(--tph-primary);
    color: white;
    border: none;
    padding: 10px 20px;
    border-radius: var(--tph-radius-sm);
    cursor: pointer;
    font-weight: 600;
    font-size: 0.95rem;
    text-decoration: none;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    transition: var(--tph-transition);
    letter-spacing: 0.3px;
}

.tph-btn:hover,
.tph-btn:focus-visible {
    background: var(--tph-primary-dark);
    transform: translateY(-1px);
    box-shadow: var(--tph-shadow-md);
    color: white;
}

/* Accessibilité : le contour de focus était invisible sur les boutons. */
.tph-btn:focus-visible,
.tph-tab-btn:focus-visible {
    outline: 2px solid var(--tph-primary);
    outline-offset: 2px;
}

.tph-btn:active {
    transform: translateY(0);
}

.tph-btn-success { background: var(--tph-success); }
.tph-btn-success:hover { background: #059669; }

/* ==========================================================================
   BOUTON RÉINITIALISER (Style Secondaire)
   ========================================================================== */
.tph-btn.tph-reset-filters {
    background: transparent;
    color: #64748b; /* Gris ardoise pour le texte */
    border: 1px solid #cbd5e1; /* Bordure fine grise */
    box-shadow: none; /* On enlève l'ombre pour le différencier de l'action principale */
}

/* L'effet au survol de la souris */
.tph-btn.tph-reset-filters:hover {
    background: #f1f5f9; /* Un gris très très clair */
    color: #334155; /* Le texte devient un peu plus foncé */
    border-color: #94a3b8; /* La bordure s'assombrit légèrement */
    transform: translateY(-1px); /* Le petit effet de soulèvement agréable */
}


/* --------------------------------------------------------------------------
   2. CATALOGUE (Filtres, Grille et Cartes)
   -------------------------------------------------------------------------- */
.tph-filters-form {
    background: var(--tph-bg-card);
    padding: 20px;
    border-radius: var(--tph-radius-md);
    margin-bottom: 30px;
    display: flex;
    flex-wrap: wrap;
    gap: 15px;
    align-items: center;
    border: 1px solid var(--tph-border);
    box-shadow: var(--tph-shadow-sm);
}

.tph-filters-form select, 
.tph-filters-form input[type="text"] {
    padding: 10px 14px;
    border: 1px solid var(--tph-border);
    border-radius: var(--tph-radius-sm);
    flex: 1;
    min-width: 150px;
    font-size: 0.95rem;
    color: var(--tph-text-main);
    background: var(--tph-bg-body);
    transition: var(--tph-transition);
}

.tph-filters-form select:focus, 
.tph-filters-form input[type="text"]:focus {
    outline: none;
    border-color: var(--tph-primary);
    box-shadow: 0 0 0 3px rgba(59, 130, 246, 0.15);
}

.tph-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
    gap: 25px;
}

.tph-card {
    background: var(--tph-bg-card);
    border-radius: var(--tph-radius-lg);
    box-shadow: var(--tph-shadow-sm);
    border: 1px solid var(--tph-border);
    padding: 24px;
    display: flex;
    flex-direction: column;
    transition: var(--tph-transition);
}

.tph-card:hover {
    transform: translateY(-4px);
    box-shadow: var(--tph-shadow-hover);
    border-color: #cbd5e1;
}

.tph-card-title {
    font-size: 1.25rem;
    font-weight: 700;
    margin: 0 0 12px 0;
    color: var(--tph-text-main);
    line-height: 1.3;
}

.tph-card-tags {
    font-size: 0.8rem;
    font-weight: 500;
    color: var(--tph-text-muted);
    margin-bottom: 15px;
}

.tph-card-tags span {
    background: var(--tph-bg-body);
    padding: 4px 10px;
    border-radius: 20px;
    border: 1px solid var(--tph-border);
    margin-right: 6px;
    margin-bottom: 6px;
    display: inline-block;
}

.tph-card-meta {
    font-size: 0.9rem;
    margin-bottom: 20px;
    flex-grow: 1;
    color: var(--tph-text-muted);
}

.tph-card-meta strong {
    color: var(--tph-text-main);
}

.tph-pagination {
    margin-top: 40px;
    text-align: center;
}

.tph-pagination a, 
.tph-pagination span {
    padding: 8px 16px;
    margin: 0 4px;
    border: 1px solid var(--tph-border);
    border-radius: var(--tph-radius-sm);
    text-decoration: none;
    color: var(--tph-text-muted);
    font-weight: 500;
    transition: var(--tph-transition);
}

.tph-pagination a:hover {
    background: var(--tph-bg-body);
    color: var(--tph-text-main);
}

.tph-pagination .current {
    background: var(--tph-primary);
    color: white;
    border-color: var(--tph-primary);
}


/* --------------------------------------------------------------------------
   3. MA SÉANCE (Mise en page globale et Playlist)
   -------------------------------------------------------------------------- */
.tph-seance-app {
    display: grid;
    /* minmax( 0, 1fr ) et non 1fr : le minimum automatique d'une piste « 1fr »
       vaut « auto », c'est-a-dire la taille du contenu. Une seule image trop
       large suffisait donc a faire gonfler la piste au-dela du conteneur et a
       etirer toute la page (mesure : 3067 px de piste dans une colonne de
       664 px). Avec un minimum explicite a 0, la piste reste bornee et c'est
       l'image qui se plie. */
    grid-template-columns: 320px minmax(0, 1fr);
    gap: 30px;
    align-items: start;
}

.tph-seance-sidebar {
    background: var(--tph-bg-card);
    padding: 20px;
    border-radius: var(--tph-radius-md);
    border: 1px solid var(--tph-border);
    box-shadow: var(--tph-shadow-sm);
}

.tph-playlist-list {
    list-style: none;
    padding: 0;
    margin: 0;
}

.tph-playlist-item {
    background: var(--tph-bg-body);
    padding: 12px 15px !important; 
    border: 1px solid transparent;
    margin-bottom: 10px;
    border-radius: var(--tph-radius-sm);
    display: flex;
    justify-content: space-between;
    align-items: center;
    transition: var(--tph-transition);
}

.tph-playlist-item.active {
    background: var(--tph-bg-card);
    border-color: var(--tph-primary);
    box-shadow: var(--tph-shadow-sm);
}

.tph-playlist-item.active .tph-play-item {
    color: var(--tph-primary);
    font-weight: 700;
}

.tph-playlist-item:hover:not(.active) {
    background: var(--tph-bg-card);
    border-color: var(--tph-border);
}

.tph-drag-handle {
    cursor: grab;
    color: #94a3b8;
    margin-right: 12px;
    font-size: 1.2rem;
    user-select: none;
    transition: color 0.2s;
}

.tph-drag-handle:active {
    cursor: grabbing !important;
    color: var(--tph-primary) !important;
}

.tph-remove-item {
    color: var(--tph-text-muted);
    cursor: pointer;
    font-size: 1.3rem;
    font-weight: bold;
    transition: color 0.2s;
}

.tph-remove-item:hover { color: var(--tph-danger); }

.ui-sortable-helper {
    box-shadow: var(--tph-shadow-md);
    background: var(--tph-bg-card);
    opacity: 0.95;
    border: 1px solid var(--tph-primary) !important;
    transform: scale(1.02);
}


/* --------------------------------------------------------------------------
   4. LE LECTEUR (Studio)
   -------------------------------------------------------------------------- */
.tph-seance-stage {
    min-width: 0;
    background: var(--tph-bg-card);
    padding: 25px; 
    border-radius: var(--tph-radius-lg);
    box-shadow: var(--tph-shadow-md);
    border: 1px solid var(--tph-border);
    
    display: flex;
    flex-direction: column;

    /* HAUTEUR AUTOMATIQUE (1.2.0)
       La scene etait figee a 80 % de la hauteur d'ecran, avec un ascenseur
       interne : sur une etude de plusieurs pages, l'eleve devait faire defiler
       une petite lucarne au milieu de la page. Elle grandit desormais avec son
       contenu, toutes les pages de la partition sont affichees a la suite, et
       c'est la page du site qui defile — un seul ascenseur au lieu de deux. */
    height: auto;
}

#tph-stage-content {
    display: flex;
    flex-direction: column;
    flex-grow: 1;
    min-height: 0;
    /* Sans min-width: 0, un element flex refuse de descendre sous la taille
       de son contenu : la piste de grille etait alors forcee de s'elargir. */
    min-width: 0;
}

.tph-stage-empty {
    text-align: center;
    color: var(--tph-text-muted);
    padding-top: 10vh;
}

.tph-sticky-header {
    /* Maintenant que c'est la page qui defile, l'entete doit coller en haut de
       l'ecran : le titre, les outils et les fleches Precedent/Suivant restent
       accessibles meme au bas de la quatrieme page d'une etude. */
    position: sticky;
    /* Si un jour le site adopte un entete fixe, il suffira de definir
       --tph-sticky-offset (la hauteur de cet entete) pour que le bandeau du
       lecteur vienne se caler juste en dessous au lieu de passer derriere. */
    top: var(--tph-sticky-offset, 0px);

    background: var(--tph-bg-card);
    z-index: 10;
    padding-top: 10px;
    padding-bottom: 5px;
    border-bottom: 1px solid var(--tph-border);
    margin-bottom: 20px;
    flex-shrink: 0;
}

/* La zone vide « Pret a jouer ? » a besoin d'une hauteur propre, puisque la
   scene ne fixe plus la sienne. */
.tph-stage-empty {
    min-height: 40vh;
}

#tph-active-title {
    color: var(--tph-text-main);
    font-weight: 800;
    letter-spacing: -0.5px;
}

.tph-active-meta {
    display: flex;
    gap: 15px;
    color: var(--tph-text-muted);
    margin-bottom: 15px;
    font-weight: 500;
}

.tph-conseil-box {
    background: var(--tph-warning-bg);
    border-left: 4px solid var(--tph-warning-text);
    color: #92400e;
    padding: 15px;
    margin-bottom: 20px;
    border-radius: 0 var(--tph-radius-sm) var(--tph-radius-sm) 0;
}

.tph-scrollable-content {
    flex-grow: 1;
    /* L'ascenseur interne disparait : c'est la page qui defile.
       Il est retabli uniquement en plein ecran (voir section 6). */
    overflow-y: visible;
    min-width: 0;
}

.tph-scrollable-content::-webkit-scrollbar { width: 6px; }
.tph-scrollable-content::-webkit-scrollbar-track { background: transparent; }
.tph-scrollable-content::-webkit-scrollbar-thumb { background: #cbd5e1; border-radius: 10px; }
.tph-scrollable-content::-webkit-scrollbar-thumb:hover { background: #94a3b8; }


/* ==========================================================================
   5. CENTRAGE ET TAILLE DU CONTENU (Partitions)
   ========================================================================== */
.tph-exercice-body {
    text-align: center;
    font-size: 1.05rem;
    line-height: 1.6;
    color: var(--tph-text-main);
}

/* On nettoie les boîtes invisibles générées par l'éditeur WordPress */
.tph-exercice-body figure,
.tph-exercice-body .wp-block-image {
    margin: 0 0 25px 0 !important; 
    width: 100%;
    display: block;
}

/* On force toutes les images à s'étirer à 100% de la zone de lecture */
.tph-exercice-body img {
    display: block;
    margin: 0 auto !important;
    width: 100% !important; /* <-- La magie opère ici */
    /* Ceinture et bretelles : si la partition ne se charge pas, ou si le
       navigateur retient une variante beaucoup plus grande que prevu, elle ne
       doit en aucun cas pouvoir elargir la page. */
    max-width: 100% !important;
    height: auto !important; /* Garde les proportions intactes sans déformer la partition */
    border-radius: var(--tph-radius-sm);
    box-shadow: var(--tph-shadow-sm);
    
    /* NOUVEAU : Blocage des comportements tactiles natifs (Anti-zoom, Anti-menu) */
    -webkit-touch-callout: none; /* Bloque le menu "Enregistrer l'image" sur iOS */
    -webkit-user-select: none;   /* Empêche la sélection au toucher */
    user-select: none;
    -webkit-user-drag: none;     /* Empêche de faire "glisser" l'image */
    pointer-events: none;        /* Rend l'image "transparente" aux clics : le doigt glisse directement sur le lecteur ! */
}

    /* Désactive les liens (<a>) générés par WordPress autour des images */
.tph-exercice-body .wp-block-image a,
.tph-exercice-body figure a,
.tph-exercice-body a:has(img) {
    pointer-events: none !important;
    cursor: default !important;
    display: block;
}


/* ==========================================================================
   6. MODE PLEIN ÉCRAN OPTIMISÉ
   ========================================================================== */
:fullscreen .tph-seance-stage { height: 100dvh; padding: 25px 40px; border-radius: 0; border: none; }
:-webkit-full-screen .tph-seance-stage { height: 100dvh; padding: 25px 40px; border-radius: 0; border: none; }

/* En plein ecran, la scene occupe tout l'ecran : c'est le seul cas ou
   l'ascenseur interne a encore un sens (la page, elle, ne defile plus). */
:fullscreen .tph-scrollable-content,
:-webkit-full-screen .tph-scrollable-content { overflow-y: auto; padding-right: 15px; }

:fullscreen .tph-scrollable-content::-webkit-scrollbar,
:-webkit-full-screen .tph-scrollable-content::-webkit-scrollbar { width: 6px; }

:fullscreen .tph-sticky-header { padding-top: 10px; margin-bottom: 15px; }
:fullscreen #tph-active-title { font-size: 1.5rem; margin-bottom: 5px; }
:fullscreen .tph-active-meta { font-size: 0.9rem; margin-bottom: 10px; }
:fullscreen .tph-stage-controls { padding-bottom: 10px; }

:-webkit-full-screen .tph-sticky-header { padding-top: 10px; margin-bottom: 15px; }
:-webkit-full-screen #tph-active-title { font-size: 1.5rem; margin-bottom: 5px; }
:-webkit-full-screen .tph-active-meta { font-size: 0.9rem; margin-bottom: 10px; }


/* ==========================================================================
   7. LE HUB CENTRAL (Onglets)
   ========================================================================== */
.tph-hub-wrapper {
    /* Suit la largeur « large » définie par le thème plutôt qu'une valeur
       arbitraire : le hub s'aligne ainsi sur les autres blocs de la page. */
    max-width: var(--wp--style--global--wide-size, 1400px);
    margin: 0 auto;
    /* La police n'est plus imposée : elle est héritée du site. */
    font-family: var(--tph-font, inherit);
}

/* Les titres internes du hub suivent la police de titre du site. */
.tph-hub-wrapper h2,
.tph-hub-wrapper h3,
.tph-card-title,
#tph-active-title {
    font-family: var(--tph-font-heading, inherit);
}

.tph-hub-tabs {
    display: flex;
    flex-wrap: wrap;
    gap: 12px;
    margin-bottom: 25px;
    border-bottom: 2px solid var(--tph-border);
    padding-bottom: 15px;
}

.tph-tab-btn {
    background: transparent;
    border: none;
    padding: 10px 20px;
    font-size: 1.05rem;
    font-weight: 600;
    color: var(--tph-text-muted);
    cursor: pointer;
    border-radius: 30px; /* Style "Pillule" très moderne */
    transition: var(--tph-transition);
}

.tph-tab-btn:hover {
    background: var(--tph-bg-body);
    color: var(--tph-text-main);
}

/* --- COULEURS SPÉCIFIQUES POUR CHAQUE ONGLET ACTIF --- */

/* 1. Ma Séance : Vert Émeraude (Action / Pratique) */
.tph-tab-btn[data-target="tph-tab-seance"].active {
    background: var(--tph-tab-seance);
    color: white;
    box-shadow: 0 4px 10px rgba(16, 185, 129, 0.3);
}

/* 2. Catalogue d'Exercices : Bleu ---
   Attention : cet onglet utilisait var(--tph-primary). Depuis que la palette
   est héritée du site, --tph-primary vaut le bleu de Tubarama (#2C5F8D) :
   l'onglet aurait donc changé de teinte. On fige ici sa couleur d'origine. */
.tph-tab-btn[data-target="tph-tab-exercices"].active {
    background: var(--tph-tab-exercices);
    color: white;
    box-shadow: 0 4px 10px rgba(59, 130, 246, 0.3);
}

/* Nouvel onglet Études & Pièces (à ajouter si ce n'est pas déjà fait !) */
.tph-tab-btn[data-target="tph-tab-etudes"].active {
    background: var(--tph-tab-etudes); /* Indigo profond */
    color: white;
    box-shadow: 0 4px 10px rgba(219, 39, 119, 0.3);
}

/* 3. Programmes : Violet */
.tph-tab-btn[data-target="tph-tab-programmes"].active {
    background: var(--tph-tab-programmes);
    color: white;
    box-shadow: 0 4px 10px rgba(139, 92, 246, 0.3);
}

/* 4. Générateur Aléatoire : Orange */
.tph-tab-btn[data-target="tph-tab-generateur"].active {
    background: var(--tph-tab-generateur);
    color: white;
    box-shadow: 0 4px 10px rgba(245, 158, 11, 0.3);
}

/* 5. Favoris : Rose (Cœur) */
.tph-tab-btn[data-target="tph-tab-favoris"].active {
    background: var(--tph-tab-favoris);
    color: white;
    box-shadow: 0 4px 10px rgba(236, 72, 153, 0.3);
}

/* 6. Mon Suivi : Cyan (Statistiques) */
.tph-tab-btn[data-target="tph-tab-suivi"].active {
    background: var(--tph-tab-suivi);
    color: white;
    box-shadow: 0 4px 10px rgba(6, 182, 212, 0.3);
}

/* --------------------------------------------------------------------------
   8. OPTIMISATION MOBILE (CHANGEMENTS DEMANDÉS)
   -------------------------------------------------------------------------- */
/* ==========================================================================
   BASCULE SUR LA LARGEUR RÉELLE DISPONIBLE, PAS SUR CELLE DE LA FENÊTRE
   --------------------------------------------------------------------------
   Le hub est inséré dans la colonne de contenu du site, qui fait environ
   670 px — même sur un écran de 1400 px. Une requête @media classique ne voit
   que la fenêtre : elle ne se déclenchait donc JAMAIS sur ordinateur, et la
   mise en page à deux colonnes (320 px de playlist + le lecteur) restait
   écrasée dans 670 px. Une requête de conteneur mesure la place réellement
   disponible, quelle que soit la taille de l'écran.
   ========================================================================== */
/* Le conteneur est posé sur le WRAPPER et non sur .tph-hub-content : la barre
   d'onglets est un frère de .tph-hub-content, pas un descendant, et n'aurait
   donc jamais été concernée par la requête. */
.tph-hub-wrapper { container-type: inline-size; container-name: tph-hub; }

@container tph-hub (max-width: 860px) {
    .tph-seance-app   { grid-template-columns: minmax(0, 1fr); gap: 20px; }
    .tph-seance-stage { height: auto; }

    /* Les onglets défilent horizontalement au lieu de s'empiler sur trois
       lignes, ce qui repoussait tout le contenu vers le bas. */
    .tph-hub-tabs {
        flex-wrap: nowrap;
        overflow-x: auto;
        -webkit-overflow-scrolling: touch;
        scrollbar-width: none;
        padding-bottom: 10px;
        margin-bottom: 15px;
        border-bottom: 1px solid var(--tph-border);
    }
    .tph-hub-tabs::-webkit-scrollbar { display: none; }
    .tph-tab-btn { flex: 0 0 auto; white-space: nowrap; font-size: 0.95rem; padding: 8px 16px; }

    /* Les quatre tuiles de statistiques tombaient en 3 + 1, la dernière seule
       sur sa ligne. Deux par deux, c'est équilibré et les libellés respirent. */
    .tph-stat-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}

/* Repli pour les navigateurs sans requêtes de conteneur : la bascule sur la
   fenêtre vaut mieux que rien. */
@supports not (container-type: inline-size) {
    @media (max-width: 980px) {
        .tph-seance-app   { grid-template-columns: minmax(0, 1fr); gap: 20px; }
        .tph-seance-stage { height: auto; }
    }
}

@media (max-width: 768px) {
    /* Masquage titre/meta pour navigation */
    #tph-active-title, 
    .tph-active-meta,
    .tph-stage-header span#tph-progress {
        display: none !important;
    }

    .tph-seance-app { grid-template-columns: minmax(0, 1fr); gap: 20px; }

    .tph-sticky-header {
        margin-bottom: 10px !important;
        padding-bottom: 5px !important;
        border-bottom: none !important;
    }

    .tph-hub-tabs { 
        flex-wrap: nowrap; 
        overflow-x: auto; 
        -webkit-overflow-scrolling: touch;
        padding-bottom: 10px;
        margin-bottom: 15px;
        border-bottom: none;
        scrollbar-width: none; 
    }
    .tph-hub-tabs::-webkit-scrollbar { display: none; }
    
    .tph-tab-btn {
        flex: 0 0 auto; 
        white-space: nowrap; 
        font-size: 0.95rem;
        padding: 8px 16px;
    }

    .tph-seance-stage { height: auto; padding: 10px !important; }
    .tph-exercice-body img { width: 100% !important; }

    /* Outils flottants */
    #tph-metronome-panel, #tph-drone-panel, #tph-tuner-panel {
        position: absolute;
        left: 10px;
        right: 10px;
        z-index: 100;
        background: white;
        border: 1px solid var(--tph-primary);
        box-shadow: var(--tph-shadow-md);
        padding: 15px !important;
    }

    .tph-stage-controls {
        display: none; 
        flex-direction: row !important;
        flex-wrap: wrap;
        gap: 8px !important;
        padding: 10px;
        background: #f1f5f9;
        border-radius: var(--tph-radius-sm);
    }

    .tph-mobile-tools-toggle {
        display: block !important;
        width: 100%;
        background: var(--tph-bg-body);
        border: 1px solid var(--tph-border);
        color: var(--tph-primary);
        padding: 6px !important;
        font-size: 0.75rem !important;
        font-weight: bold;
        margin-bottom: 8px;
        cursor: pointer;
    }
}

.tph-mobile-tools-toggle { display: none; }

/* ==========================================================================
   PLEIN ÉCRAN FORCÉ (Contournement Apple / iPad / iOS)
   ========================================================================== */
.tph-ios-fullscreen {
    position: fixed !important;
    top: 0 !important;
    left: 0 !important;
    width: 100vw !important;
    height: 100dvh !important;
    max-width: none !important;
    z-index: 999999 !important; /* Pour passer au-dessus des menus de ton thème WordPress */
    background: var(--tph-bg-body, #ffffff) !important;
    overflow-y: auto !important;
    margin: 0 !important;
    border-radius: 0 !important;
    padding: 20px !important;
    box-sizing: border-box !important;
}

/* ==========================================================================
   9. GAMIFICATION (niveau, quêtes du jour, badges, notifications)
   --------------------------------------------------------------------------
   Tout hérite de la palette ci-dessus : ce bloc n'introduit aucune couleur
   codée en dur, à l'exception de l'or des badges débloqués et du rouge de la
   flamme de série, qui sont des signaux et non des éléments de charte.
   ========================================================================== */

/* --- Bandeau de série, affiché en haut de « Ma Séance » --- */
#tph-gamif-streak { margin-bottom: 18px; }

.tph-streak-inner {
    display: flex;
    align-items: center;
    gap: 12px;
    padding: 12px 14px;
    background: var(--tph-bg-body);
    border: 1px solid var(--tph-border);
    border-radius: var(--tph-radius-sm);
}

.tph-streak-flame { font-size: 1.6rem; line-height: 1; filter: grayscale(1); }
.tph-streak-flame.is-lit { filter: none; }

.tph-streak-text { display: flex; flex-direction: column; line-height: 1.3; }
.tph-streak-text strong { color: var(--tph-text-main); font-size: 1rem; }
.tph-streak-text em { color: var(--tph-text-muted); font-size: 0.82rem; font-style: normal; }

/* --- Panneau complet, en haut de « Mon Suivi » --- */
#tph-gamif-panel {
    background: var(--tph-bg-card);
    border: 1px solid var(--tph-border);
    border-radius: var(--tph-radius-md);
    padding: 22px;
    margin-bottom: 25px;
}

.tph-gamif-head {
    display: flex;
    align-items: center;
    gap: 18px;
    flex-wrap: wrap;
    padding-bottom: 18px;
    border-bottom: 1px solid var(--tph-border);
}

.tph-gamif-level { display: flex; align-items: center; gap: 12px; }

.tph-gamif-level-num {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 48px;
    height: 48px;
    border-radius: 50%;
    background: var(--tph-primary);
    color: #fff;
    font-size: 1.35rem;
    font-weight: 700;
    flex-shrink: 0;
}

.tph-gamif-level-title {
    font-family: var(--tph-font-heading, inherit);
    font-weight: 700;
    font-size: 1.05rem;
    color: var(--tph-text-main);
}

.tph-gamif-bar-wrap { flex: 1 1 200px; min-width: 160px; }

.tph-gamif-bar {
    height: 10px;
    border-radius: 5px;
    background: var(--tph-bg-body);
    border: 1px solid var(--tph-border);
    overflow: hidden;
}

.tph-gamif-bar-fill {
    height: 100%;
    background: var(--tph-primary);
    border-radius: 5px;
    transition: width 0.6s cubic-bezier(0.4, 0, 0.2, 1);
}

.tph-gamif-bar-label {
    display: block;
    margin-top: 6px;
    font-size: 0.8rem;
    color: var(--tph-text-muted);
    text-align: right;
}

.tph-gamif-subtitle {
    font-family: var(--tph-font-heading, inherit);
    font-size: 1rem;
    color: var(--tph-text-main);
    margin: 22px 0 12px;
    display: flex;
    align-items: baseline;
    gap: 8px;
}

.tph-gamif-count { font-size: 0.82rem; font-weight: 400; color: var(--tph-text-muted); }

/* --- Quêtes du jour --- */
.tph-quest-list { list-style: none; padding: 0; margin: 0; }

.tph-quest {
    display: flex;
    align-items: center;
    gap: 10px;
    padding: 10px 12px;
    margin-bottom: 8px;
    background: var(--tph-bg-body);
    border: 1px solid var(--tph-border);
    border-radius: var(--tph-radius-sm);
    font-size: 0.92rem;
    color: var(--tph-text-main);
}

.tph-quest.is-done {
    border-color: var(--tph-success);
    background: color-mix(in srgb, var(--tph-success) 8%, transparent);
}

.tph-quest.is-done .tph-quest-label { text-decoration: line-through; opacity: 0.7; }

.tph-quest-label { flex: 1; }
.tph-quest-icon  { font-size: 1.05rem; }
.tph-quest-xp    { font-size: 0.78rem; font-weight: 700; color: var(--tph-text-muted); white-space: nowrap; }
.tph-quest.is-done .tph-quest-xp { color: var(--tph-success); }

/* --- Collection de badges --- */
.tph-badge-grid {
    list-style: none;
    padding: 0;
    margin: 0;
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(96px, 1fr));
    gap: 10px;
}

.tph-badge {
    display: flex;
    flex-direction: column;
    align-items: center;
    text-align: center;
    gap: 4px;
    padding: 12px 6px;
    border: 1px solid var(--tph-border);
    border-radius: var(--tph-radius-sm);
    background: var(--tph-bg-body);
    cursor: help;
}

.tph-badge-icon  { font-size: 1.7rem; line-height: 1; }
.tph-badge-label { font-size: 0.74rem; line-height: 1.25; color: var(--tph-text-main); }
.tph-badge-progress { font-size: 0.68rem; color: var(--tph-text-muted); }

.tph-badge.is-locked { opacity: 0.45; }
.tph-badge.is-locked .tph-badge-icon { filter: grayscale(1); }

.tph-badge.is-unlocked {
    border-color: #d4a017;
    background: color-mix(in srgb, #d4a017 10%, transparent);
}

/* --- Notifications éphémères --- */
.tph-toast-stack {
    position: fixed;
    left: 50%;
    bottom: 24px;
    transform: translateX(-50%);
    z-index: 999999;
    display: flex;
    flex-direction: column;
    gap: 8px;
    align-items: center;
    pointer-events: none;
    width: max-content;
    max-width: min(92vw, 420px);
}

.tph-toast {
    display: flex;
    align-items: center;
    gap: 12px;
    padding: 12px 18px;
    border-radius: var(--tph-radius-md);
    background: var(--tph-text-main);
    color: #fff;
    box-shadow: var(--tph-shadow-md);
    opacity: 0;
    transform: translateY(12px);
    transition: opacity 0.35s ease, transform 0.35s ease;
}

.tph-toast.is-visible { opacity: 1; transform: translateY(0); }

.tph-toast-icon { font-size: 1.4rem; line-height: 1; }
.tph-toast-text { display: flex; flex-direction: column; line-height: 1.3; }
.tph-toast-text strong { font-size: 0.98rem; }
.tph-toast-text em { font-size: 0.8rem; font-style: normal; opacity: 0.85; }

/* Respect du réglage système « réduire les animations ». */
@media (prefers-reduced-motion: reduce) {
    .tph-toast,
    .tph-gamif-bar-fill,
    .tph-btn,
    .tph-card { transition: none !important; }
    .tph-btn:hover,
    .tph-card:hover { transform: none !important; }
}

@media (max-width: 768px) {
    #tph-gamif-panel { padding: 16px; }
    .tph-gamif-head { gap: 12px; }
    .tph-badge-grid { grid-template-columns: repeat(auto-fill, minmax(80px, 1fr)); }
}


/* ==========================================================================
   10. BLOCS D'ONGLET (remplacent les styles en ligne des gabarits)
   --------------------------------------------------------------------------
   Ces classes reprennent à l'identique les styles qui étaient écrits dans les
   attributs style="" des gabarits. Les couleurs viennent maintenant des
   variables héritées du site.
   ========================================================================== */

.tph-pane-intro { text-align: center; margin-bottom: 30px; padding-top: 10px; }
.tph-pane-intro h2 { margin-top: 0; color: var(--tph-text-main); }
.tph-pane-intro p  { color: var(--tph-text-muted); margin-bottom: 0; }

.tph-suivi-card { border-top: 4px solid var(--tph-tab-suivi); }

.tph-pane-title    { margin-top: 0; text-align: center; color: var(--tph-text-main); }
.tph-pane-subtitle { text-align: center; color: var(--tph-text-muted); margin-bottom: 30px; }

.tph-section-title {
    font-family: var(--tph-font-heading, inherit);
    font-size: 1.2rem;
    color: var(--tph-text-main);
    margin-bottom: 15px;
    padding-bottom: 10px;
    border-bottom: 2px solid var(--tph-border);
}

/* --- Tuiles de statistiques --- */
.tph-stat-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
    gap: 15px;
    margin-bottom: 30px;
}

.tph-stat {
    background: var(--tph-bg-body);
    border: 1px solid var(--tph-border);
    border-radius: var(--tph-radius-sm);
    padding: 20px;
    text-align: center;
}

.tph-stat-icon  { font-size: 2rem; margin-bottom: 5px; line-height: 1; }
.tph-stat-value { font-size: 1.5rem; font-weight: 700; color: var(--tph-text-main); }
.tph-stat-label { font-size: 0.85rem; color: var(--tph-text-muted); }

/* --- Historique --- */
.tph-history-list { list-style: none; padding: 0; margin: 0; }

.tph-history-item {
    background: var(--tph-bg-body);
    border: 1px solid var(--tph-border);
    border-radius: var(--tph-radius-sm);
    padding: 15px;
    margin-bottom: 10px;
    display: flex;
    justify-content: space-between;
    align-items: center;
}

.tph-history-date { color: var(--tph-text-main); display: block; margin-bottom: 3px; font-weight: 700; }
.tph-history-meta { font-size: 0.85rem; color: var(--tph-text-muted); }

.tph-history-duree {
    background: var(--tph-bg-card);
    border: 1px solid var(--tph-border);
    color: var(--tph-text-main);
    padding: 4px 10px;
    border-radius: 20px;
    font-weight: 700;
    font-size: 0.9rem;
    white-space: nowrap;
}

.tph-history-empty { color: var(--tph-text-muted); text-align: center; padding: 20px; }

/* --- Actions secondaires --- */
.tph-pane-actions { text-align: center; margin-top: 30px; }

.tph-btn.tph-btn-ghost-danger {
    background: transparent;
    color: var(--tph-danger);
    border: 1px solid var(--tph-danger);
    font-size: 0.85rem;
    box-shadow: none;
}

.tph-btn.tph-btn-ghost-danger:hover {
    background: color-mix(in srgb, var(--tph-danger) 10%, transparent);
    color: var(--tph-danger);
}

/* --- Raccourcis de la playlist vide ---
   Ils reprennent le code couleur des onglets vers lesquels ils mènent. */
.tph-playlist-empty-actions { display: flex; flex-direction: column; gap: 10px; }
.tph-playlist-empty-text    { color: var(--tph-text-muted); margin: 0 0 20px; font-size: 0.95rem; }

.tph-nav-shortcut { width: 100%; }
.tph-nav-shortcut[data-target="tph-tab-exercices"]  { background: var(--tph-tab-exercices); }
.tph-nav-shortcut[data-target="tph-tab-etudes"]     { background: var(--tph-tab-etudes); }
.tph-nav-shortcut[data-target="tph-tab-programmes"] { background: var(--tph-tab-programmes); }
.tph-nav-shortcut[data-target="tph-tab-generateur"] { background: var(--tph-tab-generateur); }

/* --- Barre latérale de séance --- */
.tph-sidebar-title { margin-top: 0; font-family: var(--tph-font-heading, inherit); }

/* Ces deux blocs portaient un style="display:none" dans le HTML. Le passage en
   CSS évite que le navigateur les affiche une fraction de seconde avant que le
   JavaScript ne prenne la main. tph-playlist.js pose ensuite « flex » en ligne,
   ce qui active enfin la direction colonne et l'espacement (jusqu'ici sans
   effet, car jQuery .show() repassait l'élément en « block »). */
.tph-playlist-empty   { display: none; text-align: center; padding: 10px 0; }
.tph-playlist-actions { display: none; flex-direction: column; gap: 10px; margin-top: 20px; }

.tph-playlist-actions .tph-btn { width: 100%; }

.tph-btn.tph-btn-save   { background: #1fb8b2; color: #fff; }
.tph-btn.tph-btn-save:hover { background: #189a95; }

.tph-btn.tph-btn-danger { background: var(--tph-danger); color: #fff; }
.tph-btn.tph-btn-danger:hover { background: #dc2626; }

/* Les raccourcis gardent leur couleur d'onglet au survol : on assombrit
   légèrement plutôt que de basculer sur la couleur principale. */
.tph-btn.tph-nav-shortcut:hover { filter: brightness(0.92); }

/* ==========================================================================
   11. PLAFOND DES COMMANDES DU LECTEUR
   --------------------------------------------------------------------------
   Depuis que la séance passe en une seule colonne dans la colonne de contenu
   du site, le lecteur dispose de toute la largeur (environ 850 px). Les trois
   boutons d'outils, en « flex: 1 1 auto », s'étiraient alors sur 250 px chacun
   et les flèches Précédent / Suivant sur près de 400 px : des barres démesurées
   pour des commandes secondaires, qui écrasaient visuellement la partition.

   On plafonne donc la zone de commandes et les panneaux d'outils, et on les
   centre. La partition, elle, garde toute la largeur : c'est le contenu que
   l'élève vient lire.
   ========================================================================== */
.tph-stage-controls,
#tph-metronome-panel,
#tph-drone-panel,
#tph-tuner-panel {
    max-width: 640px;
    margin-left: auto;
    margin-right: auto;
}

/* Le titre et les méta-informations suivent le même axe pour rester alignés
   avec les commandes plutôt que de flotter tout à gauche d'une large zone. */
.tph-sticky-header > #tph-active-title,
.tph-sticky-header > .tph-active-meta,
.tph-sticky-header > .tph-stage-header {
    max-width: 640px;
    margin-left: auto;
    margin-right: auto;
}


/* ==========================================================================
   12. COHÉRENCE CHROMATIQUE PAR ONGLET
   --------------------------------------------------------------------------
   Chaque onglet porte déjà une couleur dans sa pastille de navigation. Les
   boutons d'action à l'intérieur du panneau reprennent désormais cette même
   couleur : bleu dans « Exercices Techniques », indigo dans « Études &
   Pièces », violet dans « Programmes », etc. L'élève associe ainsi une teinte
   à un type de contenu, et le repère fonctionne aussi bien dans la barre
   d'onglets que dans le contenu.

   Le mécanisme : chaque panneau déclare sa teinte dans --tph-tab-accent, et
   une seule règle s'en sert. Ajouter un onglet demande une seule ligne.
   ========================================================================== */
#tph-tab-seance     { --tph-tab-accent: var(--tph-tab-seance); }
#tph-tab-exercices  { --tph-tab-accent: var(--tph-tab-exercices); }
#tph-tab-etudes     { --tph-tab-accent: var(--tph-tab-etudes); }
#tph-tab-programmes { --tph-tab-accent: var(--tph-tab-programmes); }
#tph-tab-generateur { --tph-tab-accent: var(--tph-tab-generateur); }
#tph-tab-favoris    { --tph-tab-accent: var(--tph-tab-favoris); }
#tph-tab-suivi      { --tph-tab-accent: var(--tph-tab-suivi); }

/* Boutons d'action principaux du panneau.
   Sont volontairement exclus : le bouton « Réinitialiser » (secondaire), les
   boutons à valeur sémantique fixe (terminer = vert, supprimer = rouge), et
   les raccourcis de navigation, qui portent déjà la couleur de l'onglet vers
   lequel ils mènent. */
.tph-tab-pane .tph-btn:not(.tph-reset-filters):not(.tph-btn-ghost-danger):not(.tph-btn-success):not(.tph-btn-danger):not(.tph-btn-save):not(.tph-nav-shortcut) {
    background: var(--tph-tab-accent, var(--tph-primary));
}

.tph-tab-pane .tph-btn:not(.tph-reset-filters):not(.tph-btn-ghost-danger):not(.tph-btn-success):not(.tph-btn-danger):not(.tph-btn-save):not(.tph-nav-shortcut):hover {
    background: var(--tph-tab-accent, var(--tph-primary));
    filter: brightness(0.9);
}

/* Les éléments d'interface qui signalent l'état actif suivent la même teinte. */
.tph-tab-pane .tph-pagination .current {
    background: var(--tph-tab-accent, var(--tph-primary));
    border-color: var(--tph-tab-accent, var(--tph-primary));
}

.tph-tab-pane .tph-filters-form select:focus,
.tph-tab-pane .tph-filters-form input[type="text"]:focus {
    border-color: var(--tph-tab-accent, var(--tph-primary));
    box-shadow: 0 0 0 3px color-mix(in srgb, var(--tph-tab-accent, var(--tph-primary)) 18%, transparent);
}

.tph-tab-pane .tph-card:hover {
    border-color: color-mix(in srgb, var(--tph-tab-accent, var(--tph-primary)) 45%, var(--tph-border));
}

/* Un liseré discret en haut de chaque carte rappelle la couleur de l'onglet. */
.tph-tab-pane .tph-grid .tph-card {
    border-top: 3px solid var(--tph-tab-accent, var(--tph-primary));
}

/* Le focus clavier reprend aussi la teinte du panneau. */
.tph-tab-pane .tph-btn:focus-visible {
    outline-color: var(--tph-tab-accent, var(--tph-primary));
}

/* ==========================================================================
   13. APERÇU DE LA PARTITION DANS LES FICHES DU CATALOGUE
   --------------------------------------------------------------------------
   La vignette déborde volontairement le rembourrage de la carte pour venir
   se coller sous le liseré coloré de l'onglet.

   L'image est mise à l'échelle sur la LARGEUR, jamais sur la hauteur, puis le
   cadre rogne ce qui dépasse par le bas. On voit donc toujours la partition
   sur toute sa largeur, et le début du morceau — la portée qui permet de le
   reconnaître.

   C'est un changement par rapport à « object-fit: cover », qui ajustait sur la
   dimension la plus contraignante : une image plus large que le cadre (rapport
   supérieur à 2,15:1, typiquement un système isolé) se retrouvait rognée sur
   les côtés, ce qui donnait un effet de zoom incohérent d'une fiche à l'autre.

   La hauteur du cadre, elle, ne bouge jamais : les tuiles restent alignées.
   ========================================================================== */
.tph-card-preview {
    /* Compense le padding de 24 px de la carte pour occuper toute sa largeur. */
    margin: -24px -24px 16px;
    height: 150px;
    overflow: hidden;
    background: var(--tph-bg-body);
    border-bottom: 1px solid var(--tph-border);
    border-radius: calc(var(--tph-radius-lg) - 1px) calc(var(--tph-radius-lg) - 1px) 0 0;

    /* Ancre l'image en haut du cadre. Une image trop haute déborde et se fait
       rogner par le bas ; une image inhabituellement plate laisse apparaître
       le fond sous elle, plutôt que d'être étirée. */
    display: flex;
    align-items: flex-start;
    justify-content: center;
}

.tph-card-preview .tph-card-preview-img,
.tph-card-preview img {
    display: block;
    width: 100%;
    /* hauteur libre : c'est la largeur qui commande. */
    height: auto;
    max-width: 100%;
    /* Sans cela, le conteneur flex comprimerait l'image pour la faire entrer. */
    flex-shrink: 0;

    /* Astuce : dans un conteneur flex, une marge automatique sur l'axe
       transversal absorbe l'espace libre et prime sur align-items — mais
       seulement s'il y a de l'espace libre. Résultat, sans une seule ligne de
       JavaScript :
         · image plus haute que le cadre  -> aucun espace libre, les marges
           valent 0, l'image reste ancrée en haut et se fait rogner par le bas ;
         · image plus plate que le cadre  -> elle est centrée verticalement,
           au lieu de laisser une bande de fond vide sous elle. */
    margin-top: auto;
    margin-bottom: auto;
    transition: filter 0.25s ease;
}

/* Au survol, on éclaircit légèrement plutôt que d'agrandir : un agrandissement
   rognerait les bords et redonnerait l'impression de zoom qu'on vient d'éviter. */
.tph-card:hover .tph-card-preview img { filter: brightness(1.05); }

/* Une image absente ne doit pas laisser un cadre vide disgracieux. */
.tph-card-preview img[alt=""]:not([src]),
.tph-card-preview img[src=""] { display: none; }

@media (prefers-reduced-motion: reduce) {
    .tph-card-preview img,
    .tph-card:hover .tph-card-preview img { transition: none; filter: none; }
}

@media (max-width: 768px) {
    .tph-card-preview { height: 120px; }
}
