Offre Durée limitée : -10% sur tout le site* avec le code WELCOME10

Installer xSound sur un serveur FiveM : audio 3D et sons personnalisés

Mis à jour le 5 novembre 2026 20 min de lecture 11 sections

Un serveur FiveM sans ambiance sonore se reconnaît tout de suite : la boîte de nuit est muette, la radio du véhicule ne diffuse rien, l'alarme de la banque ne retentit que dans l'imagination des joueurs. xSound est la bibliothèque audio open source que la plupart des scripts FiveM utilisent aujourd'hui pour jouer des fichiers sons personnalisés et de la musique, avec un vrai audio 3D positionnel qui s'atténue avec la distance. Ce tutoriel s'adresse à la personne qui administre le serveur, chez un hébergeur ou sur un VPS qu'elle gère elle-même : installation de la dernière version stable de la ressource xsound côté serveur, y compris manuellement sous Linux et sous Windows, configuration de l'audio 3D, ajout de vos propres fichiers audio dans html/sounds, remplacement d'interact-sound sans casser les scripts existants, et exemples d'appels côté client et côté serveur pour ESX comme pour QBCore. Si votre serveur n'est pas encore en ligne, commencez par notre guide de mise en place d'un serveur FiveM.

xSound, la bibliothèque audio de référence sur FiveM

xSound est une ressource FiveM publiée sous licence MIT par Xogy, annoncée sur le forum Cfx.re en 2020 sous le titre xSound, audio library for FiveM et maintenue sur GitHub. Ce n'est pas un script « prêt à jouer » avec une boombox ou un jukebox intégré : c'est une API audio que les autres ressources appellent par exports. Concrètement, xSound ouvre une page NUI invisible (une page web embarquée dans le client FiveM, rendue par le Chromium Embedded Framework, le moteur open source de Google Chrome) et y pilote la bibliothèque JavaScript Howler pour lire des fichiers audio, ou le lecteur YouTube intégré pour les liens YouTube. Chaque son est identifié par un nom, et une série de fonctions permet de le positionner dans le monde, de régler son volume, sa distance d'audition, de le mettre en pause ou de le détruire.

Pourquoi passer par xSound plutôt que par les fonctions audio natives de GTA V ? Les natives ne jouent que les banques sonores du jeu. Pour diffuser votre propre jingle, la musique d'un bar ou une sirène personnalisée, il faut une ressource qui lit des fichiers .ogg ou .mp3 livrés avec le serveur, ou une URL. Avant xSound, le standard était interact-sound, qui joue un fichier à volume fixe sans notion de position. xSound reprend son API en option et ajoute l'audio 3D, les événements de lecture et les liens YouTube.

Solution audioSons personnalisésAudio 3D positionnelLecture d'URL ou YouTubeMaintenance
Natives GTA (PlaySoundFrontend et consorts) Non, banques sonores du jeu uniquement Oui pour les sons du jeu Non Intégrées au client
interact-sound Oui, fichiers .ogg dans client/html/sounds Non, volume fixe avec filtre de distance Non Dernier commit en septembre 2022
xSound Oui, fichiers .ogg et .mp3 dans html/sounds Oui, atténuation linéaire avec la distance Oui, URL directe ou lien YouTube Version stable 1.5.1 (10 novembre 2025), branche expérimentale 1.1 (28 mai 2026)

Deux lignées cohabitent sur GitHub. La branche master porte la version stable 1.5.1, celle que nous installons ici. La branche experimental (1.0-experimental en décembre 2025, 1.1-experimental en mai 2026) déplace tout le lecteur dans un DUI, une page web isolée, pour que les plantages liés au lecteur YouTube n'emportent pas la page NUI principale. Elle vaut le test si vous diffusez beaucoup de YouTube, mais gardez la stable en production tant que vos scripts n'ont pas été vérifiés dessus.

Prérequis côté serveur

  • Un serveur FiveM (FXServer), sous Windows ou sous Linux, sur lequel vous avez accès aux fichiers (panel de l'hébergeur, client SFTP ou FTP, ou ligne de commande sur un VPS) et à la console txAdmin. Sur nos offres serveur FiveM, txAdmin est préinstallé et le répertoire resources est accessible depuis le panel.
  • Un framework déjà en place si vous voulez l'intégration d'objets utilisables : ESX Legacy ou QBCore. xSound fonctionne aussi sans framework.
  • Des fichiers audio au format .ogg (recommandé, léger) ou .mp3. Chaque fichier est téléchargé par tous les clients au démarrage de la ressource : gardez-les courts et compressés.
  • Côté joueurs, un accès Internet normal : la page NUI de xSound charge Howler et DOMPurify depuis cdnjs.cloudflare.com, jQuery depuis ajax.googleapis.com et l'API YouTube depuis youtube.com. Un client qui bloque ces domaines n'entendra rien.

Installer la ressource xsound

Téléchargez l'archive de la dernière version stable, la 1.5.1, depuis la page des releases GitHub et décompressez-la dans le répertoire resources de votre serveur FiveM : depuis le gestionnaire de fichiers du panel, ou sous Windows par un clic droit sur l'archive puis « Extraire tout ». Le dossier doit s'appeler exactement xsound : tous les scripts l'appellent par exports.xsound, et un nom différent casserait chaque appel. Vérifiez qu'il contient bien fxmanifest.lua, config.lua, les dossiers client, server, html et addon à la racine, et pas un sous-dossier xsound-1.5.1 intermédiaire.

resources/
└── [local]/
    └── xsound/
        ├── fxmanifest.lua
        ├── config.lua
        ├── client/
        ├── server/
        ├── addon/
        └── html/
            ├── index.html
            ├── scripts/
            └── sounds/        (vos fichiers .ogg et .mp3)

Ajoutez ensuite la ligne de démarrage dans server.cfg, avant les scripts qui dépendent de xSound. La commande ensure démarre la ressource si elle est arrêtée et la redémarre sinon, ce qui en fait la forme la plus sûre dans un fichier de configuration :

ensure xsound

Sans redémarrer le serveur, vous pouvez charger la nouvelle ressource depuis la console txAdmin : refresh rescanne le dossier resources et lit les manifestes, puis ensure xsound la démarre. Pour tester sans attendre un script complet, créez une mini-ressource xsound-test avec un manifeste et un script client :

-- resources/[local]/xsound-test/fxmanifest.lua
fx_version 'cerulean'
game 'gta5'
dependency 'xsound'
client_script 'client.lua'
-- resources/[local]/xsound-test/client.lua
RegisterCommand('testson', function()
    -- joue html/sounds/bip.ogg de la ressource xsound, volume 50 %, audible partout
    exports.xsound:PlayUrl('test_bip', './sounds/bip.ogg', 0.5)
end, false)

Après ensure xsound-test, la commande /testson dans le chat doit jouer le fichier. Si rien ne sort, la section dépannage en fin de guide liste les causes habituelles. Le manifeste de xSound déclare fx_version 'cerulean' et cible gta5 ainsi que rdr3, avec l'avertissement d'usage sur RedM : la ressource se charge donc aussi sur un serveur RedM, en version préliminaire.

Installation manuelle sur un VPS Linux ou sous Windows

Chez un hébergeur de serveurs de jeu, le panel dépose l'archive et redémarre la ressource en deux clics. Sur un FXServer que vous administrez vous-même, sur un VPS Linux sous Ubuntu ou Debian ou sur une machine Windows, les mêmes étapes se font à la main. La documentation Cfx.re sépare deux dossiers : les binaires du serveur (l'archive fx.tar.xz sous Linux, server.7z sous Windows, téléchargée depuis la page des artefacts) et le dossier de données server-data, qui contient server.cfg et le répertoire resources. C'est dans ce second répertoire que va xsound. Sous Linux, travaillez depuis un compte utilisateur avec sudo plutôt qu'en root : le serveur n'a aucune raison de tourner avec des privilèges root, et les fichiers déposés appartiendront ainsi au compte qui lance FXServer :

# Ubuntu / Debian : décompresser l'archive et la renommer, depuis le répertoire resources
sudo apt install -y unzip
cd ~/FXServer/server-data/resources
unzip ~/xsound-1.5.1.zip
mv xsound-1.5.1 xsound
ls xsound/html/sounds    # le répertoire doit exister, même vide

Pour transférer vos fichiers audio depuis votre poste, un client SFTP comme FileZilla ou WinSCP, ou la commande scp, suffit : connectez-vous à l'adresse IP du VPS avec votre clé SSH (voir notre guide pour configurer une clé SSH sans perdre l'accès) et glissez les fichiers dans resources/xsound/html/sounds. Évitez le FTP en clair, qui transmet le mot de passe sans chiffrement. Sous Windows, le dépôt se fait dans l'Explorateur : clic droit sur l'archive, « Extraire tout », puis copie du dossier dans C:\FXServer\server-data\resources.

Le lancement du serveur change selon le système : bash ~/FXServer/server/run.sh +exec server.cfg depuis le dossier server-data sous Linux, FXServer.exe +exec server.cfg sous Windows. Lancé sans l'argument +exec, FXServer démarre txAdmin, qui crée un dossier txData et sert son panel web sur le port 40120 par défaut ; c'est depuis cette console que vous taperez ensuite refresh puis ensure xsound. Un manifeste illisible ou un fichier déclaré dans files mais absent du disque se signale dans le log de cette console dès le démarrage de la ressource : relisez-le avant de chercher ailleurs. Les joueurs rejoignent ensuite le serveur par son adresse IP et le port 30120, ou par un nom de domaine avec un enregistrement SRV. Pour que FXServer reparte seul au boot de la machine, créez un service systemd ; nos guides choisir la version des artefacts et FiveM sous Docker sur un VPS Linux couvrent le reste de l'installation du serveur lui-même.

Configurer l'audio 3D positionnel

L'audio 3D de xSound repose sur un mécanisme simple. Chaque son dynamique a une position vector3 dans le monde et une distance maximale d'audition, 10 unités par défaut. Le script client envoie la position du joueur à la page NUI toutes les 300 ms dès qu'il a bougé d'au moins 0,1 unité, et la page recalcule le volume de chaque son : atténuation linéaire, soit le volume maximal multiplié par (1 moins la distance divisée par la distance maximale), et silence au-delà. Il n'y a pas de rendu binaural ni de 7.1 : l'auteur précise dans le sujet du forum que JavaScript et HTML ne le permettent pas dans ce contexte, et que la spatialisation est simulée par le volume.

Les réglages globaux vivent dans config.lua à la racine de la ressource :

OptionValeur par défautRôle
config.RefreshTime300Intervalle en millisecondes entre deux envois de la position du joueur à la page NUI. Plus bas, plus fluide, plus coûteux.
config.distanceBeforeUpdatingPos40Marge ajoutée à la distance d'un son pour décider s'il est « proche ». Au-delà de distance + 40, le son est détruit silencieusement côté NUI et recréé depuis le cache quand le joueur revient.
config.interact_sound_enablefalseActive l'émulateur interact-sound (section suivante).
config.interact_sound_file"ogg"Extension ajoutée aux noms de fichiers reçus par l'émulateur.
config.Messagestextes anglaisMessages du mode streamer et de refus de permission, à traduire pour un serveur français.
config.AddonListcrewPhone = falseActive les addons optionnels du dossier addon.

Pour placer un son dans le monde, utilisez PlayUrlPos au lieu de PlayUrl, puis ajustez la portée avec Distance. Les sons 3D se règlent avec setVolumeMax (le plafond atteint quand le joueur est sur la source), les sons globaux avec setVolume :

-- client.lua : radio d'ambiance en boucle devant un bâtiment, audible à 25 unités
local pos = vector3(215.76, -810.12, 30.73) -- remplacez par les coordonnées de votre lieu
exports.xsound:PlayUrlPos('radio_bar', './sounds/jazz.ogg', 0.8, pos, true)
exports.xsound:Distance('radio_bar', 25)

-- déplacer la source (par exemple pour suivre un véhicule)
exports.xsound:Position('radio_bar', GetEntityCoords(GetVehiclePedIsIn(PlayerPedId(), false)))

-- baisser le plafond de volume d'un son 3D, puis l'arrêter
exports.xsound:setVolumeMax('radio_bar', 0.4)
exports.xsound:Destroy('radio_bar')

Deux détails qui évitent des tickets. D'abord, un son lancé avec loop à true n'est pas détruit en fin de lecture (destroyOnFinish passe à false), alors qu'un son ponctuel l'est automatiquement : pensez à appeler Destroy quand une boucle n'a plus lieu d'être, sinon elle reste en mémoire chez chaque client. Ensuite, le mode streamer : la commande /streamermode, intégrée à xSound, coupe et détruit tous les sons chez le joueur qui la tape, pour qu'un streameur n'ait pas de musique protégée dans sa diffusion. Un joueur qui « n'entend plus rien » l'a parfois activée sans le savoir.

Ajouter des fichiers sons personnalisés dans html/sounds

Le dossier html/sounds est vide à l'installation (il ne contient qu'un fichier .gitkeep, ajouté en version 1.4.3 pour éviter un avertissement en console). C'est là que vont vos fichiers audio personnalisés. Le manifeste de xSound déclare déjà dans sa section files tous les fichiers de ce répertoire portant les extensions .ogg et .mp3 : ils sont ajoutés au packfile de la ressource et téléchargés par chaque client à la connexion, sans rien modifier dans fxmanifest.lua. Placez-les directement dans html/sounds ; si vous créez des sous-répertoires, ajoutez le motif correspondant dans la section files.

Le format et la compression comptent autant que l'emplacement. L'Ogg Vorbis est le format à privilégier : compression efficace, lecture native dans le Chromium embarqué de la NUI, et c'est l'extension attendue par défaut par l'émulateur interact-sound. Un MP3 fonctionne aussi, mais un WAV non compressé de trente secondes pèse plusieurs Mo pour rien. Pour convertir vos fichiers manuellement sur votre poste, sous Windows, macOS ou Linux, ffmpeg suffit (sudo apt install ffmpeg sous Ubuntu et Debian). Son encodeur libvorbis accepte une qualité de -1 à 10, 3 par défaut, et un son d'ambiance positionnel n'a pas besoin de stéréo puisque xSound simule la position par le volume, sans balance gauche-droite :

ffmpeg -i alarme_banque.wav -c:a libvorbis -q:a 4 -ac 1 alarme_banque.ogg

Dans vos scripts, un fichier local se référence par un chemin relatif à la page NUI de xSound, c'est-à-dire ./sounds/nom-du-fichier.ogg, extension comprise. C'est exactement ce que fait l'émulateur interact-sound en interne, et cela fonctionne quelle que soit la ressource qui appelle l'export. Trois règles pratiques :

  • Respectez la casse du nom de fichier et bannissez espaces et accents : alarme_banque.ogg plutôt que Alarme Banque.ogg.
  • Redémarrez la ressource après chaque ajout : ensure xsound dans la console txAdmin reconstruit le packfile. Un fichier déposé en SFTP sans redémarrage n'existe pas pour les clients déjà connectés.
  • Surveillez le poids total du dossier. Dix musiques de 5 Mo, c'est 50 Mo de plus à télécharger pour chaque joueur avant d'entrer sur le serveur. Pour une playlist longue, hébergez les fichiers sur un serveur web en HTTPS et passez l'URL complète à PlayUrl : notre guide publier un service sur un VPS Linux en HTTPS couvre le reverse proxy et le certificat.

Les liens YouTube sont détectés sur la présence de « youtube » avec un paramètre ?v=, ou d'un lien court youtu.be, et lus par le lecteur YouTube intégré. L'auteur prévient que certaines vidéos refusent de se lancer à cause de restrictions d'intégration ou de droits d'auteur, et la branche expérimentale est précisément née de changements de l'API YouTube fin 2025. Pour un son critique (alarme, annonce, jingle), privilégiez toujours un fichier local.

Remplacer interact-sound sans casser les scripts existants

Beaucoup de scripts FiveM, surtout les plus anciens, déclenchent leurs sons par les événements d'interact-sound : InteractSound_SV:PlayOnSource pour un clic de menu, InteractSound_SV:PlayWithinDistance pour une sirène entendue autour d'un joueur. Faire tourner interact-sound et xSound côte à côte est possible, mais c'est l'erreur classique : dès que vous activez l'émulateur de xSound, les deux ressources enregistrent les mêmes noms d'événements, et chaque son est joué deux fois. L'objectif est donc de migrer, pas de cumuler.

  1. Ouvrez xsound/config.lua et passez config.interact_sound_enable = true. Si vos fichiers interact-sound sont en .ogg, laissez config.interact_sound_file = "ogg", sinon adaptez l'extension.
  2. Copiez tous les fichiers de interact-sound/client/html/sounds vers xsound/html/sounds, en conservant les noms : les scripts appellent les sons par nom sans extension, et l'émulateur reconstruit le chemin ./sounds/nom.ogg.
  3. Désactivez l'ancienne ressource : retirez ensure interact-sound (ou start interact-sound) de server.cfg, arrêtez-la (stop interact-sound) et supprimez son dossier.
  4. Redémarrez xSound avec ensure xsound et testez un script qui utilisait interact-sound.

L'émulateur couvre les quatre événements serveur d'origine et les trois événements client qu'ils déclenchent :

Événement serveur (déclenché par vos scripts)ParamètresCe que fait xSound côté client
InteractSound_SV:PlayOnSourcefichier, volumeJoue le son uniquement chez le joueur émetteur (PlayUrl)
InteractSound_SV:PlayOnOneid serveur du joueur, fichier, volumeJoue le son chez ce joueur (PlayUrl)
InteractSound_SV:PlayOnAllfichier, volumeJoue le son chez tous les joueurs connectés
InteractSound_SV:PlayWithinDistancedistance max, fichier, volumeSon 3D placé sur le joueur émetteur (PlayUrlPos puis Distance), audible dans le rayon donné

Une différence à connaître : l'émulateur reçoit l'identifiant serveur du joueur émetteur et le résout côté client avec GetPlayerFromServerId. Si l'émetteur est hors de la zone de streaming du client (OneSync), le son n'est pas joué chez ce client, ce qui est de toute façon le comportement attendu pour un son de proximité. Les scripts qui attendaient des coordonnées à la place d'un identifiant, comme le second gestionnaire du serveur interact-sound d'origine, doivent passer par les exports xSound décrits ci-dessous.

Les appels côté client et côté serveur

Les exports de xSound existent en deux jeux presque symétriques. Côté client, la fonction agit sur le joueur local. Côté serveur, elle prend un source en premier argument (l'identifiant du joueur ciblé, ou -1 pour tous les joueurs connectés) et envoie l'ordre au client par l'événement interne xsound:stateSound. Le nom du son est la clé : relancer PlayUrl avec un nom existant remplace le son en cours.

ExportCôté clientCôté serveur
Jouer un son globalPlayUrl(nom, url, volume, boucle, options)PlayUrl(source, nom, url, volume, boucle)
Jouer un son 3DPlayUrlPos(nom, url, volume, vector3, boucle, options)PlayUrlPos(source, nom, url, volume, vector3, boucle)
Déplacer la sourcePosition(nom, vector3)Position(source, nom, vector3)
Changer la portéeDistance(nom, distance)Distance(source, nom, distance)
Pause, reprise, arrêtPause(nom), Resume(nom), Destroy(nom)Mêmes fonctions avec source en premier
VolumesetVolume(nom, v) (global), setVolumeMax(nom, v) (3D)Mêmes fonctions avec source en premier
Position de lecturesetTimeStamp(nom, secondes)setTimeStamp(source, nom, secondes)
FondusfadeIn(nom, durée, volume), fadeOut(nom, durée)Client uniquement
ÉvénementsonPlayStart, onPlayEnd, onLoading, onPlayPause, onPlayResumeClient uniquement
InformationssoundExists, isPlaying, isPaused, getDistance, getPosition, getInfo, getAllAudioInfo, isPlayerCloseToAnySoundClient uniquement

Côté client, les événements se passent dans la table options au moment de la lecture. Exemple d'un jingle d'arrivée suivi d'une action une fois la lecture terminée :

-- client.lua
exports.xsound:PlayUrl('intro', './sounds/intro.ogg', 0.5, false, {
    onPlayEnd = function()
        TriggerEvent('monserveur:afficherMenu')
    end
})

Côté serveur, le cas typique est un son 3D déclenché pour tout le monde autour d'un point, par exemple une alarme de braquage réservée aux administrateurs :

-- server.lua
RegisterCommand('alarme', function(source)
    local pos = vector3(215.76, -810.12, 30.73)
    exports.xsound:PlayUrlPos(-1, 'alarme_banque', './sounds/alarme.ogg', 1.0, pos, true)
    exports.xsound:Distance(-1, 'alarme_banque', 60)
end, true) -- true : commande restreinte, soumise à l'ACE command.alarme

RegisterCommand('finalarme', function(source)
    exports.xsound:Destroy(-1, 'alarme_banque')
end, true)

Point important pour l'administration : xSound ne synchronise rien par lui-même. Un joueur qui se connecte après le lancement de l'alarme ne l'entend pas, et un joueur qui se reconnecte perd la musique du bar. L'auteur recommande de garder en mémoire côté serveur la liste des sons actifs et de les rejouer à l'arrivée de chaque joueur, ce que permet justement l'appel PlayUrlPos(source, ...) ciblé sur le nouveau venu. C'est votre script, pas xSound, qui porte cette logique.

Intégration avec ESX et QBCore

Le besoin le plus fréquent est un objet utilisable, une boombox ou un poste radio, qui diffuse un son 3D à la position du joueur. La logique xSound est identique dans les deux frameworks ; seule la façon d'enregistrer l'objet change. Dans les deux cas, déclarez dependency 'xsound' dans le manifeste de votre script pour qu'il ne démarre pas avant la bibliothèque audio. Pour choisir entre les deux frameworks, voyez notre comparatif ESX Legacy ou QBCore.

ESX Legacy. L'objet boombox doit exister dans la table items de la base de données ; sinon ESX.UseItem affiche un avertissement et ignore l'appel. Le rappel enregistré par ESX.RegisterUsableItem reçoit l'identifiant du joueur et le nom de l'objet :

-- server.lua (ESX Legacy)
ESX = exports['es_extended']:getSharedObject()

ESX.RegisterUsableItem('boombox', function(source, item)
    local coords = GetEntityCoords(GetPlayerPed(source))
    local nom = 'boombox_' .. source
    exports.xsound:PlayUrlPos(-1, nom, './sounds/boombox.ogg', 0.7, coords, true)
    exports.xsound:Distance(-1, nom, 20)
end)

RegisterCommand('stopboombox', function(source)
    exports.xsound:Destroy(-1, 'boombox_' .. source)
end, false)

QBCore. L'objet est déclaré dans shared/items.lua de qb-core. La documentation recommande de mettre l'objet cœur en cache dans une variable locale, et depuis qb-core 1.3.0 de ne demander que les parties utiles, ici Functions :

-- server.lua (QBCore)
local QBCore = exports['qb-core']:GetCoreObject({'Functions'})

QBCore.Functions.CreateUseableItem('boombox', function(source, item)
    local Player = QBCore.Functions.GetPlayer(source)
    if not Player then return end
    local coords = GetEntityCoords(GetPlayerPed(source))
    local nom = 'boombox_' .. source
    exports.xsound:PlayUrlPos(-1, nom, './sounds/boombox.ogg', 0.7, coords, true)
    exports.xsound:Distance(-1, nom, 20)
end)

Pour une boombox qui suit le joueur, complétez avec un thread client qui appelle Position toutes les secondes tant que isPlaying renvoie vrai, puis Destroy quand il range l'objet. Les scripts de boombox ou de jukebox du marché font exactement cela au-dessus de xSound : avant d'en acheter un, notre guide scripts FiveM, où les trouver et lesquels éviter rappelle ce qu'il faut vérifier.

Dépannage : les pannes audio les plus fréquentes

  • Aucun son, pour personne. Vérifiez dans le log de la console txAdmin que xsound est bien démarré, et qu'il l'est avant les scripts qui l'appellent. Dans la console F8 d'un client, une erreur qui mentionne un export introuvable dans la ressource xsound signale une ressource absente, arrêtée ou renommée.
  • La ressource refuse de démarrer. Dossier mal nommé (xsound-1.5.1 au lieu de xsound), archive décompressée avec un niveau de dossier en trop, ou, sur un VPS Linux, fichiers déposés par un autre compte sans droit de lecture pour l'utilisateur qui lance FXServer (ls -l dans le dossier pour vérifier). Le log de démarrage dans la console donne le chemin exact qui pose problème.
  • Aucun son chez un seul joueur. Mode streamer activé par /streamermode, ou domaines CDN (cdnjs.cloudflare.com, ajax.googleapis.com, youtube.com) bloqués par un pare-feu ou un bloqueur côté client.
  • Un fichier ajouté ne se lance pas. Extension oubliée dans l'URL (./sounds/bip.ogg, pas ./sounds/bip), casse différente, fichier dans un sous-répertoire non déclaré dans files, transfert SFTP interrompu (comparez la taille du fichier sur le serveur et sur votre poste), ou ressource non redémarrée après le dépôt.
  • Chaque son est joué deux fois. interact-sound tourne encore à côté de l'émulateur xSound. Arrêtez-le et retirez-le de server.cfg.
  • Une vidéo YouTube reste muette. Intégration désactivée par l'ayant droit, ou changement de l'API YouTube : testez le même lien dans un navigateur en mode intégré, remplacez par un fichier local pour les sons critiques, et essayez la branche expérimentale si le problème est généralisé.
  • Baisse de FPS avec beaucoup de sons 3D. Chaque son dynamique est recalculé à chaque envoi de position. Détruisez les sons inutiles, augmentez config.RefreshTime et limitez le nombre de sources simultanées. Le guide optimiser les performances d'un serveur FiveM couvre le reste du diagnostic.
  • Le son ne suit pas le véhicule. PlayUrlPos fixe une position : c'est à votre script d'appeler Position régulièrement. Pour la voix des joueurs, c'est un autre sujet, traité dans notre guide installer pma-voice sur FiveM.

Conclusion

xSound donne à un serveur FiveM une couche audio complète pour quelques minutes d'installation, que le serveur tourne chez un hébergeur ou sur votre propre VPS : une ressource à déposer dans resources, une ligne ensure xsound dans server.cfg, des fichiers .ogg compressés dans html/sounds, et des exports identiques côté client et côté serveur pour l'audio 3D positionnel. La migration depuis interact-sound tient en un drapeau de configuration et un déplacement de fichiers, à condition de désactiver l'ancienne ressource pour éviter les doublons. Le reste, synchronisation des sons pour les joueurs qui arrivent, objets utilisables ESX ou QBCore, suivi d'une source mobile, relève de vos scripts. Pour que tout cela tourne sans accroc, le serveur doit suivre : nos offres serveur FiveM vont de 4 à 64 Go de RAM DDR4 avec txAdmin et protection anti-DDoS inclus, hébergées en France, et notre guide configurer txAdmin détaille la console depuis laquelle vous piloterez vos ressources.

FAQ

Qu'est-ce que xSound et à quoi sert-il sur un serveur FiveM ?

xSound est une bibliothèque audio open source (licence MIT) pour FiveM, publiée par Xogy en 2020 et maintenue sur GitHub. Elle ouvre une page NUI invisible chez chaque joueur et y lit des fichiers .ogg ou .mp3, des URL directes ou des liens YouTube, avec un audio 3D positionnel dont le volume baisse avec la distance. Ce n'est pas un script de boombox prêt à l'emploi : c'est une API que vos autres ressources appellent par exports (PlayUrl, PlayUrlPos, Distance, Destroy) côté client comme côté serveur.

Quelle version de xSound installer : la stable ou l'expérimentale ?

Installez la version stable 1.5.1, publiée le 10 novembre 2025 sur la branche master, qui corrige notamment la transmission de destroyOnFinish côté serveur et la reprise de sons mis en pause. La branche experimental (1.0 en décembre 2025, 1.1 en mai 2026) déplace le lecteur dans un DUI isolé pour que les plantages du lecteur YouTube n'affectent pas la page NUI principale. Réservez-la à un serveur de test si vous diffusez beaucoup de YouTube, et gardez la stable en production tant que vos scripts n'y ont pas été validés.

Où placer mes fichiers sons personnalisés et comment les appeler ?

Déposez vos fichiers .ogg ou .mp3 dans le dossier html/sounds de la ressource xsound, sans espaces ni accents dans les noms. Le fxmanifest.lua de xSound déclare déjà ces fichiers : ils sont ajoutés au packfile et téléchargés par chaque client. Dans vos scripts, référencez-les par le chemin relatif ./sounds/nom-du-fichier.ogg, extension comprise, par exemple exports.xsound:PlayUrl('bip', './sounds/bip.ogg', 0.5). Redémarrez la ressource avec ensure xsound après chaque ajout, sinon les clients ne voient pas le nouveau fichier.

Comment fonctionne l'audio 3D de xSound ?

Un son créé avec PlayUrlPos reçoit une position vector3 et une distance maximale d'audition (10 unités par défaut, modifiable avec Distance). Le script client envoie la position du joueur à la page NUI toutes les 300 ms (config.RefreshTime) dès qu'il a bougé, et le volume est recalculé de façon linéaire : volume maximal sur la source, zéro au-delà de la distance. Au-delà de la distance plus 40 unités (config.distanceBeforeUpdatingPos), le son est détruit en silence et recréé depuis le cache quand le joueur se rapproche. La spatialisation est simulée par le volume, sans rendu binaural ni 7.1.

Puis-je garder interact-sound en même temps que xSound ?

Non si vous activez l'émulateur de xSound (config.interact_sound_enable = true) : les deux ressources enregistrent alors les mêmes événements InteractSound_SV et InteractSound_CL, et chaque son est joué deux fois. La bonne méthode est de migrer : activer l'émulateur, copier les fichiers de interact-sound/client/html/sounds vers xsound/html/sounds en conservant les noms, retirer ensure interact-sound de server.cfg, arrêter la ressource et supprimer son dossier. Les scripts qui déclenchent PlayOnSource, PlayOnOne, PlayOnAll ou PlayWithinDistance continuent de fonctionner sans modification.

Les joueurs qui se connectent après le lancement d'un son l'entendent-ils ?

Non. xSound ne synchronise pas l'état des sons entre les joueurs : un appel serveur avec source à -1 envoie l'ordre aux joueurs connectés à cet instant, et personne d'autre. L'auteur recommande de conserver côté serveur la liste des sons actifs (nom, URL, position, distance, volume) et de les rejouer pour chaque nouveau joueur avec PlayUrlPos(source, ...) ciblé sur lui au moment où il charge. Cette logique appartient à votre script, pas à xSound.

xSound fonctionne-t-il avec ESX et QBCore ?

Oui, et de la même façon : xSound ne dépend d'aucun framework. Sur ESX Legacy, enregistrez un objet utilisable avec ESX.RegisterUsableItem('boombox', function(source, item) ... end) et appelez exports.xsound:PlayUrlPos(-1, nom, url, volume, GetEntityCoords(GetPlayerPed(source)), true) dans le rappel ; l'objet doit exister dans la table items de la base de données. Sur QBCore, récupérez l'objet cœur avec exports['qb-core']:GetCoreObject() puis utilisez QBCore.Functions.CreateUseableItem avec le même rappel ; l'objet est déclaré dans shared/items.lua. Dans les deux cas, ajoutez dependency 'xsound' au fxmanifest.lua de votre script.

Pourquoi un joueur n'entend aucun son alors que les autres oui ?

Deux causes reviennent sans cesse. Le mode streamer : la commande /streamermode, intégrée à xSound, coupe et détruit tous les sons chez le joueur qui la tape, et certains l'activent sans le savoir. Et les CDN bloqués : la page NUI de xSound charge Howler et DOMPurify depuis cdnjs.cloudflare.com, jQuery depuis ajax.googleapis.com et l'API YouTube depuis youtube.com ; un pare-feu, un antivirus ou un bloqueur côté client qui filtre ces domaines empêche le lecteur de se charger.

Comment installer xSound manuellement sur un VPS Linux ou sous Windows, sans panel ?

Sur un FXServer auto-hébergé, la ressource va dans le répertoire resources du dossier server-data (celui qui contient server.cfg), pas dans le dossier des binaires. Sous Ubuntu ou Debian : sudo apt install unzip, puis unzip de l'archive dans resources et renommage du dossier xsound-1.5.1 en xsound, depuis un compte sudo plutôt qu'en root. Transférez vos fichiers audio en SFTP (FileZilla, WinSCP ou scp) vers resources/xsound/html/sounds. Sous Windows, clic droit sur l'archive, « Extraire tout », puis copie du dossier dans C:\FXServer\server-data\resources. Ajoutez ensure xsound dans server.cfg, lancez le serveur (bash run.sh +exec server.cfg sous Linux, FXServer.exe +exec server.cfg sous Windows, ou sans +exec pour passer par txAdmin sur le port 40120) et lisez le log de démarrage pour repérer un manifeste ou un fichier manquant.

Quel format audio choisir et comment compresser mes sons pour xSound ?

L'Ogg Vorbis, extension .ogg : il est lu nativement par le Chromium embarqué de la NUI, c'est le format attendu par défaut par l'émulateur interact-sound, et sa compression réduit fortement le poids téléchargé par chaque joueur. Le MP3 est accepté aussi. Convertissez vos fichiers manuellement avec ffmpeg sur votre poste (Windows, macOS ou Linux) : ffmpeg -i son.wav -c:a libvorbis -q:a 4 -ac 1 son.ogg. L'option -q:a règle la qualité de l'encodeur libvorbis entre -1 et 10 (3 par défaut), et -ac 1 passe en mono, suffisant pour un son positionnel puisque xSound simule la distance par le volume. Gardez des noms de fichiers sans espaces ni accents et redémarrez la ressource avec ensure xsound après chaque ajout.