Tutoriel 2026-04-19

Créer un addon de vêtements custom pour FiveM

OntelMonke

OntelMonke

Administrateur et développeur chez Agency Scripts

Comprendre le système vestimentaire du GTA V

GTA V utilise un système de vêtements basé sur des composants dans lequel chaque vêtement peut être « dessiné » dans un emplacement de composant spécifique. Il y a 12 emplacements pour composants sur un pédalier, allant de la tête (composant 0) aux chaussures (composant 6) en passant par les sacs et accessoires. Chaque emplacement de composant peut contenir plusieurs dessinables, et chaque dessinable peut avoir plusieurs variations de texture. Par exemple, le composant 11 (hauts) peut avoir un dessin 15 (une veste en cuir) avec des textures 0 à 3 représentant des variantes de couleurs noir, marron, rouge et blanc. Comprendre cette hiérarchie de composants, de dessins et de textures est essentiel avant de pouvoir créer des vêtements personnalisés, car chaque pièce que tu ajoutes doit s'insérer dans cette structure existante. Le modèle pédagogique multijoueur (MP) ajoute une autre couche avec son propre mappage dessinable qui diffère des personnages solo, et les serveurs FiveM utilisent exclusivement les modèles MP en mode libre.

Structure et diffusion des ressources

Les vêtements personnalisés dans FiveM fonctionnent via le système de streaming. Tu créez une ressource qui indique au jeu de charger des fichiers dessinables et de texture supplémentaires aux côtés des ressources du jeu de base. La structure des ressources suit des conventions de dénomination strictes que le moteur de jeu utilise pour identifier le modèle ped, le composant et l'index dessinable auquel appartient chaque fichier. Une mauvaise structure des dossiers est la cause la plus courante pour laquelle les vêtements n'apparaissent pas dans le jeu. Ton ressource a besoin d'un fxmanifest.lua qui déclare les fichiers de streaming, et les données réelles sur les vêtements vont dans un stream répertoire avec la hiérarchie de sous-dossiers correcte.

-- fxmanifest.lua for a clothing addon
fx_version 'cerulean'
game 'gta5'

-- The resource name matters: it determines load priority
-- Prefix with zzz_ to ensure it loads after base game assets
this_is_a_map 'yes'
lua54 'yes'

-- All streaming assets inside /stream/ are auto-detected
-- No need to list individual files

Le dossier stream suit une hiérarchie précise. Pour les vêtements masculins MP freemode, les fichiers vont dans stream/mp_m_freemode_01_mp_m_[dlcname]/. Pour les femmes, remplacer mp_m avec mp_f. Dans ce dossier, tu places les fichiers YDD (dictionnaire dessinable), YTD (dictionnaire de textures) et YMT (métadonnées). La convention de dénomination code le composant et l'index dessinable que chaque fichier représente. Un fichier nommé mp_m_freemode_01_mp_m_mypack_jbib_000_u.ydd est dessinable 0 pour le composant 11 (jbib = jacket/tops) sur le ped mâle freemode du pack DLC "mypack".

-- Folder structure example
stream/
  mp_m_freemode_01_mp_m_mypack/
    mp_m_freemode_01_mp_m_mypack.ymt          -- metadata file
    mp_m_freemode_01_mp_m_mypack_jbib_000_u.ydd   -- tops drawable 0
    mp_m_freemode_01_mp_m_mypack_jbib_diff_000_a_uni.ytd  -- texture for tops 0
    mp_m_freemode_01_mp_m_mypack_jbib_001_u.ydd   -- tops drawable 1
    mp_m_freemode_01_mp_m_mypack_jbib_diff_001_a_uni.ytd  -- texture for tops 1
    mp_m_freemode_01_mp_m_mypack_lowr_000_u.ydd   -- pants drawable 0
    mp_m_freemode_01_mp_m_mypack_lowr_diff_000_a_uni.ytd  -- texture for pants 0

ID de composants et conventions de dénomination

Chaque composant vestimentaire possède une abréviation spécifique utilisée dans le nom du fichier. Les mémoriser est essentiel car une seule faute de frappe signifie que le jeu ne peut pas trouver ton élément. La carte des composants est : tête (composant 0, pas de vêtements), berde (1, masques), cheveux (2), supérieur (3, bras/gants), plus bas (4, pantalon/jambes), main (5, sacs/parachutes), pieds (6, chaussures), teef (7, accessoires comme des chaînes), accès (8, maillots de corps/accessoires corporels), tâche (9, gilet pare-balles), décl (10, autocollants/badges), et jbib (11, hauts/vestes). Les accessoires utilisent un système différent : p_head (chapeaux), p_yeux (lunettes), p_ears (boucles d'oreilles), et p_lpoignet/p_rpoignet (montres/bracelets).

-- Component ID reference for scripting
local ComponentNames = {
    [0]  = 'head',   -- Face (not clothing)
    [1]  = 'berd',   -- Masks
    [2]  = 'hair',   -- Hair styles
    [3]  = 'uppr',   -- Arms / Gloves
    [4]  = 'lowr',   -- Pants / Legs
    [5]  = 'hand',   -- Bags / Parachutes
    [6]  = 'feet',   -- Shoes
    [7]  = 'teef',   -- Accessories (chains, ties)
    [8]  = 'accs',   -- Undershirts
    [9]  = 'task',   -- Body Armor
    [10] = 'decl',   -- Decals / Badges
    [11] = 'jbib',   -- Tops / Jackets
}

-- Get total drawables for a component (useful for clothing menus)
local function GetMaxDrawables(ped, componentId)
    return GetNumberOfPedDrawableVariations(ped, componentId)
end

-- Get texture count for a specific drawable
local function GetMaxTextures(ped, componentId, drawableId)
    return GetNumberOfPedTextureVariations(ped, componentId, drawableId)
end

-- Apply clothing to ped
local function SetClothing(ped, componentId, drawableId, textureId)
    SetPedComponentVariation(ped, componentId, drawableId, textureId, 0)
end

Comprendre les fichiers YMT

Le fichier YMT (Ped Metadata) est la colle qui maintient ensemble un paquet de vêtements. Il s'agit d'un fichier XML qui indique au moteur de jeu combien de dessinables existent dans chaque composant, combien de textures chaque dessinable possède, quel audio jouer lorsque les vêtements bougent et diverses propriétés de rendu. Sans un YMT correctement configuré, le jeu ne reconnaîtra pas tes dessinables même si les fichiers YDD et YTD sont parfaitement conçus. Le YMT doit répertorier chaque combinaison de dessin et de texture dans ton pack. Une seule entrée manquante signifie que l'élément sera invisible. La modification manuelle des fichiers YMT est sujette aux erreurs, c'est pourquoi la plupart des créateurs utilisent des outils tels que CodeWalker ou des générateurs YMT dédiés qui créent automatiquement le fichier à partir du contenu de ton dossier d'actifs.

<!-- Simplified YMT structure (XML representation) -->
<CPedVariationInfo>
  <availComp>
    <!-- Bitfield indicating which components have data -->
    <Item value="2048" />  <!-- Only jbib (component 11) -->
  </availComp>
  <compInfos>
    <Item> <!-- Component 11 (jbib / tops) -->
      <drawblDict>
        <Item>  <!-- Drawable 0 -->
          <numAlternatives value="0" />
          <numTexVariations value="3" />  <!-- 3 color variants -->
          <clothData>
            <ownsCloth value="false" />
          </clothData>
        </Item>
        <Item>  <!-- Drawable 1 -->
          <numAlternatives value="0" />
          <numTexVariations value="2" />  <!-- 2 color variants -->
          <clothData>
            <ownsCloth value="false" />
          </clothData>
        </Item>
      </drawblDict>
    </Item>
  </compInfos>
</CPedVariationInfo>

Variations et qualité des textures

Chaque dessin peut avoir plusieurs variations de texture, qui représentent différentes couleurs ou motifs du même modèle de vêtement. Le fichier de texture de base utilise le modèle de dénomination [pack]_[component]_diff_[drawableIndex]_[textureIndex]_uni.ytd. Les textures doivent être créées par puissance de deux (512x512, 1024x1024, 2048x2048) pour une compatibilité GPU optimale. Les textures à haute résolution sont plus belles mais consomment plus de VRAM, ce qui est une ressource limitée, en particulier sur les serveurs où les joueurs chargent simultanément des dizaines de packs de vêtements personnalisés. Une règle pratique consiste à utiliser 1024 x 1024 pour la plupart des vêtements et à réserver 2048 x 2048 pour les articles comportant des détails fins comme des logos brodés ou des motifs complexes. Chaque fichier YTD peut contenir plusieurs couches de texture, notamment des cartes diffuses (couleur), normales (détails de surface) et spéculaires (brillance), bien que la plupart des packs de vêtements FiveM n'utilisent que la couche diffuse pour que la taille des fichiers reste gérable.

Créer un script de menu de vêtements

Une fois que ton ressource de streaming fonctionne, tu as besoin d'un moyen pour que les joueurs puissent parcourir et appliquer les vêtements. Un script de menu de vêtements parcourt tous les dessins disponibles par composant et permet aux joueurs de les prévisualiser sur leur personnage en temps réel. La logique de base utilise GetNumberOfPedDrawableVariations pour déterminer combien de drawables existent pour chaque composant, puis SetPedComponentVariation pour appliquer celui sélectionné. Enveloppez-le dans un menu ox_lib ou NUI pour une expérience utilisateur raffinée. La partie délicate consiste à gérer les aperçus à la première personne et les angles de caméra afin que les joueurs puissent voir ce qu'ils essaient sans problèmes de détourage ou de zoom gênants.

-- client/clothing_menu.lua
local function OpenClothingMenu()
    local ped = PlayerPedId()
    local components = {}

    for compId = 0, 11 do
        local maxDrawables = GetNumberOfPedDrawableVariations(ped, compId)
        if maxDrawables > 0 then
            local currentDrawable = GetPedDrawableVariation(ped, compId)
            local currentTexture = GetPedTextureVariation(ped, compId)
            local maxTextures = GetNumberOfPedTextureVariations(ped, compId, currentDrawable)

            table.insert(components, {
                id = compId,
                label = ComponentNames[compId] or ('Component ' .. compId),
                drawable = currentDrawable,
                texture = currentTexture,
                maxDrawable = maxDrawables - 1,
                maxTexture = maxTextures - 1,
            })
        end
    end

    -- Build menu options
    local options = {}
    for _, comp in ipairs(components) do
        options[#options + 1] = {
            title = comp.label,
            description = ('Drawable: %d/%d | Texture: %d/%d'):format(
                comp.drawable, comp.maxDrawable, comp.texture, comp.maxTexture),
            onSelect = function()
                OpenComponentEditor(comp.id)
            end
        }
    end

    lib.registerContext({ id = 'clothing_menu', title = 'Wardrobe', options = options })
    lib.showContext('clothing_menu')
end

local function OpenComponentEditor(componentId)
    local ped = PlayerPedId()
    local maxDraw = GetNumberOfPedDrawableVariations(ped, componentId) - 1

    -- Interactive drawable browser with live preview
    local input = lib.inputDialog('Select Clothing', {
        { type = 'slider', label = 'Style', min = 0, max = maxDraw, default = GetPedDrawableVariation(ped, componentId) },
    })

    if input then
        local drawableId = input[1]
        local maxTex = GetNumberOfPedTextureVariations(ped, componentId, drawableId) - 1
        SetPedComponentVariation(ped, componentId, drawableId, 0, 0)

        if maxTex > 0 then
            local texInput = lib.inputDialog('Select Color', {
                { type = 'slider', label = 'Variant', min = 0, max = maxTex, default = 0 },
            })
            if texInput then
                SetPedComponentVariation(ped, componentId, drawableId, texInput[1], 0)
            end
        end
    end
end

Problèmes courants et dépannage

Le problème le plus fréquent est que les vêtements apparaissent comme invisibles ou comme étant des articles inappropriés. Cela remonte presque toujours à un fichier YMT incorrect qui ne déclare pas correctement le nombre de dessins ou le nombre de textures. Vérifiez que ton YMT répertorie le nombre exact de dessins et de textures qui existent dans ton dossier de flux. Un autre problème courant est l'ordre de chargement des ressources : si ton pack de vêtements se charge avant les ressources du jeu de base, les indices pouvant être dessinés peuvent entrer en collision et écraser les vêtements vanille. Préfixez le nom de ton ressource avec zzz_ pour garantir qu'il se charge en dernier. Le flou de la texture indique généralement que le YTD utilise une résolution trop faible ou que les mipmaps ne sont pas générés correctement. Générez toujours des mipmaps lors de l'exportation de tes fichiers YTD dans CodeWalker. Enfin, si les vêtements apparaissent sur les modèles masculins mais pas sur les femmes ou vice versa, vérifiez que tu disposes de dossiers séparés pour mp_m_freemode_01 et mp_f_freemode_01 avec des fichiers de maillage correctement sexués, car les modèles pédestres masculins et féminins ont des squelettes différents et nécessitent une géométrie distincte.

Optimisation des performances du serveur

Les packs de vêtements personnalisés sont l’un des principaux contributeurs à la taille de téléchargement du serveur et à l’utilisation de la VRAM client. Un seul pack mal optimisé contenant 100 éléments haute résolution peut ajouter des gigaoctets aux besoins de téléchargement de ton serveur. Pour que les choses restent gérables, compressez tes textures YTD au format DXT5 ou BC7, qui offre une bonne qualité visuelle pour une fraction de la taille du fichier brut. Limitez chaque pack à un nombre raisonnable d'éléments, généralement de 20 à 50 pièces, et répartissez les collections plus importantes sur plusieurs ressources pouvant être chargées indépendamment. Pensez à proposer une version « allégée » de packs populaires avec des textures 512x512 pour les joueurs utilisant du matériel bas de gamme. Côté scripts, évitez d'appeler à plusieurs reprises SetPedComponentVariation en boucle car chaque appel déclenche une mise à jour du modèle. Regroupez les changements de vêtements en collectant toutes les mises à jour des composants et en les appliquant en séquence dans une seule image afin de minimiser les éclats visuels et la surcharge de rendu.

Partager cet article

Prêt à améliorer votre serveur ?

Découvrez nos scripts FiveM premium dans la boutique Agency Scripts ou rejoignez notre communauté Discord pour le support et les mises à jour.