Aller au menu - Aller au contenu

[Plan du site] Vous êtes ici --- > Le Site du Zéro > Les tutoriels > Officiels > Programmation > Apprenez à programmer en C ! > [Pratique] Création de jeux 2D en SDL > Jouer du son avec FMOD > Lecture du tutoriel

Jouer du son avec FMOD

Avatar
Auteur : M@teo21
Difficulté : Connaisseur (3 / 5)
Note : 18 / 20 (18 votes)
Visualisations : 132 420

Plus d'informations Plus d'informations
Depuis le début de la partie III, nous avons appris à placer des images dans la fenêtre, à faire interagir l'utilisateur par tous les moyens possibles et imaginables (clavier, souris, joystick...), à écrire du texte, mais il manque clairement un élément : le son !

Ce chapitre va combler ce manque. Nous allons découvrir une librairie spécialisée dans le son : FMOD.

Faites chauffer les enceintes, c'est DJ M@teo qui mixe ce soir :soleil:
Sommaire du chapitre :
Icône du chapitre
Chapitre précédent Sommaire Chapitre suivant

Installer FMOD

Pourquoi FMOD ?



Vous le savez maintenant : la SDL n'est pas seulement une librairie graphique. Elle permet aussi de gérer le son via un module appelé SDL_audio. Alors que vient faire une librairie externe qui n'a rien à voir comme FMOD dans ce chapitre ?

C'est en fait un choix que j'ai fait après de nombreux tests. J'aurais pu vous expliquer comment gérer le son en SDL mais j'ai préféré ne pas le faire.
Je m'explique.

Pourquoi j'ai évité SDL_audio



La gestion du son en SDL est "bas niveau". Trop à mon goût. Il faut effectuer plusieurs manipulations très précises pour jouer du son. C'est donc complexe et je ne trouve pas ça amusant. Il y a bien d'autres librairies qui proposent de jouer du son simplement.

Petit rappel : une librairie "bas niveau" est une librairie proche de l'ordinateur. On doit donc connaître un peu le fonctionnement interne de l'ordinateur pour s'en servir et il faut généralement plus de temps pour arriver à faire la même chose qu'avec une librairie "haut niveau".
N'oubliez pas que tout est relatif : il n'y a pas les librairies bas niveau d'un côté et les librairies haut niveau de l'autre. Certaines sont juste plus ou moins haut niveau que d'autres. Par exemple FMOD est plus haut niveau que le module SDL_audio de la SDL.


Autre détail important, la SDL ne permet de jouer que des sons au format WAV. Le format WAV est un format de son non compressé. Une musique de 3 minutes dans ce format prend plusieurs dizaines de Mo, contrairement à un format compressé comme MP3 ou Ogg qui occupe beaucoup moins d'espace (2-3 Mo).

En fait, si on y réfléchit bien, c'était un peu pareil avec les images. La SDL ne gère que les BMP (images non compressées) à la base. On a dû installer une librairie supplémentaire (SDL_image) pour pouvoir lire d'autres images comme les JPEG, PNG, GIF, etc.

Eh bien figurez-vous qu'il y a une librairie équivalente pour le son : SDL_mixer. Elle est capable de lire un grand nombre de formats audio, parmi lesquels les MP3, les Ogg, les Midi... Et pourtant, j'ai évité de vous parler de cette librairie là encore. Pourquoi ?


Pourquoi j'ai évité SDL_mixer



SDL_mixer est une librairie qu'on ajoute en plus de la SDL à la manière de SDL_image. Elle est simple à utiliser et lit beaucoup de formats audio différents. Toutefois, après mes tests, il s'est avéré que la librairie comportait des bugs gênants en plus d'être relativement limitée en fonctionnalités.

C'est donc pour cela que je me suis ensuite penché sur FMOD, une librairie qui n'a certes rien à voir avec la SDL, mais qui a l'avantage d'être puissante et réputée.


Télécharger FMOD



Si je vous raconte tout ça, c'est pour vous expliquer que le choix de FMOD n'est pas anodin. C'est tout simplement parce que c'est la meilleure librairie gratuite que j'ai pu trouver.
Elle est aussi simple à utiliser que SDL_mixer, avec un avantage non négligeable : elle n'est pas buggée :D

FMOD permet en outre de réaliser plusieurs effets intéressants que SDL_mixer ne propose pas, comme des effets sonores 3D.

Pour télécharger la librairie, il vous faut l'adresse du site de FMOD. La voici :



FMOD est une librairie gratuite mais pas sous license LGPL, contrairement à la SDL. Cela signifie que vous pouvez l'utiliser gratuitement du temps que vous ne réalisez pas de programme payant avec. Si vous voulez faire payer votre programme, il faudra payer une redevance à l'auteur (je vous laisse consulter les prix sur le site de FMOD).


Image utilisateur

Rendez-vous sur la page des téléchargements (Downloads) et prenez FMOD 3.
Attention, il y a plusieurs versions de FMOD, en particulier une plus récente et appelée FMOD Ex (il s'agit en fait de FMOD 4). Toutefois, FMOD Ex est une librairie C++, contrairement à FMOD 3 qui est une librairie C.



FMOD Ex, bien qu'écrite en C++, peut être utilisée en C en faisant quelques légères manipulations. Ce n'est toutefois pas la librairie que nous utiliserons ici. FMOD 3 est toujours supportée par ses créateurs et suffit amplement à nos besoins.


Téléchargez donc FMOD 3, il s'agit de la section "FMOD 3.75 Programmers API" sur la page Downloads (il peut s'agir d'une version plus récente si FMOD 3 a évolué). Prenez la version correspondant à votre système d'exploitation : Windows 32 / 64 bits si vous êtes sous Windows.
Vous remarquerez au passage que FMOD fonctionne sur un très grand nombre de plateformes, en particulier sur des consoles de jeux comme la XBOX, la PS2, la PS3, la PSP, la Wii, etc. Cette librairie a été utilisée par plusieurs jeux professionnels parus sur console, ça devrait vous rassurer quant à sa qualité ;)


Installer FMOD



Le fichier que vous avez téléchargé est un fichier ZIP (si c'est un exécutable c'est que vous avez pris FMOD Ex et non FMOD 3 !). L'installation se déroule de la même manière qu'avec les autres librairies qu'on a vues jusqu'ici.

  1. Vous avez un dossier "Api" avec la DLL de FMOD (fmod.dll) à placer dans le répertoire de votre projet.
    fmod64.dll, que vous trouverez dans le même dossier, est la DLL adaptée aux systèmes d'exploitation 64 bits, pour ceux qui ont des processeurs 64 bits.
    Si vous n'êtes pas sûr de la DLL à prendre, utilisez fmod.dll, il y a 99% de chances pour que ce soit la bonne. Si vous êtes sous Windows XP par exemple, c'est que vous n'êtes pas sous un OS 64 bits, vous pouvez donc prendre fmod.dll.
  2. Dans le dossier "api/inc", vous trouverez les .h. Placez-les à côté des autres .h dans le dossier de votre IDE. Par exemple "Code Blocks/mingw32/include/FMOD" (j'ai créé un dossier spécial pour FMOD comme pour SDL).
  3. Dans le dossier "api/lib", récupérez le fichier qui correspond à votre compilateur.
    • Si vous utilisez Code Blocks ou Dev-C++, donc le compilateur mingw, copiez "libfmod.a" dans le dossier "lib" de votre IDE.
      Dans le cas de Code Blocks, c'est le dossier "CodeBlocks/mingw32/lib".
    • Si vous utilisez Visual C++, récupérez le fichier "fmodvc.lib"
  4. Enfin, et c'est peut-être le plus important, dans le dossier "documentation" vous trouverez un fichier d'aide qui correspond à la documentation de FMOD. Je vous conseille de le placer quelque part sur votre disque dur et d'en faire un raccourci bien visible, par exemple dans le menu Démarrer.
    En effet, la documentation liste toutes les possibilités de FMOD dans le détail. Dans ce chapitre, on ne pourra voir que les principales. Si vous voulez allez plus loin, il faudra donc vous plonger dans cette doc ;)

    La doc est aussi accessible en ligne à l'adresse : http://www.fmod.org/docs.


Il reste à configurer notre projet. Là encore, c'est comme les autres fois : vous ouvrez votre projet avec votre IDE favori et vous ajoutez le fichier .a (ou .lib) à la liste des fichiers que le linker doit récupérer.
Sous Code Blocks (j'ai l'impression de me répéter ^^ ), menu Project / Build Options, onglet Linker, cliquez sur "Add" et indiquez où se trouve le fichier .a. Si on vous demande "Keep as a relative path ?", je vous conseille de répondre non, mais dans les deux cas de toute manière ça devrait marcher.


Voilà qui est bien :)
FMOD est installé, voyons voir rapidement de quoi il est constitué.


Les différentes sections de FMOD



FMOD 3 est en fait la combinaison de 2 librairies :



Dans ce chapitre, nous verrons les trois types de sons car ils se chargent et se lisent avec des fonctions différentes :

Initialiser et libérer FMOD

Comme la plupart des librairies écrites en C, il faut charger FMOD (on dit aussi "initialiser") et le libérer quand on n'en a plus besoin. Ca ne devrait pas beaucoup vous changer de la SDL à ce niveau :p

Inclure le header



Avant toute chose, vous avez dû le faire instinctivement maintenant mais ça ne coûte rien de le préciser, il faut inclure le fichier .h de FMOD.

Code : C
1
#include <FMOD/fmod.h>


J'ai placé ce fichier dans un sous-dossier "FMOD". Adaptez cette ligne en fonction de la position du fichier si chez vous c'est différent.


Initialiser FMOD



On initialise FMOD avec la fonction FSOUND_Init.
Elle prend 3 paramètres :



Nous pouvons donc initialiser FMOD comme ceci :

Code : C
1
FSOUND_Init(44100, 32, 0);


Ce qui signifie : fréquence de 44 100 Hz (qualité CD au mieux), 32 canaux et pas d'options particulières (flag = 0).


Libérer FMOD



On arrête FMOD de la manière la plus simple qui soit :

Code : C
1
FSOUND_Close();


Est-ce que j'ai vraiment besoin de commenter ce code ? :D

Les sons courts

Nous commencerons par étudier les sons courts.
Un "son court", comme je l'appelle, est un son qui dure généralement quelques secondes (parfois moins d'une seconde) et qui est généralement destiné à être joué régulièrement.

Quelques exemples de sons courts :

Bref, ça correspond à tous les sons qui ne sont pas des musiques.
Généralement, ces sons sont tellements courts qu'on ne prend pas la peine de les compresser. On les trouve donc le plus souvent au format WAV non compressé.


Trouver des sons courts



Avant de commencer, il serait bien de connaître quelques sites qui proposent des banques de sons. En effet, tout le monde ne veut pas forcément enregistrer les sons chez soi (pour les bruits de balle par exemple, vous avez intérêt à être armé ! :-° ).

Ca tombe bien, le net regorge de sons courts, généralement au format WAV.
Où les trouver ? Ca peut paraître bête, on n'y pense pas forcément (et pourtant on devrait), mais Google est notre ami. Au hasard, je tape "Free Sounds", ce qui signifie "sons gratuits" en anglais, et boum... des centaines de millions de résultats !

Rien qu'avec les sites de la première page, vous devriez trouver votre bonheur.
Personnellement, j'ai retenu FindSounds.com, un moteur de recherche pour sons. Je ne sais pas si c'est le meilleur, mais en tout cas il est bien complet.

Si vous ne savez pas quels mots-clés taper pour votre recherche, rendez-vous sur la page des exemples de recherche.
Certes, il faut connaître quelques mots d'anglais (mais si vous voulez programmer de toute façon, comment voulez-vous faire sans être au moins capable de lire l'anglais ?).


En recherchant "gun", on trouve des tonnes de sons de tir de fusil, en tapant "footsteps" on trouve des bruits de pas, etc etc. :)

Image utilisateur
Le site FindSounds.com, un moteur de recherche de sons courts (ici, des bruits de porte)


Bonne pioche et bons téléchargements ;)


Les étapes à suivre pour jouer un son



La première étape consiste à charger en mémoire le son que vous voulez jouer.
Il est conseillé de charger tous les sons qui seront fréquemment utilisés dans le jeu dès le début du programme. Vous les libérerez à la fin. En effet, une fois que le son est chargé en mémoire, sa lecture est très rapide.


Le pointeur



Première étape : créer un pointeur de type FSOUND_SAMPLE qui représentera notre son.

Code : C
1
FSOUND_SAMPLE *tir = NULL;



Charger le son



Deuxième étape : charger le son avec la fonction FSOUND_Sample_Load. Elle prend... 5 paramètres :



La fonction renvoie l'adresse mémoire où a été chargé le son.
Voici un exemple de chargement :

Code : C
1
tir = FSOUND_Sample_Load(FSOUND_FREE, "pan.wav", 0, 0, 0);


Ici, je charge le son "pan.wav" et je le place dans le premier canal libre. Le pointeur tir fera référence à ce son par la suite.
Vous remarquerez qu'en règle générale on laisse les 3 derniers paramètres à 0.

Si vous voulez faire les tests en même temps que moi (et si vous ne voulez pas vous devriez :p ), voici le fichier son pan.wav sur lequel nous allons travailler par la suite.


La fonction renvoie NULL si le fichier n'a pas été chargé. Vous avez tout intérêt à vérifier si le chargement a réussi ou s'il a échoué.


Jouer le son



Vous voulez jouer le son ? Pas de problème avec la fonction FSOUND_PlaySound !
Il suffit de lui donner un numéro de canal sur lequel jouer ainsi que le pointeur sur le son. Pour le numéro de canal, ne vous prenez pas la tête et envoyez FSOUND_FREE pour laisser FMOD gérer ça ;)

Code : C
1
FSOUND_PlaySound(FSOUND_FREE, tir);



Libérer le son de la mémoire



Lorsque vous n'avez plus besoin du son, vous devez le libérer de la mémoire.
Il n'y a rien de plus simple, il suffit d'indiquer le pointeur à libérer avec la fonction FSOUND_Sample_Free

Code : C
1
FSOUND_Sample_Free(tir);



Exemple : un jeu de tir



Le mieux maintenant est de résumer tout ce qu'on a vu dans un cas concret de programme écrit en SDL.
Il n'y avait rien de compliqué et, normalement, vous ne devriez avoir aucune difficulté à réaliser cet exercice.


Le sujet



Votre mission est simple : créer un jeu de tir.
Bon, on ne va pas réaliser un jeu complet ici, mais déjà juste la gestion du viseur. Je vous ai justement fait un petit viseur sous Paint ;)

Image utilisateur
Oui je sais...
J'aurais dû faire les Beaux Arts


Bref, voilà les objectifs :


Ca peut être le début d'un jeu de tir.
Trop facile ? Ok alors à vous de jouer :D


La correction



Voici le code complet :

Code : C
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
#include <stdlib.h>
#include <stdio.h>
#include <SDL/SDL.h>
#include <SDL/SDL_image.h>
#include <FMOD/fmod.h>

int main(int argc, char *argv[])
{
    SDL_Surface *ecran = NULL, *viseur = NULL;
    SDL_Event event;
    SDL_Rect position;
    int continuer = 1;
    FSOUND_SAMPLE *tir = NULL;

    /* Initialisation de FMOD */
    FSOUND_Init(44100, 32, 0);

    /* Chargement du son et vérification du chargement */
    tir = FSOUND_Sample_Load(FSOUND_FREE, "pan.wav", 0, 0, 0);
    if (tir == NULL)
    {
        fprintf(stderr, "Impossible de lire pan.wav\n");
        exit(EXIT_FAILURE);
    }

    /* Initialisation de la SDL */
    SDL_Init(SDL_INIT_VIDEO);

    SDL_ShowCursor(SDL_DISABLE);
    ecran = SDL_SetVideoMode(640, 480, 32, SDL_HWSURFACE | SDL_DOUBLEBUF);
    SDL_WM_SetCaption("Gestion du son avec FMOD", NULL);

    viseur = IMG_Load("viseur.png");


    while (continuer)
    {
        SDL_WaitEvent(&event);


        switch(event.type)
        {
            case SDL_QUIT:
                continuer = 0;
                break;
            case SDL_MOUSEBUTTONDOWN:
                /* Lorqu'on clique, on joue le son */
                FSOUND_PlaySound(FSOUND_FREE, tir);
                break;
            case SDL_MOUSEMOTION:
                /* Lorsqu'on déplace la souris, on place le centre du viseur à la position de la souris
                ... D'où notamment le "viseur->w / 2" pour réussir à faire cela */
                position.x = event.motion.x - (viseur->w / 2);
                position.y = event.motion.y - (viseur->h / 2);
                break;
        }

        SDL_FillRect(ecran, NULL, SDL_MapRGB(ecran->format, 0, 0, 0));
        SDL_BlitSurface(viseur, NULL, ecran, &position);
        SDL_Flip(ecran);
    }

    /* On ferme la SDL */
    SDL_FreeSurface(viseur);
    SDL_Quit();

    /* On libère le son et on ferme FMOD */
    FSOUND_Sample_Free(tir);
    FSOUND_Close();

    return EXIT_SUCCESS;
}


Aperçu du mini-jeu :

Image utilisateur
Le jeu avec le viseur. Quand on clique avec la souris, on entend "PAN !" :p


Le mieux est encore de voir le résultat en vidéo avec le son !



Ici, j'ai chargé FMOD avant la SDL et je l'ai libéré après la SDL. Il n'y a pas de règles au niveau de l'ordre (j'aurais tout aussi bien pu faire l'inverse). J'ai choisi de charger la SDL et d'ouvrir la fenêtre après le chargement de FMOD pour que le jeu soit prêt à être utilisé dès que la fenêtre s'ouvre (sinon il aurait peut-être fallu attendre quelques millisecondes le temps que FMOD se charge).
Bref, vous faites comme vous voulez c'est un peu du détail ça de toute manière ;)

Le code est, je pense, suffisamment commenté. Il n'y a pas de piège particulier, pas de nouveauté fracassante.

On notera la "petite" difficulté qui consistait à blitter le centre du viseur au niveau du pointeur de la souris. Le calcul de la position de l'image est fait en fonction.
Je vous fais un petit tableau pour ceux qui n'auraient pas encore compris la différence. Pour l'occasion, j'ai réactivé l'affichage du pointeur de la souris pour qu'on voie comment est placé le viseur par rapport au pointeur.

Code incorrect
(viseur mal placé)
Image utilisateur Code : C
1
2
position.x = event.motion.x;
position.y = event.motion.y;
Code correct
(viseur bien placé)
Image utilisateur Code : C
1
2
position.x = event.motion.x - (viseur->w / 2);
position.y = event.motion.y - (viseur->h / 2);



Idées d'amélioration



Ce code est la base d'un jeu de shoot. Vous avez le viseur, le bruit de tir, il ne vous reste plus qu'à faire apparaître ou défiler des ennemis et à marquer le score du joueur.
Comme d'hab, c'est à vous de jouer. Vous vouliez faire un jeu ? Qu'à cela ne tienne, vous avez le niveau maintenant et même un code de base pour démarrer un jeu de tir ! Qu'est-ce que vous attendez franchement ? ;)

Bien sûr, les forums du Site du Zéro sont toujours là pour vous aider si vous êtes bloqués à un moment de la création de votre jeu. Il est normal de rencontrer des difficultés, quel que soit le niveau qu'on ait ^^

Les musiques (MP3, OGG, WMA...)

En théorie, la fonction FSOUND_Sample_Load permet de charger n'importe quel type de son, y compris les formats compressés MP3, OGG, WMA. Le problème concerne les sons "longs", c'est-à-dire les musiques.
En effet, une musique dure en moyenne 3 à 4 minutes. Or, la fonction FSOUND_Sample_Load charge tout le fichier en mémoire (et c'est la version décompressée qui est mise en mémoire, donc ça prend beaucoup de place !).

Si vous avez un son long (on va parler de "musique" dorénavant ^^ ), il est préférable de le charger en streaming, c'est-à-dire d'en charger des petits bouts au fur et à mesure de la lecture. C'est ce que font tous les lecteurs audio pour info.


Trouver des musiques



Là, on rentre en terrain miné, épineux, explosif (comme vous préférez).
En effet, la plupart des musiques et chansons que l'on connaît sont soumises au droit d'auteur. Même si vous ne faites qu'un petit programme, il faut verser une redevance à l'auteur à la SACEM (du moins en France c'est l'organisation qui s'occupe de ça).

Ne comptez pas sur moi pour vous expliquer comment télécharger ces chansons, tout le monde sait que c'est illégal (ce qui n'empêche pas tout le monde de le faire).

Donc, mis à part les MP3 soumis à droit d'auteur, que nous reste-t-il ?
Heureusement, il y a des chansons libres de droit ! Les auteurs vous autorisent à diffuser librement leurs chansons, il n'y a donc aucun problème pour que vous les utilisiez dans vos programmes.

Si votre programme est payant, il faudra en parler à l'artiste à moins que celui-ci n'autorise explicitement une utilisation commerciale de son oeuvre.
Une chanson libre de droit peut être téléchargée, copiée et écoutée librement, mais ça ne veut pas dire qu'on vous autorise à vous faire de l'argent sur le dos des artistes !


Bon, la question maintenant est : où trouver des musiques libres de droit ?
On pourrait faire une recherche de Free Music sur Google, mais là, pour le coup, Google n'est pas notre ami :(
En effet, allez savoir pourquoi, on a beau taper le mot "Free", on tombe quand même sur des sites qui nous proposent d'acheter des musiques !

Il existe heureusement des sites (à connaître !) qui sont dédiés à la musique libre de droit. Là, je vous recommande Jamendo qui est un très bon site, mais ce n'est pas le seul qui existe dans le domaine.



Les chansons sont classées par style. Vous avez beaucoup de choix. On y trouve du bon, du moins bon, du très très bon, du très très nul... En fait, tout dépend de vos goûts et de votre récéptivité aux différents styles de musique ^^
De préférence, prenez une chanson qui peut servir de musique de fond et qui correspond bien à l'univers de votre jeu.

Personnellement, j'ai flâné sur le site en écoutant des musiques dans les styles que j'aime bien (Rock, Pop Rock, Punk...) et je suis tombé sur une petite perle alors je vais utiliser cette chanson dans la suite de ce chapitre.
L'artiste en question est un groupe français, Hype, et l'album s'appelle Lies and Speeches.

Image utilisateur
Jamendo.com propose des musiques libre de droit (ici le groupe Hype)


Je suis parfaitement conscient que les goûts et les couleurs ne se discutent pas. N'ayez donc pas peur de prendre une autre musique si celle-ci ne vous plaisait pas.


J'ai donc téléchargé l'album et je vais utiliser la chanson "Home" au format MP3.
Vous pouvez la télécharger directement depuis le Site du Zéro (5,2 Mo) si vous voulez faire des tests en même temps que moi. C'est un des avantages de la musique libre : on peut la copier / distribuer librement, donc ne nous gênons pas ^^


Les étapes à suivre pour jouer une musique



Comme d'habitude, il faut que FMOD soit chargé avec FSOUND_Init et déchargé avec FSOUND_Close :)


Le pointeur



Cette fois, le pointeur doit être de type FSOUND_STREAM.

Code : C
1
FSOUND_STREAM *musique = NULL;



Charger le son



Comme je vous ai dit, le son sera chargé progressivement (on dit "en streaming"). Toutefois, il faut quand même ouvrir le fichier, car pour l'instant notre pointeur musique vaut toujours NULL je vous rappelle ;)

On utilise ici la fonction FSOUND_Stream_Open. Elle prend 4 paramètres, ce sont les 4 mêmes derniers paramètres que ceux de la fonction FSOUND_Sample_Load qu'on a vue tout à l'heure.
En clair, indiquez le nom du fichier à ouvrir dans le premier paramètre, et laissez les 3 autres paramètres à 0.

La fonction retourne une adresse mémoire qu'on récupère avec notre pointeur musique.

Code : C
1
musique = FSOUND_Stream_Open("Hype_Home.mp3", 0, 0, 0);


Il est là encore fortement conseillé de vérifier si le fichier a bien été chargé. En cas d'échec, le pointeur vaut NULL.


Jouer la musique



C'est très simple, on fait appel à FSOUND_Stream_Play.
Elle prend 2 paramètres :



On peut donc jouer notre musique avec :

Code : C
1
FSOUND_Stream_Play(FSOUND_FREE, musique);


Et voilà le travail ^^
Mais ce n'est pas tout. Dans le cas d'une musique, il peut être bien de savoir modifier le volume, gérer les répétitions de la chanson, la mettre en pause ou même l'arrêter. C'est ce genre de choses que nous allons voir maintenant.


Modifier le volume



Avec la fonction FSOUND_SetVolume, vous pouvez changer le volume d'un canal.

Code : C
1
FSOUND_SetVolume(FSOUND_ALL, 120);


Il faut envoyer 2 paramètres :


Cette fonction permet aussi de changer le volume des sons courts, et pas seulement celui des sons streamés (longs).


Répétition de la chanson



On a souvent besoin de répéter la musique de fond. C'est justement ce que propose la fonction FSOUND_Stream_SetLoopCount. Elle prend 2 paramètres :



Avec ce code source, notre musique sera donc répétée à l'infini :

Code : C
1
FSOUND_Stream_SetLoopCount(musique, -1);


Pour que la répétition fonctionne, il faut envoyer FSOUND_LOOP_NORMAL en second paramètre de la fonction FSOUND_Stream_Open.


Mettre en pause la chanson



Il y a ici 2 fonctions à connaître :



Ce bout de code de fenêtre SDL met en pause la chanson si on appuie sur P, et la réactive si on appuie à nouveau sur P ensuite.

Code : C
1
2
3
4
5
6
7
8
9
case SDL_KEYDOWN:
    if (event.key.keysym.sym == SDLK_p) // Si on appuie sur P
    {
        if (FSOUND_GetPaused(1)) // Si la chanson est en pause
            FSOUND_SetPaused(FSOUND_ALL, 0); // On enlève la pause
        else // Sinon, elle est en cours de lecture
            FSOUND_SetPaused(FSOUND_ALL, 1); // On met en pause
    }
    break;



Stopper la lecture



Il suffit d'appeler FSOUND_Stream_Stop. On lui envoie le pointeur vers la chanson à arrêter.

Code : C
1
FSOUND_Stream_Stop(musique);



Et bien d'autres choses



On peut faire beaucoup d'autres choses, mais je ne vais pas vous les énumérer toutes ici, autant répéter la doc ! Je vous invite donc à la lire si vous cherchez des fonctions supplémentaires ;)


Libérer la mémoire



Pour décharger la musique de la mémoire, appelez FSOUND_Stream_Close et donnez-lui le pointeur.

Code : C
1
FSOUND_Stream_Close(musique);



Code complet de lecture du MP3



Le code ci-dessous vous montre un programme jouant la musique "Home" qu'on a récupéré sur Jamendo.
La musique est jouée dès le début du programme. On peut la mettre en pause en appuyant sur P.

Code : C
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
int main(int argc, char *argv[])
{
    SDL_Surface *ecran = NULL, *pochette = NULL;
    SDL_Event event;
    SDL_Rect position;
    int continuer = 1;
    FSOUND_STREAM *musique = NULL;

    FSOUND_Init(44100, 32, 0);
    musique = FSOUND_Stream_Open("Hype_Home.mp3", FSOUND_LOOP_NORMAL, 0, 0); /* On ouvre la musique */
    if (musique == NULL) /* On vérifie si elle a bien été ouverte (IMPORTANT) */
    {
        fprintf(stderr, "Impossible de lire Hype_Home.mp3\n");
        exit(EXIT_FAILURE);
    }

    FSOUND_Stream_SetLoopCount(musique, -1); /* On active la répétition de la musique à l'infini */
    FSOUND_Stream_Play(FSOUND_FREE, musique); /* On joue la musique */

    SDL_Init(SDL_INIT_VIDEO);


    ecran = SDL_SetVideoMode(640, 480, 32, SDL_HWSURFACE | SDL_DOUBLEBUF);
    SDL_WM_SetCaption("Gestion du son avec FMOD", NULL);
    pochette = IMG_Load("hype_liesandspeeches.jpg");
    position.x = 0;
    position.y = 0;


    while (continuer)
    {
        SDL_WaitEvent(&event);
        switch(event.type)
        {
            case SDL_QUIT:
                continuer = 0;
                break;
            case SDL_KEYDOWN:
                if (event.key.keysym.sym == SDLK_p) //Si on appuie sur P
                {
                    if (FSOUND_GetPaused(1)) // Si la chanson est en pause (sur le canal 1)
                        FSOUND_SetPaused(1, 0); // On enlève la pause
                    else // Sinon, elle est en cours de lecture
                        FSOUND_SetPaused(1, 1); // On active la pause
                }
                break;
        }

        SDL_FillRect(ecran, NULL, SDL_MapRGB(ecran->format, 0, 0, 0));
        SDL_BlitSurface(pochette, NULL, ecran, &position);
        SDL_Flip(ecran);
    }

    FSOUND_Stream_Close(musique); /* On libère la mémoire */
    FSOUND_Close();

    SDL_FreeSurface(pochette);
    SDL_Quit();

    return EXIT_SUCCESS;
}


Histoire d'avoir autre chose qu'une fenêtre noire, j'ai mis la pochette de l'album en image de fond. Bien entendu, ce qui nous intéresse, c'est comment est jouée la musique hein, pas la pochette :D

Donc bon, en image ça donne juste une fenêtre SDL avec la pochette :

Image utilisateur
L'intérêt dans cette image, c'est le son qui se joue derrière
(euh oui certes, les images ne produisent pas de son...)


Bon, allez, je crois qu'une vidéo sera plus convaincante ^^


Les musiques (MIDI)

Les musiques de type MIDI sont très différentes des musiques de type MP3, OGG ou WMA qu'on vient d'étudier. En effet, au lieu d'enregistrer la musique (avec un micro :p ), cette fois la musique est créée de toutes pièces sur l'ordinateur. On n'enregistre que des notes de musique, ce qui explique pourquoi on ne peut pas enregistrer la voix.

L'avantage ? En enregistrant uniquement les notes, on obtient des fichiers très très petits. Vous avez peut-être déjà remarqué que les MIDI étaient de tous petits fichiers.
Le défaut ? Eh bien on ne peut pas enregistrer de voix et les effets autorisés par le format, bien que nombreux, sont limités.

Ce format est donc inadapté pour enregistrer des musiques qui passent à la radio par exemple (mais certains essaient de les recréer !), en revanche il est tout à fait adapté pour jouer de vieilles musiques de l'époque de la Super-NES, GameBoy, MegaDrive, etc. :)


Trouver des MIDI



Google "Free Midi"
Etonnant non ? ^^

On trouve des tooooonnes de MIDI sur le net. Je m'en fais pas pour vous, vous trouverez votre bonheur !
Personnellement, j'ai retenu MusicRobot.com, un moteur de recherche pour fichiers MIDI.

Image utilisateur
Le moteur de recherche de fichiers MIDI MusicRobot.com
(ici, à la recherche d'un MIDI de Mario)


Personnellement, j'ai récupéré la musique de Mario (ah les souvenirs :D ). Vous pouvez la télécharger pour vos tests si vous le voulez.


Les étapes à suivre pour jouer un MIDI



Les fonctions pour jouer des MIDI commencent par le préfixe FMUSIC au lieu de FSOUND.
Toutefois, les fonctions de chargement et de déchargement de FMOD à utiliser restent les mêmes, et elles ont bien le préfixe FSOUND.

Bon vous commencez à avoir l'habitude alors je vais aller un peu plus vite maintenant dans le listing des fonctions ;)


Le pointeur



Code : C
1
FMUSIC_MODULE *musique = NULL;



Charger un MIDI



Code : C
1
musique = FMUSIC_LoadSong("mario.mid");


La fonction prend un seul paramètre, comme vous le voyez c'est encore plus simple.
Elle renvoie NULL si le fichier n'a pas pu être chargé.


Jouer un MIDI



Code : C
1
FMUSIC_PlaySong(musique);



Répéter un MIDI



Code : C
1
FMUSIC_SetLooping(musique, 1);


Cette fois, c'est un peu différent. Il faut envoyer 1 (VRAI) pour que la musique soit répétée à l'infini.


Mettre en pause un MIDI



La fonction FMUSIC_GetPaused indique si la chanson est en pause ou pas.

Code : C
1
FMUSIC_GetPaused(musique);


La fonction FMUSIC_SetPaused met en pause ou réactive la lecture de la chanson.

Code : C
1
FMUSIC_SetPaused(musique, 1);


Envoyez 1 pour mettre en pause, 0 pour relancer la lecture.

Exemple de code gérant la pause si on appuie sur P :

Code : C
1
2
3
4
5
6
7
8
case SDL_KEYDOWN:
    if (event.key.keysym.sym == SDLK_p) //Si on appuie sur P
    {
        if (FMUSIC_GetPaused(musique)) // Si la chanson est en pause
            FMUSIC_SetPaused(musique, 0); // On enlève la pause
        else // Sinon, elle est en cours de lecture
            FMUSIC_SetPaused(musique, 1); // On active la pause
    }


Attention : bien que similaire, ce code est différent du code de pause qu'on a vu tout à l'heure. En particulier, il n'y a pas de canal à indiquer ici.



Modifier le volume



Code : C
1
FMUSIC_SetMasterVolume(musique, 150);


Le second paramètre correspond au volume.


Stopper la lecture



Code : C
1
FMUSIC_StopSong(musique);


Libérer la musique MIDI



Code : C
1
FMUSIC_FreeSong(musique);



Code d'exemple pour résumer



Code : C
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
int main(int argc, char *argv[])
{
    SDL_Surface *ecran = NULL, *niveau = NULL;
    SDL_Event event;
    SDL_Rect position;
    int continuer = 1;
    FMUSIC_MODULE *musique = NULL;

    FSOUND_Init(44100, 32, 0);
    musique = FMUSIC_LoadSong("mario.mid"); // Chargement de la chanson
    if (musique == NULL)
    {
        fprintf(stderr, "Impossible de lire mario.mid\n");
        exit(EXIT_FAILURE);
    }
    FMUSIC_SetLooping(musique, 1); // Répétition infinie
    FMUSIC_PlaySong(musique); // On joue la chanson


    SDL_Init(SDL_INIT_VIDEO);

    ecran = SDL_SetVideoMode(640, 480, 32, SDL_HWSURFACE | SDL_DOUBLEBUF);
    SDL_WM_SetCaption("Gestion du son avec FMOD", NULL);
    niveau = IMG_Load("mario_niveau.jpg"); // Je me permets de mettre une petite image de fond ^^
    position.x = 0;
    position.y = 0;


    while (continuer)
    {
        SDL_WaitEvent(&event);
        switch(event.type)
        {
            case SDL_QUIT:
                continuer = 0;
                break;
            case SDL_KEYDOWN:
                if (event.key.keysym.sym == SDLK_p) //Si on appuie sur P
                {
                    if (FMUSIC_GetPaused(musique)) // Si la chanson est en pause
                        FMUSIC_SetPaused(musique, 0); // On enlève la pause
                    else // Sinon, elle est en cours de lecture
                        FMUSIC_SetPaused(musique, 1); // On active la pause
                }
                break;
        }

        SDL_FillRect(ecran, NULL, SDL_MapRGB(ecran->format, 0, 0, 0));
        SDL_BlitSurface(niveau, NULL, ecran, &position);
        SDL_Flip(ecran);
    }

    FMUSIC_FreeSong(musique); // Déchargement de la chanson
    FSOUND_Close();

    SDL_FreeSurface(niveau);
    SDL_Quit();

    return EXIT_SUCCESS;
}


Ce code reprend les fonctions principales qu'on vient de voir.
J'ai même mis une image de fond pour l'ambiance ^^

Image utilisateur
Oui oui il y a la musique de Mario en fond !
(mais n'allez pas croire que c'est un jeu, c'est juste une image !)


Bien sûr, c'est mieux quand on a la musique en fond derrière ^^
Je vous propose donc de voir ce que ça donne en vidéo.

La musique MIDI de Mario (240 Ko)
(la compression Flash a un peu déterioré le son désolé :-° )


Bien sûr, ce n'est pas un vrai jeu, rien ne bouge, mais on s'y croirait ! Et puis, rien n'empêche de le coder, ce jeu ;)

Q.C.M.

Pourquoi les sons longs (musiques type MP3) ne doivent pas être chargés avec la fonction FSOUND_Sample_Load ?
J'utilise 2 sons dans mon programme : l'un est échantillonné sur 22 050 Hz, l'autre sur 11 025 Hz.
Quelle est la fréquence d'échantillonnage la plus adaptée que je dois donner à la fonction FSOUND_Init si je veux que la qualité de ces 2 sons reste maximale ?
A quoi correspond un volume de 255 envoyé à la fonction &lt;italique&gt;FSOUND_SetVolume&lt;/italique&gt; ?
Pourquoi les fichiers MIDI sont-ils si légers ?

Statistiques de réponses au QCM


Ce chapitre devrait vous avoir permis de démarrer dans la manipulation du son dans vos programmes (du moins je l'espère ^^ ). Que vous vouliez créer un jeu, un lecteur MP3 ou même un simple programme utilitaire, vous aurez la plupart du temps besoin de faire appel à une librairie comme FMOD pour gérer le son.

Il faut reconnaître que tout cela n'est pas bien compliqué. Il faut juste savoir quelles fonctions utiliser dans le bon ordre et savoir gérer la mémoire correctement (c'est-à-dire utiliser les fonctions de lecture streamées sur des sons longs par exemple).

Toutefois, nous n'avons pas vu toutes les fonctionnalités de FMOD, loin de là ! La librairie gère de nombreux effets audio (écho, distorsion, effets de son 3D...), l'enregistrement, et bien d'autres choses encore ! Comme je ne peux pas tout vous détailler, je vous recommande de lire la documentation de FMOD.
A votre stade, il est vraiment primordial que vous commenciez à être capable de lire des documentations. N'ayez pas peur, la doc ne vous mangera pas :p Vous y découvrirez toutes les fonctions que propose la librairie, ce qui vous permettra de vous perfectionner encore plus :)
Chapitre précédent Sommaire Chapitre suivant
Retour en haut Retour en haut


Créé : le 29/07/2005 à 00:29:36
Modifié : le 13/09/2008 à 17:07:06
Avancement : 100%
Licence : Copie non autorisée

Changer de design | En savoir plus | Plan du site | Politique d'accessibilité | Règles | RSS tutoriels | RSS news
Édité par Simple IT SARL : Nous contacter | Notre blog | Revue de presse | Publicité

Y'a plus rien à lire, faut remonter maintenant !

Hébergement web - Correction de tutoriels - Créer un site
Vous souhaitez apparaître ici ? Contactez-nous.

Nombre de connectés 351 Zéros connectés | Requêtes SQL 8 requêtes | Temps de génération de la page : Total (SQL) 0.0613s (0.0192s)