Changeset 1784 for code/trunk/src/audio/AudioStream.cc
- Timestamp:
- Sep 15, 2008, 10:54:25 AM (16 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
code/trunk/src/audio/AudioStream.cc
r1747 r1784 26 26 * 27 27 */ 28 28 29 #include "AudioStream.h" 29 30 30 #include "util/Debug.h" 31 #include "util/Error.h"32 31 33 32 namespace audio 34 33 { 35 AudioStream::AudioStream(std::string path) 36 { 37 this->path = path; 38 loaded = false; 39 } 40 41 void AudioStream::open() 42 { 43 int result; 44 45 oggFile = fopen(path.c_str(), "rb"); 46 if(!oggFile) 47 { 48 orxonox::Error("Could not open Ogg file "+path); 49 return; 50 } 51 52 if((result = ov_open(oggFile, &oggStream, NULL, 0)) < 0) 53 { 54 fclose(oggFile); 55 orxonox::Error("Could not open Ogg stream. " + errorString(result)); 56 return; 57 } 58 59 loaded = true; 60 61 vorbisInfo = ov_info(&oggStream, -1); 62 vorbisComment = ov_comment(&oggStream, -1); 63 64 if(vorbisInfo->channels == 1) 65 format = AL_FORMAT_MONO16; 66 else 67 format = AL_FORMAT_STEREO16; 68 69 70 alGenBuffers(2, buffers); 71 check(); 72 alGenSources(1, &source); 73 check(); 74 75 alSource3f(source, AL_POSITION, 0.0, 0.0, 0.0); 76 alSource3f(source, AL_VELOCITY, 0.0, 0.0, 0.0); 77 alSource3f(source, AL_DIRECTION, 0.0, 0.0, 0.0); 78 alSourcef (source, AL_ROLLOFF_FACTOR, 0.0 ); 79 alSourcei (source, AL_SOURCE_RELATIVE, AL_FALSE ); 80 } 81 82 83 84 85 void AudioStream::release() 86 { 87 88 alSourceStop(source); 89 empty(); 90 alDeleteSources(1, &source); 91 check(); 92 alDeleteBuffers(1, buffers); 93 check(); 94 95 ov_clear(&oggStream); 96 loaded = false; 97 98 } 99 100 101 102 103 void AudioStream::display() 104 { 105 if (loaded) 106 { 107 COUT(3) 108 << "version " << vorbisInfo->version << std::endl 109 << "channels " << vorbisInfo->channels << std::endl 110 << "rate (hz) " << vorbisInfo->rate << std::endl 111 << "bitrate upper " << vorbisInfo->bitrate_upper << std::endl 112 << "bitrate nominal " << vorbisInfo->bitrate_nominal << std::endl 113 << "bitrate lower " << vorbisInfo->bitrate_lower << std::endl 114 << "bitrate window " << vorbisInfo->bitrate_window << std::endl 115 << std::endl 116 << "vendor " << vorbisComment->vendor << std::endl; 117 118 for(int i = 0; i < vorbisComment->comments; i++) 119 { 120 COUT(3) << " " << vorbisComment->user_comments[i] << std::endl; 121 } 122 123 COUT(3) << std::endl; 124 } 125 } 126 127 128 129 130 bool AudioStream::playback() 131 { 132 if (!loaded) 133 { 134 return false; 135 } 136 137 if(playing()) 138 return true; 139 140 if(!stream(buffers[0])) 141 return false; 142 143 if(!stream(buffers[1])) 144 return false; 145 146 alSourceQueueBuffers(source, 2, buffers); 147 alSourcePlay(source); 148 149 return true; 150 } 151 152 153 154 155 bool AudioStream::playing() 156 { 157 if (!loaded) 158 { 159 return false; 160 } 161 162 ALenum state; 163 alGetSourcei(source, AL_SOURCE_STATE, &state); 164 return (state == AL_PLAYING); 165 } 166 167 168 169 170 bool AudioStream::update() 171 { 172 int processed; 173 bool active = true; 174 175 alGetSourcei(source, AL_BUFFERS_PROCESSED, &processed); 176 177 while(processed--) 178 { 179 ALuint buffer; 180 181 alSourceUnqueueBuffers(source, 1, &buffer); 182 check(); 183 184 active = stream(buffer); 185 186 alSourceQueueBuffers(source, 1, &buffer); 187 check(); 188 } 189 190 if (active==false) 191 { 192 loaded = false; 193 } 194 return active; 195 } 196 197 198 199 200 bool AudioStream::stream(ALuint buffer) 201 { 202 char pcm[BUFFER_SIZE]; 203 int size = 0; 204 int section; 205 int result; 206 207 while(size < BUFFER_SIZE) 208 { 209 result = ov_read(&oggStream, pcm + size, BUFFER_SIZE - size, 0, 2, 1, §ion); 210 211 if(result > 0) 212 size += result; 213 else 214 if(result < 0) 215 orxonox::Error(errorString(result)); 216 else 217 break; 218 } 219 220 if(size == 0) 221 return false; 222 223 alBufferData(buffer, format, pcm, size, vorbisInfo->rate); 224 check(); 225 226 return true; 227 } 228 229 230 231 void AudioStream::empty() 232 { 233 int queued; 234 235 alGetSourcei(source, AL_BUFFERS_QUEUED, &queued); 236 237 while(queued--) 238 { 239 ALuint buffer; 240 241 alSourceUnqueueBuffers(source, 1, &buffer); 242 check(); 243 } 244 } 245 246 247 248 249 void AudioStream::check() 250 { 251 int error = alGetError(); 252 253 if(error != AL_NO_ERROR) 254 orxonox::Error("OpenAL error was raised."); 255 } 256 257 258 259 std::string AudioStream::errorString(int code) 260 { 261 switch(code) 262 { 263 case OV_EREAD: 264 return std::string("Read from media."); 265 case OV_ENOTVORBIS: 266 return std::string("Not Vorbis data."); 267 case OV_EVERSION: 268 return std::string("Vorbis version mismatch."); 269 case OV_EBADHEADER: 270 return std::string("Invalid Vorbis header."); 271 case OV_EFAULT: 272 return std::string("Internal logic fault (bug or heap/stack corruption."); 273 default: 274 return std::string("Unknown Ogg error."); 275 } 276 } 34 AudioStream::AudioStream(std::string path) 35 { 36 this->path = path; 37 loaded = false; 38 } 39 40 void AudioStream::open() 41 { 42 int result; 43 44 oggFile = fopen(path.c_str(), "rb"); 45 if (!oggFile) 46 { 47 COUT(2) << "AudioStream: Could not open Ogg file " << path << std::endl; 48 return; 49 } 50 51 if ((result = ov_open(oggFile, &oggStream, NULL, 0)) < 0) 52 { 53 fclose(oggFile); 54 COUT(2) << "AudioStream: Could not open Ogg stream. " << errorString(result) << std::endl; 55 return; 56 } 57 58 loaded = true; 59 60 vorbisInfo = ov_info(&oggStream, -1); 61 vorbisComment = ov_comment(&oggStream, -1); 62 63 if (vorbisInfo->channels == 1) 64 format = AL_FORMAT_MONO16; 65 else 66 format = AL_FORMAT_STEREO16; 67 68 69 alGenBuffers(2, buffers); 70 check(); 71 alGenSources(1, &source); 72 check(); 73 74 alSource3f(source, AL_POSITION, 0.0, 0.0, 0.0); 75 alSource3f(source, AL_VELOCITY, 0.0, 0.0, 0.0); 76 alSource3f(source, AL_DIRECTION, 0.0, 0.0, 0.0); 77 alSourcef (source, AL_ROLLOFF_FACTOR, 0.0 ); 78 alSourcei (source, AL_SOURCE_RELATIVE, AL_FALSE ); 79 } 80 81 82 83 void AudioStream::release() 84 { 85 alSourceStop(source); 86 empty(); 87 alDeleteSources(1, &source); 88 check(); 89 alDeleteBuffers(1, buffers); 90 check(); 91 92 ov_clear(&oggStream); 93 loaded = false; 94 } 95 96 97 98 void AudioStream::display() 99 { 100 if (loaded) 101 { 102 COUT(3) 103 << "version " << vorbisInfo->version << std::endl 104 << "channels " << vorbisInfo->channels << std::endl 105 << "rate (hz) " << vorbisInfo->rate << std::endl 106 << "bitrate upper " << vorbisInfo->bitrate_upper << std::endl 107 << "bitrate nominal " << vorbisInfo->bitrate_nominal << std::endl 108 << "bitrate lower " << vorbisInfo->bitrate_lower << std::endl 109 << "bitrate window " << vorbisInfo->bitrate_window << std::endl 110 << std::endl 111 << "vendor " << vorbisComment->vendor << std::endl; 112 113 for (int i = 0; i < vorbisComment->comments; i++) 114 { 115 COUT(3) << " " << vorbisComment->user_comments[i] << std::endl; 116 } 117 118 COUT(3) << std::endl; 119 } 120 } 121 122 123 124 bool AudioStream::playback() 125 { 126 if (!loaded) 127 { 128 return false; 129 } 130 131 if (playing()) 132 return true; 133 134 if (!stream(buffers[0])) 135 return false; 136 137 if (!stream(buffers[1])) 138 return false; 139 140 alSourceQueueBuffers(source, 2, buffers); 141 alSourcePlay(source); 142 143 return true; 144 } 145 146 147 148 149 bool AudioStream::playing() 150 { 151 if (!loaded) 152 { 153 return false; 154 } 155 156 ALenum state; 157 alGetSourcei(source, AL_SOURCE_STATE, &state); 158 return (state == AL_PLAYING); 159 } 160 161 162 163 164 bool AudioStream::update() 165 { 166 int processed; 167 bool active = true; 168 169 alGetSourcei(source, AL_BUFFERS_PROCESSED, &processed); 170 171 while (processed--) 172 { 173 ALuint buffer; 174 175 alSourceUnqueueBuffers(source, 1, &buffer); 176 check(); 177 178 active = stream(buffer); 179 180 alSourceQueueBuffers(source, 1, &buffer); 181 check(); 182 } 183 184 if (active==false) 185 { 186 loaded = false; 187 } 188 return active; 189 } 190 191 192 193 194 bool AudioStream::stream(ALuint buffer) 195 { 196 char pcm[BUFFER_SIZE]; 197 int size = 0; 198 int section; 199 int result; 200 201 while (size < BUFFER_SIZE) 202 { 203 result = ov_read(&oggStream, pcm + size, BUFFER_SIZE - size, 0, 2, 1, §ion); 204 205 if (result > 0) 206 size += result; 207 else 208 if (result < 0) 209 COUT(2) << "AudioStream: " << errorString(result) << std::endl; 210 else 211 break; 212 } 213 214 if (size == 0) 215 return false; 216 217 alBufferData(buffer, format, pcm, size, vorbisInfo->rate); 218 check(); 219 220 return true; 221 } 222 223 224 225 void AudioStream::empty() 226 { 227 int queued; 228 229 alGetSourcei(source, AL_BUFFERS_QUEUED, &queued); 230 231 while (queued--) 232 { 233 ALuint buffer; 234 235 alSourceUnqueueBuffers(source, 1, &buffer); 236 check(); 237 } 238 } 239 240 241 242 243 void AudioStream::check() 244 { 245 int error = alGetError(); 246 247 if (error != AL_NO_ERROR) 248 COUT(2) << "AudioStream: OpenAL error was raised." << std::endl; 249 } 250 251 252 253 std::string AudioStream::errorString(int code) 254 { 255 switch (code) 256 { 257 case OV_EREAD: 258 return std::string("Read from media."); 259 case OV_ENOTVORBIS: 260 return std::string("Not Vorbis data."); 261 case OV_EVERSION: 262 return std::string("Vorbis version mismatch."); 263 case OV_EBADHEADER: 264 return std::string("Invalid Vorbis header."); 265 case OV_EFAULT: 266 return std::string("Internal logic fault (bug or heap/stack corruption."); 267 default: 268 return std::string("Unknown Ogg error."); 269 } 270 } 277 271 } 278 272
Note: See TracChangeset
for help on using the changeset viewer.