/*
 * /light façon Frutiz — LE BUREAU (étape 1 : le shell).
 *
 * Sur grand écran, /light quitte la mise en page « une rubrique plein écran »
 * pour retrouver le bureau de main.swf : un fond d'écran, la main bar posée
 * en haut à gauche, les rubriques en ICÔNES, et chaque rubrique ouverte dans
 * une FENÊTRE déplaçable au chrome du bureau Flash (pastille de couleur,
 * replier, fermer).
 *
 * Tout est sous `body.bureau-frutiz`, une classe que bureau-frutiz.js ne pose
 * que sur desktop (≥ 768 px) : le mobile ne voit JAMAIS ces règles — c'est le
 * contrat (« laisse la version mobile inchangée »).
 *
 * Le chrome des fenêtres est refait en CSS d'après main.swf : cadre blanc
 * arrondi, barre-titre à pastille colorée (fraise du salon, poire de
 * l'historique…), boutons replier/fermer saumon, corps vert d'eau. Les icônes
 * du bureau sont les tuiles du tiroir mobile REPARENTÉES (mêmes nœuds, mêmes
 * clics, mêmes voyants), simplement rhabillées en petites icônes étiquetées.
 */

/* La Verdana pixel EMBARQUÉE dans les SWF d'époque (verdana_10pt_st, police
   #602 de main.swf), déjà extraite pour les portages de jeux. Le bureau s'en
   sert pour le chiffre du niveau : d'époque, ce n'est pas un afficheur à
   segments mais un glyphe plein. */
@font-face {
  font-family: 'VerdanaSwf';
  src: url('/snake3/fontes/verdana10.woff') format('woff');
  font-weight: normal; font-style: normal; font-display: swap;
}
/* Les DEUX fontes de l'encart `digital`, extraites de main.swf. Le bytecode
   les nomme sans ambiguïté : le champ du NIVEAU (DefineEditText #430) tire sur
   la fonte #428 « impact » en 11 px, et celui du RANG (#413) sur la fonte
   #412 « lcd » en 22 px. Ni Verdana ni afficheur à segments — d'où le chiffre
   trapu et sans empattement au pied qu'on lit sur le rendu d'époque.

   TOUT CE QUI SUIT REPOSE SUR LEURS MÉTRIQUES. Les hauteurs de ligne et les
   rattrapages du pixel plus bas sont calés sur l'ascendante déclarée par la
   fonte (1033/1024 d'em pour « impact », 1024/1024 pour « lcd »). Ces valeurs
   vivent dans DEUX tables — `hhea`, que lit FreeType (Linux), et `OS/2`, que
   lisent Windows et macOS — et l'extraction n'en écrivait qu'une correctement :
   la seconde était décalée de deux octets, si bien que les mêmes règles
   donnaient un rendu juste ici et des chiffres remontés de trois pixels chez
   les joueurs. Voir scripts/lib/table-os2.js et test/fontesSwf.test.js. */
@font-face {
  font-family: 'ImpactSwf';
  src: url('/frutiz/fontes/impact.woff') format('woff');
  font-weight: normal; font-style: normal; font-display: swap;
}
@font-face {
  font-family: 'LcdSwf';
  src: url('/frutiz/fontes/lcd.woff') format('woff');
  font-weight: normal; font-style: normal; font-display: swap;
}

/* ── Le bureau lui-même ─────────────────────────────────────────────────── */
body.bureau-frutiz #app { position: relative; }
body.bureau-frutiz #bureau {
  position: absolute; inset: 0; z-index: 1;
  background: #ADE76B;                /* le vert du portail, sans fond posé */
  overflow: hidden;
}
/* La couche HAUTE : la main bar et ses meubles, au-dessus des fenêtres —
   les profondeurs du SWF (les fenêtres passent SOUS la barre, recal les
   borne d'ailleurs sous cornerY = 106). */
body.bureau-frutiz #bureau-haut {
  position: absolute; inset: 0; z-index: 20; pointer-events: none;
}
body.bureau-frutiz #bureau-haut > * { pointer-events: auto; }
/* Le tiroir mobile et sa quincaillerie n'existent plus sur le bureau : tout
   ce qui servait (main bar, grille, compte) a été reparenté sur le bureau. */
body.bureau-frutiz #home-panel,
body.bureau-frutiz #home-backdrop { display: none !important; }
/* La barre du haut mobile vit désormais DANS la fenêtre du salon. Hors d'une
   fenêtre, elle n'a pas sa place à l'écran. */
body.bureau-frutiz #topbar { display: none; }
body.bureau-frutiz .fen #topbar {
  display: flex; flex-shrink: 0;
  border-bottom: 1px solid #DDDDDD;
}
body.bureau-frutiz .fen #topbar #menu-btn { display: none; }
/* Aucune rubrique ne s'affiche plein écran : elles vivent en fenêtres. */
body.bureau-frutiz #app > .panel { display: none !important; }

/* ── LA MAIN BAR (MainBar, DoInitAction #775 0x6afba ; mesures 1:1) ───────
   drawInterface : trois drawSmoothSquare empilés — le sombre (`darkest`,
   +2 px tout autour, rayon 12), le liseré (`shade` #DDDDDD), le fond blanc
   (rayon 8, −2 px). La boîte est DÉCALÉE de −10 en x/y : les coins hauts et
   gauche sortent de l'écran, seul le bas-droit s'arrondit. height = 76,
   margin = 6. Largeur (update 0x6bfbb) : 1370 − cornerX − la zone frusion —
   soit le bord droit MOINS 142 px, minimum 600 (minWidth). Vérifié au pixel
   sur le rendu 1:1 : blanc 0..74, #DDD 74..76, #444 76..78. */
body.bureau-frutiz #bureau-coin,
body.bureau-frutiz #bureau-coin-noir {
  /* décalée de −2 : le liseré et le contour des bords haut/gauche sortent de
     l'écran, comme la boîte du SWF décalée de −10 — à l'écran, blanc pur. */
  position: absolute; left: calc(var(--cornerX) - 11px); top: -2px; z-index: 2;
  width: calc(100vw - 131px - var(--cornerX)); min-width: 600px; height: 78px;
  box-sizing: border-box; overflow: hidden;
  background: #fff;
  border-radius: 0 0 12px 0;
  box-shadow: inset 0 0 0 2px #DDDDDD;
}
/* Le CONTOUR SOMBRE est un clip à part, et plus bas : `drawInterface` le pose
   dans `mcInterfaceBlack` (profondeur 2) tandis que le liseré et le fond
   blanc vont dans `mcInterface` (10). Entre les deux vivent `mcTabBlack` (4)
   et `mcTab` (8) — les onglets. Le trait sombre du bas passe donc SOUS eux,
   et ce qu'on lit à sa place, c'est la couture grise de l'onglet. */
body.bureau-frutiz #bureau-coin-noir {
  z-index: 0; background: none; box-shadow: 0 0 0 2px #444444;
  pointer-events: none;
}
/* L'INTÉRIEUR de la barre, au gabarit d'époque (initFrameSet 0x6bb6c, relevé
   1:1). La barre fait 76 de haut, marge 6 : il reste 64 px de contenu, et
   TOUT y tient — là où le tiroir mobile étale 110 px de bouille.
     • `screen` (FrutiScreen) : un CARRÉ de côté height − 2·margin = 64,
       posé à x = cornerX + margin = 9 + 6 = 15 (mesuré : bouille 15..79,
       y 6..70) — d'où la marge gauche 17 (le bloc est décalé de −2) ;
     • `info` : la colonne de droite, qui démarre à x 84 — `digital`
       (cpDigital, min 130×45, étiré à 143 : mesuré x 85..228, y 6..51) et,
       dessous, la rangée des 7 `butPushEmoteIcon` (struct 19 + margin 2 :
       PAS de 21 px exactement — mesuré 88, 109, 130, 151, 172, 193, 214) ;
     • `tile` : la zone extensible, blanche, qui remplit le reste. */
body.bureau-frutiz #bureau-coin .mainbar {
  /* marge gauche 17 : l'anneau de la bouille commence à x 15 dans le rendu
     1:1, et `#bureau-coin` est posé à −2. */
  margin: 8px 8px 8px 17px; padding: 0;
  border-radius: 0; border: 0; box-shadow: none; background: none;
  width: max-content; max-width: calc(100% - 25px);
}
body.bureau-frutiz #bureau-coin .mb-top { gap: 5px; align-items: flex-start; }
body.bureau-frutiz #bureau-coin .mb-avatar { flex: 0 0 64px; height: 64px; }
/* Le cadre de la bouille, c'est `cp.FrutiScreen` — et depuis qu'on a décodé
   `drawCustomSquare` (cf. PLAN.md) on n'a plus à le mesurer, on le CALCULE :
   FrutiScreen se peint en `frSystem`, soit color = [white, green, white], avec
   `{outline: 2, inline: 1, curve: 6}`. La loi donne alors un liseré extérieur
   de 2 px `color[0].shade` = white.shade = #DDDDDD, un anneau intérieur de
   1 px `color[0].darker` = white.darker = #888888, et un rayon de 6 sur la
   boîte du #888888 (le liseré extérieur, lui, s'arrondit à curve + outline =
   8, ce que le box-shadow refait tout seul en gonflant le rayon de son
   épaisseur). Le relevé 1:1 concordait déjà : la boîte du #888888 fait
   exactement 64×64 (x 15..78, y 6..69), la taille de la FrutiScreen. */
body.bureau-frutiz #bureau-coin .mb-avatar .frame {
  inset: 0; border-radius: 6px; box-shadow: 0 0 0 2px #DDDDDD;
}
/* L'anneau sombre est tracé PAR-DESSUS la bouille : `stage`, `cadre` et
   `reflet` sont des ENFANTS du cadre, et une ombre interne passerait dessous.
   Un calque dédié, transparent au clic, le remet au premier plan. */
body.bureau-frutiz #bureau-coin .mb-avatar .frame::after {
  content: ""; position: absolute; inset: 0; border-radius: 6px;
  box-shadow: inset 0 0 0 1px #888888; z-index: 6; pointer-events: none;
}
/* Le REFLET de l'écran, `frutiScreenLight` (#395) : il appartient au même
   objet, il est donc AUSSI sur la bouille de la main bar. Relevé d'époque :
   `#E2F9CB` en x 74 y 10, soit exactement `#C5F297` sous un blanc à 50 % — et
   la peau du Frutiz s'éclaircit dessous, preuve qu'il passe PAR-DESSUS (il
   est à la profondeur 50, hors du masque). Calé sur le bord droit
   (`light._x = width`), à 2 px du bord et 2 px du haut, et il ne s'étire
   pas. */
body.bureau-frutiz #bureau-coin .mb-avatar .frame::before {
  content: ""; position: absolute; right: 2px; top: 2px;
  width: 42.7px; height: 31.8px; z-index: 7; pointer-events: none;
  background: url('/frutiz/sprites/ecran-reflet.svg') 0 0 / 42.7px 31.8px no-repeat;
}
body.bureau-frutiz #bureau-coin #home-avatar-fiche { inset: 0; border-radius: 6px; }
/* La colonne de droite démarre UN pixel plus bas que la bouille (liseré de la
   bouille en y 4, liseré de l'encart en y 5) et laisse 3 px entre l'encart et
   la rangée des émotions (encart jusqu'à y 47, liserés y 48-49, blanc y 50,
   émotions à partir de y 51). */
body.bureau-frutiz #bureau-coin .mb-right {
  gap: 3px; height: 65px; width: 146px; margin-top: 1px;
}
/* L'encart `digital` d'époque tient en 45 px de haut, là où le tiroir mobile
   en prend 72 : ses quatre zones (les 9 barres de progression en haut-gauche,
   la coupe et le rang en haut-droite, « NIV n » en bas-gauche, les raccourcis
   en bas-droite) sont remises au gabarit relevé sur le rendu 1:1. */
/* Arrondi RELEVÉ : le fond atteint son bord gauche dès 1 à 2 px du haut —
   un rayon de 2, pas les 5 du tiroir mobile. Et l'encart a, comme le cadre de
   la bouille, un LISERÉ INTERNE plus sombre qui lui donne son relief :
   mesuré `#97AD80` sur le bord gauche (x 84) et `#A2AF94` en haut (y 7),
   juste à l'intérieur des 2 px de `#DDDDDD`. */
/* Les 45 px du bytecode comptent les DEUX liserés : le rendu 1:1 donne le
   #DDDDDD en y 5-6 et y 48-49, donc une boîte utile de 41 px (y 7..47) et
   146 px de large (x 84..229). */
body.bureau-frutiz #bureau-coin .mb-encart {
  flex: 0 0 41px; border-radius: 2px;
  box-shadow: inset 0 0 0 1px #97AD80, 0 0 0 2px #DDDDDD;
}
/* LA FINITION DE L'ENCART, telle quelle. `cpDigital` (#417) pose en dernier
   (profondeur 7) la forme #416 : elle porte D'UN SEUL TENANT le trait de
   séparation sous la coupe (`#73B01E`), l'ombre du bas (noir 20 %), le liseré
   du haut (blanc 40 %), la grande brillance en L qui longe le haut et le bord
   droit (blanc 50 %) — et l'ÉCLAT OPAQUE du coin haut-droit, le seul morceau
   qui manquait et qui fait tout l'effet. Reproduire ces cinq pièces à la main
   n'aurait donné qu'un à-peu-près ; on pose le dessin d'origine.
   Le SVG est cadré sur le clip entier, donc dans le repère de la PLAQUE
   (150×45) : d'où le débord de 2 px, l'épaisseur du liseré `#DDDDDD` que la
   boîte de l'encart (146×41) ne compte pas. */
body.bureau-frutiz #bureau-coin .mb-encart::after {
  content: ""; position: absolute; inset: -2px; z-index: 4; pointer-events: none;
  background: url('/frutiz/sprites/encart-reflet.svg') left top / 100% 100% no-repeat;
}
/* Du coup les deux pièces que le light dessinait à la main font double emploi
   sur le bureau : le trait de séparation et l'ancien reflet. Le mobile, lui,
   les garde — ces règles ne valent que sous `.bureau-frutiz`. */
body.bureau-frutiz #bureau-coin .enc-divider,
body.bureau-frutiz #bureau-coin .reflet-niv { display: none; }
/* Les 9 barres de progression, au relevé 1:1 (colonne x=90 du rendu) : des
   barres de **2 px séparées de 1 px**, de y 9 à 35 (9×2 + 8×1 = 26), larges
   de 27 (x 86..113) — pas les filets de 1 px du tiroir mobile. Vide
   `#A2EB56`, PLEIN `#73B01E`, l'écart laissant voir le fond `#C8F39A` de
   l'encart. Le remplissage d'époque va du BAS vers le HAUT et, dans une
   barre, de gauche à droite (barre partielle mesurée : `#73B01E` 86..99 puis
   `#A2EB56` 100..113) — c'est déjà la loi de setHomeProgress. */
body.bureau-frutiz #bureau-coin .enc-progress {
  /* le bord d'époque laisse UN pixel de fond avant la première barre
     (liseré 84, fond 85, barre 86) — collées au liseré, elles paraissaient
     sans marge. */
  left: 2px; top: 2px; width: 27px; height: 26px;
}
body.bureau-frutiz #bureau-coin .enc-progress i { height: 2px; background: #A2EB56; }
body.bureau-frutiz #bureau-coin .enc-progress i::before { background: #73B01E; }
/* La coupe et le rang commencent à x 110 dans le rendu d'époque (contre 123
   au tiroir) : l'espace entre les barres de progression et la colonne de
   droite est plus serré. Le trait de séparation part du même bord. */
body.bureau-frutiz #bureau-coin .enc-trophy { left: 33px; top: 3px; height: 17px; gap: 2px; }
body.bureau-frutiz #bureau-coin .enc-divider { left: 34px; right: 4px; top: 21px; }
body.bureau-frutiz #bureau-coin .enc-trophy .tro { height: 16px; }
/* Le RANG : fonte « lcd » du SWF, 22 px — la taille inscrite dans le champ
   texte #413, qui DÉCLARE aussi son encre : `#73B01E`. (Le rendu Ruffle
   échantillonne `#73AF1E` — c'est son anticrénelage, pas la couleur ; le
   champ fait foi.) */
body.bureau-frutiz #bureau-coin .enc-trophy .val {
  font-family: 'LcdSwf', Verdana, sans-serif; font-size: 22px;
  font-weight: normal; color: #73B01E; text-shadow: none;
  /* la coupe tombe juste, mais le chiffre est centré 2 px trop bas dans sa
     ligne : d'époque son sommet est au niveau de celui de la coupe (y 11). */
  position: relative; top: -2px;
}
/* « NIV n » : le bloc d'époque va de x 87 à 108 et fait 8 px d'encre (contre
   6 au tiroir) — le sigle est donc plus grand. Et le CHIFFRE n'est pas un
   afficheur à segments : c'est un glyphe plein de la Verdana pixel embarquée
   dans les SWF (verdana_10pt_st), celle-là même que les portages de jeux
   utilisent déjà. */
/* Le sigle « NIV » est un SVG qui porte 4 px de marge interne en bas : pour que
   son encre finisse en y 44 comme d'époque, la boîte descend d'un pixel sous le
   biseau — l'encart est en `overflow:hidden`, rien ne dépasse. */
/* LA LOI DE `barLevel` (sprite #431), lue au twip près dans le fichier :
     · le sigle est la forme #429, posée en (4.35, 28.75) — 14,2 × 17,4, la
       taille NATURELLE du SVG extrait : le rendre en 17 px l'écrasait de 2 %,
       d'où des jambages d'un demi-pixel trop épais ;
     · le NIVEAU est le champ #430, posé en (14.6, 28.75), cadre (2.9, −2) de
       16,7 × 17,4. Les 2 px de gouttière que Flash réserve de chaque côté
       ôtés, il reste une zone utile de **12,7 × 13,4** qui commence 0,95 px
       après le sigle — et ce champ déclare `align CENTRE`.
   C'est ce dernier point qui manquait : le chiffre poussait vers la droite au
   lieu de rester centré sur sa colonne, si bien qu'à deux chiffres « NIV 13 »
   débordait sur la rangée de raccourcis. Une boîte FIXE et centrée règle le
   cas de 1 comme celui de 32.
   Le +2 px vertical : Flash pose la ligne de texte sous le haut de la zone
   utile, là où CSS centre le glyphe dans son interligne — deux pixels d'écart,
   relevés au comparatif 1:1 (l'encre doit courir des lignes 36 à 44). */
body.bureau-frutiz #bureau-coin .enc-niv {
  left: 2px; bottom: -1px; gap: 0.95px; align-items: flex-start;
}
body.bureau-frutiz #bureau-coin .enc-niv .niv-img { height: 17.4px; width: 14.2px; }
body.bureau-frutiz #bureau-coin .enc-niv .lvl {
  font-family: 'ImpactSwf', Impact, sans-serif; font-size: 11px;
  font-weight: normal; color: #73B01E;
  flex: 0 0 12.7px; text-align: center; line-height: 13.4px; margin-top: 2px;
}
/* Les raccourcis d'époque tiennent plus HAUT (bloc y 26..47 contre 26..50) et
   dans l'ORDRE : l'aide, le forum, le courrier, l'historique, les événements,
   les jeux — l'ordre du tiroir mobile est autre. */
/* La rangée de raccourcis est CALÉE À GAUCHE, au DÉBUT du trait de séparation
   (x 117), et non à son bout. Les six icônes du rendu 1:1 y sont centrées sur
   124, 139, 154, 169, 184 et 199 : un pas de 15 px exactement, à partir de
   x 117. Elles font 15 px et non 13 — la plus large (l'avertissement) couvre
   14 px d'encre — et se touchent, sans marge entre les boutons. */
body.bureau-frutiz #bureau-coin .mb-shortcuts { left: 32px; right: auto; bottom: 4px; }
body.bureau-frutiz #bureau-coin .sc-btn { padding: 0; }
body.bureau-frutiz #bureau-coin .sc-btn img { width: 15px; height: 15px; }
body.bureau-frutiz #bureau-coin .sc-btn[data-sc="Aide"] { order: 0; }
body.bureau-frutiz #bureau-coin .sc-btn[data-sc="Forum"] { order: 1; }
body.bureau-frutiz #bureau-coin .sc-btn[data-sc="Mail"] { order: 2; }
body.bureau-frutiz #bureau-coin .sc-btn[data-sc="Historique"] { order: 3; }
body.bureau-frutiz #bureau-coin .sc-btn[data-sc="Warning"] { order: 4; }
body.bureau-frutiz #bureau-coin .sc-btn[data-sc="Jeux"] { order: 5; }
/* Le REFLET : la brillance d'époque est une tache douce au coin haut-droit,
   centrée vers (222, 11) et large d'une quinzaine de pixels — pas le long
   dégradé du tiroir mobile. L'image est bien celle du SWF (forme #409, blanc
   à 50 %) : seule sa POSE change ici. À revoir : le rendu Flash y monte
   jusqu'au blanc pur, l'extraction n'en garde que la moitié — il y a
   probablement deux couches superposées à l'origine. */
body.bureau-frutiz #bureau-coin .reflet-niv { right: 0; top: 1px; height: 16px; }
body.bureau-frutiz #bureau-coin .mb-emotes { flex: 0 0 21px; justify-content: flex-start; }
/* Le gris autour d'une émotion est un ANNEAU ROND, pas une plaque carrée :
   la carte relevée sur le rendu 1:1 (y 51..71) dessine, pour chacun des sept
   boutons, un cercle de 21 px en #DDDDDD dont le disque de 17 px occupe le
   centre — il reste donc 2 px de gris tout autour, et le fond redevient BLANC
   au-dessus et au-dessous. Les cercles voisins se touchent (4 px de #DDDDDD
   entre deux disques : 2 de chaque anneau). Le « diffus » que l'on croit voir
   n'est que l'anti-crénelage du cercle. Un fond rond de 21 px derrière
   l'icône le reproduit exactement. */
body.bureau-frutiz #bureau-coin .mb-emotes { gap: 0; }
/* Le cercle d'époque couvre PLEINEMENT ses 21 colonnes (x 84..104 en #DDDDDD
   franc, x 83 resté blanc) : Flash ne dégrade pas le pixel tangent, là où le
   navigateur lui applique sa couverture réelle — un quart de teinte — et
   l'anneau paraît deux fois trop fin. Un demi-pixel d'ombre portée, qui suit
   le même arrondi, rend le bord franc et soude les cercles voisins (4 px de
   gris entre deux disques, comme sur le rendu 1:1). */
body.bureau-frutiz #bureau-coin .em-btn {
  flex: 0 0 21px; width: 21px; height: 21px; padding: 0;
  background: #DDDDDD; border-radius: 50%;
  box-shadow: 0 0 0 .5px #DDDDDD;
}
body.bureau-frutiz #bureau-coin .em-btn img { width: 17px; max-width: 17px; height: 17px; }
/* L'ORDRE d'époque (bande #102, images 1 à 7 = setEmote 0 à 6) : le neutre,
   la colère, la tristesse, le sourire, le rire à pleines dents, le rictus,
   puis le rire aux éclats. Le tiroir mobile les range autrement — on ne
   touche qu'à l'affichage du bureau, jamais au DOM partagé. */
body.bureau-frutiz #bureau-coin .em-btn[data-e="5"] { order: 0; }
body.bureau-frutiz #bureau-coin .em-btn[data-e="1"] { order: 1; }
body.bureau-frutiz #bureau-coin .em-btn[data-e="2"] { order: 2; }
body.bureau-frutiz #bureau-coin .em-btn[data-e="3"] { order: 3; }
body.bureau-frutiz #bureau-coin .em-btn[data-e="4"] { order: 4; }
body.bureau-frutiz #bureau-coin .em-btn[data-e="7"] { order: 5; }
body.bureau-frutiz #bureau-coin .em-btn[data-e="6"] { order: 6; }
/* La bannière quotidienne n'a pas cours dans la barre d'époque. */
body.bureau-frutiz #bureau-coin .daily-banner { display: none; }

/* ── LES ONGLETS (`MainBarTab` #781) : un onglet S'ÉTIRE ─────────────────
   Le clip `tab` n'est pas d'une pièce, et c'est toute l'affaire. C'est une
   PLAQUE étirable au-dessus d'un PIED, doublés d'une silhouette sombre :

       barre (#204 → #203)  120 × 18, de y −18 à 0, posée à (−16, 0) et
                            écrasée à 0,2222 — 4 px de haut au repos ;
       bottom (#202)        le PIED (#188, 120 × 23 à 1,5 ; −2,05), avec la
                            pastille (`ico`) à 17,5 ; 2,95 et le titre
                            (champ #190) à 37,25 ; 4,3 ;
       tabFond (#187)       la silhouette sombre — `fondH` sous la plaque,
                            `fondB` sous le pied. Elle ne vit PAS dans le
                            clip : `init` l'attache à `bar.mcTabBlack`, un
                            conteneur posé SOUS toute la rangée.

   La plaque est bornée en bas par `barre._y` et monte de `barre._height` :
   elle occupe donc `_y − _height` .. `_y`, et ce qui dépasse au-dessus de 0
   passe sous la barre principale. Trois positions de repos, et une seule
   règle :

       scrollUp   : barre._y → flActive × 4   (0 rangé, 4 actif)
       attachMenu : barre._height = tabMenuMargeUp + n × tabMenuSpace
       scrollDown : barre._y → barre._height  (la plaque descend d'autant)

   Le menu ne se pose donc pas SUR l'onglet : c'est la plaque étirée qui lui
   fait son fond, et l'onglet descend pour lui laisser la place. D'où les
   deux variables : `--y` (barre._y) et `--h` (barre._height), que le JS
   anime au 0,8 ^ tmod d'époque.

   L'origine du clip tombe au bas de la barre principale (mcTab._y = 76), à
   `cornerX + rang × tabSpace` (110). */
body.bureau-frutiz #bureau-onglets {
  position: absolute; left: var(--cornerX); top: 76px;
  height: 0; right: 0; z-index: 1; pointer-events: none;
}
/* `mcTabBlack` : la silhouette de TOUS les onglets, sous TOUS les onglets.
   Rangée dans le clip de chacun, celle du rang 0 déborderait par-dessus la
   plaque du rang 1 (les onglets se chevauchent de 13 px). */
body.bureau-frutiz #bureau-onglets-noir {
  position: absolute; left: 0; top: 0; width: 0; height: 0; z-index: 0;
}
body.bureau-frutiz .fb-onglet,
body.bureau-frutiz .fb-onglet-fond {
  position: absolute; left: 0; top: 0; width: 0; height: 0;
  --y: 0px; --h: 4px;
}
body.bureau-frutiz .fb-onglet { cursor: pointer; pointer-events: auto; }
/* L'ARRIVÉE : `init` pose le clip à `_y = −30` et lui donne un `addSlide`
   vers `pos.y = 0` — l'onglet TOMBE de sous la barre. */
body.bureau-frutiz .fb-onglet.pose,
body.bureau-frutiz .fb-onglet-fond.pose { transition: top .3s cubic-bezier(.2, .7, .3, 1); }
body.bureau-frutiz .fb-onglet i,
body.bureau-frutiz .fb-onglet-fond i {
  position: absolute; display: block; pointer-events: none;
  background-repeat: no-repeat; background-size: 100% 100%;
}
/* La silhouette sombre — `updateFond` : fondH suit la plaque, fondB le pied. */
body.bureau-frutiz .ot-fondh {
  left: -17.5px; top: calc(var(--y) - var(--h)); width: 123px; height: var(--h);
  background-image: url('/frutiz/sprites/onglet_fondh.svg');
}
body.bureau-frutiz .ot-fondb {
  left: -17.5px; top: var(--y); width: 122.95px; height: 23.5px;
  background-image: url('/frutiz/sprites/onglet_fondb.svg');
}
/* La plaque étirable, puis le pied. */
body.bureau-frutiz .ot-barre {
  left: -16px; top: calc(var(--y) - var(--h)); width: 120px; height: var(--h);
  background-image: url('/frutiz/sprites/onglet_barre.svg');
}
body.bureau-frutiz .ot-pied {
  left: -16px; top: calc(var(--y) - 2.05px); width: 120px; height: 23px;
  background-image: url('/frutiz/sprites/onglet_pied.svg');
}
/* LA COUTURE : le clip `tab` a un TROISIÈME enfant, la forme #205, posée à
   (0, 0) à la profondeur 13 — au-dessus du pied (3) ET de la plaque (10).
   Une bande `#999999` de 123 × 2,5 à cheval sur l'origine (y −0,5 à 2), qui
   recoud l'onglet au liseré sombre de la barre. Elle ne suit RIEN : ni `--y`
   ni `--h` ne la touchent, et c'est bien ce que dit le relevé 1:1 — la bande
   grise court de cornerX au bord droit du dernier onglet, quel que soit
   l'onglet actif. */
body.bureau-frutiz .fb-onglet .ot-couture {
  left: -17.5px; top: -0.5px; width: 123px; height: 2.5px; z-index: 1;
  background-image: url('/frutiz/sprites/onglet_couture.svg');
}
/* LA PASTILLE est un BOUTON : `MainBarTab.init` accroche `bottom.but`, dont
   l'`onPress` déroule le menu du slot. `ico` est ancré à (17,5 ; 2,95) dans
   le pied — soit x 0 dans le repère du clip — et le fruit lui-même occupe,
   DANS ce clip, le cadre (1,35 ; 1,7)–15,85 × 15,05. D'où le (1,35 ;
   `--y` + 4,65) : le relevé 1:1 pose l'orange du rang 0 actif en y 86..96. */
body.bureau-frutiz .fb-onglet-ico {
  position: absolute; left: 1.35px; top: calc(var(--y) + 4.65px);
  width: 15.85px; height: 15.05px; padding: 0; border: 0;
  background: transparent no-repeat left top / 15.85px 15.05px;
  cursor: pointer; z-index: 2;
}
/* LE TITRE : le champ #190 du pied, à (37,25 ; 4,3) — soit, le pied étant
   posé à −17,5, x 19,75 dans le repère du clip. Verdana 10 gras noir. */
body.bureau-frutiz .fb-onglet span {
  position: absolute; left: 19.75px; top: calc(var(--y) + 4.3px);
  width: 82.85px; height: 16px; line-height: 16px;
  font: 700 10px Verdana, Arial, sans-serif; color: #000000;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
  user-select: none; -webkit-user-select: none;
}
/* LE MENU (`MainBarTab.attachMenu`) : il ne flotte pas au curseur et n'a pas
   de fond à lui — les entrées sont attachées DANS le clip, à `menuMc._y =
   barre._y`, et c'est la plaque étirée qui leur sert de plaque. Chaque
   `butText` fait 100 × tabMenuSpace, marge gauche 4, et se pose à
   `_y = −(i × tabMenuSpace + 16)` : l'index 0 EN BAS. `FPTab.getMenu` rendant
   [« Vers bureau », « Fermer »], on lit donc, de haut en bas, « Fermer » puis
   « Vers bureau ». */
body.bureau-frutiz .fb-onglet .ot-menu {
  position: absolute; top: var(--y); height: 0;
  z-index: 3; pointer-events: none;
}
/* LE STYLE D'UNE ENTRÉE, tel que le SWF le compose :
   `Standard.getTextStyle()` donne `{ color: 0, font: "Verdana", size: 10 }`
   — du Verdana 10 NOIR — et `Standard.getButTextBasicBehavior()` donne le
   comportement `colorText` : `over` = 15168875 (#E7756B, le rose du survol),
   `press` = 14540253 (#DDDDDD). La base n'est pas fournie : `setBehavior` la
   prend alors dans le champ, donc le noir du style.
   Le GRAS, lui, n'arrive jamais : `attachMenu` passe bien un
   `textFormat: { bold: true }` dans l'objet d'initialisation, mais aucune des
   trois classes (`But`, `but.Text`, `but.TextBasic`) ne le relit — seul
   `textStyle` compte, et il est vide. Le relevé 1:1 le confirme, les libellés
   du menu sont maigres là où l'étiquette de l'onglet est grasse. On garde le
   bug d'origine.
   La gouttière de 2 px est celle de tout `TextField` Flash : `pos.x` vaut
   `margin.x.min × margin.x.ratio` = 0, et l'encre du « F » tombe en x 126
   pour un bouton posé en 123. */
body.bureau-frutiz .fb-onglet .ot-menu button {
  position: absolute; left: 0; box-sizing: border-box;
  padding: 0 0 3px 2px; border: 0; background: none; pointer-events: auto;
  font: 400 10px Verdana, Arial, sans-serif; color: #000000;
  text-align: left; cursor: pointer; white-space: nowrap;
}
body.bureau-frutiz .fb-onglet .ot-menu button:hover { color: #E7756B; }
body.bureau-frutiz .fb-onglet .ot-menu button:active { color: #DDDDDD; }
/* L'AVERTISSEMENT d'un slot (`MainBarTab.warning`) : un message est arrivé
   dans une conversation qu'on ne regarde pas. `addColorFlash` alterne toutes
   les 500 ms entre `FEMC.setColor` et `FEMC.killColor` — soit une teinte de
   `0xFFB1AB` à 30 %, une demi-seconde sur deux. Une teinte, pas un
   clignotement de luminosité : le calque rose à 30 % d'opacité donne
   exactement `fond × 0,7 + rose × 0,3`, et le masque le confine au DESSIN
   (l'onglet garde ses coins transparents). */
@keyframes fb-onglet-clignote {
  0%, 49.99% { opacity: 0; }
  50%, 100%  { opacity: .3; }
}
body.bureau-frutiz .fb-onglet .ot-teinte {
  background: #FFB1AB; opacity: 0; z-index: 4;
  -webkit-mask-repeat: no-repeat; mask-repeat: no-repeat;
  -webkit-mask-size: 100% 100%; mask-size: 100% 100%;
}
body.bureau-frutiz .fb-onglet .ot-teinte.ot-barre {
  -webkit-mask-image: url('/frutiz/sprites/onglet_barre.svg');
  mask-image: url('/frutiz/sprites/onglet_barre.svg');
  background-image: none;
}
body.bureau-frutiz .fb-onglet .ot-teinte.ot-pied {
  -webkit-mask-image: url('/frutiz/sprites/onglet_pied.svg');
  mask-image: url('/frutiz/sprites/onglet_pied.svg');
  background-image: none;
}
body.bureau-frutiz .fb-onglet.clignote .ot-teinte {
  animation: fb-onglet-clignote 1s steps(1, end) infinite;
}

/* ── UNE FENÊTRE EN ONGLET ────────────────────────────────────────────────
   `WinStandard.initTabMode()` retire le bandeau (`winTopBar`) et masque la
   poignée : l'onglet EST la barre de titre. Et la fenêtre occupe TOUT
   l'espace du bureau — `tab.w = mcw − cornerX`, `tab.h = mch − cornerY`. */
body.bureau-frutiz .fen.fen-en-onglet {
  left: var(--cornerX) !important; top: var(--cornerY) !important;
  width: calc(100% - var(--cornerX)) !important;
  height: calc(100% - var(--cornerY)) !important;
  display: none; border-radius: 0; box-shadow: none;
}
body.bureau-frutiz .fen.fen-en-onglet.fen-onglet-vue { display: flex; }
body.bureau-frutiz .fen.fen-en-onglet > .fen-titre,
/* `initTabMode` (0x5463f) : une fenêtre passée en onglet cache sa poignée. */
body.bureau-frutiz .fen.fen-en-onglet > .fen-poignee,
body.bureau-frutiz .fen.fen-en-onglet > .fen-poignee-vue { display: none; }
/* La GLISSADE de `putInTab()` : la fenêtre sort par le haut avant de passer
   en onglet (`pos.y = −(pos.h + 100)`). Ctrl enfoncée, Flash saute l'anim. */
body.bureau-frutiz .fen.fen-glisse {
  transition: transform .28s ease-in;
  transform: translateY(calc(-100% - 100px));
}
/* Le bureau s'escamote quand un onglet prend la main :

       FPDesktop.onDeactivate = function () {
         this.mcDesk.iconList.removeMovieClip();   // la rangée d'icônes
         this.mcDesk._visible = false;             // le fond du bureau
         …
       }                                           (0xb9574)

   MAIS PAS LE FOND D'ÉCRAN. `wallPaper` est un manager à part
   (`WallPaperMng`, 0x9a5e8), que `FPDesktop` ne touche jamais : l'image
   reste peinte derrière tout, et c'est elle qu'on lit dans la bande qui
   sépare le haut de la fenêtre, la barre et la frusion.

   La preuve est dans ceux qui la cachent EXPRÈS, parce qu'elle est encore
   là : le slot du forum appelle `wallPaper.hide()` (0x6e2fa) et un jeu
   `wallPaper.hideImage()` (0x36cb1) — deux appels qui ne voudraient rien
   dire si un onglet actif l'avait déjà effacée.

   Ici le fond d'écran est peint sur `#bureau` lui-même (`poserFond`) et les
   icônes sont ses ENFANTS : on n'escamote donc que les enfants, et l'on
   coupe la souris sur ce qui reste — un clip invisible ne reçoit rien. */
body.bureau-frutiz.fb-onglet-actif #bureau { pointer-events: none; }
body.bureau-frutiz.fb-onglet-actif #bureau > *,
body.bureau-frutiz.fb-onglet-actif .fen:not(.fen-onglet-vue) { display: none; }
/* La rangée d'icônes est nommée à part : sa règle de mise en place porte DEUX
   identifiants (`#bureau #home-grid`), et l'emporterait sur le `> *`
   ci-dessus, qui n'en a qu'un. C'est pourtant elle que `onDeactivate` retire
   en premier — `iconList.removeMovieClip()`. */
body.bureau-frutiz.fb-onglet-actif #bureau #home-grid { display: none; }

/* ── LE LECTEUR FRUSION (clip `frusion` #324, aplati tel quel) ────────────
   Ce n'est pas un conteneur vide : sa première image porte TOUT le meuble —
   le panneau blanc aux quatre coins arrondis avec son liseré et son contour,
   la cuve grise, et les trois fruits (rouge, jaune, vert) au-dessus. Cadre
   (−117.5, 0)–(1.5, 77.5). Posé au relevé 1:1 : le contour tombe en
   x 1258..1376 sur une scène de 1380 — soit 4 px du bord droit — et de
   y 0 à 77.5. (Les deux boutons ronds du bas, casque et éjection, sont
   attachés au runtime par FrusionSlot : ils viendront avec le lecteur.) */
body.bureau-frutiz #frusion-boite {
  position: absolute; top: 0; right: 4px; width: 119px; height: 77.5px;
  z-index: 2;
}
/* Les COUCHES, dans l'ordre des profondeurs du clip : le fond (1), le berceau
   du tiroir (3), la plaque du milieu (9), le TIROIR (10) et sa jaquette, puis
   la FAÇADE (21 et 34) — une plaque opaque PERCÉE de la cuve, par laquelle on
   voit tourner le disque. Toutes partagent le cadre du clip, elles se
   superposent donc telles quelles. */
body.bureau-frutiz #frusion-boite .fr-couche,
body.bureau-frutiz #frusion-boite .fr-mobile {
  position: absolute; left: 0; top: 0; width: 119px; height: 77.5px;
  pointer-events: none;
}
body.bureau-frutiz #frusion-boite .fr-couche {
  background: left top / 119px 77.5px no-repeat;
}
body.bureau-frutiz #frusion-boite .fr-arriere { background-image: url('/frutiz/sprites/frusion-arriere.svg'); }
body.bureau-frutiz #frusion-boite .fr-fondslot { background-image: url('/frutiz/sprites/frusion-fondslot.svg'); }
body.bureau-frutiz #frusion-boite .fr-milieu { background-image: url('/frutiz/sprites/frusion-milieu.svg'); }
body.bureau-frutiz #frusion-boite .fr-slot { background-image: url('/frutiz/sprites/frusion-slot.svg'); }
body.bureau-frutiz #frusion-boite .fr-avant { background-image: url('/frutiz/sprites/frusion-avant.svg'); }
/* LE DISQUE. `but.icon.Full` ne le met pas à l'échelle (`_xscale = 100`) : il
   fait ses 63 px. `slot.disc._y = −63` le pose au-dessus de l'origine du
   tiroir — au relevé 1:1, son centre tombe 32,25 px plus haut, c'est-à-dire
   au ras de la corde de la cuve : on n'en voit que la moitié basse, et c'est
   ce qui donne le demi-disque qui tourne du rendu d'époque. */
body.bureau-frutiz #frusion-boite .fr-disque {
  position: absolute; left: 28px; top: 7.25px; width: 63px; height: 63px;
  display: none; pointer-events: none;
}
body.bureau-frutiz #frusion-boite .fr-disque.plein { display: block; }
body.bureau-frutiz #frusion-boite .fr-disque.reprenable { pointer-events: auto; cursor: grab; }
body.bureau-frutiz #frusion-boite .fr-disque .ex-disque {
  position: absolute; left: 0; top: 0; width: 63px; height: 63px;
  display: block; transform: none;
}
body.bureau-frutiz #frusion-boite .fr-disque .ex-disque img {
  position: absolute; left: 0; top: 0; width: 63px; height: 63px;
}
body.bureau-frutiz #frusion-boite .fr-disque .ex-disque img.jaquette {
  width: 61px; height: 61px; left: 1px; top: 1px;
}
/* LA ZONE DE DÉPÔT : `slot.dropBox = this` — c'est le TIROIR qu'on vise, pas
   la console. Relevé 1:1 sur le tiroir sorti : il occupe x 28..91 dans la
   boîte, et descend jusqu'à 74 px sous l'origine du tiroir. */
body.bureau-frutiz #frusion-boite .fr-cible {
  position: absolute; left: 28px; top: 71px; width: 63px; height: 74px;
  pointer-events: none;
}
/* Elle n'attrape les dépôts que TIROIR SORTI : rentrée, elle couvrirait un
   morceau de bureau sans rien y faire. */
body.bureau-frutiz #frusion-boite.fr-ouvert .fr-cible { pointer-events: auto; }
/* LES DEUX BOUTONS RONDS, aux places du clip : `#317` (le casque, pushReset)
   en (−100, 60) et `#313` (l'éjection, pushEject) en (−15,85, 60), dans un
   repère dont l'origine tombe à x 117,5 — soit x 17,5 et 101,65 dans la
   boîte. Leurs dessins font 20 px et sont centrés sur ce point. */
body.bureau-frutiz #frusion-boite .fr-but {
  position: absolute; top: 50px; width: 20px; height: 20px;
  border: 0; padding: 0; cursor: pointer; color: transparent; font-size: 0;
  background: transparent center / 20px 20px no-repeat;
}
body.bureau-frutiz #frusion-boite .fr-casque { left: 7.5px; }
body.bureau-frutiz #frusion-boite .fr-eject { left: 91.65px; }
body.bureau-frutiz #frusion-boite .fr-casque { background-image: url('/frutiz/sprites/frusionCasque_up.svg'); }
body.bureau-frutiz #frusion-boite .fr-casque:hover { background-image: url('/frutiz/sprites/frusionCasque_over.svg'); }
body.bureau-frutiz #frusion-boite .fr-casque:active { background-image: url('/frutiz/sprites/frusionCasque_down.svg'); }
body.bureau-frutiz #frusion-boite .fr-eject { background-image: url('/frutiz/sprites/frusionEject_up.svg'); }
body.bureau-frutiz #frusion-boite .fr-eject:hover { background-image: url('/frutiz/sprites/frusionEject_over.svg'); }
body.bureau-frutiz #frusion-boite .fr-eject:active { background-image: url('/frutiz/sprites/frusionEject_down.svg'); }

/* L'ICÔNE GLISSÉE (`_global.createDragIcon`) : le dessin du fichier au bout
   du curseur, centré dessus et transparent aux clics — c'est ce qu'il y a
   DESSOUS qui reçoit le dépôt. */
body.bureau-frutiz .fb-glisse-icone {
  position: fixed; z-index: 3000; pointer-events: none;
  transform: translate(-50%, -50%);
}
body.bureau-frutiz .fb-glisse-icone .ex-disque {
  position: relative; left: 0; top: 0; transform: none;
  display: block; width: 63px; height: 63px;
}
body.bureau-frutiz .fb-glisse-icone .ex-disque img { position: absolute; width: 63px; height: 63px; }
body.bureau-frutiz .fb-glisse-icone .ex-disque img.jaquette {
  width: 61px; height: 61px; left: 1px; top: 1px;
}
/* Une bouille attrapée depuis le carnet : `but.Icon.display` met `icoRatio`
   à 1 pour un `frutibouille` — l'aperçu fait donc r4 de côté, 37 px. */
body.bureau-frutiz .fb-glisse-icone .ex-bouille {
  position: relative; left: 0; top: 0; display: block; width: 37px; height: 37px;
}
body.bureau-frutiz .fb-glisse-icone .ex-bouille iframe,
body.bureau-frutiz .fb-glisse-icone .ex-bouille canvas { width: 37px; height: 37px; border: 0; }

/* ── LES RACCOURCIS DU BUREAU (`cp.DragIconList`) ────────────────────────────
   `FPDesktop.displayIconList` attache un `cpDragIconList` avec une marge de
   18 en x, 12 en y, et `attachIcon` donne à chaque case
   `displayParameters.icon.size.large` de côté — 80. La grille avance de
   `size.large + 4`, soit 84, et `updateIcons` pose bêtement `_x = pos.x` :
   aucune animation, l'icône claque à sa place.

   L'étiquette suit `but.icon.Standard` : `textRatio = 0,5`, donc le dessin
   occupe la moitié haute (37) et le libellé la moitié basse, centré. Un
   DISQUE passe par `but.icon.Full` — pas d'étiquette du tout. */
body.bureau-frutiz .fb-raccourci {
  position: absolute; width: 80px; height: 80px; z-index: 2;
  display: flex; flex-direction: column; align-items: center;
  cursor: pointer; user-select: none; -webkit-user-select: none;
}
body.bureau-frutiz .fb-raccourci .ex-bouille,
body.bureau-frutiz .fb-raccourci .ex-img {
  position: relative; left: 0; top: 4px; display: block;
}
body.bureau-frutiz .fb-raccourci .ex-bouille { width: 37px; height: 37px; }
body.bureau-frutiz .fb-raccourci .ex-bouille iframe,
body.bureau-frutiz .fb-raccourci .ex-bouille canvas { width: 37px; height: 37px; border: 0; }
/* `but.icon.Full` : 63 px de côté, 7 px sous le haut de la case, sans nom. */
body.bureau-frutiz .fb-raccourci .ex-disque {
  position: relative; left: 0; top: 7px; transform: none;
  display: block; width: 63px; height: 63px;
}
body.bureau-frutiz .fb-raccourci .ex-disque img { position: absolute; width: 63px; height: 63px; }
body.bureau-frutiz .fb-raccourci .ex-disque img.jaquette {
  width: 61px; height: 61px; left: 1px; top: 1px;
}
/* L'étiquette du bureau prend la couleur que `displayIconList` calcule : celle
   du fond d'écran s'il en impose une, sinon `colorSet.green.overdark`. */
body.bureau-frutiz .fb-raccourci .fb-r-lbl {
  position: absolute; left: 3px; top: 41px; width: 74px;
  font: 700 11px Verdana, Arial, sans-serif; text-align: center;
  color: var(--fond-txt, #2C4A0F); line-height: 1.15;
  text-shadow: 0 0 3px rgba(var(--fond-halo, 255,255,255), .9);
  overflow: hidden; word-break: break-word;
}
body.bureau-frutiz .fb-raccourci:active .ex-bouille,
body.bureau-frutiz .fb-raccourci:active .ex-img { transform: scale(.9); }

/* Le menu du fond d'écran (`FPDesktop.getMenu`) : la même typographie que
   les entrées de menu d'un onglet — Verdana 10 noir, rose au survol. */
body.bureau-frutiz .fb-menu-bureau {
  position: fixed; z-index: 4000; background: #FFFFFF;
  box-shadow: 0 0 0 2px #DDDDDD; border-radius: 3px; padding: 4px 0;
}
body.bureau-frutiz .fb-menu-bureau button {
  display: block; width: 100%; border: 0; background: none; cursor: pointer;
  font: 400 10px Verdana, Arial, sans-serif; color: #000000;
  padding: 3px 10px 3px 8px; text-align: left; white-space: nowrap;
}
body.bureau-frutiz .fb-menu-bureau button:hover { color: #E7756B; }
body.bureau-frutiz .fb-menu-bureau button:active { color: #DDDDDD; }

/* La fenêtre d'un dossier du bureau : la même grille de cases que les deux
   explorateurs, sur le blanc de `frSystem`. */
body.bureau-frutiz .fen .fb-dossier-panneau {
  flex: 1; min-height: 0; overflow: auto; padding: 8px;
  display: flex; flex-wrap: wrap; align-content: flex-start; gap: 0;
  background: #FFFFFF;
}
body.bureau-frutiz .fen .fb-dossier-vide {
  margin: 0; padding: 12px 8px;
  font: 400 11px Verdana, Arial, sans-serif; color: #5A7D33;
}

/* ── LA FRUTIMANDALA (cpWheelMng #640 + les peaux /wheel/wheel0|1.swf) ────
   Les couches, exactement les profondeurs du SWF : le châssis de FOND
   (#609, prof. 1 et #613, prof. 3) ; `inside` (#407, prof. 8), le plateau
   VIDE où les cadrans s'attachent ; les quatre boutons (prof. 12 à 21) et le
   verre (#639, prof. 25) PAR-DESSUS — sans quoi la roue mangerait le bouton
   vert, qui tombe pourtant à l'intérieur du disque.
   Pose relevée : le châssis occupe 200×80 au bout droit de la barre (bord
   droit de la barre mesuré à x 1240, bouton vert finissant à 1230). Le centre
   des cadrans est celui de `inside` — (93,1 ; −37,5) dans cpWheelMng, soit
   (99,4 ; −33,15) dans le cadre du châssis. Les coins du châssis tombent à
   149 du centre, hors du disque des frutisignes (rayon 126) : les boutons y
   restent au clair. Vérifié 1:1 contre le rendu Ruffle : l'heure « 11:22 »
   occupe la même boîte de 112×22 au même endroit. */
body.bureau-frutiz #frutimandala {
  /* calage vérifié sur un repère commun aux deux rendus, le bouton « G » :
     x 1049..1093, y 52..67 dans main.swf — la couche se pose donc au bord
     droit de la barre (right −2, le contour la recouvrant) et 4 px sous son
     haut, le reste dépassant sous la barre qui l'écrête, comme d'époque. */
  position: absolute; top: 4px; right: -2px; width: 200px; height: 80px;
  z-index: 2; overflow: hidden;
}
/* Le VERRE est à la profondeur 25 : au-dessus des boutons eux-mêmes. */
body.bureau-frutiz #frutimandala .md-dessus {
  position: absolute; inset: 0; z-index: 4; pointer-events: none;
  background: url('/frutiz/sprites/frutimandala-dessus.svg') left top / 200px 80px no-repeat;
}
/* LE BOL. La profondeur 1 de cpWheelMng est un clip nommé `mask` (#609) :
   plat en haut, arrondi en bas, il ne se dessine pas — il découpe. C'est lui
   qui donne aux deux cadrans leur silhouette de quartier de fruit, et sans
   lui le cadran jour/nuit (un bitmap OPAQUE peint jusque dans ses coins sur
   le vert du bureau) laisserait une écharpe verte le long du bol. */
body.bureau-frutiz #frutimandala .md-cadran {
  position: absolute; inset: 0; z-index: 2; pointer-events: none;
  -webkit-mask: url('/frutiz/sprites/frutimandala-masque.svg') left top / 200px 80px no-repeat;
  mask: url('/frutiz/sprites/frutimandala-masque.svg') left top / 200px 80px no-repeat;
}
/* `inside`, `wheel<dp>` et `display` sont des POINTS : chacun ne porte que sa
   rotation, autour du centre du cadran, et le dessin pend dessous. C'est
   ainsi qu'`animDisk` fait tourner le plateau entier pendant que `display`
   contre-tourne pour garder l'heure droite. */
body.bureau-frutiz #frutimandala .md-inside,
body.bureau-frutiz #frutimandala .md-roue,
body.bureau-frutiz #frutimandala .md-display,
body.bureau-frutiz #frutimandala .md-heure {
  position: absolute; width: 0; height: 0; transform-origin: 0 0;
}
body.bureau-frutiz #frutimandala .md-roue,
body.bureau-frutiz #frutimandala .md-display { left: 0; top: 0; }
body.bureau-frutiz #frutimandala .md-art {
  position: absolute; background-repeat: no-repeat;
}
/* `attachMovie("extGameNumb", "hour", 1, {…, _y: 52})` : l'afficheur pend à
   52 px sous le centre, et son compteur est mis à l'échelle 85 %. */
body.bureau-frutiz #frutimandala .md-heure {
  top: 52px; transform: scale(.85);
}
body.bureau-frutiz #frutimandala .md-heure i {
  position: absolute; width: 37.95px; height: 34.55px;
  background-repeat: no-repeat; background-size: 37.95px 34.55px;
}
/* Les quatre boutons, aux places du clip. Les deux triangles rouges ne font
   RIEN d'époque (`pressLeft`/`pressRight` sont vides) : ils gardent leurs
   trois états, mais pas de curseur de main. */
body.bureau-frutiz #frutimandala .md-but {
  position: absolute; padding: 0; border: 0; background: transparent no-repeat;
  background-size: 100% 100%; cursor: pointer; z-index: 3;
}
body.bureau-frutiz #frutimandala .md-mandalaGauche,
body.bureau-frutiz #frutimandala .md-mandalaDroite { cursor: default; }
body.bureau-frutiz #frutimandala .md-mandalaGauche { background-image: url('/frutiz/sprites/mandalaGauche_up.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaGauche:hover { background-image: url('/frutiz/sprites/mandalaGauche_over.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaGauche:active { background-image: url('/frutiz/sprites/mandalaGauche_down.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaDroite { background-image: url('/frutiz/sprites/mandalaDroite_up.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaDroite:hover { background-image: url('/frutiz/sprites/mandalaDroite_over.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaDroite:active { background-image: url('/frutiz/sprites/mandalaDroite_down.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaSwap { background-image: url('/frutiz/sprites/mandalaSwap_up.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaSwap:hover { background-image: url('/frutiz/sprites/mandalaSwap_over.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaSwap:active { background-image: url('/frutiz/sprites/mandalaSwap_down.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaValider { background-image: url('/frutiz/sprites/mandalaValider_up.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaValider:hover { background-image: url('/frutiz/sprites/mandalaValider_over.svg'); }
body.bureau-frutiz #frutimandala .md-mandalaValider:active { background-image: url('/frutiz/sprites/mandalaValider_down.svg'); }

/* ── LA LANGUETTE DU MODE RAPIDE (`testRetour` #587) ──────────────────────
   `MainBar.toggleHalfHide` l'attache à `_y = hideHeight` (220) dans la barre :
   une fois celle-ci remontée d'autant, elle tombe au ras du haut de l'écran,
   à l'abscisse de la barre (cornerX). Le dessin fait 14,05×14 ; le champ
   « mode rapide » suit à 16,3, en Verdana gras 10 `#4D7417`.
   `_visible = false` jusqu'à `endMove` : elle n'apparaît qu'une fois la barre
   partie — d'où la classe « vu ». */
body.bureau-frutiz #mode-rapide {
  position: absolute; left: var(--cornerX); top: 0; z-index: 30;
  width: 96px; height: 16px; padding: 0; border: 0; background: none;
  text-align: left; cursor: pointer; visibility: hidden;
  font: 700 10px Verdana, Arial, sans-serif; color: #4D7417;
  user-select: none; -webkit-user-select: none;
}
body.bureau-frutiz #mode-rapide.vu { visibility: visible; }
body.bureau-frutiz #mode-rapide i {
  position: absolute; left: 0; top: 0; width: 14.05px; height: 14px;
  background: url('/frutiz/sprites/mode-rapide.svg') left top / 14.05px 14px no-repeat;
}
body.bureau-frutiz #mode-rapide span {
  position: absolute; left: 16.3px; top: -0.3px; line-height: 13px;
  white-space: nowrap;
}

/* ── La pilule « N en ligne » ─────────────────────────────────────────────
   Elle ne flotte pas dans le coin : elle est POSÉE SUR le lecteur, en haut.
   Mesuré 1:1 : x 1271..1369 (98 de large), y 8..32 (24 de haut) — soit
   11 px du bord droit ; fond `#526B3A`, point `#2ECC40`, texte `#CFF599`. */
body.bureau-frutiz #pill-enligne {
  position: absolute; top: 8px; right: 11px; z-index: 3;
  width: 98px; height: 24px; box-sizing: border-box;
  padding: 0 7px; border-radius: 12px;
  background: #526B3A; color: #CFF599;
  font: 700 11px Verdana, Arial, sans-serif; line-height: 24px;
  display: flex; align-items: center; gap: 5px;
  user-select: none; -webkit-user-select: none;
}
body.bureau-frutiz #pill-enligne .point {
  width: 8px; height: 8px; border-radius: 50%; background: #2ECC40;
}

/* ── LE PANNEAU DES CONTACTS (`_global.SideList`, DoInitAction sprite#847,
   0xa05b7) — la « languette » n'est que sa poignée ────────────────────────
   Constantes du prototype (0xa1708) : **wSide 9**, **wShade 3**, wMain 120
   (la liste ouverte), hSearch 24. `update` (0xa0b4c) trace DEUX rectangles
   pleine hauteur (mch) : le BLANC `FEMC.drawSquare(0xFFFFFF)` de largeur
   wSide (+ wMain quand la liste est ouverte), puis le LISERÉ
   `drawSquare(0xDDDDDD)` de largeur wShade collé au bord DROIT. À côté,
   `ombre` = le clip `carreFond` (#584, un carré `#444444`) réduit à
   `_width = 2`, posé à `main.cornerX` et haut de mch (init 0xa0a92,
   onStageResize 0xa0c94). Relevé au pixel 1:1 : blanc 0..6, `#DDDDDD` 6..9,
   `#444444` 9..11 — au twip près. `init` pose d'ailleurs
   **`main.cornerX = wSide`** : le bureau commence à 9 px du bord. */
/* Profondeurs relevées : la BANDE passe PAR-DESSUS la barre (à y=40, son
   liseré #DDDDDD se lit encore à 6..9), mais son OMBRE passe DESSOUS (le
   #444444 y disparaît) — l'ombre est attachée à `main`, la bande non. */
/* DÉPLIER la bande (`toggle` 0xa0e2a) : `activate` pose
   `main.cornerX = wMain + wSide` (129) et `deActivate` le remet à `wSide` (9).
   Tout le bureau suit cette borne — la barre, l'onglet, la rangée d'icônes et
   le bornage des fenêtres — ce que reproduit la variable `--cornerX`. Relevé
   1:1 : ouverte, blanc 0..125, `#DDDDDD` 126..128, `#444444` 129..130, et la
   première icône passe du centre 53 au centre 173, soit +120 = wMain. */
/* La borne est posée sur le BODY : `#bureau-coin`, l'onglet et la poignée
   vivent dans `#bureau-haut`, qui est un FRÈRE de `#bureau` — une variable
   posée sur le bureau ne les atteindrait pas. */
body.bureau-frutiz { --cornerX: 9px; --cornerY: 106px; }
body.bureau-frutiz.contacts-ouverts { --cornerX: 129px; }
body.bureau-frutiz #side-list {
  position: absolute; left: 0; top: 0; bottom: 0; z-index: 3;
  width: var(--cornerX);
  background: linear-gradient(to right,
    #FFFFFF 0 calc(var(--cornerX) - 3px), #DDDDDD calc(var(--cornerX) - 3px) var(--cornerX));
}
/* L'OMBRE passe SOUS la barre — et donc sous les onglets, qui vivent DEDANS
   (`mcTab` est un enfant de la barre). Au même z-index que la rangée
   d'onglets, elle traversait la plaque d'un trait sombre de 2 px. */
body.bureau-frutiz #side-list-ombre {
  position: absolute; left: var(--cornerX); top: 0; bottom: 0; width: 2px; z-index: 0;
  background: #444444;
}
/* Le contenu du panneau. `buildList` (0xa1038) masque la liste à
   `wMain × (mch − hSearch)` : elle s'arrête donc 24 px avant le bas, où se
   pose `butSearch` (`_y = 770`, une constante en dur comme le `_y = 800` de
   la poignée). Chaque ligne fait **18 px** et chaque niveau de dossier décale
   de **5 px** (`buildElement` 0xa1243) ; un dossier REPLIÉ ajoute un cinquième
   de ligne (`currentLine += 0.2`), soit 3,6 px de respiration. */
body.bureau-frutiz #side-list .sl-liste {
  position: absolute; left: 0; top: 0; width: 120px; bottom: 24px;
  overflow-x: hidden; overflow-y: auto; display: none;
}
body.bureau-frutiz.contacts-ouverts #side-list .sl-liste { display: block; }
/* L'EN-TÊTE DE DOSSIER, `sideListTitle` (#215), avec SES pièces extraites :
   `fond` (forme #209, une barre `#999999` de 100×12 que `buildElement`
   ÉTIRE — `fond._width = fondD._x`) et `fondD` (#213, dont l'image 1 est la
   forme #211 : le BOUT ARRONDI de la barre et son bouton clair `#CCCCCC`,
   20,65 × 12). Le libellé est le champ #214 : variable `title`, font #189
   (Verdana) 10 px, couleur DÉCLARÉE **`#FFFFFF`**, aligné à gauche — du blanc
   sur la barre grise. La fonte #189 ne porte pas le drapeau gras, mais le
   champ n'a pas `UseOutlines` : Flash tire alors la Verdana du SYSTÈME, et le
   rendu d'époque est bien GRAS — la même graisse que l'onglet « Bureau », qui
   use du même champ.
   QUIRK conservé : `fondD.gotoAndStop(1)` est appelé sans condition — le bout
   ne change JAMAIS d'image, replié ou non. */
body.bureau-frutiz #side-list .sl-dossier > .sl-titre {
  position: relative; display: block; width: 100%;
  height: 18px; padding: 0; border: 0; background: none;
  font: 700 10px Verdana, Arial, sans-serif; color: #FFFFFF;
  cursor: pointer; text-align: left;
}
body.bureau-frutiz #side-list .sl-titre .plaque {
  position: absolute; left: 0; right: 20.65px; top: 3px; height: 12px;
  background: url('/frutiz/sprites/sl-dossier-fond.svg') left top / 100% 12px no-repeat;
}
body.bureau-frutiz #side-list .sl-titre .bout {
  position: absolute; right: 0; top: 3px; width: 20.65px; height: 12px;
  background: url('/frutiz/sprites/sl-fleche-1.svg') left top / 20.65px 12px no-repeat;
}
body.bureau-frutiz #side-list .sl-titre .nom {
  position: relative; display: block; padding-left: 4px; line-height: 18px;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
body.bureau-frutiz #side-list .sl-dossier.replie { margin-bottom: 3.6px; }
body.bureau-frutiz #side-list .sl-dossier.replie > .sl-contenu { display: none; }
body.bureau-frutiz #side-list .sl-contenu { margin-left: 5px; }
/* LA LIGNE DE CONTACT, `userSlot` (#261) : sa forme de fond fait 120 × 18 —
   d'où la hauteur de ligne. `UserSlot.init` (0x633dc) attache la bande
   `status` (#253) comme `icon` sans lui donner de `_x`, mais le dessin n'est
   PAS centré sur l'origine pour autant : la bande pose son contenu à +9, ce
   qui annule le −9 interne du fond, et l'icône occupe donc **x 0,5..17,5** —
   pile à gauche du pseudo, qui commence à 20.
   Le fond de l'icône est la forme #216 (`iconBackgroundId = 2`) : un carré
   arrondi de 17, vide, au liseré `#CCCCCC`. Le voyant est la bande #222, dont
   `ico.gotoAndStop(presence + 1)` choisit l'image : présence 1 (le serveur
   envoie `p="1"` quand une socket est ouverte) → la pastille VERTE `#ADE76B` ;
   présence 0 → l'image 1, la pastille SAUMON `#E3756A` à reflet. La grise
   `#CCCCCC` est l'image 3, un troisième état que le carnet n'utilise pas. */
body.bureau-frutiz #side-list .sl-contact {
  position: relative; display: block; width: 100%;
  height: 18px; padding: 0; border: 0; background: none;
  cursor: pointer; text-align: left;
}
body.bureau-frutiz #side-list .sl-contact .voyant {
  position: absolute; left: .5px; top: .5px; width: 17px; height: 17px;
  background: url('/frutiz/sprites/sl-presence-0.svg') center center / 8px 8px no-repeat,
              url('/frutiz/sprites/sl-icone-fond.svg') left top / 17px 17px no-repeat;
}
body.bureau-frutiz #side-list .sl-contact.en-ligne .voyant {
  background-image: url('/frutiz/sprites/sl-presence-1.svg'),
                    url('/frutiz/sprites/sl-icone-fond.svg');
}
/* EN PARTIE : `onStatusObj` fait `icon.gotoAndStop("internal")` — l'icône du
   JEU remplace la pastille de présence dans le même cadre de 17. Le dessin
   est celui que la liste des connectés d'un salon pose déjà à gauche du
   pseudo ; il remplit le cadre, moins son liseré. */
body.bureau-frutiz #side-list .sl-contact .voyant.jeu {
  background-size: 15px 15px, 17px 17px;
  background-position: center center, left top;
}
/* Le pseudo : `initText` (0x6353a) pose le champ à **`_x = 20`**, large de
   100 et haut de 20, au style `Standard.getTextStyle().def` — Verdana 10,
   couleur 0 — que la méthode passe en GRAS (`textFormat.bold = true`). */
body.bureau-frutiz #side-list .sl-contact .nom {
  /* Le champ descend de 4 px : dans la ligne de 18, le pseudo ne se centre
     pas sur le voyant mais s'assoit sur sa ligne de base. */
  position: absolute; left: 20px; width: 100px; top: 4px; height: 14px;
  line-height: 14px; font: 700 10px Verdana, Arial, sans-serif; color: #000000;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
/* LE PSEUDO CHANGE DE COULEUR AU SURVOL. Ce n'est pas un ornement ajouté : le
   champ n'est pas un texte mais un `butText` (`UserSlot.initText` l'attache),
   et tout `butText` sans comportement déclaré se voit poser celui de la
   maison — `Standard.getButTextBasicBehavior()` (0x4985a) :

       { type: "colorText", color: { press: 0xDDDDDD, over: 0xE7756B } }

   `setBehavior` (0x9fd26) complète ce qui manque — `base` n'est pas donné,
   il prend donc la couleur PROPRE du champ — puis, pour le type
   « colorText » (0x9fe44), câble six méthodes de bouton :

       onRollOver → over      onPress          → press
       onRollOut  → base      onDragOut        → base
       onRelease  → over      onReleaseOutside → base

   D'où les deux règles ci-dessous, et rien de plus : `:hover` couvre
   onRollOver et onRelease (le curseur est encore dessus), `:active` couvre
   onPress, et tout le reste revient à `base` de lui-même. */
/* …et tant que le genre est INCONNU. `UserSlot.onInfoBasic` (0x63a51) écrase
   ce comportement par défaut dès que le serveur a dit `sx` : le pseudo passe
   alors au bleu du garçon ou au rouge de la fille, survol compris (les règles
   sont dans light.html). */
body.bureau-frutiz #side-list .sl-contact:not([data-genre]):hover .nom { color: #E7756B; }
body.bureau-frutiz #side-list .sl-contact:not([data-genre]):active .nom { color: #DDDDDD; }
/* La boîte de RECHERCHE : `mcSearchButton` (#441), que `buildList` attache à
   `_y = 770`. L'art est EXTRAIT du SWF — la pastille grise et sa loupe, dans
   leur cadre (9,95 ; 0,65)–(105,85 ; 22,67) — ce qui pose l'ensemble
   exactement où le rendu 1:1 le montre (x 10..105, encre y 771..785). Seul le
   mot « recherche » est du texte : c'est un champ, pas un dessin. */
body.bureau-frutiz #side-list .sl-recherche {
  position: absolute; left: 9.95px; top: 770.65px; width: 95.9px; height: 22.02px;
  display: none; align-items: flex-start; padding: 2px 0 0 24px;
  border: 0; background: url('/frutiz/sprites/recherche.svg') left top / 95.9px 22.02px no-repeat;
  font: 700 10px Verdana, Arial, sans-serif; color: #FFFFFF;
  cursor: pointer; text-align: left;
}
body.bureau-frutiz.contacts-ouverts #side-list .sl-recherche { display: flex; }
/* La poignée : `sideListContact` (#436) est un DefineButton2 — l'art est
   extrait tel quel (plaque, liseré, lettres PIVOTÉES d'un quart de tour),
   états compris : au repos les lettres sont `#666666`, au survol elles
   passent au SAUMON `#E7756B`. SideList.init l'attache à `_x = wSide` (9) et
   onStageResize la pose à **`_y = 800`** — une constante en dur, la hauteur
   de scène d'époque : la poignée est donc collée EN BAS. Son cadre va de
   (−7.75, −84.15) à (12, 0) : à l'écran, x 1.25..21, 84.15 de haut. */
body.bureau-frutiz #languette-contacts {
  position: absolute; left: calc(var(--cornerX) - 7.75px); bottom: 0; z-index: 4;
  width: 19.75px; height: 84.15px; padding: 0; border: 0;
  background: url('/frutiz/sprites/butContact_up.svg') center / 19.75px 84.15px no-repeat;
  cursor: pointer; color: transparent; font-size: 0;
}
body.bureau-frutiz #languette-contacts:hover {
  background-image: url('/frutiz/sprites/butContact_over.svg');
}
body.bureau-frutiz #languette-contacts:active {
  background-image: url('/frutiz/sprites/butContact_down.svg');
}

/* Le compte (« connecté en tant que… », Se déconnecter) : une mention de bas
   de bureau, discrète — décalée pour laisser la languette CONTACTS. */
body.bureau-frutiz #bureau .home-compte {
  position: absolute; left: 30px; bottom: 6px; z-index: 3;
  padding: 0; text-align: left; font-size: 11px;
  color: var(--fond-txt, #335511);
  text-shadow: 0 0 3px var(--fond-halo, rgba(255,255,255,.85));
}

/* ── Les icônes du bureau (la grille du tiroir, rhabillée) ────────────────
   FPDesktop.displayIconList (0xba0af) ne pose PAS les icônes lui-même : il
   attache un `cpDragIconList` et lui passe la boîte utile
   (`mcw − main.cornerX`, `mch − main.cornerY`) plus la marge de
   `Standard.getMargin()`, corrigée en `x.min = 18`, `y.min = 12`. C'est
   `cp.IconList.updateStruct` (0x4f6fc) qui en tire la grille :

     utile  = côté − 2·marge
     pas    = size + space
     max    = floor(utile / pas)          ← combien tiennent
     reste  = utile − (max·size + (max−1)·space)
     coin   = marge  |  marge + reste/2  |  marge + reste   selon `align`

   puis `alignIcon` (0x4f946) remplit un axe INTÉRIEUR avant de faire un pas
   sur l'axe extérieur — d'où, sur un écran large, une seule RANGÉE.

   Le relevé 1:1 (ref1-icones.png, bureau dégagé) donne les nombres :
   quinze icônes, centres à **53 + 76·k** (pas mesuré 75,96 sur 14
   intervalles), donc `size` 64 et `space` 12. Le dessin est CENTRÉ sur la
   ligne y 128,5 — soit une case d'icône de 46 px partant de y 106, c'est-à-
   dire `main.cornerY` — et l'étiquette commence juste dessous, en y 152,
   avec 13 px d'interligne (« Boîte de réception » et « Mon historique »
   passent à deux lignes : le champ fait 64, pas 76). */
body.bureau-frutiz #bureau #home-grid {
  /* La rangée commence AU COIN du bureau : `main.cornerY`, que le repli de la
     barre (« mode rapide ») fait passer de 106 à 10. Les icônes remontent
     alors, comme d'époque. */
  position: absolute; top: var(--cornerY); left: calc(var(--cornerX) + 6px); right: 16px; z-index: 2;
  display: flex; flex-flow: row wrap; align-content: flex-start;
  align-items: flex-start; justify-content: flex-start; gap: 12px 0;
  margin: 0; padding: 0;
}
body.bureau-frutiz #bureau .home-tile {
  display: flex; flex-direction: column; align-items: center; gap: 0;
  width: 76px; padding: 0 6px; margin: 0; box-sizing: border-box;
  background: none; border: 0; border-radius: 0; box-shadow: none;
  cursor: pointer;
}
/* Aucun effet de SURVOL : sur le rendu 1:1, le curseur posé sur une icône ne
   change rien à son étiquette. Seul l'appui la souligne — la règle du tiroir
   mobile (`.home-tile:active .lbl`), qui vaut donc aussi ici. */
/* Une icône DÉPOSÉE quitte la rangée pour une position libre sur le bureau ;
   l'espaceur garde sa case ouverte derrière elle (d'époque, les voisines ne se
   décalent pas pour combler le trou). Rien n'est retenu d'une session à
   l'autre : au rechargement, tout revient dans la rangée. */
body.bureau-frutiz #bureau .home-tile.posee { position: absolute; z-index: 3; }
body.bureau-frutiz #bureau .home-tile.en-main { cursor: grabbing; }
body.bureau-frutiz #bureau .home-trou { flex: 0 0 auto; pointer-events: none; }
body.bureau-frutiz #bureau .home-tile .ico {
  width: 64px; height: 44px; display: flex; align-items: center; justify-content: center;
  background: none; border: 0; box-shadow: none; font-size: 30px;
}
/* La TAILLE des dessins. Le tiroir mobile étire chaque icône jusqu'à remplir
   sa case ; d'époque, elles sont posées à leur taille propre, et elles ne font
   pas toutes la même — c'est l'artwork tel quel. Deux constats du relevé :
     • les quatre icônes tirées de fileIcon.swf en SVG (courrier, historique,
       préférences, club) tombent TOUTES à 0,60 de leur taille native — le
       SVG a été sorti à 5/3 de l'original. Les événements, même provenance,
       suivent la règle (51×48 → 31×29) ;
     • les PNG portent des marges transparentes INÉGALES (l'inventaire n'en
       remplit que 82 %, le forum 70 % en largeur) : la contrainte doit donc
       viser leur ENCRE et pas le fichier. Les tailles ci-dessous sont
       calculées — part d'encre relevée dans le fichier, puis mise à l'échelle
       pour retrouver la boîte d'époque.
   `max-*` laisse l'image garder ses proportions : la dimension contraignante
   l'emporte. */
body.bureau-frutiz #bureau .home-tile .ico img { max-width: 42px; max-height: 42px; }
/* extraits de fileIcon.swf en SVG, sans marge : 0,60 de leur taille native */
body.bureau-frutiz #bureau .home-tile[data-go="mail"]       .ico img { max-width: 37px; max-height: 27px; }
body.bureau-frutiz #bureau .home-tile[data-go="historique"] .ico img { max-width: 23px; max-height: 39px; }
body.bureau-frutiz #bureau .home-tile[data-go="evenements"] .ico img { max-width: 31px; max-height: 29px; }
body.bureau-frutiz #bureau .home-tile[data-go="reglages"]   .ico img { max-width: 31px; max-height: 37px; }
body.bureau-frutiz #bureau .home-tile[data-go="club"]       .ico img { max-width: 30px; max-height: 37px; }
/* PNG : la boîte tient compte de la marge transparente du fichier */
body.bureau-frutiz #bureau .home-tile[data-go="disques"]    .ico img { max-width: 33px; max-height: 33px; }
body.bureau-frutiz #bureau .home-tile[data-go="inventaire"] .ico img { max-width: 43px; max-height: 39px; }
body.bureau-frutiz #bureau .home-tile[data-go="forum"]      .ico img { max-width: 35px; max-height: 43px; }
body.bureau-frutiz #bureau .home-tile[data-go="chat"]       .ico img { max-width: 45px; max-height: 42px; }
body.bureau-frutiz #bureau .home-tile[data-go="scores"]     .ico img { max-width: 35px; max-height: 38px; }
body.bureau-frutiz #bureau .home-tile[data-go="shop"]       .ico img { max-width: 36px; max-height: 32px; }
body.bureau-frutiz #bureau .home-tile[data-go="trombi"]     .ico img { max-width: 42px; max-height: 42px; }
/* L'ORDRE d'époque, relevé sur le bureau dégagé : la boîte de réception, les
   disques, l'inventaire, Gaspard, les contacts, la corbeille, le forum, la
   liste noire, les salons, l'historique, les préférences, les scores, la
   boutique, le bouilloscope, le club. Le light n'a pas les quatre rubriques
   Flash (Gaspard, Mes contacts, Corbeille, Liste noire) et en a une de plus,
   les Événements — rangée contre l'historique, avec qui elle partage sa
   fenêtre. On ne réordonne que l'AFFICHAGE : le DOM reste celui du mobile. */
body.bureau-frutiz #bureau .home-tile[data-go="mail"]       { order: 0; }
body.bureau-frutiz #bureau .home-tile[data-go="disques"]    { order: 1; }
body.bureau-frutiz #bureau .home-tile[data-go="inventaire"] { order: 2; }
body.bureau-frutiz #bureau .home-tile[data-go="forum"]      { order: 3; }
body.bureau-frutiz #bureau .home-tile[data-go="chat"]       { order: 4; }
body.bureau-frutiz #bureau .home-tile[data-go="historique"] { order: 5; }
body.bureau-frutiz #bureau .home-tile[data-go="evenements"] { order: 6; }
body.bureau-frutiz #bureau .home-tile[data-go="reglages"]   { order: 7; }
body.bureau-frutiz #bureau .home-tile[data-go="scores"]     { order: 8; }
body.bureau-frutiz #bureau .home-tile[data-go="shop"]       { order: 9; }
body.bureau-frutiz #bureau .home-tile[data-go="trombi"]     { order: 10; }
body.bureau-frutiz #bureau .home-tile[data-go="club"]       { order: 11; }
/* L'étiquette d'époque : du texte posé À NU sur le fond (mesuré #335511 sur
   l'aplat #ADE76B, ref-bureau-propre.png) — main.swf ne met AUCUN halo, la
   lisibilité vient de la couleur de texte imposée par le fond d'écran
   (--fond-txt, la loi WallPaperMng). */
body.bureau-frutiz #bureau .home-tile .lbl {
  font: normal 11px Verdana, Arial, sans-serif; line-height: 13px;
  text-align: center; color: var(--fond-txt, #335511);
  max-width: 64px;
}

/* ── Les fenêtres — le chrome de WinStandard, au relevé près ────────────────
   Tout vient du bytecode et du rendu Ruffle mesuré (public/frutiz/PLAN.md) :
   drawInterface trace un rectangle arrondi RAYON 10, contour 1 px #444444,
   liseré 2 px #DDDDDD, fond #FFFFFF ; dropShadow pose un dégradé radial noir
   alpha 50→0 de rayon 17 décalé de 10 (la lueur ne déborde qu'en bas-droite) ;
   les bords du cadre font 6 px (initFrameSet) ; le titre est gras 11 px
   #444444 derrière la pastille `rond` teintée. */
body.bureau-frutiz #bureau-fenetres {
  position: absolute; inset: 0; z-index: 10; pointer-events: none;
}
/* La fenêtre est bâtie comme `drawCustomSquare` la peint, en TROIS plaques
   emboîtées — plus d'ombre interne, qui ne courbait pas le blanc :
     • le CONTOUR, la bordure de 1 px `#444444`, arrondie à curve + outline
       = 10 + 1 = 11 (CSS ajoute l'épaisseur au rayon toute seule) ;
     • le LISERÉ, le fond `#DDDDDD` de la fenêtre, vu dans les 2 px de
       padding, arrondi à curve = 10 ;
     • le FOND BLANC, une plaque à part (::before) rentrée de 2 px et
       arrondie à curve − inline = 8.
   C'est cette troisième plaque qui manquait : le blanc du bandeau était
   peint sur toute la boîte et gardait donc les coins carrés. Relevé sur le
   rendu 1:1 : le blanc démarre en x 12 / y 108 et sa courbe se referme vers
   x 18 en haut — un rayon de 8, exactement. */
body.bureau-frutiz .fen {
  position: absolute; pointer-events: auto; box-sizing: border-box;
  display: flex; flex-direction: column;
  background: #DDDDDD; border-radius: 10px;
  border: 1px solid #444444; padding: 2px;
  box-shadow: 7px 7px 17px -4px rgba(0, 0, 0, .5);
  min-width: 160px; max-width: calc(100vw - 12px); max-height: calc(100vh - 106px);
}
body.bureau-frutiz .fen::before {
  content: ""; position: absolute; inset: 2px; z-index: 0;
  background: #fff; border-radius: 8px; pointer-events: none;
}
/* Le bandeau et le corps se posent SUR la plaque blanche, et n'en peignent
   plus : le bandeau tenait un fond blanc du chrome mobile, qui recouvrait la
   courbe et rendait le coin carré. */
body.bureau-frutiz .fen-titre,
body.bureau-frutiz .fen-corps {
  position: relative; z-index: 1; background: transparent;
}
/* Le BANDEAU fait **16 px**, pas un de plus — relevé au pixel sur le rendu 1:1
   (scratchpad/ref3-salons.png, fenêtre posée en y 105) : contour en 105,
   liseré 106-107, bandeau BLANC 108..123, puis le contour du contenu en 124.
   Dedans : la pastille (encre x 17..28, y 108..121), le titre gras 11 px
   `#444444` qui démarre à x 31, et les deux boutons collés au bord droit (la
   croix, encre x 257..267). Les boutons gardent leur boîte de 21 px — celle
   du dessin d'origine — et DÉBORDENT donc un peu du bandeau, comme en Flash,
   où rien ne les rogne. */
body.bureau-frutiz .fen-titre {
  display: flex; align-items: center; gap: 0;
  height: 16px; padding: 0 0 0 3px; box-sizing: content-box;
  /* Flash n'a que la flèche : pas de croix de déplacement sur le bandeau. */
  cursor: default; user-select: none; -webkit-user-select: none;
  font: 700 11px Verdana, Arial, sans-serif; color: #444444;
  flex-shrink: 0;
}
/* La pastille : un FRUIT de la bande #198 de main.swf (une frame étiquetée
   par type de fenêtre) — l'orange par défaut, la fraise pour les salons, le
   citron des alertes… Les SVG partagent un cadre commun (~15.9×15.1) pour
   se poser tous au même endroit du bandeau, comme la bande d'origine. */
body.bureau-frutiz .fen-pastille {
  width: 16px; height: 15px; flex-shrink: 0;
  background: url('/frutiz/sprites/fruit_default.svg') center / contain no-repeat;
}
body.bureau-frutiz .fen-titre .txt {
  flex: 1; overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
/* Les boutons du bandeau : les DefineButton2 de butGroupWinTop (#180),
   extraits état par état (scripts/extract-frutiz-bureau.js). Le détail
   d'époque : au REPOS seul le glyphe se dessine, la plaque colorée (21×21)
   n'arrive qu'au survol, et l'appui la fonce. Bouton 1 = fermer (la croix,
   plaque beige), 2 = l'enroulement/onglet (les traits, plaque bleue),
   3 = l'aide (le « ? », plaque verte — pas encore branché). */
body.bureau-frutiz .fen-btn {
  width: 21px; height: 21px; flex-shrink: 0;
  border: 0; padding: 0; cursor: pointer; color: transparent;
  background: transparent center / 21px 21px no-repeat;
}
body.bureau-frutiz .fen-btn.fermer { background-image: url('/frutiz/sprites/butWinTop1_up.svg'); }
body.bureau-frutiz .fen-btn.fermer:hover { background-image: url('/frutiz/sprites/butWinTop1_over.svg'); }
body.bureau-frutiz .fen-btn.fermer:active { background-image: url('/frutiz/sprites/butWinTop1_down.svg'); }
body.bureau-frutiz .fen-btn.plier { background-image: url('/frutiz/sprites/butWinTop2_up.svg'); }
body.bureau-frutiz .fen-btn.plier:hover { background-image: url('/frutiz/sprites/butWinTop2_over.svg'); }
body.bureau-frutiz .fen-btn.plier:active { background-image: url('/frutiz/sprites/butWinTop2_down.svg'); }
/* Le corps : la zone du contenu, dans les 6 px de bords du frameSet. */
body.bureau-frutiz .fen-corps {
  flex: 1; min-height: 0; display: flex; flex-direction: column;
  margin: 0 6px 6px; overflow: hidden; background: transparent;
}
/* Replié : la barre-titre seule, comme l'enroulement du bureau Flash. */
body.bureau-frutiz .fen.pliee .fen-corps,
body.bureau-frutiz .fen.pliee .fen-poignee,
body.bureau-frutiz .fen.pliee .fen-poignee-vue { display: none; }
body.bureau-frutiz .fen.pliee { min-width: 220px; }

/* ── LA POIGNÉE DE REDIMENSIONNEMENT ──────────────────────────────────────
   LA ZONE SENSIBLE d'abord : `initButtons` (0x5449d) attache le symbole
   `transp` — un bouton dont la forme de hit fait 100 × 100 — à
   `_xscale = _yscale = 30` (0x544b7), et `updateDeskSize` (0x5400c) le pose à
   `pos.w − 20, pos.h − 20`. Soit un carré de 30 ancré 20 px avant le coin,
   qui DÉBORDE donc de 10 px : c'est ce débordement qu'on attrape, et c'est
   pour cela que la poignée du portage — collée à 8 px À L'INTÉRIEUR — ne
   tombait jamais où l'œil la cherche.

   Elle reste TRANSPARENTE : d'époque le clip est un bouton sans image, à la
   profondeur 160, sous le frameSet. On ne le voit jamais ; ce qu'on voit,
   c'est la pastille que le survol fait naître (cf. `.fen-poignee-vue`). */
body.bureau-frutiz .fen-poignee {
  /* −11 et non −10 : une position absolue se règle sur la boîte de
     REMPLISSAGE, qui commence 1 px après le bord de la fenêtre (le liseré
     `#444444`). Un pixel de compensation, et le carré déborde bien de 10. */
  position: absolute; right: -11px; bottom: -11px; width: 30px; height: 30px;
  background: none; cursor: nwse-resize; z-index: 3;
}
/* LA PASTILLE, elle, n'existe que le temps du survol — `startResizeAnim`
   (0x568c1) la crée, `removeResizeArrow` la retire. Trois `drawOval`
   concentriques autour de (−9, −9) dans le clip, plus l'icône au centre :

     outline Ø 20  `darkest` #444444   ·  shade Ø 18 `shade` #DDDDDD
     main    Ø 14  `main`    #FFFFFF   ·  resizeIcon 12 × 12

   Les teintes sont celles de `style.global.color[0]`, et `getWinStyle`
   (0x4957f) donne à `global` la famille **white** : la pastille est blanche
   cerclée de gris sur TOUTES les fenêtres, quel que soit leur fruit.

   L'origine du clip est son coin bas-droit (les cercles vont de −19 à +1) :
   posée en (w+9, h+9) par l'animation, elle centre les cercles sur le COIN
   exact de la fenêtre. `transform-origin: 0 0` reproduit le `_xscale` de
   Flash, qui met à l'échelle autour de l'origine du clip. */
body.bureau-frutiz .fen-poignee-vue {
  position: absolute; left: 0; top: 0; width: 0; height: 0;
  transform-origin: 0 0; pointer-events: none; z-index: 4;
}
body.bureau-frutiz .fen-poignee-vue i {
  position: absolute; display: block; border-radius: 50%;
}
body.bureau-frutiz .fen-poignee-vue .pv-anneau {
  left: -19px; top: -19px; width: 20px; height: 20px; background: #444444;
}
body.bureau-frutiz .fen-poignee-vue .pv-ombre {
  left: -18px; top: -18px; width: 18px; height: 18px; background: #DDDDDD;
}
body.bureau-frutiz .fen-poignee-vue .pv-chair {
  left: -16px; top: -16px; width: 14px; height: 14px; background: #FFFFFF;
}
body.bureau-frutiz .fen-poignee-vue .pv-icone {
  left: -15px; top: -15px; width: 12px; height: 12px; border-radius: 0;
  background: url('/frutiz/sprites/resizeIcon.svg') no-repeat center / 12px 12px;
}

/* LE FANTÔME du déplacement et du redimensionnement (win.Ghost) : la
   silhouette blanche — 4 arcs de coin 10×10 épais de 2 et 4 traits de 2 px
   (formes #157/#159 du SWF), soit exactement ce contour-ci. La fenêtre ne
   bouge pas tant qu'on tient le fantôme. */
body.bureau-frutiz .fen-fantome {
  position: absolute; pointer-events: none; z-index: 1400;
  border: 2px solid #fff; border-radius: 10px;
}

/* Le panneau logé dans une fenêtre s'affiche — c'est SA fenêtre qui le cadre. */
body.bureau-frutiz .fen .panel.active { display: flex; flex: 1; min-height: 0; }
/* Les panneaux qui portent leur PROPRE chrome mobile (la coque .fenetre avec
   son entête) le déposent en entrant dans une fenêtre du bureau : main.swf ne
   met qu'UNE barre-titre. Le corps de la fenêtre d'historique est BLANC
   (mesuré ref-historique.png), les cartes d'entrées #CCF599 bordées ~#B6E580,
   leur texte #335511 — le même vert très sombre que les étiquettes d'icônes. */
body.bureau-frutiz .fen .fenetre { background: #fff; border-radius: 0; box-shadow: none; }
body.bureau-frutiz .fen .fenetre > .fen-titre { display: none; }
body.bureau-frutiz .fen #evt-panel { padding: 0; background: #fff; }
body.bureau-frutiz .fen .evt-item { background: #CCF599; border-color: #B6E580; }
body.bureau-frutiz .fen .evt-item .txt { color: #335511; }
body.bureau-frutiz .fen #evt-page { color: #A4A4A4; }
/* Le cadrage « largeur de lecture » du chat plein écran n'a plus cours dans
   une fenêtre : le panneau épouse la fenêtre, la poignée se tait. */
body.bureau-frutiz .fen #chat-panel { max-width: none; align-self: stretch; width: 100%; }
body.bureau-frutiz .fen #chat-poignee { display: none; }

/* ── « Salons publics » (win.RoomList 0xbebb6, cp.RoomList 0x70733) ─────────
   La fenêtre que le light n'avait pas : côté mobile on choisit son salon dans
   un menu déroulant, côté bureau d'époque c'est une fenêtre à soi, avec une
   rangée par salon et son affluence.

   Le corps se serre : `.fen-corps` laisse 6 px partout, mais le relevé 1:1
   (scratchpad/ref3-salons.png, fenêtre x 9..273 y 105..392) donne **2 px** de
   blanc entre le liseré de la fenêtre et le contour du compo. */
body.bureau-frutiz .fen #salons-panel {
  padding: 0; background: transparent; gap: 2px;
}
/* Le corps se cale sur le relevé : le contour du compo tombe en x 13-14 et
   267-268, donc 1 px de blanc à gauche et 2 à droite du liseré de la fenêtre
   (la largeur d'époque est impaire, l'écart part d'un côté). */
body.bureau-frutiz .fen:has(#salons-panel.active) .fen-corps { margin: 0 2px 2px 1px; }
/* La LISTE, peinte elle aussi par `drawCustomSquare` : contour de 2 px
   `#DDDDDD`, liseré de 2 px, et `curve: 3` comme les styles de contenu de
   getOldWinStyle — d'où un rayon extérieur de curve + outline = 5, et 3 pour
   le contenu. Relevé au coin haut-gauche : le `#DDDDDD` démarre en x 17 sur
   la ligne du haut et rejoint x 13 quatre pixels plus bas.
   Le LISERÉ est ROSE (`#FEABAB`) et se voit sur trois côtés seulement : les
   rangées, posées à `_y = i * 20` depuis le haut du compo, recouvrent celui
   du haut mais pas ceux des côtés ni celui du bas (relevé : x 15-16 et
   265-266 en rose sur une rangée IMPAIRE, donc ce n'est pas la rangée ; et
   y 364-365 en rose juste avant le `#DDDDDD`). D'où le padding, nul en haut.
   Ce même rose remplit la place laissée libre sous la dernière rangée — le
   `main` du compo n'est pas mesurable, la liste d'époque étant pleine. */
body.bureau-frutiz #salons-panel .sp-liste {
  flex: 1; min-height: 0; overflow-y: auto;
  border: 2px solid #DDDDDD; box-sizing: border-box; border-radius: 5px;
  background: #FEABAB; padding: 0 2px 2px;
}
/* Une rangée = **20 px** (reg7, écrit en dur dans setList) et `_y = i * 20` :
   aucun écart entre elles. Le texte est la Verdana 10 de `getTextStyle`,
   encre `#BA4444` relevée au cœur des glyphes. Une rangée sur DEUX — les
   PAIRES, `i % 2 == 0` — reçoit `bgColor = pal.bg.shade` ; les autres gardent
   le fond de base. Au survol, les deux passent à `#FFF2F2`. */
body.bureau-frutiz #salons-panel .sp-salon {
  display: block; width: 100%; height: 20px; padding: 0 3px; box-sizing: border-box;
  border: 0; margin: 0; cursor: pointer; text-align: left;
  font: normal 10px Verdana, Arial, sans-serif; line-height: 20px; color: #BA4444;
  background: #FEC9C9; white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
body.bureau-frutiz #salons-panel .sp-salon.paire { background: #FEABAB; }
body.bureau-frutiz #salons-panel .sp-salon:hover { background: #FFF2F2; }
/* La barre du bas (`frameCreate`, un cpDocument de 18 px de haut minimum posé
   dans la marge basse) : 4 px de marge, le bouton, 10 px, le champ. */
body.bureau-frutiz #salons-panel .sp-pied {
  flex: 0 0 16px; display: flex; align-items: center; gap: 12px; padding: 0 1px;
}
/* Le bouton `butPushStandard` (#465) est une GÉLULE de 16 px de haut : le
   dessin extrait donne l'anneau `#F28687` de 1,5 px et le fond `#FFAAAD`, le
   relevé donne l'encre `#660000` et l'éclat `#FFEAEC` du bout droit. Une
   gélule s'étire — on la refait donc en CSS plutôt que d'étirer le SVG, qui
   déformerait ses bouts ronds. */
body.bureau-frutiz #salons-panel .sp-creer {
  position: relative;
  flex: 0 0 120px; height: 16px; padding: 0; border: 0; border-radius: 8px;
  background: #FFAAAD; box-shadow: inset 0 0 0 1.5px #F28687;
  font: 700 10px Verdana, Arial, sans-serif; color: #660000;
  cursor: pointer; white-space: nowrap;
}
/* LE REFLET du bouton. Le dessin (#462) porte une troisième forme, en
   `#FFEAEC` : un filet qui longe l'INTÉRIEUR du bord haut (y 2,85..3,4 sur
   les 16 de haut, de x 5,3 à 34,2) puis s'enroule autour du bout DROIT
   jusqu'à y 12,65. Un filet de 1 px sur une gélule rentrée de 1,5, bordée en
   haut et à droite, redonne exactement ce tracé — et il s'étire, ce que le
   SVG ne saurait faire sans écraser ses bouts ronds. */
body.bureau-frutiz #salons-panel .sp-creer::after {
  content: ""; position: absolute; inset: 1.5px; pointer-events: none;
  border-radius: 6.5px;
  border-top: 1px solid #FFEAEC; border-right: 1px solid #FFEAEC;
  border-left: 0; border-bottom: 0;
}
body.bureau-frutiz #salons-panel .sp-creer[disabled] { cursor: default; }
/* Le champ `<i v="roomName">` (`inputField` #170, 14 px de haut) : le dessin
   d'origine est GRIS et se fait teinter à l'emploi — d'où le vert relevé,
   `#DDFFBB` = green.light dans le fond et `#94DB39` = green.dark au bord. */
body.bureau-frutiz #salons-panel .sp-nom {
  flex: 1; min-width: 0; height: 14px; padding: 0 6px; border: 0;
  border-radius: 7px; background: #DDFFBB; box-shadow: inset 0 0 0 1px #94DB39;
  font: normal 10px Verdana, Arial, sans-serif; color: #335511;
}

/* ── LA FENÊTRE DU SALON (win.Chat 0x690f4, qui étend win.Dialog) ───────────
   Le light met sa barre d'outils EN HAUT, avec un menu déroulant de salons.
   Le bureau d'époque met quatre boutons EN COLONNE À GAUCHE, et pas de menu :
   le salon se choisit dans la fenêtre « Salons publics ».

   `genLeftIconList` (0x691da) déclare les quatre, chacun un `butPush` de
   `param {link: 'butPushSmallPink', frame: N, outline: 2, curve: 4}`. Dans
   l'ordre du tableau (InitArray dépile depuis le sommet, cf. PLAN.md) :
   la BOUILLE (frame 3, toggleScreenList), la LISTE (frame 2, toggleUserList),
   les FEUTRES (frame 4, togglePenList), l'AVERTISSEMENT (frame 5,
   box.whining). Le rendu 1:1 les montre exactement dans cet ordre.

   `displayLeftIconList` (0x693c9) donne le gabarit : `struct.x.size = 22`,
   `struct.y.size = 22`, `space = 4` des deux côtés, et le compo
   `leftIconListFrame` a `min: {w: 24, h: 0}`. Relevé au pixel : la gélule
   fait **20×20**, son contour `#DDDDDD` 2 px l'entoure (donc 24 de large,
   la largeur du compo), et deux boutons sont séparés de 2 px de blanc —
   soit un PAS de 26. */
/* Le corps du salon : 2 px de blanc à gauche et à droite, **4** en bas —
   relevé, la ligne de saisie finit en y 415 et le liseré de la fenêtre
   commence en 420. */
body.bureau-frutiz .fen:has(#chat-panel.active) .fen-corps {
  flex-direction: row; gap: 0; margin: 0 2px 4px;
}
/* La colonne descend de 2 px : d'époque le contour `#DDDDDD` du premier
   bouton tombe en y 288-289 et la gélule en 290, soit 2 px de blanc entre le
   haut du corps et le contour. Le contour du bouton, comme celui d'un écran
   à bouille, est une ombre portée qui DÉBORDE dans les 2 px de rembourrage du
   panneau : relevé 1:1, la gélule occupe x 429..448 et son contour 427..450,
   quand le bord du contenu est en 429. La colonne fait donc la largeur d'une
   gélule — 20 — et laisse SIX px avant le fil, exactement comme la pile des
   bouilles : le compo commence en 455, soit 429 + 20 + 6. */
body.bureau-frutiz .fen #topbar {
  flex: 0 0 24px; width: 20px; flex-direction: column; align-items: center;
  gap: 6px; padding: 2px 0 0; border: 0; background: transparent;
  margin-right: 6px;
  height: max-content;
}
/* Le menu déroulant des salons n'a plus lieu d'être : c'est « Salons
   publics » qui choisit le salon, comme d'époque. */
body.bureau-frutiz .fen #topbar #menu-btn,
body.bureau-frutiz .fen #topbar #room-select { display: none; }
/* Les quatre gélules, dans l'ordre du bytecode. */
/* Le param du bouton dit `curve: 4` : la gélule est arrondie à 4, et son
   contour — 2 px au-delà — à 4 + 2 = 6. CSS gonfle tout seul le rayon d'une
   ombre portée de son épaisseur : il suffit d'arrondir la boîte à 4. */
body.bureau-frutiz .fen #topbar .icon-btn {
  flex: 0 0 20px; width: 20px; height: 20px; min-width: 0; padding: 0;
  border: 0; border-radius: 4px; background: transparent;
  box-shadow: 0 0 0 2px #DDDDDD; margin: 0;
  background-position: center; background-repeat: no-repeat; background-size: 20px 20px;
}
body.bureau-frutiz .fen #topbar .icon-btn img { display: none; }
body.bureau-frutiz .fen #topbar #bouille-toggle {
  order: 0; background-image: url('/frutiz/sprites/chat-but-bouille.svg');
}
body.bureau-frutiz .fen #topbar #users-btn {
  order: 1; background-image: url('/frutiz/sprites/chat-but-userlist.svg');
}
body.bureau-frutiz .fen #topbar #pen-btn {
  order: 2; background-image: url('/frutiz/sprites/chat-but-penlist.svg');
}
body.bureau-frutiz .fen #topbar #chat-warning {
  order: 3; background-image: url('/frutiz/sprites/chat-but-warning.svg');
  cursor: default;
}
/* Le panneau du salon remplit ce qui reste, sans marge à lui. */
/* Le panneau se rentre de 2 px : c'est la place que prend le CONTOUR de la
   zone des messages, qu'une ombre portée dessine HORS de la boîte. */
body.bureau-frutiz .fen #chat-panel {
  flex: 1; min-width: 0; gap: 0; padding: 2px 2px 0; background: transparent;
}
/* LA ZONE DES MESSAGES est un compo peint par `drawCustomSquare` : contour
   2 px `#DDDDDD` (white.shade), liseré 2 px `#ADE76B` (green.shade), fond
   `#CCF599` (green.main) — et le drapeau `chrome`, donc LE REFLET : un
   dégradé blanc de 10 px qui part de 80 % au bord du compo et s'éteint.
   Le liseré en mange les deux premiers, d'où les 0,64 relevés sur la
   première ligne visible (mesuré 0,608, puis 0,51, 0,43, 0,35, 0,275, 0,196,
   0,118, 0,039, 0 — une descente linéaire jusqu'au dixième pixel). */
body.bureau-frutiz .fen #chat-panel #messages {
  flex: 1; min-height: 0; margin: 0; padding: 4px 6px;
  background:
    linear-gradient(to bottom, rgba(255,255,255,.64) 0, rgba(255,255,255,0) 8px),
    #CCF599;
  border: 2px solid #ADE76B; border-radius: 5px;
  box-shadow: 0 0 0 2px #DDDDDD;
}
/* LA LIGNE DE SAISIE, c'est `inputField` (#170) tel quel, SANS teinture :
   14 px de haut, corps `#EEEEEE`, arête haute `#CCCCCC` — le relevé donne
   `#CCCCCC` sur une ligne puis `#EEEEEE` sur treize. Elle fait la largeur de
   la zone des messages, et rien ne l'accompagne : d'époque il n'y a NI
   bouton « Envoyer » NI aide aux accents, on valide à Entrée. */
/* La ligne de saisie s'aligne sur le LISERÉ de la zone des messages, pas sur
   son contour : relevé x 443..604 quand le compo va de 441 à 606. Et elle en
   est séparée de 4 px de blanc. */
/* 6 px de marge et non 4 : d'époque il y a 4 px de blanc sous le CONTOUR de
   la zone des messages, et ce contour est une ombre portée, hors de la boîte
   — il faut donc lui rendre ses 2 px en plus. */
body.bureau-frutiz .fen #chat-panel .compose {
  padding: 0; background: transparent; border: 0; gap: 0; margin-top: 6px;
}
body.bureau-frutiz .fen #chat-panel #accent-toggle,
body.bureau-frutiz .fen #chat-panel #compose-send { display: none; }
/* Le RAYON n'est pas maximal : le bout de `inputField` est la forme #166, un
   dessin de 4×14 dont le tracé part de (0,0) et arrive en (−4,4) par une
   seule courbe — un quart de rond de RAYON 4 sur une barre de 14, là où la
   gélule pleine en demanderait 7. Le relevé au pixel le confirme : le bord
   gauche n'atteint x 523 qu'en y 506, quatre lignes sous le haut de la barre.
   Le liseré `#CCCCCC` du haut fait partie du même dessin. */
body.bureau-frutiz .fen #chat-panel .compose input {
  height: 14px; padding: 0 7px; border: 0; border-radius: 4px;
  background: #EEEEEE; box-shadow: inset 0 1px 0 #CCCCCC;
  font: normal 10px Verdana, Arial, sans-serif; color: #333333;
}
/* LE TEXTE des messages, au relevé : les bandes d'encre du rendu 1:1 tombent
   en y 297..305, 314..322, 330..338 — soit une hauteur d'encre de 9 px et un
   INTERLIGNE de 17. Neuf pixels de hauteur de capitale, c'est du 12 px en
   Verdana. Et l'encre est `#335511`, green.overdark — la même que les
   étiquettes d'icônes du bureau, pas le vert délavé du fil mobile.
   La ligne système reste en italique, comme d'époque. */
body.bureau-frutiz .fen #chat-panel #messages .msg {
  margin: 0; font-size: 12px; line-height: 17px; color: #335511;
}
body.bureau-frutiz .fen #chat-panel #messages .msg.system { font-size: 12px; color: #335511; }

/* ── Les TROIS PANNEAUX du salon ────────────────────────────────────────────
   Les trois premiers boutons de la colonne ouvrent chacun un compo, et le
   bytecode dit exactement où :
     • `displayScreenList` (0x6973d) — `cpScreenList`, min 100×200, dans
       `margin.LEFT` : les bouilles du salon, à gauche de la conversation ;
     • `displayUserList`  (0x695a7) — `cpUserList`, dans `margin.RIGHT` ;
     • `displayPenList`   (0x69849) — `cpPenList`, min 120×48, inséré dans
       `main` à l'index 2, donc ENTRE la conversation et la ligne de saisie.
   Le light avait les trois fonctions, mais en habits mobiles : un tiroir qui
   glisse, une bande flottante, une bouille en surimpression. Ici elles se
   rangent comme d'époque.

   Détail relevé : quand la liste des BOUILLES s'ouvre, la colonne des icônes
   se met en RANGÉE — `toggleScreenList` remplace `min.h` par
   `lefIconListHMaxLarge` = 4 + 24 × ceil(4/4) = 28. */
/* En RANGÉE, la colonne se couche AU-DESSUS DE LA PILE DES BOUILLES — dans
   la marge gauche, pas en bandeau sur toute la largeur : `mcLeftIconList` et
   `screenList` sont tous deux dans `margin.left`, un cadre de type « w » qui
   empile ses enfants en hauteur. Le fil de discussion, lui, ne descend PAS :
   relevé sur la fenêtre d'époque en grand, les quatre gélules occupent
   x 427..528 y 295..315 pendant que le compo commence en (533, 295) — même
   hauteur de départ. `lefIconListHMaxLarge` lui donne 24 px de haut. */
body.bureau-frutiz .fen #topbar.en-rangee {
  flex: 0 0 24px; flex-direction: row; justify-content: flex-start;
  width: max-content; height: 24px; padding: 2px 0 0; gap: 6px;
  /* `align-items: center` vient du mode COLONNE, où il centre les gélules en
     largeur. Couché, il les centrerait en HAUTEUR dans les 24 px et les
     descendrait d'un pixel : le relevé les veut à 2 px du haut, contour
     compris, comme dans la colonne. */
  align-items: flex-start;
}

/* LES FEUTRES — les dessins du SWF, pas une peinture. Chaque feutre est le
   bitmap #595 recomposé : capuchon gris de 7 px de large sur 14 de haut,
   posé sur un corps de 5 px de large et 22 de haut, anneau et pointe
   blanche. Sept px de large, QUARANTE de haut au repos, au PAS DE 12 — d'où
   les 5 px d'écart. La teinte court des lignes 19 à 51 de la planche
   (`résultat = couleur + (gris − 255)`) : le capuchon et le pied restent
   gris quelle que soit la couleur.
   La rangée se pose à MÊME le blanc de la fenêtre : le rendu d'époque ne lui
   met ni cadre ni fond, et il ne la fait pas passer à la ligne — au-delà de
   la largeur, les derniers feutres sont simplement coupés. */
/* Quarante-huit pixels de haut : 4 de blanc, le feutre sur 40, 4 de blanc —
   c'est exactement le `min` que `displayPenList` donne au compo (120×48,
   0x69849). Et 5 px de retrait à gauche : d'époque le premier capuchon tombe
   en x 528 quand la colonne du milieu commence en 523. */
body.bureau-frutiz .fen #chat-panel #pen-bar {
  flex: 0 0 auto; flex-wrap: nowrap; gap: 5px; padding: 4px 0 4px 5px; margin-top: 0;
  background: transparent; border: 0; border-radius: 0;
  box-shadow: none; overflow: hidden;
}
/* Les TROIS dessins sont alignés PAR LE BAS : la pointe ne bouge jamais.
   D'où une case de 42 (le plus haut des trois, le survol) remontée de 2 pour
   que le bas reste à sa place, et une image posée `center bottom`. */
body.bureau-frutiz .fen #chat-panel #pen-bar .pen-swatch {
  width: 7px; height: 42px; margin-top: -2px; flex: 0 0 7px;
  border: 0; border-radius: 0;
  box-shadow: none; transform: none; color: transparent; font-size: 0;
  background: var(--feutre-image, none) center bottom / 7px 40px no-repeat !important;
  image-rendering: pixelated;
}
/* « Aucun feutre » n'existe pas d'époque — c'est une commodité du light, et
   sa croix décalerait toute la rangée d'un pas. Sur le bureau elle s'efface :
   on se déchoisit en recliquant son feutre, comme `selectPen` (0x821f4). */
body.bureau-frutiz .fen #chat-panel #pen-bar .pen-swatch.none { display: none; }
/* Le feutre CHOISI est DÉCAPUCHONNÉ : `selectPen` (0x821f4) envoie son `gfx`
   à la frame 5 et rend l'autre à la frame 1. Ce dessin-là fait 37 px au lieu
   de 40 ; posé au même haut, il finit donc 3 px plus haut que ses voisins —
   le feutre semble se soulever. C'est toute la marque de la sélection, le SWF
   n'en met pas d'autre. */
body.bureau-frutiz .fen #chat-panel #pen-bar .pen-swatch.sel {
  background: var(--feutre-image-sel, var(--feutre-image, none)) center bottom / 7px 37px no-repeat !important;
}
/* AU SURVOL, le feutre S'ENTROUVRE : son CAPUCHON monte de deux pixels et
   découvre deux lignes du fût. Rien d'autre ne bouge — la pointe reste où
   elle est, le corps garde sa couleur.
   Le bytecode fait croire à autre chose : `cp.PenList` définit `rollOverPen`
   (0x8244c) et `rollOutPen`, qui demandent une peinture vers le blanc à 50 %
   puis 100. Mais RIEN NE LES APPELLE — le `link` du bouton (0x8212c) ne
   branche que `onPress`. Ce sont deux fonctions mortes, et le rendu d'époque
   le confirme : le corps du feutre survolé ne pâlit pas d'un iota.
   Ce qui bouge, c'est la FRAME : un `butCustom` prend ses états dans la bande
   du `gfx` (repos / survol / appui) à partir de `frameDecal`. Frame 1 au
   repos, frame 2 au survol — le capuchon relevé.
   Le feutre CHOISI, lui, ne réagit plus : `frameDecal` passe à 5 et le relevé
   1:1 donne exactement les mêmes pixels, survolé ou non. */
body.bureau-frutiz .fen #chat-panel #pen-bar .pen-swatch:hover {
  background: var(--feutre-image-survol, var(--feutre-image, none)) center bottom / 7px 42px no-repeat !important;
}
body.bureau-frutiz .fen #chat-panel #pen-bar .pen-swatch.sel:hover {
  background: var(--feutre-image-sel, var(--feutre-image, none)) center bottom / 7px 37px no-repeat !important;
}
/* Le feutre MULTICOLORE est un article du revival : la planche #595 n'a pas
   de teinte pour lui. On lui prête donc la SILHOUETTE du feutre — le PNG sert
   de masque — et on la remplit d'un arc-en-ciel puisé dans les dix-sept
   teintes. C'est le seul feutre dessiné et non extrait, et il est signalé
   comme tel dans le carnet. */
body.bureau-frutiz .fen #chat-panel #pen-bar .pen-swatch.mc,
body.bureau-frutiz .fen #chat-panel #pen-bar .pen-swatch.mc:hover {
  background: linear-gradient(#FF6600, #EBB601, #5EA523, #47B9C9, #472899, #962761) !important;
  -webkit-mask: url('/frutiz/sprites/feutre-0.png') center bottom / 7px 40px no-repeat;
  mask: url('/frutiz/sprites/feutre-0.png') center bottom / 7px 40px no-repeat;
}
body.bureau-frutiz .fen #chat-panel #pen-bar .pen-swatch.mc:hover {
  -webkit-mask: url('/frutiz/sprites/feutre-0-survol.png') center bottom / 7px 42px no-repeat;
  mask: url('/frutiz/sprites/feutre-0-survol.png') center bottom / 7px 42px no-repeat;
}
body.bureau-frutiz .fen #chat-panel #pen-bar .pen-swatch.mc.sel,
body.bureau-frutiz .fen #chat-panel #pen-bar .pen-swatch.mc.sel:hover {
  -webkit-mask: url('/frutiz/sprites/feutre-0-sel.png') center bottom / 7px 37px no-repeat;
  mask: url('/frutiz/sprites/feutre-0-sel.png') center bottom / 7px 37px no-repeat;
}

/* LES BOUILLES, à gauche. Le compo `cpScreenList` n'a pas de fond à lui : ce
   qu'on voit, c'est une `cp.FrutiScreen` par personne — le MÊME écran que
   celui qui encadre la bouille de la main bar. D'où le même calcul (cf. plus
   haut) : liseré extérieur 2 px `white.shade` = `#DDDDDD`, anneau intérieur
   1 px `white.darker` = `#888888`, rayon 6. Le dégradé vert du fond vient
   avec la bouille elle-même, pas du panneau. */
/* `cpScreenList` est une PILE d'écrans, pas une surimpression : un écran de
   100×100 par personne du salon. Le relevé 1:1 donne le premier en x 417..516
   et y 313..415 — cent pixels de côté, liseré compris — quand le corps de la
   fenêtre, lui, descend jusqu'en 510 : la colonne ne s'étire pas, elle
   s'empile depuis le haut. */
body.bureau-frutiz .fen #chat-panel #bouille-overlay {
  position: static; width: 100px; flex: 0 0 100px; display: none;
  align-self: stretch; background: transparent; border: 0; border-radius: 0;
  box-shadow: none;
  /* Rien ne ROGNE ici. Le contour `#DDDDDD` d'un écran est peint HORS de sa
     boîte (2 px, comme celui d'une gélule) : un `overflow` sur la colonne le
     mangeait des quatre côtés — d'où des écrans qui semblaient collés à la
     rangée et au fil. Le relevé le veut bien là : ligne y=400, `#DDDDDD` en
     427..428 puis l'anneau `#888888` en 429. La colonne n'a de toute façon
     jamais à défiler : `max = floor(hauteur / (taille + écart))` décide du
     nombre d'écrans AVANT de les poser, et l'aquarium, lui, rogne dans
     l'écran (c'est là que les bouilles entrent par la gauche). */
  overflow: visible;
  /* Quatre px sous la rangée d'icônes : les contours (2 px de chaque côté)
     s'y logent et il reste 2 px de blanc — le MÊME écart que le cadre « w »
     de `margin.left` met entre deux gélules de la colonne. Relevé d'époque,
     colonne x=440 : contour du bouton 315..316, blanc 317..318, contour de
     l'écran 319..320, anneau #888888 en 321, dessin en 322. */
  margin: 4px 6px 0 0; padding: 0;
  /* Sur mobile la zone est une SURIMPRESSION du fil : elle laisse passer la
     souris pour qu'on puisse lire dessous. Ici c'est un panneau à part, et
     chaque écran est un BOUTON — `cp.FrutiScreen` branche `onRollOver`,
     `onRollOut` et `onPress`. Il lui faut donc le curseur. */
  pointer-events: auto;
}
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-ecran { cursor: pointer; }
/* …sauf la scène de l'émotion, qui joue DANS l'écran : son iframe avalerait
   le clic destiné à la fiche. */
body.bureau-frutiz .fen #chat-panel #bouille-overlay #bouille-overlay-stage { pointer-events: none; }
body.bureau-frutiz .fen #chat-panel.bouilles-ouvertes #bouille-overlay {
  display: flex; flex-direction: column; align-items: flex-start; justify-content: flex-start;
}
/* Un écran, c'est `cp.FrutiScreen` — le MÊME objet que le cadre de la bouille
   de la main bar. D'où le même calcul (cf. plus haut) : liseré extérieur 2 px
   `white.shade` = `#DDDDDD`, anneau intérieur 1 px `white.darker` = `#888888`,
   rayon 6. Le dégradé vert du fond vient avec la bouille elle-même. Les
   écrans se suivent au pas de `size + ecart`, soit 102 (`screen<i>._y =
   i × (size + ecart)`, `ecart = 2` au prototype) : les deux liserés se
   touchent et se confondent, exactement comme d'époque. */
/* Le fond de l'écran est le DESSIN du SWF — `frutiScreenBackground` (#139),
   que `drawScreen` ÉTIRE à la taille de l'écran (`inside.bg._width = width`,
   `_height = height`), d'où le `100% 100%`. Ce n'est pas un cercle propre :
   c'est un dessin à la main — un pourtour `#A2E866` aux contours ondulants,
   une bande `#C5F297`, et un cœur en dégradé radial `#D6F7B5` → `#C5F297`
   dont le centre est DÉCALÉ en haut à gauche. Le cercle CSS que j'en avais
   tiré au pixel en donnait les teintes, pas la forme. */
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-ecran {
  position: relative; flex: 0 0 100px; width: 100px; height: 100px;
  background: url('/frutiz/sprites/ecran-fond.svg') 0 0 / 100% 100% no-repeat;
  border-radius: 6px; box-shadow: 0 0 0 2px #DDDDDD;
  overflow: hidden; margin: 0 0 2px;
}
/* Et le REFLET, `frutiScreenLight` (#395) : un croissant blanc à 50 %, posé
   au-dessus de TOUT — il est à la profondeur 50, hors du masque — et calé sur
   le bord droit (`light._x = width`), à 2 px du bord et 2 px du haut. Il ne
   s'étire pas : c'est un dessin de 42,7 × 31,8, la même taille sur un écran
   carré comme sur la grande bande du mode CLB. */
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-ecran::before {
  content: ""; position: absolute; right: 2px; top: 2px;
  width: 42.7px; height: 31.8px; z-index: 7; pointer-events: none;
  background: url('/frutiz/sprites/ecran-reflet.svg') 0 0 / 42.7px 31.8px no-repeat;
}
/* MODE CLB : quand il y a plus de monde que d'écrans qui tiennent, il n'en
   reste qu'UN, et il prend toute la zone (`extWidth = width`,
   `extHeight = height`). C'est la grande bande verticale où passe la bouille
   de qui s'exprime. */
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-ecran.clb {
  flex: 1 1 auto; height: auto; align-self: stretch; margin: 0;
}
/* Chaque bouille de l'aquarium : un carré du PETIT côté de la zone, posé en
   absolu à sa hauteur, qui entre par la gauche en glissant. */
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-ecran.clb .bo-clb {
  position: absolute; left: 0; z-index: 3;
  transition: left .42s cubic-bezier(.16, .72, .27, 1);
}
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-ecran.clb .bo-clb img,
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-ecran.clb .bo-clb canvas {
  width: 100%; height: 100%; margin: 0;
}
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-clb #bouille-overlay-stage {
  left: 0; top: 0; right: 0; bottom: 0; width: auto; height: auto;
}
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-clb #bouille-overlay-stage iframe,
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-clb #bouille-overlay-stage canvas {
  width: 100%; height: 100%;
}
/* L'anneau sombre passe PAR-DESSUS la bouille, comme dans la main bar : une
   ombre interne sur la boîte passerait sous l'image. */
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-ecran::after {
  content: ""; position: absolute; inset: 0; border-radius: 6px;
  box-shadow: inset 0 0 0 1px #888888; z-index: 6; pointer-events: none;
}
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-ecran img {
  display: block; width: 98px; height: 98px; margin: 1px; border: 0;
  object-fit: contain;
}
/* `!important` : `FPBouilleVignette` pose `width:100%;height:100%` EN LIGNE —
   ce qui est juste partout ailleurs, mais pas ici : l'écran fait 100 px et la
   bouille s'y pose en RETRAIT d'un pixel, comme l'image qu'elle remplace. */
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-ecran > canvas.fp-bvig {
  display: block; width: 98px !important; height: 98px !important;
  margin: 1px; border: 0;
}
/* ── LA BULLE DE SURVOL D'UNE BOUILLE ───────────────────────────────────────
   `cp.FrutiScreen.setTip` (0x6299a) branche `onRollOver` sur
   `tip.displayCallBack({id:'frutiScreen'+u, cb:{obj:win.box,
   method:'getTipDocLong', args:u}})` ; `TipTextMng.display` attache alors le
   clip `tipText` sur `main` à la profondeur `Depths.tipText` — au-dessus de
   tout, et sans jamais prendre la souris.

   Relevé 1:1 sur Ruffle (fenêtre 626×486, trois survols) :
     • coin haut-gauche = (souris.x − 1, souris.y + 19), et la bulle NE SUIT
       PAS le curseur : elle se pose une fois et n'y bouge plus ;
     • boîte 122 × 48, arrondi extérieur 6 ; de l'extérieur vers la chair :
       1 px #66AA22 · 2 px #DDFFBB · 2 px #94DB39 · 1 px #ADE76B · #CCF599 ;
     • un reflet blanc en haut de la chair, de .72 à 0 sur 9 px — les neuf
       valeurs mesurées (#EFFCDE … #CEF59D) tombent au centième ;
     • Verdana 10 px, interligne 12, encre noire, 3 px de marge à gauche,
       aucune marge en haut : trois lignes remplissent la chair (36 = 3 × 12).
   La largeur NE S'ADAPTE PAS au texte : « zoe » comme « Gaspard » donnent
   122. D'où la chair fixe à 110 (104 de texte + 2 × 3 de marge). */
body.bureau-frutiz .bo-tip {
  position: fixed; z-index: 60; display: none; pointer-events: none;
  box-sizing: content-box; width: 104px; padding: 0 3px;
  background: linear-gradient(rgba(255, 255, 255, .72), rgba(255, 255, 255, 0) 9px), #CCF599;
  /* 2 px, et non 1 : le rayon d'une ombre à écart n'est `rayon + écart` que
     si le rayon ATTEINT l'écart ; en dessous, la spec le rabote —
     `r + s(1 + (r/s − 1)³)`. Avec r = 1 et s = 5 le coin extérieur ne faisait
     que 3,4 px au lieu des 6 du relevé ; avec r = 2 il tombe à 5,9. */
  border: 1px solid #ADE76B; border-radius: 2px;
  /* Et une OMBRE PORTÉE sous le tout : le relevé la donne noire, à ~.20
     contre le liseré et éteinte 4 px plus loin, un peu plus marquée sous la
     bulle que sur ses flancs (d'où le pixel de décalage). */
  box-shadow: 0 0 0 2px #94DB39, 0 0 0 4px #DDFFBB, 0 0 0 5px #66AA22,
              0 1px 5px 5px rgba(0, 0, 0, .4);
  font: 10px/12px Verdana, Geneva, sans-serif; color: #000000;
  /* Un champ Flash n'avale pas l'espace de tête : la deuxième ligne du relevé
     commence bien par « ␣: 22 ans ». Sans `pre-wrap`, HTML le mangerait. */
  white-space: pre-wrap; word-wrap: break-word;
}
body.bureau-frutiz .bo-tip.vue { display: block; }
/* Le pseudo tient sa ligne à lui seul : c'est ainsi que le champ HTML du SWF
   rend `<b>$u</b> : …` — vérifié sur « zoe » comme sur « Gaspard ». */
body.bureau-frutiz .bo-tip b { display: block; font-weight: 700; }

/* Le pseudo n'est pas écrit sous l'écran : d'époque il n'apparaît qu'en
   infobulle au survol. Et la scène du light — la bouille en surimpression du
   fil — se déplace DANS l'écran de la personne le temps d'une émotion : c'est
   là que le SWF la joue. Ailleurs, elle ne se montre pas. */
body.bureau-frutiz .fen #chat-panel #bouille-overlay #bouille-overlay-name { display: none; }
body.bureau-frutiz .fen #chat-panel #bouille-overlay #bouille-overlay-stage {
  display: none; position: absolute; left: 1px; top: 1px; right: auto; bottom: auto;
  width: 98px; height: 98px; transform: none; opacity: 1; z-index: 5;
}
body.bureau-frutiz .fen #chat-panel #bouille-overlay #bouille-overlay-stage.joue { display: block; }
/* L'écran qui joue une émotion ne montre QUE le lecteur : sa vignette figée
   s'efface. Le SWF n'a qu'une bouille par écran — elle s'anime, elle ne se
   double pas. (`visibility` et non `display` : l'image garde sa place, et
   revenir de l'animation ne fait pas sauter la mise en page.) */
/* `!important` : `FPBouilleThumb` pose `style.visibility = "visible"` EN LIGNE
   quand la vignette a fini de charger (c'est ainsi qu'il cache l'icône
   d'image cassée le temps du rendu) — une règle de feuille n'en viendrait
   pas à bout. */
/* Le sélecteur vise la VIGNETTE FIGÉE, c'est-à-dire l'enfant DIRECT de
   l'écran — pas tout ce qui traîne dedans. Depuis que les bouilles sont
   rendues en JS, le lecteur est un canevas lui aussi, et il vit DANS l'écran
   le temps de l'animation : un `.bo-anime canvas` sans `>` le masquait avec
   la vignette, et l'écran devenait blanc pendant les quatre secondes de
   l'émotion. */
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-anime > img,
body.bureau-frutiz .fen #chat-panel #bouille-overlay .bo-anime > canvas { visibility: hidden !important; }
body.bureau-frutiz .fen #chat-panel #bouille-overlay #bouille-overlay-stage iframe {
  width: 98px; height: 98px; border: 0; display: block;
}

/* LES CONNECTÉS, à droite — et ce sont les DESSINS du SWF, pas une peinture
   CSS. `userListBackground` (#352) monte le panneau en trois pièces, qu'on a
   sorties séparément parce qu'elles ne s'étirent pas ensemble :
     • `user-list-pilule.svg` (122×20) — la gélule rose, en haut ET en bas ;
     • `user-list-boite.svg` (122×119) — la boîte verte de la liste, reprise
       en `border-image` pour que ses coins ne se déforment pas ;
     • `user-slot.svg` (120×18) — la bande d'une personne.
   La liste du light garde ses nœuds et ses clics, elle change d'habits. */
body.bureau-frutiz .fen #chat-panel #users-drawer {
  position: static; transform: none; width: 122px;
  /* Le relevé donne 4 px de blanc entre la boîte et le cadre de la fenêtre,
     et le light y était exactement ; deux px de plus à la demande. */
  margin: 0 2px 0 6px; box-shadow: none;
  background: transparent; border: 0; border-radius: 0;
  display: none; height: auto; min-height: 0; padding: 0; gap: 4px;
}
body.bureau-frutiz .fen #chat-panel #users-drawer.open { display: flex; flex-direction: column; }
/* Pas de titre : le panneau d'époque n'en a pas. Les deux gélules qui
   encadrent la boîte sont les BOUTONS DE DÉFILEMENT — c'est exactement ce
   que le light y met déjà, il suffisait de leur rendre leur dessin. */
body.bureau-frutiz .fen #chat-panel #users-drawer h3 { display: none; }
body.bureau-frutiz .fen #chat-panel #users-drawer .users-scroll {
  flex: 0 0 20px; width: 100%; margin: 0; padding: 0; border: 0;
  background: url('/frutiz/sprites/user-list-pilule.svg') center / 100% 20px no-repeat;
  cursor: pointer;
}
body.bureau-frutiz .fen #chat-panel #users-drawer .users-scroll img { display: none; }
/* La BOÎTE : le dessin tient un chapeau arrondi de 10 px, un corps droit de
   100 et un pied arrondi de 10 (le chapeau retourné). On le découpe donc à
   10 en `border-image` : les coins gardent leur rayon, le corps s'étire.
   Le relevé 1:1 donne la première bande à 10 px sous le bord de la boîte —
   c'est exactement l'épaisseur de cette bordure. */
/* La boîte ne DÉFILE pas elle-même : un `overflow` rogne au bord de la zone
   de remplissage, c'est-à-dire À L'INTÉRIEUR de la bordure — et les bandes,
   qui doivent aller d'un bord à l'autre, s'y faisaient couper de 10 px.
   Le défilement est donc confié à un enfant (`.ul-defile`) qui déborde de la
   bordure par des marges négatives, et qui rogne, lui, sur les 122 px pleins. */
body.bureau-frutiz .fen #chat-panel #users-drawer #users-list {
  flex: 1; min-height: 0; overflow: visible; padding: 0; margin: 0;
  background: transparent; border-radius: 0; box-shadow: none;
  border: 10px solid transparent; border-image: url('/frutiz/sprites/user-list-boite.svg') 10 fill / 10px stretch;
}
body.bureau-frutiz .fen #chat-panel #users-drawer #users-list .ul-defile {
  margin: 0 -10px; width: calc(100% + 20px); height: 100%;
  overflow-x: hidden; overflow-y: auto; scrollbar-width: none;
}
body.bureau-frutiz .fen #chat-panel #users-drawer #users-list .ul-defile::-webkit-scrollbar { display: none; }
/* Une personne = la bande `userSlot` (#261), 18 px de haut, et rien de plus :
   le tiroir mobile en fait des tuiles de 48 px en Verdana 22 gras.
   La bande d'époque va d'un bord à l'autre de la boîte : relevé 1:1, la boîte
   occupe x 557..678 et la bande 557..676 — 120 px, elle RECOUVRE à gauche
   l'anneau gris ET le liseré vert. Et le pseudo est CENTRÉ (« temoinchat5 »
   sur 71 px dans une bande de 120, à 2 px du milieu). */
body.bureau-frutiz .fen #chat-panel #users-drawer .u {
  height: 18px; min-height: 18px; width: 120px; padding: 0 4px; margin: 0; border: 0;
  background: url('/frutiz/sprites/user-slot.svg') left top / 120px 18px no-repeat;
  font: 700 10px Verdana, Arial, sans-serif; color: #22224A;
  font-weight: 700; font-size: 10px; letter-spacing: 0; text-shadow: none;
  line-height: 18px; display: flex; align-items: center; justify-content: center;
  gap: 4px; overflow: hidden; white-space: nowrap; box-sizing: border-box;
}
/* UNE LIGNE SUR DEUX seulement porte la bande. `cp.UserList` (0x66d4b) le dit
   au bit près : `backgroundId = 2 − ((i / 2) == Math.round(i / 2))`, soit 1
   pour les rangs pairs et 2 pour les impairs — et l'image 2 de la bande #260
   est VIDE (c'est celle dont le panneau des contacts se sert, où aucune ligne
   n'a de fond). Une ligne sur deux laisse donc voir le `#E8F8D1` de la boîte :
   voilà l'alternance. */
body.bureau-frutiz .fen #chat-panel #users-drawer .u:nth-child(even) { background-image: none; }
/* La liste des connectés est faite du MÊME `userSlot` que le carnet, donc du
   même `butText` : le pseudo vire au `#E7756B` sous le curseur et au
   `#DDDDDD` sous le doigt (cf. la note du carnet, plus haut). Seul le PSEUDO
   suit — la pastille de staff et le lieu ne sont pas des champs d'époque. */
body.bureau-frutiz .fen #chat-panel #users-drawer .u:not([data-genre]):hover span:not(.badge) { color: #E7756B; }
body.bureau-frutiz .fen #chat-panel #users-drawer .u:not([data-genre]):active span:not(.badge) { color: #DDDDDD; }
body.bureau-frutiz .fen #chat-panel #users-drawer .u:hover .lieu,
body.bureau-frutiz .fen #chat-panel #users-drawer .u:active .lieu { color: #6c8f3a; }
body.bureau-frutiz .fen #chat-panel #users-drawer .u.avec-lieu { flex-direction: row; }
body.bureau-frutiz .fen #chat-panel #users-drawer .u .haut {
  display: flex; align-items: center; gap: 4px; min-width: 0;
}
/* Les pastilles du light n'existent pas d'époque : `cp.UserList` n'écrit que
   le pseudo. Celle du « toi » ne dit rien qu'on ne sache — elle saute. Celle
   du staff reste, à l'échelle de la bande et dans la palette verte : elle
   signale les modérateurs, que le revival ne signale nulle part ailleurs. */
body.bureau-frutiz .fen #chat-panel #users-drawer .u .badge.moi { display: none; }
body.bureau-frutiz .fen #chat-panel #users-drawer .u .badge {
  flex: 0 0 auto; padding: 0 3px; border-radius: 5px;
  font: 700 8px Verdana, Arial, sans-serif; line-height: 11px; letter-spacing: 0;
  background: #94DB39; color: #FFFFFF; text-shadow: none;
}
body.bureau-frutiz .fen #chat-panel #users-drawer .u .lieu {
  position: static; font: normal 9px Verdana, Arial, sans-serif; color: #6c8f3a;
  background: transparent; padding: 0; border: 0;
}
body.bureau-frutiz .fen #chat-panel #users-drawer .vide {
  font: normal 10px Verdana, Arial, sans-serif; color: #6c8f3a; padding: 6px 4px;
}
/* « Tout le site » n'existe pas d'époque : c'était un ajout du light. Sur le
   bureau, le panneau ne montre que CE salon — le seul que le protocole
   connaisse — et les onglets disparaissent avec lui. */
body.bureau-frutiz .fen #chat-panel #users-drawer #drawer-onglets { display: none; }
/* Le voile du tiroir mobile n'a plus lieu d'être : le panneau est DANS la
   fenêtre, il ne recouvre rien. */
body.bureau-frutiz .fen #chat-panel #drawer-backdrop { display: none !important; }
/* Le fil et ses panneaux se rangent en GRILLE : bouilles | conversation |
   connectés sur la première ligne, puis les feutres et la saisie pleine
   largeur. Une grille plutôt qu'un flex qui passe à la ligne, parce qu'ici
   c'est la PREMIÈRE ligne qui doit prendre toute la hauteur restante — un
   `flex-wrap` la partage entre les lignes, et la rangée des feutres se
   retrouvait à flotter au milieu du blanc. Une colonne dont le panneau est
   masqué se réduit à zéro d'elle-même. */
/* Les deux panneaux latéraux sont des MARGES de la fenêtre (`margin.LEFT` et
   `margin.RIGHT`) : ils descendent sur toute la hauteur du corps. Les feutres
   et la saisie, eux, sont dans `main` — la colonne du MILIEU — et s'arrêtent
   donc au bord du fil. Le relevé 1:1 le prouve : la ligne de saisie va de 443
   à 604 quand la boîte des connectés occupe déjà 557..678 sur la même ligne.
   L'écart entre colonnes est de 6 px : deux pour le contour de gauche, deux
   pour celui de droite, deux de blanc au milieu (bouilles 417..516, fil
   523..550, connectés 557..678 — 100 + 6 + 28 + 6 + 122 = 262, la largeur
   utile au pixel près). Cet écart est porté par les MARGES des deux panneaux
   et non par un `column-gap` : une colonne fermée ne doit rien coûter, et un
   écart de grille se paierait même sans panneau. */
body.bureau-frutiz .fen #chat-panel {
  display: grid;
  grid-template-columns: auto minmax(0, 1fr) auto;
  grid-template-rows: auto minmax(0, 1fr) auto auto auto;
  column-gap: 0; row-gap: 0;
}
/* La colonne d'icônes tient TOUTE la marge gauche quand elle est debout, et
   seulement sa première ligne quand elle se couche — la pile des bouilles
   prend alors le reste. Le fil, lui, part toujours de la première ligne. */
body.bureau-frutiz .fen #chat-panel #topbar { grid-area: 1 / 1 / -1 / 2; }
body.bureau-frutiz .fen #chat-panel #topbar.en-rangee { grid-area: 1 / 1 / 2 / 2; }
body.bureau-frutiz .fen #chat-panel #bouille-overlay { grid-area: 2 / 1 / -1 / 2; }
body.bureau-frutiz .fen #chat-panel #messages { grid-area: 1 / 2 / 3 / 3; }
body.bureau-frutiz .fen #chat-panel #users-drawer { grid-area: 1 / 3 / -1 / 4; }
body.bureau-frutiz .fen #chat-panel #pen-bar { grid-area: 3 / 2; }
body.bureau-frutiz .fen #chat-panel #accent-bar { grid-area: 4 / 2; }
body.bureau-frutiz .fen #chat-panel .compose { grid-area: 5 / 2; }


/* ══ LES DEUX JOURNAUX — « Mon historique » et « Événements » ═══════════════
   `box.UserLog` et `box.SiteLog` (0x582a9, 0xa9da2) n'ajoutent rien à
   `win.Log` (DoInitAction sprite#750, 0x57281) qu'une icône : `linkIco` vaut
   « icoUserLog » (#533) ou « icoSiteLog » (#576), un clip dont chaque IMAGE
   est une illustration et dont on choisit l'image par le TYPE de l'entrée
   (`gotoAndStop(item.type)` — d'où les étiquettes « forum », « chat »,
   « levelUp », « médaille »…). Ces images sont déjà sorties du SWF dans
   /fb/histo_*.svg et /fb/evt_*.svg : le mobile s'en sert déjà.

   Ce que dit `win.Log` :
     • `flResizable = false` — la fenêtre ne se redimensionne pas ;
     • `main.showFrame` min 300 × 200, sans fond ;
     • `blocMax = 5` — CINQ blocs par page, quoi qu'il arrive ;
     • `pageMax = ceil(liste.length / 5) − 1`, `prevPage`/`nextPage` bornent ;
     • chaque bloc est un `cpDocument` de style `frSheet`, min 300 × 60,
       marge `y.min = 6`, contenant une case de 60 (l'illustration) et le
       texte ;
     • le texte est `<b>date - </b>contenu`, et TOUT en gras si l'entrée est
       neuve (`flNew`) — la date sort de `Lang.formatDateString('short', t)`,
       « mar 25 aout 23:16 », que le light écrit déjà pareil ;
     • le pied est un `cpPageSelector` min 300 × 24 dans `margin.bottom`, qui
       affiche « (index+1)/(pageMax+1) ».

   Relevé 1:1 (fenêtre 314 × 246 posée en 375, 293) :
     cadre 375 · #DDDDDD 376-377 · bandeau 296..311 · séparateur 312-313
     carte 1 : #DDDDDD 312-313 · #ADE76B 314-315 · chair 316..371 ·
               #ADE76B 372-373 · #DDDDDD 374-375
     blanc 376-377, puis la carte 2 : #DDDDDD 378-379 · #ADE76B 380-381 …
   Soit une carte de 60 de haut liseré vert compris (le `min.h` du bytecode),
   un contour `#DDDDDD` de 2 px PEINT HORS de la boîte, et 6 px d'un bloc à
   l'autre — dont 4 mangés par les deux contours. Exactement la loi des
   écrans à bouille.
   Horizontalement : blanc 378-379, contour 380-381, liseré 382-383, chair
   384.., le texte commence en 444 — soit une case d'illustration de 60.
   Le reflet de la chair : blanc .64 → 0 sur 8 px (huit valeurs mesurées).
   L'encre : `#335511`, Verdana gras 10 px, interligne 12. */
body.bureau-frutiz .fen #evt-panel { display: flex; flex-direction: column; min-height: 0; }
body.bureau-frutiz .fen #evt-panel .fenetre {
  display: flex; flex-direction: column; flex: 1 1 auto; min-height: 0;
  background: transparent; border: 0; border-radius: 0; box-shadow: none;
}
/* Le bandeau du panneau mobile fait doublon avec celui de la fenêtre. */
body.bureau-frutiz .fen #evt-panel .fen-titre { display: none; }
/* Le corps se serre, comme celui du salon : le relevé donne 2 px de blanc
   entre le liseré de la fenêtre et le contour du premier bloc — pas les 6 px
   que `.fen-corps` laisse par défaut. */
body.bureau-frutiz .fen:has(#evt-panel) .fen-corps { margin: 0 2px 0; }
body.bureau-frutiz .fen #evt-panel #evt-liste {
  flex: 1 1 auto; min-height: 0;
  /* Rien ne rogne : le contour `#DDDDDD` d'un bloc est peint HORS de sa
     boîte, et il vient toucher le bandeau pour le premier. */
  overflow: visible;
  background: #FFFFFF; padding: 2px 2px 0;
}
/* Un bloc : la case de 60 pour l'illustration, puis le texte. Le contour
   `#DDDDDD` est une ombre à écart — il déborde de la boîte, comme d'époque,
   et vient toucher le séparateur du bandeau pour le premier bloc. */
body.bureau-frutiz .fen #evt-panel .evt-item {
  display: flex; gap: 0; align-items: flex-start;
  box-sizing: border-box; width: 300px; height: 60px; min-height: 60px;
  margin: 0 0 6px; padding: 0;
  background: linear-gradient(rgba(255, 255, 255, .64), rgba(255, 255, 255, 0) 8px), #CCF599;
  border: 2px solid #ADE76B; border-radius: 0;
  box-shadow: 0 0 0 2px #DDDDDD;
}
body.bureau-frutiz .fen #evt-panel .evt-item .vis {
  flex: 0 0 60px; width: 60px; height: 56px; align-self: stretch;
  display: flex; align-items: center; justify-content: center; overflow: hidden;
}
body.bureau-frutiz .fen #evt-panel .evt-item .vis img { max-width: 60px; max-height: 56px; }
/* LA TYPO. Le 12 px relevé sur la carte d'époque tassait le texte dans une
   case de 60 : la ligne y passait au ras du bord et la date mangeait le
   début du message. On descend à 9 px, et la DATE prend sa propre ligne —
   le message commence alors toujours au même endroit, quelle que soit la
   longueur de « mar 25 aout 23:16 ». Le tiret qui les séparait n'a plus
   d'objet : il est masqué (il reste pour le mobile, qui garde la ligne). */
body.bureau-frutiz .fen #evt-panel .evt-item .txt {
  flex: 1 1 auto; min-width: 0; overflow: hidden;
  font-size: 9px; line-height: 12px; font-weight: 400;
  color: #335511; word-break: normal; overflow-wrap: break-word;
}
body.bureau-frutiz .fen #evt-panel .evt-item .quand { font-weight: 700; display: block; }
body.bureau-frutiz .fen #evt-panel .evt-item .quand i { display: none; }
/* Une entrée NEUVE a toute sa ligne en gras — et rien de plus : le SWF ne
   l'agrandit pas (c'était une liberté du mobile, qui la garde). */
body.bureau-frutiz .fen #evt-panel .evt-item.neuf .txt { font-weight: 700; font-size: 9px; }
/* LE PIED : les deux gélules aux extrémités, le compte au milieu. Le dessin
   est celui du SWF (/fb/fleche_*.svg), en 16 px, ceint de 2 px `#DDDDDD`
   comme toutes les gélules du bureau. */
/* LE PIED fait 24 (`cpPageSelector`, min 300 × 24) et la gélule 16, ceinte
   de ses 2 px : 2 + 20 + 2 en hauteur, et le contour à 1 px du bord du
   corps. Relevé : contour 381..382 et 514..515, gélule 383..398 / 516..531. */
body.bureau-frutiz .fen #evt-panel .fen-pied {
  flex: 0 0 24px; height: 24px; align-items: center;
  padding: 2px 1px; box-sizing: border-box; background: #FFFFFF; margin: 0;
}
body.bureau-frutiz .fen #evt-panel .fen-page {
  width: 16px; height: 16px; margin: 0 2px; border-radius: 4px;
  box-shadow: 0 0 0 2px #DDDDDD;
}
body.bureau-frutiz .fen #evt-panel .fen-page img { width: 16px; height: 16px; }
body.bureau-frutiz .fen #evt-panel .fen-page:active img { transform: none; }
/* D'époque les deux gélules gardent leurs couleurs même quand il n'y a qu'une
   page : `cpPageSelector` ne les grise pas. Elles ne font rien, voilà tout. */
body.bureau-frutiz .fen #evt-panel .fen-page[disabled] { opacity: 1; }
body.bureau-frutiz .fen #evt-panel #evt-page {
  font: 400 12px/14px Verdana, Geneva, sans-serif; color: #000000;
}
body.bureau-frutiz .fen #evt-panel .evt-vide,
body.bureau-frutiz .fen #evt-panel .evt-charge {
  font-size: 12px; line-height: 12px; font-weight: 700; color: #335511; padding: 12px 6px;
  text-align: left;
}

/* ══ LES SCORES — `box.Score` (0xade18) ════════════════════════════════════
   La seule fenêtre du bureau qui ne soit pas verte : son `winType` vaut
   « winScore » (0xc1128) et lui donne la rampe MIEL. Relevé 1:1 sur le rendu
   d'époque (fenêtre 610 × 328 posée en 375, 293) :

     cadre 375 · #DDDDDD 376-377 · bandeau blanc 296..311
     colonne GAUCHE   contour 380-381 · liseré `#FACE68` 382-383 ·
                      chair `#FBD888` 384..539 · liseré 540-541 · contour 542-543
     blanc 544-545
     colonne DROITE   contour 546-547 · liseré 548-549 · chair 550..975 …
     et en hauteur : liste 314..587, sélecteur de jour 592..615,
                     panneau de droite 314..613.

   Soit 160 pour la colonne de gauche, 430 pour celle de droite, et 6 px d'un
   panneau à l'autre — dont 4 mangés par les deux contours, comme partout
   ailleurs sur ce bureau. Le reflet de la chair est le même que celui des
   cartes du journal : blanc .64 → 0 sur 8 px.

   Le BANDEAU, lui, ne dit pas « Scores » mais « Scores - Burning kiwi -
   mer 26 aout » : c'est le classement choisi qui le nomme (cf. `retitrer`). */
body.bureau-frutiz .fen:has(#scores-panel) .fen-corps { margin: 0 2px 0; }
body.bureau-frutiz .fen #scores-panel {
  display: flex; flex-direction: column; min-height: 0; padding: 0;
  /* Le corps de la fenêtre est BLANC sous les deux panneaux — c'est lui qu'on
     voit autour d'eux et derrière le sélecteur de jour. */
  background: #FFFFFF;
}
body.bureau-frutiz .fen #scores-panel #sc-fenetre {
  margin: 0; border: 0; border-radius: 0; box-shadow: none;
  background: transparent; overflow: visible;
}
/* Le bandeau du panneau mobile fait doublon avec celui de la fenêtre. */
body.bureau-frutiz .fen #scores-panel #sc-titre { display: none; }
body.bureau-frutiz .fen #scores-panel #sc-corps {
  flex: 1 1 auto; min-height: 0; display: flex; gap: 6px;
  /* 4 px sous les colonnes : le contour du panneau de droite s'y loge
     (614-615) et il reste 2 px de blanc avant le liseré de la fenêtre. */
  padding: 2px 2px 4px; overflow: visible;
}
body.bureau-frutiz .fen #scores-panel #sc-gauche {
  flex: 0 0 160px; width: 160px; gap: 0; overflow: visible;
}
/* Les deux panneaux : chair miel, liseré `#FACE68`, contour `#DDDDDD` PEINT
   HORS de la boîte — d'où `overflow: visible` sur ce qui les porte. */
body.bureau-frutiz .fen #scores-panel #sc-liste,
body.bureau-frutiz .fen #scores-panel #sc-table {
  box-sizing: border-box;
  background: linear-gradient(rgba(255, 255, 255, .64), rgba(255, 255, 255, 0) 8px), #FBD888;
  border: 2px solid #FACE68; border-radius: 0;
  box-shadow: 0 0 0 2px #DDDDDD;
  scrollbar-width: none;
}
body.bureau-frutiz .fen #scores-panel #sc-liste::-webkit-scrollbar,
body.bureau-frutiz .fen #scores-panel #sc-table::-webkit-scrollbar { display: none; }
body.bureau-frutiz .fen #scores-panel #sc-liste {
  flex: 1 1 auto; min-height: 0; padding: 0; overflow-y: auto;
}
body.bureau-frutiz .fen #scores-panel #sc-table {
  flex: 1 1 auto; min-width: 0; padding: 2px 4px; overflow-y: auto;
}
/* Le SÉLECTEUR DE JOUR, sous la liste : mêmes gélules que le pied des
   journaux, même bande de 24. Relevé : contour 594..613, gélule 596..611,
   et 4 px de blanc entre le contour de la liste et la bande. */
body.bureau-frutiz .fen #scores-panel #sc-pied {
  flex: 0 0 24px; height: 24px; box-sizing: border-box;
  /* La bande fait 24 et les gélules s'y calent EN BAS : relevé 594..613 pour
     leur contour, quand la bande va de 590 à 613. */
  margin: 2px 0 0; padding: 0 1px; gap: 0; background: transparent;
  align-items: flex-end;
}
body.bureau-frutiz .fen #scores-panel #sc-pied button {
  width: 16px; height: 16px; border-radius: 4px; box-shadow: 0 0 0 2px #DDDDDD;
}
body.bureau-frutiz .fen #scores-panel #sc-pied button img { width: 16px; height: 16px; }
body.bureau-frutiz .fen #scores-panel #sc-pied button[disabled] { opacity: 1; }
body.bureau-frutiz .fen #scores-panel #sc-jour {
  font-size: 12px; line-height: 14px; color: #000000; font-weight: 400;
}
/* Un titre de section : le podium ou la coupe, puis le mot en grand. Relevé :
   encre 320..333 pour « Challenge », soit du 18 px, et le dessin sur 20. */
body.bureau-frutiz .fen #scores-panel .sc-section {
  gap: 3px; padding: 1px 2px 0; font-size: 18px; line-height: 20px; color: #000000;
}
body.bureau-frutiz .fen #scores-panel .sc-section img { width: 20px; height: 22px; }
/* Une ligne de classement : la médaille puis le nom, au pas de 16. */
body.bureau-frutiz .fen #scores-panel .sc-rk {
  gap: 3px; padding: 0 2px 0 8px; font-size: 12px; line-height: 16px; color: #000000;
}
body.bureau-frutiz .fen #scores-panel .sc-rk img { width: 13px; height: 14px; }
body.bureau-frutiz .fen #scores-panel .sc-rk.on { background: transparent; font-weight: 400; }
/* Le panneau de droite : l'encre est noire et grasse, comme le titre de la
   colonne de gauche. */
body.bureau-frutiz .fen #scores-panel #sc-table .sc-entete,
body.bureau-frutiz .fen #scores-panel #sc-table .sc-vide {
  font-size: 12px; line-height: 16px; color: #000000; font-weight: 700;
}
/* Le message d'un classement vide se pose EN HAUT À GAUCHE, droit — d'époque
   c'est « Classement vide pour le moment », une ligne de texte comme une
   autre, pas une invite centrée. (La phrase, elle, reste celle du light : le
   mobile la partage.) */
body.bureau-frutiz .fen #scores-panel #sc-table .sc-vide {
  text-align: left; font-style: normal; padding: 0; margin: 0;
}
body.bureau-frutiz .fen #scores-panel #sc-table .sc-ligne {
  font-size: 12px; line-height: 16px; color: #000000; min-height: 16px;
}
body.bureau-frutiz .fen #scores-panel #sc-table .sc-ligne.moi { background: transparent; }
body.bureau-frutiz .fen #scores-panel #sc-table .sc-moi,
body.bureau-frutiz .fen #scores-panel #sc-table .sc-pod span { color: #000000; }



/* ── LA FICHE (`win.Frutiz` sprite#753 0x583ad, `FrutizInfo` 0x94ba0) ────────
   `win.Frutiz extends WinStandard` : c'est une FENÊTRE, pas une boîte de
   dialogue. Rien ne s'assombrit derrière elle, et `initInterface` la rend
   glissable par son cadre —

     mcInterface.onPress = function() { box.activate(); initDrag(); }

   Le mobile en fait une carte modale, à raison : sur un téléphone une
   fenêtre flottante n'a nulle part où flotter. Ici on lui rend sa nature.

   LE HAUT (`base = 42`), monté par `initFrameSet` :

     margin.top → up (type "h", marge x.min 12, y.min 5, y.ratio 1)
       screenFrame  `frutiScreen`, style frSystem, fix { w: base+36, h: base }
       mid (type "w", min 240)
         info   `cpFrutizBasicInfo`, min 200 × 20   — le pseudo et l'âge
         icon (type "h", marge x.min 4, x.ratio 1)
           left   `basicIconList` des boutons blancs, align "start"
           right  `basicIconList` d'UN bouton : `butPushSmallPink` image 13,
                  outline 2, curve 4 → toggleAdvancedMode

   LE BAS, que `initAdvancedMode` ajoute et `exitAdvancedMode` retire :

     main → explorer  `cpDocument`, style frSheet, flBackground,
                      min { w: 250, h: 244 }, marge y.min 4, y.ratio 1

   et `getMenuLine` ouvre chaque page par les quatre onglets — du TEXTE, gras
   et centré, en style 1 sauf le courant qui prend 1 + 10 = 11.

   Relevé 1:1 (scratchpad/fr-2-ouverte.png, origine au trait sombre de la
   fenêtre, 324 de large) :

     y   2      #444444   le trait de la fenêtre
     y   3-4    #DDDDDD   ·   y 5..53   #FFFFFF   — le HAUT est blanc
     y   8..49            la plaque : 42 de haut, cerclée de #888888
     y  54-55   #DDDDDD   ·   56-57 #ADE76B   ·   58..65 le reflet blanc
     y  66..297 #CCF599   la chair de la feuille
     y  79-80   #ADE76B   le filet sous les onglets
     y 180-181, 277-278   les deux autres filets de la page
     x 315-316  #ADE76B   ·  317-318 #DDDDDD  ·  323 #444444

   Les encres : le pseudo prend la couleur du GENRE (`UserSlot.onInfoBasic` —
   #242169 pour un garçon, #BB4444 pour une fille), l'âge #404040, l'onglet
   courant #842929, les autres et tout le corps #335511. */
/* Le voile du mobile devient, ici, une simple COUCHE transparente : la fiche
   est une fenêtre du bureau, elle ne noircit rien et n'arrête pas la souris.
   Mais elle reste commandée par `.show`, comme sur le mobile — sans quoi une
   fiche vide flottait en permanence au-dessus du bureau. */
body.bureau-frutiz #fiche-backdrop {
  position: fixed; inset: 0; z-index: 70;
  display: none; background: none; padding: 0;
  pointer-events: none;                /* le bureau reste vivant DERRIÈRE */
}
body.bureau-frutiz #fiche-backdrop.show { display: block; }
body.bureau-frutiz #fiche {
  position: absolute; left: var(--fx, 220px); top: var(--fy, 120px);
  width: 324px; max-height: none; overflow: visible;
  pointer-events: auto;
  background: #FFFFFF; border: 0; border-radius: 6px;
  box-shadow: 0 0 0 2px #DDDDDD, 0 0 0 3px #444444, 2px 3px 6px rgba(0,0,0,.35);
  padding: 0;
}
/* LE HAUT : la plaque à gauche, puis les deux lignes. `base = 42`. */
body.bureau-frutiz #fiche .fiche-haut {
  align-items: stretch; gap: 0; padding: 5px 12px 5px 5px;
}
body.bureau-frutiz #fiche .fiche-plaque {
  height: 42px; width: 76px; box-sizing: border-box;
  padding: 2px 6px 2px 3px; margin-right: 6px; gap: 2px;
  background: #C5F297; border: 1px solid #888888; border-radius: 4px;
  box-shadow: 0 0 0 2px #DDDDDD;
}
/* `fix: { w: base + 36, h: base }` : la bouille tient les 36 de gauche, l'écran
   du niveau les 36 de droite. Le gabarit du mobile en fait 60 de côté — trop
   haut d'un tiers pour une plaque de 42. */
/* LA PLAQUE, relevée trait par trait (`frutiScreen`, 76 × 42) :

     x  0..76  ·  y  8..49   la plaque, cerclée de #888888
     x  8..42  ·  y  9..39   le panneau de la BOUILLE, #D6F7B5 — trente et un
                             de haut seulement, pas toute la plaque
     x 43..69  ·  y 15..37   les rayures de l'écran
     x 43..72  ·  y 41..48   « NIV 1 », en vert sombre SUR le fond #C5F297
     x 70..73  ·  y 10..14   le REFLET — il est sur l'ÉCRAN, pas sur la
                             bouille : la colonne x=20 ne montre aucune
                             brillance de y 9 à 39. */
body.bureau-frutiz #fiche .fiche-plaque .fa-frame {
  width: 35px; height: 31px; border-radius: 2px; background: #D6F7B5;
  align-self: flex-start;
}
/* L'ÉCRAN DU NIVEAU. Le premier relevé m'avait trompé : la chair de l'écran
   est le #A2EB56 vif (x 43..69 en travers), et ce sont des traits FINS de
   #D6F7B5, un pixel tous les trois, qui la rayent — de y 14 à 37. Pas des
   barres claires sur fond sombre : un écran vert rayé de lignes de balayage.
   Le gabarit mobile en fait neuf barres empilées ; ici c'est la rayure qui
   compte, on la peint d'un trait et on range les barres. */
body.bureau-frutiz #fiche .fiche-plaque .fa-jauge {
  gap: 0; width: 27px; align-self: flex-start; margin-top: 5px;
}
body.bureau-frutiz #fiche .fiche-plaque .fa-progress {
  width: 27px; height: 23px; gap: 0; display: block;
  background: repeating-linear-gradient(to bottom,
    #A2EB56 0, #A2EB56 2px, #D1F5AB 2px, #D1F5AB 3px);
}
body.bureau-frutiz #fiche .fiche-plaque .fa-progress i { display: none; }
/* « NIV 1 » ne vit pas dans l'écran : il est posé sur le fond de la plaque,
   sous les rayures, en vert sombre. */
body.bureau-frutiz #fiche .fiche-plaque .fa-niv {
  height: 9px; margin-top: 3px; justify-content: flex-start; gap: 2px;
}
body.bureau-frutiz #fiche .fiche-plaque .fa-niv img { height: 8px; width: auto; }
body.bureau-frutiz #fiche .fiche-plaque .fa-niv b { font-size: 8px; color: #73AF1E; }
/* LE REFLET, que le relevé donne en clair : une bande brillante en haut de la
   plaque (#EAFBDA en y 10-11) et un liseré #E2F9CB au bord droit (x 73-74).
   Ce sont les deux dessins de la mainbar — `reflet_bouille` sur la bouille,
   `reflet_niveau` sur l'écran —, à l'échelle d'une plaque de 42. */
/* LE REFLET : le seul que le relevé montre est sur le haut-droit de l'ÉCRAN
   (#E2F9CB en x 70..73). La brillance de la bouille n'existe pas ici — le
   dessin `reflet_bouille` de la mainbar n'a rien à faire sur cette plaque. */
body.bureau-frutiz #fiche .fiche-plaque .cadre,
body.bureau-frutiz #fiche .fiche-plaque .reflet { display: none; }
body.bureau-frutiz #fiche .fiche-plaque .reflet-niv {
  display: block; position: absolute; left: 43px; top: 3px;
  width: 30px; height: auto; z-index: 3; opacity: 1; pointer-events: none;
}
body.bureau-frutiz #fiche .fiche-droite {
  display: flex; flex-direction: column; justify-content: space-between;
  min-width: 0; flex: 1;
}
/* La ligne d'identité : le voyant, le pseudo à la couleur de son GENRE,
   l'âge et le pays poussés à droite, la croix au bout. */
body.bureau-frutiz #fiche .fiche-nom-ligne {
  display: flex; align-items: center; gap: 5px; height: 20px;
}
body.bureau-frutiz #fiche #fiche-pseudo {
  font: 700 11px Verdana, Arial, sans-serif; color: #242169;
}
/* (Le pseudo de la fiche prend la couleur du GENRE — `UserSlot.onInfoBasic`,
   0x63a51. La règle vit maintenant dans light.html, où elle vaut pour les deux
   mises en page, et avec les valeurs exactes du bytecode : #242169 et
   #BB4444. Celle qui était ici disait #BB4A44, un chiffre de travers.) */
body.bureau-frutiz #fiche .fiche-nom-ligne .meta {
  margin-left: auto; font: 400 11px Verdana, Arial, sans-serif; color: #404040;
  white-space: nowrap;
}
/* LA CROIX : `WinStandard` la pose au coin HAUT-DROIT de la fenêtre, pas au
   bout d'une ligne de texte. */
body.bureau-frutiz #fiche #fiche-fermer {
  position: absolute; right: 5px; top: 5px; z-index: 4;
  width: 13px; height: 13px; padding: 0; border: 0; background: none;
  cursor: pointer;
}
body.bureau-frutiz #fiche #fiche-fermer img { width: 13px; height: 13px; display: block; }
body.bureau-frutiz #fiche .fiche-nom-ligne .meta { padding-right: 18px; }
/* La rangée d'actions : les boutons blancs collés à GAUCHE (`x.align
   "start"`), le bouton rose au BOUT (`x.align "end"`). Chacun porte le
   contour de deux pixels que `butPush` dessine. */
body.bureau-frutiz #fiche .fiche-actions {
  display: flex; align-items: flex-start; gap: 6px; height: 22px;
}
body.bureau-frutiz #fiche .fiche-actions button {
  width: 20px; height: 20px; min-width: 0; min-height: 0; box-sizing: border-box;
  padding: 0; border: 0; flex: 0 0 20px; align-self: flex-start;
  border-radius: 4px; box-shadow: 0 0 0 2px #DDDDDD; background: #FFFFFF;
  cursor: pointer; overflow: hidden;
}
body.bureau-frutiz #fiche .fiche-actions button img {
  width: 20px; height: 20px; display: block; margin: 0; object-fit: contain;
}
/* `butPushSmallPink` (#378) : sa PLAQUE est un dessin, pas une couleur — la
   forme #359. Le triangle vient de sa propre bande `icon` (#374) à l'image 13,
   la forme #369. Relevé en x 293..316 et y 28..51 : vingt d'art, deux de
   contour de chaque côté. */
body.bureau-frutiz #fiche .fiche-actions #fiche-avance {
  margin-left: auto;
  background: url('/frutiz/sprites/fiche-rose.svg') center / 20px 20px no-repeat;
}
/* Le triangle ne fait que 8,15 × 8,75 dans son cadre : posé sur les vingt de
   la plaque il doit rester petit et CENTRÉ, pas la remplir. */
body.bureau-frutiz #fiche .fiche-actions #fiche-avance img {
  content: url('/frutiz/sprites/fiche-rose-tri.svg');
  width: 9px; height: 9px; margin: 5.5px auto;
}
/* LE BAS : la feuille verte (`frSheet`), collée sous le haut blanc. */
body.bureau-frutiz #fiche .fiche-corps {
  margin: 0; border: 0; border-radius: 0 0 5px 5px;
  background: linear-gradient(to bottom, rgba(255,255,255,.55) 0, rgba(255,255,255,0) 8px), #CCF599;
  box-shadow: inset 0 2px 0 #ADE76B, inset 0 -2px 0 #ADE76B,
              inset 2px 0 0 #ADE76B, inset -2px 0 0 #ADE76B;
  overflow: hidden;
}
/* LES ONGLETS : quatre colonnes ÉGALES de texte gras centré, séparées du
   corps par le filet #ADE76B relevé en y 79-80. */
body.bureau-frutiz #fiche .fiche-onglets {
  display: grid; grid-template-columns: repeat(4, 1fr);
  margin: 2px 2px 0; padding: 4px 0 3px; border: 0;
  border-bottom: 2px solid #ADE76B; background: none;
}
body.bureau-frutiz #fiche .fiche-onglets button {
  border: 0; background: none; cursor: pointer; padding: 2px 0;
  font: 700 12px Verdana, Arial, sans-serif; color: #335511; text-align: center;
  text-transform: lowercase;         /* `categoryList` : "frutiz", "perso"… */
}
body.bureau-frutiz #fiche .fiche-onglets button.actif { color: #842929; }
body.bureau-frutiz #fiche .fiche-onglets button:hover { color: #E7756B; }
/* LA PAGE : `getPageObj` la borne à 250 × 240 ; la fenêtre en fait 324, on
   garde la hauteur et on laisse la largeur suivre. */
body.bureau-frutiz #fiche .fiche-page {
  height: 240px; padding: 8px 6px 6px; overflow-y: auto;
  font: 400 11px Verdana, Arial, sans-serif; color: #335511;
}
body.bureau-frutiz #fiche .fiche-titre {
  color: #335511; font-size: 12px; text-transform: lowercase;
}
body.bureau-frutiz #fiche .fiche-titre::before,
body.bureau-frutiz #fiche .fiche-titre::after { background: #ADE76B; height: 2px; }
body.bureau-frutiz #fiche .fiche-signes,
body.bureau-frutiz #fiche .fiche-medailles { border-bottom: 2px solid #ADE76B; }
/* Le pas d'une rangée, relevé sur les cinq lignes de l'onglet « frutiz » :
   l'encre des libellés tombe en 187, 208, 227, 244 et 265 — dix-neuf et demi
   d'une rangée à l'autre. */
body.bureau-frutiz #fiche .fiche-ligne {
  font-size: 11px; padding: 0; height: 19.5px; align-items: center; line-height: 1;
}
/* Et le bloc des rangées se FERME sur un filet, comme il s'était ouvert :
   #ADE76B en y 180-181 au-dessus, en 277-278 au-dessous. */
body.bureau-frutiz #fiche .fiche-lignes {
  padding-bottom: 6px; border-bottom: 2px solid #ADE76B;
}
body.bureau-frutiz #fiche .fiche-ligne .lib,
body.bureau-frutiz #fiche .fiche-ligne .val { color: #335511; }
body.bureau-frutiz #fiche .fiche-jour { color: #335511; }
body.bureau-frutiz #fiche .fiche-jour .pts { color: #5A7D33; }

/* ── LA BOUTIQUE (`win.Shop`, `box.Shop`) ─────────────────────────────────
   `initFrameSet` monte la fenêtre en DEUX colonnes :

     margin.left (140)  · `bar`       : le compteur de kikooz (`cpCounter`,
                                        style `frKikooz`) et, calés à DROITE,
                                        deux `butPushSmallWhite` ;
                        · `menuFrame` : un `cpTree` de 140 au style `frSystem`
                                        — le BLANC —, puces `shopBullet` ;
     main               · `showFrame` → `menuInfoFrame`, un `cpDocument` au
                                        style `frSheet` — le VERT ;
                        · `bar`       → `pushKikooz`, la plaque orange
                                        `butPushMoreKikooz`, min 100 × 60.

   Les puces de l'arbre ne se lisent pas dans `win.Shop` : `cp.Tree` attache
   un `capsDir` (nœud) ou un `capsExe` (feuille), `box.Shop.analyseTree` pose
   `bulletLink: "shopBullet"` sur les deux, et le NUMÉRO d'image vient de la
   classe — `caps.Exe` prend l'image 1 (#563, la pastille OCRE) et `caps.Dir`
   l'image `min(niveau,2)+2`, donc 2 au premier niveau (#564, le dossier
   ROSE). Ce n'est pas « fermé / ouvert », c'est « article / rubrique ».
   `Standard.getTreeStyle()` donne les tailles — 10 pour la feuille, 16 pour
   le dossier de niveau 0 — et `Capsule.height = size + 6` les rangées.

   Relevé 1:1 (scratchpad/sr2-2-article.png, une rubrique dépliée et un
   article choisi ; origine = le trait sombre de la fenêtre, 476 × 404) :

     COLONNE DE GAUCHE
       compteur     x 6..79    y 23..48   74 × 26, coins de 5
                    contour #DDDDDD 2 · liseré #F3BE8C 2 · chair #F8D5BC
       bouton 1     x 98..121  y 25..48   24 × 24, contour #DDDDDD 2
       bouton 2     x 124..147 y 25..48   2 px entre les deux
       arbre        x 6..149   y 53..392  bord #DDDDDD 2, fond blanc
                    (49..52 sont BLANCS : le #DDDDDD de 47-48 est le
                     contour bas de la pastille, pas le haut de l'arbre)
                    rubrique : puce rose de 20, texte 16, rangée de 22
                    article  : puce ocre de 12, texte 10, rangée de 16

     COLONNE DE DROITE
       feuille      x 154..469 y 23..330
                    contour #DDDDDD 2 · liseré #ADE76B 2 · chair #CCF599
       aperçu       x 162..261 y 33..132  100 × 100 (`screen._y = 4`)
       « Acheter »  x 170..253 y 139..158  l'art 80 × 16 + 2 de contour,
                    centré sur les 100 et posé à `_y = 110 + i × 22`
       document     à partir de x 273     (la marge `x.min = 12`)
       plaque       x 314..467 y 335..398  l'art 150 × 60 + 2 de contour

   Les encres relevées : le titre #842929, tout le corps de la fiche #335511
   (#5A7D33 et #80A555 n'étaient que de l'anticrénelage), l'arbre en noir, le
   compteur #764A34. */
/* Le corps se serre : `.fen-corps` laisse 6 px partout, or la boutique d'époque
   pose son arbre à 6 de la bordure et sa plaque à 9 du bord droit. */
body.bureau-frutiz .fen:has(#shop-sheet) .fen-corps { margin: 0 6px 3px 3px; }
body.bureau-frutiz .fen #shop-sheet {
  position: static; inset: auto; transform: none; transition: none;
  max-height: none; border: 0; border-radius: 0; box-shadow: none;
  background: transparent; z-index: auto; padding: 0;
  flex: 1; min-height: 0; display: flex; flex-direction: column;
}
/* La fenêtre a sa propre barre de titre : celle de la feuille fait double
   emploi, et le voile du mobile n'a rien à faire ici. */
body.bureau-frutiz .fen #shop-sheet .sheet-head { display: none; }
body.bureau-frutiz #shop-sheet-backdrop { display: none !important; }
body.bureau-frutiz .fen #shop-sheet .sheet-body {
  flex: 1; min-height: 0; padding: 0; margin: 0; overflow: hidden;
  border: 0; border-radius: 0; box-shadow: none; background: none;
  display: grid; grid-template-columns: 148px 1fr; grid-template-rows: 28px 1fr auto;
  gap: 0;
}
/* LA BARRE DU HAUT À GAUCHE : le compteur, puis les deux boutons calés à
   droite (`struct.x.align = "end"`). */
body.bureau-frutiz .fen #shop-sheet #bo-haut {
  grid-column: 1; grid-row: 1; display: flex; align-items: flex-end; gap: 6px;
  padding: 0; margin: 0 7px 0 0; background: none; border: 0; min-width: 0;
}
/* LE COMPTEUR : `cpCounter` au style `frKikooz` — la pièce `iconCounter`
   (forme #396) à gauche, le nombre en Verdana 14 GRAS. */
body.bureau-frutiz .fen #shop-sheet .bo-solde {
  display: flex; align-items: center; gap: 3px; box-sizing: border-box;
  height: 22px; padding: 0 6px 0 3px; min-width: 69px;
  background: #F8D5BC; border: 2px solid #F3BE8C; border-radius: 5px;
  box-shadow: 0 0 0 2px #DDDDDD;
  font: 700 14px Verdana, Arial, sans-serif; color: #764A34;
}
body.bureau-frutiz .fen #shop-sheet .bo-solde img {
  width: 16px; height: 15px; display: block;
  content: url('/frutiz/sprites/shop-kikooz.svg');
}
body.bureau-frutiz .fen #shop-sheet .bo-solde strong { font: inherit; color: inherit; }
/* LES DEUX PETITS BOUTONS BLANCS : `butPushSmallWhite` — la plaque est la
   forme #473, et #501 la remplace au survol (l'image 2). */
body.bureau-frutiz .fen #shop-sheet .bq-icones {
  margin-left: auto; display: flex; gap: 6px; padding-right: 4px;
}
/* `butPush` dessine son propre fond : `outline: 2` — d'où les deux pixels de
   #DDDDDD tout autour, relevés en x 98..121 et 124..147, soit 24 × 24 pour un
   art qui n'en fait que 20. */
body.bureau-frutiz .fen #shop-sheet .bq-ico {
  position: relative; width: 20px; height: 20px; flex: 0 0 20px;
  padding: 0; border: 0; cursor: pointer; color: transparent; font-size: 0;
  box-shadow: 0 0 0 2px #DDDDDD; border-radius: 4px;
  background: url('/frutiz/sprites/shop-but-blanc.svg') center / 20px 20px no-repeat;
}
body.bureau-frutiz .fen #shop-sheet .bq-ico:hover {
  background-image: url('/frutiz/sprites/shop-but-blanc-2.svg');
}
body.bureau-frutiz .fen #shop-sheet .bq-ico i {
  position: absolute; inset: 1px; display: block;
  background: center / contain no-repeat;
}
/* L'ARBRE DES RUBRIQUES : `cpTree`, 140 de large, une boîte blanche. */
body.bureau-frutiz .fen #shop-sheet #bo-fenetre {
  display: contents;
}
body.bureau-frutiz .fen #shop-sheet #bo-rubriques {
  grid-column: 1; grid-row: 2 / span 2; margin: 8px 5px 8px 0;
  padding: 5px 0 0; overflow: auto; min-height: 0;
  background: #FFFFFF; border-radius: 3px; box-shadow: 0 0 0 2px #DDDDDD;
  display: block;
}
/* Une RUBRIQUE est un `capsDir` de niveau 0 : puce `shopBullet` image 2 — le
   dossier ROSE —, texte de 16, rangée de 16 + 6 = 22. Le mobile pose sa
   propre vignette : elle fait double emploi. */
body.bureau-frutiz .fen #shop-sheet #bo-rubriques button {
  display: flex; align-items: center; gap: 4px; width: 100%; height: 22px;
  padding: 0 4px 0 3px; border: 0; background: none; cursor: pointer;
  font: normal 16px Verdana, Arial, sans-serif; color: #000000;
  text-align: left; white-space: nowrap; overflow: hidden;
}
body.bureau-frutiz .fen #shop-sheet #bo-rubriques .bo-rub img { display: none; }
body.bureau-frutiz .fen #shop-sheet #bo-rubriques .bo-rub::before {
  content: ""; flex: 0 0 20px; width: 20px; height: 18px;
  background: url('/frutiz/sprites/shop-puce-rubrique.svg') center / 20px 18px no-repeat;
}
/* Un ARTICLE est un `capsExe` : puce image 1 — la pastille OCRE, deux fois
   plus petite —, texte de 10, rangée de 16, et un niveau d'indentation
   (`tree.offset = 8`). */
body.bureau-frutiz .fen #shop-sheet #bo-rubriques .bo-art {
  height: 16px; padding-left: 11px;
  font-size: 10px; color: #000000;
}
body.bureau-frutiz .fen #shop-sheet #bo-rubriques .bo-art::before {
  content: ""; flex: 0 0 12px; width: 12px; height: 12px;
  background: url('/frutiz/sprites/shop-puce-article.svg') center / 12px 12px no-repeat;
}
body.bureau-frutiz .fen #shop-sheet #bo-rubriques .bo-art.on { font-weight: 700; }
body.bureau-frutiz .fen #shop-sheet #bo-rubriques .bo-art.eu { color: #8AA86A; }
body.bureau-frutiz .fen #shop-sheet #bo-rubriques button:hover { background: #E8F8D3; }
/* LA FICHE : le style `frSheet` — le vert du bureau, sous son reflet. */
body.bureau-frutiz .fen #shop-sheet #bo-fiche {
  grid-column: 2; grid-row: 1 / span 2; margin: 6px 0 0 2px;
  padding: 2px 4px 6px; overflow: auto; min-height: 0;
  background: linear-gradient(to bottom, rgba(255,255,255,.6) 2px, rgba(255,255,255,0) 12px), #CCF599;
  border: 2px solid #ADE76B; border-radius: 5px; box-shadow: 0 0 0 2px #DDDDDD;
  font: normal 11px Verdana, Arial, sans-serif; color: #335511;
}
/* DEUX COLONNES, et non un bloc : `attachMenu` glisse `menuProductFrame` à
   l'index 0 de `showFrame`, qui est de type "h" — le `cp.ProductMenu` de 100
   se pose donc À GAUCHE du `cpDocument`, séparé de lui par sa marge
   `x.min = 12`. L'aperçu et « Acheter » tiennent cette colonne sur toute la
   hauteur ; le nom, le descriptif et le prix sont dans le document.

   Le mobile les met les uns SOUS les autres (240 px de large, la colonne les
   étranglerait) : ici on remet la grille d'époque, le `.bo-tete` s'effaçant
   pour que ses deux enfants deviennent des cases. */
body.bureau-frutiz .fen #shop-sheet #bo-fiche {
  display: grid; grid-template-columns: 100px 1fr; column-gap: 12px;
  align-content: start;
}
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-tete { display: contents; }
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-vue {
  grid-column: 1; grid-row: 1 / span 99;
  width: 100px; flex: none; padding: 0; border: 0; border-radius: 0;
  background: none;
}
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-txt,
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-accroche,
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-texte,
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-prix,
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-etat { grid-column: 2; }
/* `genScreen` attache `shopScreen` (#405, 100 × 100) à `_y = 4`, et lui pose
   `shopScreenLight` (#409) par-dessus — le lustre. */
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-vue .cadre {
  position: relative; width: 100px; height: 100px; margin-top: 4px;
  box-sizing: border-box; padding: 6px; overflow: hidden;
  background: url('/frutiz/sprites/shop-cadre.svg') center / 100px 100px no-repeat;
  display: flex; align-items: center; justify-content: center;
}
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-vue .cadre::after {
  content: ""; position: absolute; left: 22px; top: 4px;
  width: 73px; height: 64px; pointer-events: none;
  background: url('/frutiz/sprites/shop-cadre-reflet.svg') 0 0 / 73px 64px no-repeat;
}
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-vue .cadre > * { position: relative; z-index: 1; }
/* Le nom en `<t s="4">` : la seule encre rouge de la fiche. */
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-titre {
  font: 700 15px Verdana, Arial, sans-serif; color: #842929; margin: 0;
}
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-accroche {
  font: 700 12px Verdana, Arial, sans-serif; color: #335511; margin: 7px 0 0;
}
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-texte {
  font: normal 12px Verdana, Arial, sans-serif; color: #335511; margin: 6px 0 0;
}
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-prix {
  font: 700 12.5px Verdana, Arial, sans-serif; color: #335511; margin: 8px 0 0;
}
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-etat { margin-top: 6px; }
/* « Acheter » : `butPushShop` (#460, 80 × 16) que `butPush` entoure de deux
   pixels — 84 × 20 en tout —, centré sur les 100 et posé à
   `_y = 110 + i × 22`, soit six pixels sous l'aperçu. */
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-acheter {
  display: block; box-sizing: content-box;
  width: 80px; height: 16px; margin: 6px auto 0; padding: 0;
  border: 2px solid #ADE76B; border-radius: 8px;
  background: url('/frutiz/sprites/shop-but-acheter.svg') center / 80px 16px no-repeat;
  font: 700 10px Verdana, Arial, sans-serif; color: #FFFFFF; cursor: pointer;
  line-height: 16px; text-shadow: none;
}
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-acheter:active { filter: brightness(.9); }
body.bureau-frutiz .fen #shop-sheet #bo-fiche .bo-acheter[disabled] {
  filter: saturate(.25); cursor: default; color: #4A5F30;
}
/* LA GRANDE PLAQUE, calée à DROITE sous la fiche (`main.bar` a un `empty`
   élastique devant elle). L'art fait 150 × 60 ; `min` la borne à 100 × 60. */
body.bureau-frutiz .fen #shop-sheet .bq-pied {
  grid-column: 2; grid-row: 3; display: flex; justify-content: flex-end;
  padding: 7px 2px 0 0; margin: 0;
}
body.bureau-frutiz .fen #shop-sheet .bq-plus {
  width: 150px; height: 60px; flex: 0 0 auto; padding: 0; border: 0;
  box-shadow: 0 0 0 2px #DDDDDD; border-radius: 6px;
  background: url('/frutiz/sprites/shop-plus-kikooz.svg') center / 150px 60px no-repeat;
  cursor: pointer; color: transparent; font-size: 0;
}

/* ── LA MESSAGERIE ────────────────────────────────────────────────────────
   D'époque ce ne sont pas trois vues d'une fenêtre mais TROIS fenêtres : la
   boîte de réception est un EXPLORATEUR (`box.Explorer` sur `fileMng.inbox`,
   `list.tpl == "mail"` — la fenêtre JAUNE), lire un courrier ouvre
   `winViewMail` (500 × 400), en écrire un ouvre `winMail`. Le light n'a qu'un
   panneau à reparenter : on y rejoue les trois GABARITS l'un après l'autre.

   Relevé 1:1 (scratchpad/mr-1-boite.png — fenêtre en x 486..896 / y 146..546,
   soit 411 × 401, la taille de l'explorateur) :

     y 229-230  #DDDDDD   le contour du bandeau des colonnes
     y 231-232  #EAEA0F   son liseré
     y 233-244  reflet blanc puis #F9F977   sa chair — 18 px en tout
     y 245-246  #EAEA0F
     y 247-248  #DDDDDD   le contour du champ
     y 251-254  #DDDDDD puis #EAEA0F
     y 255-262  le même reflet, puis #F8F866
     y 277, 299, 321…     #EAEA0F : une rangée fait 22 px

   et, en travers (y=270) : #F1F13B à 631-632 et 811-812 — deux pixels de
   séparation entre les colonnes, aux abscisses 140 et « largeur − 80 »,
   exactement les `min` du `lister`. L'encre du bandeau est #404000, celle
   des rangées #5A5A00. */
body.bureau-frutiz .fen #mail-panel {
  padding: 0; gap: 0; background: transparent; min-height: 0;
  display: flex; flex-direction: column;
}
/* Les onglets du mobile n'existent pas d'époque : on change de boîte par le
   DOSSIER PARENT, comme dans n'importe quel explorateur. */
body.bureau-frutiz .fen #mail-panel #mail-head { display: none; }
/* LA BARRE D'OUTILS — `initNavigatorIconList` : pour une boîte aux lettres,
   `flNewDirectory` et `flRemoveAll` sont faux, `flUp` et `flMail` vrais. Deux
   boutons, aux mesures de l'explorateur (20 px, écart 4, marge 4). */
body.bureau-frutiz .fen #mail-panel .mx-nav {
  flex: 0 0 28px; height: 28px; box-sizing: border-box;
  padding: 4px 0 0 4px; display: flex; gap: 4px; align-items: flex-start;
}
body.bureau-frutiz .fen #mail-panel .mx-nav-but {
  width: 20px; height: 20px; flex: 0 0 20px; padding: 0; border: 0;
  border-radius: 4px; box-shadow: 0 0 0 2px #DDDDDD;
  background: transparent center / 20px 20px no-repeat;
  cursor: pointer; color: transparent; font-size: 0;
}
/* LE CHAMP, l'écorce commune : contour 2 px #DDDDDD peint HORS de la boîte,
   liseré 2 px #EAEA0F, chair #F8F866 sous un reflet blanc de 8 px. */
body.bureau-frutiz .fen #mail-panel .mx-champ,
body.bureau-frutiz .fen #mail-panel #mail-liste,
body.bureau-frutiz .fen #mail-panel #mail-lu-corps,
body.bureau-frutiz .fen #mail-panel #mail-texte {
  margin: 2px; box-sizing: border-box; overflow: auto;
  background: linear-gradient(to bottom, rgba(255,255,255,.6) 2px, rgba(255,255,255,0) 10px), #F8F866;
  border: 2px solid #EAEA0F; border-radius: 5px; box-shadow: 0 0 0 2px #DDDDDD;
}
/* LE BANDEAU DES COLONNES : sa propre boîte, 18 px, chair un ton plus clair. */
body.bureau-frutiz .fen #mail-panel .mx-entete {
  flex: 0 0 18px; height: 18px; box-sizing: border-box; display: flex;
  margin: 2px 2px 0; overflow: hidden;
  background: linear-gradient(to bottom, rgba(255,255,255,.6) 2px, rgba(255,255,255,0) 10px), #F9F977;
  border: 2px solid #EAEA0F; border-radius: 5px 5px 0 0; box-shadow: 0 0 0 2px #DDDDDD;
}
body.bureau-frutiz .fen #mail-panel .mx-col {
  flex: 0 0 auto; padding: 0 0 0 3px; border: 0; background: none;
  display: flex; align-items: center; gap: 3px; overflow: hidden;
  font: normal 10px Verdana, Arial, sans-serif; color: #404000;
  line-height: 14px; cursor: pointer; text-align: left; white-space: nowrap;
}
body.bureau-frutiz .fen #mail-panel .mx-col.big { flex: 1 1 auto; min-width: 0; }
body.bureau-frutiz .fen #mail-panel .mx-col .t { overflow: hidden; text-overflow: ellipsis; }
/* La flèche de tri, sur la SEULE colonne triée — `currentSort` part sur la
   date en DESC. */
body.bureau-frutiz .fen #mail-panel .mx-col .fl { display: none; }
body.bureau-frutiz .fen #mail-panel .mx-col.trie .fl {
  display: block; width: 0; height: 0; flex: 0 0 auto;
  border-left: 3px solid transparent; border-right: 3px solid transparent;
  border-bottom: 4px solid #6C6400;
}
body.bureau-frutiz .fen #mail-panel .mx-col.trie.desc .fl {
  border-bottom: 0; border-top: 4px solid #6C6400;
}
/* LA LISTE et ses rangées de 22 px. */
body.bureau-frutiz .fen #mail-panel #mail-vue-liste {
  flex: 1; min-height: 0; display: none; flex-direction: column; padding: 0;
}
body.bureau-frutiz .fen #mail-panel #mail-vue-liste.on { display: flex; }
body.bureau-frutiz .fen #mail-panel:not(.mx-dossiers) .mx-dossiers-champ { display: none; }
/* Le dossier parent REMPLACE la vue courante, quelle qu'elle soit — c'est un
   autre dossier de l'explorateur, pas un panneau de plus. (`!important` : les
   règles `.on` des trois vues ont la même force et viennent plus bas dans la
   feuille.) */
body.bureau-frutiz .fen #mail-panel.mx-dossiers #mail-vue-liste,
body.bureau-frutiz .fen #mail-panel.mx-dossiers #mail-vue-lecture,
body.bureau-frutiz .fen #mail-panel.mx-dossiers #mail-vue-ecriture { display: none !important; }
/* Le champ est une BOÎTE à part sous le bandeau : le relevé donne deux pixels
   de blanc entre les deux contours (y 249-250). */
body.bureau-frutiz .fen #mail-panel #mail-liste {
  flex: 1; min-height: 0; margin: 6px 2px 2px; padding: 0;
}
body.bureau-frutiz .fen #mail-panel .mx-rang {
  display: flex; align-items: center; width: 100%; height: 22px;
  padding: 0; border: 0; border-bottom: 1px solid #EAEA0F; background: none;
  font: normal 10px Verdana, Arial, sans-serif; color: #5A5A00;
  text-align: left; cursor: pointer; box-sizing: border-box;
}
/* `but.icon.Detail.display` pose l'icône à `ico._x = 2` et décale le premier
   champ de 20 : l'enveloppe tient dans ces vingt pixels. */
body.bureau-frutiz .fen #mail-panel .mx-rang .mx-ico {
  flex: 0 0 20px; width: 20px; height: 18px; margin-left: 2px;
  background: url('/frutiz/sprites/nav_new_mail.svg') left center / 16px 16px no-repeat;
}
body.bureau-frutiz .fen #mail-panel .mx-rang .mx-cell {
  flex: 0 0 auto; padding: 0 4px 0 1px; overflow: hidden;
  text-overflow: ellipsis; white-space: nowrap;
  border-right: 2px solid #F1F13B; box-sizing: border-box;
}
/* Le premier champ partage ses 140 px avec l'icône (le `+20` de `Detail`). */
body.bureau-frutiz .fen #mail-panel .mx-rang .mx-cell:first-of-type {
  width: 118px !important;
}
body.bureau-frutiz .fen #mail-panel .mx-rang .mx-cell.big { flex: 1 1 auto; min-width: 0; }
body.bureau-frutiz .fen #mail-panel .mx-rang .mx-cell:last-child { border-right: 0; }
/* Un courrier non lu s'écrit en GRAS — c'est le seul écart que le fichier
   porte dans l'explorateur d'époque (`fileIcon` passe le titre en gras tant
   que `accessFile` n'a pas été appelé). */
body.bureau-frutiz .fen #mail-panel .mx-rang.neuf { font-weight: 700; color: #404000; }
body.bureau-frutiz .fen #mail-panel .mx-rang:hover { background: rgba(255,255,255,.45); }
body.bureau-frutiz .fen #mail-panel .mail-vide,
body.bureau-frutiz .fen #mail-panel .mail-charge {
  padding: 6px; font: normal 10px Verdana, Arial, sans-serif; color: #5A5A00;
  background: none; border: 0;
}
/* LE DOSSIER PARENT : les boîtes en icônes, comme tout dossier d'explorateur. */
body.bureau-frutiz .fen #mail-panel .mx-dossiers-champ {
  flex: 1; min-height: 0; padding: 4px;
  display: flex; flex-wrap: wrap; align-content: flex-start;
}
body.bureau-frutiz .fen #mail-panel .mx-slot {
  position: relative; width: 80px; height: 80px; flex: 0 0 80px;
  border: 0; background: transparent; padding: 3px 0 0; cursor: pointer;
  display: flex; flex-direction: column; align-items: center; gap: 2px;
  font: normal 10px Verdana, Arial, sans-serif; color: #5A5A00; text-align: center;
  user-select: none; -webkit-user-select: none;
}
body.bureau-frutiz .fen #mail-panel .mx-slot img { width: 44px; height: 44px; }
body.bureau-frutiz .fen #mail-panel .mx-slot span { line-height: 11px; }

/* ── LIRE UN COURRIER (`win.ViewMail`, 500 × 400) ─────────────────────────
   `attachInfo` : QUATRE lignes de 20 px, étiquette de 60 alignée à DROITE —
   Date, De, À, Sujet — puis le corps, puis la barre du bas :
   « Mettre à la corbeille », un grand espace, « Répondre », huit pixels,
   « Faire suivre ». (Le renvoi n'existe pas côté light ; le « Retour » qu'on
   ajoute n'existait pas d'époque — les trois fenêtres se fermaient.) */
body.bureau-frutiz .fen #mail-panel #mail-vue-lecture,
body.bureau-frutiz .fen #mail-panel #mail-vue-ecriture {
  flex: 1; min-height: 0; display: none; flex-direction: column; padding: 0;
}
body.bureau-frutiz .fen #mail-panel #mail-vue-lecture.on,
body.bureau-frutiz .fen #mail-panel #mail-vue-ecriture.on { display: flex; }
body.bureau-frutiz .fen #mail-panel .mx-info { flex: 0 0 auto; padding: 2px 4px 0; }
body.bureau-frutiz .fen #mail-panel .mx-ligne,
body.bureau-frutiz .fen #mail-panel .mx-de {
  display: flex; align-items: center; height: 20px; gap: 4px;
  font: normal 10px Verdana, Arial, sans-serif; color: #000000;
}
body.bureau-frutiz .fen #mail-panel .mx-lab {
  flex: 0 0 60px; width: 60px; text-align: right; color: #5A5A00;
}
body.bureau-frutiz .fen #mail-panel .mx-val {
  flex: 1 1 auto; min-width: 0; overflow: hidden;
  text-overflow: ellipsis; white-space: nowrap;
}
/* Le bandeau du mobile fait double emploi avec l'en-tête d'époque. */
body.bureau-frutiz .fen #mail-panel .mail-entete { display: none; }
body.bureau-frutiz .fen #mail-panel #mail-lu-corps {
  flex: 1; min-height: 0; margin: 2px 4px; padding: 4px;
  font: normal 12px Verdana, Arial, sans-serif; color: #5A5A00;
  white-space: pre-wrap; word-wrap: break-word;
}
/* LA BARRE DU BAS — `attachEndButton` lui donne `margin.x.min = 4`,
   `margin.y.min = 6` et `ratio 0,66` : quatre pixels sur les flancs, six en
   haut et en bas. */
body.bureau-frutiz .fen #mail-panel .mail-actions {
  flex: 0 0 auto; display: flex; align-items: center; gap: 8px;
  padding: 6px 4px; border: 0; background: none;
}
/* `attachEndButton` compose la barre dans cet ordre : « Mettre à la
   corbeille », un grand espace, puis « Répondre ». (Le « Retour » du light
   n'existait pas d'époque — la fenêtre se fermait ; il passe en tête.) */
body.bureau-frutiz .fen #mail-panel #mail-retour { order: 0; }
body.bureau-frutiz .fen #mail-panel #mail-supprimer { order: 1; }
body.bureau-frutiz .fen #mail-panel #mail-repondre { order: 2; margin-left: auto; }
body.bureau-frutiz .fen #mail-panel #mail-annuler { order: 0; }
body.bureau-frutiz .fen #mail-panel #mail-envoyer { order: 2; margin-left: auto; }
/* Le bouton d'époque : `butPushStandard`, la pastille verte du bureau. */
body.bureau-frutiz .fen #mail-panel .ma-btn {
  height: 20px; padding: 0 10px; border: 0; border-radius: 10px;
  background: #94DB39; box-shadow: 0 0 0 2px #66AA22;
  font: 700 10px Verdana, Arial, sans-serif; color: #FFFFFF;
  cursor: pointer; white-space: nowrap;
}
body.bureau-frutiz .fen #mail-panel .ma-btn:hover { background: #ADE76B; }
body.bureau-frutiz .fen #mail-panel .ma-btn:disabled { opacity: .6; cursor: default; }

/* ── ÉCRIRE UN COURRIER (`win.Mail`) ──────────────────────────────────────
   `attachInfo` : TROIS lignes de 20 px, étiquette de 60 — De (en clair, sur
   fond), À, Sujet ; puis le corps (`textFormat: { size: 12 }`) ; puis la
   barre du bas, avec la case « garder une copie » et le bouton d'envoi.

   NON PORTÉ, et il faut le dire : `attachEditTool` pose entre les deux une
   barre de 28 px — gras, italique, souligné (`butFlagSmallPink`, images 2 à
   4) et un menu de corps de texte de 100 px. Le courrier du light est du
   texte simple d'un bout à l'autre, de la saisie à l'API : une barre de
   style n'aurait rien à teindre. Même chose pour la case « garder une copie
   dans les messages envoyés » — le serveur en garde toujours une. */
body.bureau-frutiz .fen #mail-panel .mail-form {
  flex: 1; min-height: 0; display: flex; flex-direction: column;
  padding: 2px 4px 0; gap: 0;
}
body.bureau-frutiz .fen #mail-panel .mx-de .mx-val {
  background: #FFFFFF; border-radius: 3px; box-shadow: 0 0 0 2px #DDDDDD;
  padding: 0 4px; line-height: 16px; margin: 0 2px;
}
/* Les étiquettes du mobile deviennent celles d'époque, de 60 px, sur la même
   ligne que leur champ. */
body.bureau-frutiz .fen #mail-panel .mail-form label {
  flex: 0 0 60px; width: 60px; text-align: right; padding: 0 4px 0 0;
  font: normal 10px Verdana, Arial, sans-serif; color: #5A5A00;
  line-height: 20px;
}
body.bureau-frutiz .fen #mail-panel .mail-form label[for="mail-texte"] { display: none; }
body.bureau-frutiz .fen #mail-panel #mail-a,
body.bureau-frutiz .fen #mail-panel #mail-sujet {
  height: 16px; margin: 2px 2px 2px 0; padding: 0 4px; box-sizing: border-box;
  border: 0; border-radius: 3px; box-shadow: 0 0 0 2px #DDDDDD;
  background: #FFFFFF; font: normal 10px Verdana, Arial, sans-serif; color: #000000;
}
/* Chaque étiquette et son champ tiennent sur une ligne de 20 px : la grille
   du mobile devient une pile de lignes. */
body.bureau-frutiz .fen #mail-panel .mail-form {
  display: grid; grid-template-columns: 60px 1fr; align-items: center; row-gap: 0;
}
body.bureau-frutiz .fen #mail-panel .mail-form .mx-de {
  grid-column: 1 / -1; display: grid; grid-template-columns: 60px 1fr;
  align-items: center;
}
/* La grille centre ses cellules (les étiquettes s'assoient sur la ligne de
   leur champ) : le corps, lui, doit REMPLIR sa rangée. */
body.bureau-frutiz .fen #mail-panel #mail-texte {
  grid-column: 1 / -1; align-self: stretch; height: 100%; min-height: 0; resize: none;
  margin: 2px 0; padding: 4px; box-sizing: border-box;
  font: normal 12px Verdana, Arial, sans-serif; color: #5A5A00;
}
body.bureau-frutiz .fen #mail-panel .mail-form { grid-template-rows: 20px 20px 20px 1fr auto; }
body.bureau-frutiz .fen #mail-panel .mail-erreur {
  grid-column: 1 / -1; padding: 0 2px;
  font: normal 10px Verdana, Arial, sans-serif; color: #AA2222;
}
body.bureau-frutiz .fen #mail-panel .mail-erreur.ok { color: #5A8A22; }

/* ── L'EXPLORATEUR (`win.Explorer`, `box.Explorer`) ─────────────────────────
   « Mes disques » et « Inventaire » : la fenêtre JAUNE du bureau.

   Le jaune est la couleur du type de fenêtre — `winType = "winExplorer"` — et
   c'est le même `colorSet` qui donne la banane en pastille et la teinte du
   champ. Le relevé 1:1 (scratchpad/rb-2-disques.png et rb-4-inventaire.png,
   fenêtre en x 485..885 / y 146..547) donne la rampe au pixel :

     ligne y=193 :  486 #DDDDDD  488 #FFFFFF  490 #DDDDDD
                    491 #E4E476  492 #EAEA0F  493 #F1F13B  494 #F8F866
     colonne x=686 : 146 #444444  147 #DDDDDD  149 blanc (bandeau, 16 px)
                    165 #DDDDDD  167 #EAEA0F  169 → dégradé blanc sur 8 px
                    177 #F8F866

   soit, en repartant du bord : le contour de la fenêtre, ses 2 px de liseré
   `#DDDDDD`, 2 px de blanc, le contour de 2 px `#DDDDDD` du champ, son liseré
   de 2 px `#EAEA0F` — et le fond `#F8F866` sous le REFLET, le même dégradé
   blanc de 8 px que la zone des messages du salon.

   L'encre des étiquettes est `#5A5A00`, le « jaune très sombre » du jeu de
   couleurs — exactement ce que `#335511` est au vert des icônes du bureau. */
body.bureau-frutiz .fen:has(.ex-panel.active) .fen-corps { margin: 0 2px 2px; }
body.bureau-frutiz .fen .ex-panel {
  padding: 0; gap: 0; background: transparent; min-height: 0;
}
/* LA BARRE D'OUTILS — compo « navigatorFrame », `min: {w: 80, h: 28}`, une
   liste d'icônes de 24 px de côté avec 2 px d'écart (win.Explorer.
   displayNavigatorIconList). Elle n'existe QUE si elle a des boutons : sur la
   racine de l'inventaire, il n'y en a aucun et la rangée disparaît — le champ
   remonte alors sous le bandeau, comme sur le rendu d'époque. */
body.bureau-frutiz .fen .ex-panel .ex-nav {
  flex: 0 0 28px; height: 28px; box-sizing: border-box;
  padding: 4px 0 0 4px; display: flex; gap: 4px; align-items: flex-start;
}
body.bureau-frutiz .fen .ex-panel .ex-nav[hidden] { display: none; }
/* Le bouton : `butPushNavigator` posé dans une plaque de 20 px arrondie à
   `curve: 4`, avec `outline: 2` — les 2 px de `#DDDDDD` peints AUTOUR de la
   boîte, d'où l'ombre portée plutôt qu'une bordure. */
body.bureau-frutiz .fen .ex-panel .ex-nav-but {
  width: 20px; height: 20px; flex: 0 0 20px; padding: 0; border: 0;
  border-radius: 4px; box-shadow: 0 0 0 2px #DDDDDD;
  background: transparent center / 20px 20px no-repeat;
  cursor: pointer; color: transparent; font-size: 0;
}
/* Un bouton sans action garde sa couleur : le bureau d'époque le dessine
   plein, et c'est l'infobulle qui dit pourquoi il ne fait rien. */
body.bureau-frutiz .fen .ex-panel .ex-nav-but:disabled { cursor: default; }
/* LE BANDEAU D'AVERTISSEMENT — `window.displayAlert`, un `cpDocument` posé
   entre la barre d'outils et le champ. Relevé : contour de 2 px `#DDDDDD`,
   fond blanc, et 2 px de blanc entre lui et le champ. */
body.bureau-frutiz .fen .ex-panel .ex-alerte {
  /* 30 px d'intérieur pour deux lignes, au relevé (y 195..224) : 13 px
     d'interligne et 2 px de marge haut et bas. */
  flex: 0 0 auto; margin: 0 2px 2px; padding: 2px 5px;
  border: 2px solid #DDDDDD; background: #FFFFFF; border-radius: 3px;
  /* Relevé : deux lignes d'encre en y 198..208 et 211..220 — 13 px
     d'interligne, 11 px de corps (la ligne d'époque tient 373 px pour
     soixante-seize signes), et une encre `#222222` dont l'anticrénelage
     descend par paliers réguliers (#5A5A5A, #919191, #C8C8C8). */
  font: normal 11px Verdana, Arial, sans-serif; line-height: 13px; color: #222222;
}
body.bureau-frutiz .fen .ex-panel .ex-alerte[hidden] { display: none; }
/* LE CHAMP — compo « fileIconListFrame », peint par `drawCustomSquare` comme
   la zone des messages du salon : contour 2 px `#DDDDDD`, liseré 2 px
   `#EAEA0F`, fond `#F8F866`, et le drapeau `chrome` — le reflet blanc de 8 px
   qui part à 0,6 et s'éteint. */
/* Le CONTOUR de 2 px est peint HORS de la boîte (une ombre portée, comme
   partout dans le bureau) : il lui faut donc 2 px de marge sur les quatre
   côtés, sinon `overflow: hidden` du corps le rogne — c'est ce qui manquait au
   ras du bandeau, où le relevé le veut collé (y 165-166 pour un bandeau qui
   finit en 164). */
body.bureau-frutiz .fen .ex-panel .ex-champ {
  flex: 1; min-height: 0; margin: 2px;
  padding: 4px; box-sizing: border-box; overflow: auto;
  display: flex; flex-wrap: wrap; align-content: flex-start;
  background:
    /* le reflet se compte depuis l'INTÉRIEUR du liseré : le fond d'une boîte
       part de son contour, d'où les 2 px d'avance donnés au dégradé */
    linear-gradient(to bottom, rgba(255,255,255,.6) 2px, rgba(255,255,255,0) 10px),
    #F8F866;
  border: 2px solid #EAEA0F; border-radius: 5px;
  box-shadow: 0 0 0 2px #DDDDDD;
}
/* La CASE d'une icône : 80 px de côté au relevé (les jaquettes se suivent de
   80 en 80, en largeur comme en hauteur). Dedans, `but.icon.Standard` pose
   l'icône en haut — `bx: 3, by: 4` de marge — et l'étiquette à `y = r4`,
   centrée sur toute la largeur utile. */
body.bureau-frutiz .fen .ex-panel .ex-slot {
  position: relative; width: 80px; height: 80px; flex: 0 0 80px;
  border: 0; background: transparent; padding: 0; cursor: pointer;
  user-select: none; -webkit-user-select: none;
}
/* Un disque s'ATTRAPE : le curseur le dit, et le glisser natif du navigateur
   (on tire une image) ne doit pas couper le nôtre. */
body.bureau-frutiz .fen .ex-panel .ex-slot-disque:not(.inerte) { cursor: grab; }
body.bureau-frutiz .fen .ex-panel .ex-slot img,
body.bureau-frutiz .fen .ex-panel .ex-slot .ex-disque { -webkit-user-drag: none; }
/* Le bureau d'époque ne PÂLIT rien : une icône sans action reste dessinée
   comme les autres, elle ne répond simplement pas au clic. */
body.bureau-frutiz .fen .ex-panel .ex-slot.inerte { cursor: default; }
body.bureau-frutiz .fen .ex-panel .ex-slot:focus-visible { outline: 1px dotted #5A5A00; }
body.bureau-frutiz .fen .ex-panel .ex-img,
body.bureau-frutiz .fen .ex-panel .ex-fond,
body.bureau-frutiz .fen .ex-panel .ex-bouille,
body.bureau-frutiz .fen .ex-panel .ex-disque {
  position: absolute; left: 50%; transform: translateX(-50%);
  display: block; pointer-events: none;
}
/* L'étiquette : `titleField.pos = {x: 0, y: r4, w: width, h: height × 0.5}`,
   alignée au centre, sur plusieurs lignes. 10 px de Verdana au relevé
   (« Pictos » tient en 28 px), encre `#5A5A00`. */
body.bureau-frutiz .fen .ex-panel .ex-lbl {
  position: absolute; left: 3px; top: 41px; width: 74px; height: 36px;
  text-align: center; overflow: hidden;
  font: normal 10px Verdana, Arial, sans-serif; line-height: 12px; color: #5A5A00;
}
/* LE DISQUE — `but.icon.Full` : pas d'étiquette, l'anneau du type de FD et sa
   jaquette par-dessus, 63 px de côté au relevé, à 7 px du haut de la case. */
body.bureau-frutiz .fen .ex-panel .ex-disque {
  top: 7px; width: 63px; height: 63px;
}
body.bureau-frutiz .fen .ex-panel .ex-disque img {
  position: absolute; inset: 0; width: 63px; height: 63px;
}
body.bureau-frutiz .fen .ex-panel .ex-disque img.jaquette {
  width: 61px; height: 61px; left: 1px; top: 1px;
}
body.bureau-frutiz .fen .ex-panel .ex-slot-disque:not(.inerte):active .ex-disque {
  transform: translateX(-50%) scale(.94);
}
/* L'ACCESSOIRE — `but.Icon.display` remplace l'icône par un `frutibouille` et
   met `icoRatio` à 1 : l'aperçu fait donc r4 (37 px) de côté. */
body.bureau-frutiz .fen .ex-panel .ex-bouille {
  top: 4px; width: 37px; height: 37px;
}
body.bureau-frutiz .fen .ex-panel .ex-bouille iframe,
body.bureau-frutiz .fen .ex-panel .ex-bouille canvas {
  width: 100%; height: 100%; border: 0; display: block; pointer-events: none;
}
/* LE FOND D'ÉCRAN : le cadre du SWF, et dedans la vignette du fond. */
body.bureau-frutiz .fen .ex-panel .ex-fond .vign {
  position: absolute; left: 14.5%; top: 13%; width: 71%; height: 62%;
  background: center / cover no-repeat;
}
body.bureau-frutiz .fen .ex-panel .ex-fond .ex-img {
  position: absolute; left: 0; top: 0; transform: none;
}
body.bureau-frutiz .fen .ex-panel .ex-vide {
  width: 100%; padding: 4px 2px;
  font: normal 10px Verdana, Arial, sans-serif; color: #5A5A00;
}
body.bureau-frutiz .fen .ex-panel .ex-champ.attente { cursor: progress; }
