Some conditional compiletime options to keep windows happy.
[bcl.git] / 3daudio.c
blobb6fc4e128ec8868c6178dbf7ea809de7c60b6a55
1 #include <stdlib.h>
2 #include <string.h>
3 #ifndef _WIN32
4 #include <AL/al.h>
5 #include <AL/alc.h>
6 #include <AL/alure.h>
7 #else
8 #include <alure.h>
9 #include <al.h>
10 #include <alc.h>
11 #endif
12 #include "bcl.h"
14 typedef struct {
15 char * fileName;
16 ALuint bufId;
17 int count;
18 } clip;
20 ALCdevice *device;
21 ALCcontext *context;
22 clip * clips;
23 ALuint * sources;
24 int clipsSize=20;
25 int sourcesSize=20;
26 int numClips;
27 int numSources;
29 int addClip(clip c) {
30 if (numClips>=clipsSize) {
31 clips = realloc(clips,clipsSize*2*sizeof(clip));
32 clipsSize*=2;
34 clips[numClips] = c;
35 numClips++;
36 return numClips-1;
39 void removeClip(int pos) {
40 free(clips[pos].fileName);
41 for (;pos<numClips;pos++)
42 clips[pos]=clips[pos+1];
43 numClips--;
44 if (numClips>0&&numClips <clipsSize/4) {
45 clips = realloc(clips,clipsSize/4*sizeof(clip));
46 clipsSize/=4;
50 int findClipstr(char * name) {
51 int i = 0;
52 for (;i<numClips;i++)
53 if (strcmp(name,clips[i].fileName)==0)
54 return i;
55 return -1;
58 int findClipi(int id) {
59 int i = 0;
60 for (;i<numClips;i++)
61 if (clips[i].bufId==id)
62 return i;
63 return -1;
66 int addSource(ALuint id) {
67 if (numSources>=sourcesSize) {
68 sources = realloc(sources,sizeof(ALuint)*sourcesSize*2);
69 sourcesSize*=2;
71 sources[numSources]=id;
72 numSources++;
73 return numSources -1;
76 void removeSource(int pos) {
77 for (;pos<numSources;pos++)
78 sources[pos]=sources[pos+1];
79 if (numSources>0&&numSources<sourcesSize/4) {
80 sources = realloc(sources,sizeof(ALuint)*sourcesSize/4);
81 sourcesSize/=4;
85 int findSource(int id) {
86 int i;
87 for (i = 0; i < numSources;i++)
88 if (sources[i]==id)
89 return i;
90 return -1;
93 DECLSPEC void init3dAudio() {
94 int attrlist[3];
95 attrlist[0] = ALC_FREQUENCY;
96 attrlist[1] = 44100;
97 attrlist[2] = 0;
98 device = alcOpenDevice(NULL);
99 context = alcCreateContext(device, attrlist);
100 alcMakeContextCurrent(context);
101 numClips = 0;
102 numSources = 0;
103 clips = malloc(sizeof(clip)*clipsSize);
104 sources = malloc(sizeof(ALuint)*sourcesSize);
107 DECLSPEC void terminate3dAudio() {
108 int i;
109 alDeleteSources(numSources,sources);
110 for (i = 0; i < numClips;i++) {
111 free(clips[i].fileName);
112 alDeleteBuffers(1,&clips[i].bufId);
114 free(clips);
115 free(sources);
116 alcDestroyContext(context);
117 alcCloseDevice(device);
120 DECLSPEC int load3dSound(char * file) {
121 int pos = findClipstr(file);
122 ALuint bufid;
123 if (pos==-1) {
125 ALsizei size;
126 ALsizei bits;
127 ALsizei freq;
128 ALenum format;
129 ALvoid *wave=0;
131 alGenBuffers(1,&bufid);
132 alutLoadWAVFile((ALbyte*)file, &format, &wave, &size, &freq, 0);
133 alBufferData(bufid,format,wave,size,freq);
134 free(wave);
136 bufid = alureCreateBufferFromFile(file);
137 clip c= {strdup(file),bufid,0};
138 pos = addClip(c);
140 else
141 bufid = clips[pos].bufId;
142 ALuint soundid;
143 alGenSources(1, &soundid);
144 alSourcei(soundid, AL_BUFFER, bufid);
145 addSource(soundid);
146 clips[pos].count++;
147 return soundid;
150 DECLSPEC void unload3dSound(int sound) {
151 int id,pos;
152 alGetSourcei(sound,AL_BUFFER,&id);
153 pos = findClipi(id);
154 removeSource(sound);
155 alDeleteSources(1, &sound);
156 clips[pos].count--;
157 if (clips[pos].count==0)
158 removeClip(pos);
161 DECLSPEC void set3dSoundPosition(int sound, float x, float y, float z) {
162 alSource3f(sound,AL_POSITION,x,y,z);
165 DECLSPEC void set3dSoundPitch(int sound, float pitch) {
166 alSourcef(sound,AL_PITCH,pitch);
169 DECLSPEC void play3dSound(int sound) {
170 alSourcei(sound,AL_LOOPING,AL_FALSE);
171 alSourcePlay(sound);
174 DECLSPEC void loop3dSound(int sound) {
175 alSourcei(sound,AL_LOOPING,AL_TRUE);
176 alSourcePlay(sound);
179 DECLSPEC void stop3dSound(int sound) {
180 alSourceStop(sound);