下面是一个用stream打开MP3文件的例子。MSITStore:FMOD%20SoundSystemFMOD%20Programmers%20API%20Win32documentationfmodex.chm::/HTML/FMOD_System_CreateStream.html;">System::createStream函数将打开文件并预缓冲小部分数据,然后就可以在MSITStore:FMOD%20SoundSystemFMOD%20Programmers%20API%20Win32documentationfmodex.chm::/HTML/FMOD_System_PlaySound.html;">System::playSound调用时直接播放了。
FMOD::Sound *sound; // FMOD_DEFAULT等效于FMOD_LOOP_OFF | FMOD_2D | FMOD_HARDWARE. result = system->createStream("../media/wave.mp3", FMOD_DEFAULT, 0, &sound);
ERRCHECK(result);
指定用软件混合就必须使用MSITStore:FMOD%20SoundSystemFMOD%20Programmers%20API%20Win32documentationfmodex.chm::/HTML/FMOD_MODE.html;">FMOD_SOFTWARE标记。如果你想要使用如DSP effects、spectrum analysis、getwavedata、point to point looping和其它更多的高级技术,就必须使用软件混合。
FMOD::Sound *sound; // 使用软件混合 result = system->createSound("../media/wave.mp3", FMOD_SOFTWARE, 0, &sound);
ERRCHECK(result);
下一个例子是将MP3以sample的形式载入内存而不解压,使用 MSITStore:FMOD%20SoundSystemFMOD%20Programmers%20API%20Win32documentationfmodex.chm::/HTML/FMOD_MODE.html;">FMOD_CREATECOMPRESSEDSAMPLE标记。此时如果没有指定MSITStore:FMOD%20SoundSystemFMOD%20Programmers%20API%20Win32documentationfmodex.chm::/HTML/FMOD_MODE.html;">FMOD_HARDWARE或MSITStore:FMOD%20SoundSystemFMOD%20Programmers%20API%20Win32documentationfmodex.chm::/HTML/FMOD_MODE.html;">FMOD_SOFTWARE,将默认为软件混合。硬件声音回放不支持这个标记,除非格式为ADPCM on Xbox、VAG on PS2/PSP或GCADPCM on Gamecube/Wii。 Platforms like PS3 and Xbox 360 are all done one the cpu (usually a different core to the main cpu so it does not affect performance).
FMOD::Sound *sound; // FMOD_CREATECOMPRESSEDSAMPLE标记让sample先尝试直接播放(不解压到内存),但仅限于IMA ADPCM、MP2、MP3和XMA格式 result = system->createSound("../media/wave.mp3", FMOD_CREATECOMPRESSEDSAMPLE, 0, &sound); ERRCHECK(result);
警告!
必须谨慎使用这种模式,它看上去和PCM sample很相似,但它会在运行时导致巨大CPU开销。FMOD按照声音的压缩格式,在播放时对其进行解码。
现在,要播放sound或stream只需简单地调用MSITStore:FMOD%20SoundSystemFMOD%20Programmers%20API%20Win32documentationfmodex.chm::/HTML/FMOD_System_PlaySound.html;">System::playSound就行了。
FMOD::Channel *channel; result = system->playSound(FMOD_CHANNEL_FREE, sound, false, &channel); ERRCHECK(result);
此时,声音已经在后台播放了!而你的程序将继续执行。
关于playSound的注意事项: .
如果不需要的话,可以不必获取channel句柄,可以将其设为0或NULL。如果你不需要更改这个sound实例,或者这个声音很短(不循环),就可以省去它。例如:
result = system->playSound(FMOD_CHANNEL_FREE, sound, false, 0);
ERRCHECK(result);
.
可以在开始播放时暂停,这样就可以更改声音的属性而不会被用户听见,这就是“paused”参数的用处所在。例如,如果你将paused设为true,再设置音量为0.5,然后解除暂停,此时声音就会一一般的音量播放。但如果你是将paused设为false,而其它操作相同的话,你会听见声音开始时瞬间是全音量播放的,用户可不希望听到。
result = system->playSound(FMOD_CHANNEL_FREE, sound, true, &channel);
ERRCHECK(result);
// 暂停时设定音量
result = channel->setVolume(0.5f);
ERRCHECK(result);
// 声音从这里才开始播放
result = channel->setPaused(false);
ERRCHECK(result);
.
一个“channel”就是一个声音的实例。一个声音你可以同时播放多次,每次播放都会得到一个新的channel句柄,但stream除外,它只能同时播放一次,如果你尝试多次播放,只会重复播放当前stream并返回同上次一样的channel句柄。这是因为stream只有一个缓冲和一个文件句柄。要同时播放两个stream就必须打开两次再播放两次。 .
始终使用MSITStore:FMOD%20SoundSystemFMOD%20Programmers%20API%20Win32documentationfmodex.chm::/HTML/FMOD_CHANNELINDEX.html;">FMOD_CHANNEL_FREE。FMOD会使用通道管理器自动为你选择一个未使用的channel。如果希望使用一个现有的channel来播放,就使用MSITStore:FMOD%20SoundSystemFMOD%20Programmers%20API%20Win32documentationfmodex.chm::/HTML/FMOD_CHANNELINDEX.html;">FMOD_CHANNEL_REUSE标记,这样可以避免每次调用MSITStore:FMOD%20SoundSystemFMOD%20Programmers%20API%20Win32documentationfmodex.chm::/HTML/FMOD_System_PlaySound.html;">System::playSound函数都产生一个新的实例。 .
不需要“free”或“release”一个channel句柄。所有的channel都位于你使用System::init所创建的一个pool中。当声音停止后,channel可以被复用;如果所有的channel都处于播放状态,那么其中一个优先级最低的会被抢占。其实只需增大System::init中的通道数就可以避免发生这样的情况。 .
一个channel会在播放结束时即刻失效。这意味着你不能再对其进行更改,即使做了也没有实际意义,因为它不可能再播放了。绝大多数情况下,引用一个已失效的channel会导致一个FMOD_ERR_INVALID_HANDLE错误。 Update. (This is important!) 在每一帧中调用System::update函数是很重要的,但不需要多次调用,那样只会影响效率。 该函数用于更新FMOD Ex的以下内容:
.
Platform specific routines
例如向PS2的IOP发送一个frame command packet。在这个平台上,不调用update的话就听不到声音。
.
Virtual voice emulation 不调用update,虚拟声音就不会播放。 .
3D voice calculation
如果不调用update,就算channel或listener已经正确设置,也无法听到声音移动的3D音效。 .
Geometry engine FMOD的polygon/geometry引擎需要通过update来启用。否则用户定义的occlusion/obstruction特性将无法呈现。 .
Non realtime output
FMOD_OUTPUTTYPE_NOSOUND_NRT和FMOD_OUTPUTTYPE_WAVWRITER_NRT标记需要此函数才能更新到输出(如用FMOD_OUTPUTTYPE_WAVWRITER_NRT写出到文件)。 .
Streaming engine
如果指定了FMOD_INIT_STREAM_FROM_UPDATE标记,如果用户希望在主线程中自己驱动流引擎,就必须有规律地调用update,否则会导致抖动和缓冲溢出。 关闭 调用System::release函数来关闭输出设备并释放对象关联的内存。 你不必人工关闭channel和sound,这些都在System::release中自动完成。 当然,你也可以手动关闭它们,这是个很好的编程练习(虽然是多余的)。 如果你要释放system对象就不需要调用System::close函数了,在System::release中已经包含了对System::close的调用。 资源使用配制 在程序开发中,一些开发人员希望和其它程序一样用自己的函数来访问所有的磁盘或内存。 在FMOD Ex中你可以通过System::setFileSystem函数来设置FMOD文件系统使你自己的文件程序。
要让FMOD使用你的内存系统,或将FMOD限制在一个内存块中,使用Memory_Initialize。
注意!
在Xbox和XBox 360中,必须给FMOD提供一个块内存。Xbox 360上必须使用XPhysicalAlloc来分配这块内存。更多参见"Platform specific issues"。 |