Difference between revisions of "Sound/ru"
m (Improved syntax highlighting) |
m (Some additional info) |
||
Line 28: | Line 28: | ||
SDK содержит следующие вспомогательные [http://websvn.kolibrios.org/listing.php?repname=Kolibri+OS&path=%2Fprograms%2Fdevelop%2Fsdk%2Ftrunk%2Fsound%2Fsrc%2F&#a375d81500982fc566688f871656e47fa библиотеки]: | SDK содержит следующие вспомогательные [http://websvn.kolibrios.org/listing.php?repname=Kolibri+OS&path=%2Fprograms%2Fdevelop%2Fsdk%2Ftrunk%2Fsound%2Fsrc%2F&#a375d81500982fc566688f871656e47fa библиотеки]: | ||
− | + | == init.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall InitSound(int *version); | ||
_InitSound@4: ;p_ver:dword | _InitSound@4: ;p_ver:dword | ||
+ | ; int _stdcall CreateBuffer(unsigned int format,int size,SNDBUF *buf); | ||
_CreateBuffer@12: ;format:dword,size:dword,p_str:dword | _CreateBuffer@12: ;format:dword,size:dword,p_str:dword | ||
+ | ; int _stdcall DestroyBuffer(SNDBUF hBuff); | ||
_DestroyBuffer@4: ;str:dword | _DestroyBuffer@4: ;str:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == setbuf.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall SetBuffer(SNDBUF hBuff,void* buff, int offs, int size); | ||
_SetBuffer@16: ;str:dword, src:dword, offs:dword, size:dword | _SetBuffer@16: ;str:dword, src:dword, offs:dword, size:dword | ||
+ | ; int _stdcall PlayBuffer(SNDBUF hBuff,unsigned int flags); | ||
_PlayBuffer@8: ;str:dword,flags:dword | _PlayBuffer@8: ;str:dword,flags:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndgetfmt.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall GetFormat(SNDBUF hBuff, unsigned int *format); | ||
_GetFormat@8: ;str:dword, p_fmt:dword | _GetFormat@8: ;str:dword, p_fmt:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndgetmvol.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall GetMasterVol(int* vol); | ||
proc _GetMasterVol@4 stdcall, pvol:dword | proc _GetMasterVol@4 stdcall, pvol:dword | ||
proc _GetDevInfo@8 stdcall, hSrv:dword, p_info:dword | proc _GetDevInfo@8 stdcall, hSrv:dword, p_info:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndgetpan.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall GetPan(SNDBUF hBuff, int *pan); | ||
_GetPan@8: ;str:dword, p_pan:dword | _GetPan@8: ;str:dword, p_pan:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndgetpos.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall GetBufferPos(SNDBUF hBuff, int *offset); | ||
_GetBufferPos@8: ;str:dword, p_pos:dword | _GetBufferPos@8: ;str:dword, p_pos:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndgetsize.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall GetBufferSize(SNDBUF hBuff, int *size); | ||
_GetBufferSize@8: ;str:dword, p_size:dword | _GetBufferSize@8: ;str:dword, p_size:dword | ||
+ | ; int _stdcall GetBufferFree(SNDBUF hBuff, int *free); | ||
_GetBufferFree@8: ;str:dword, p_free:dword | _GetBufferFree@8: ;str:dword, p_free:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndgetvol.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall GetVolume(SNDBUF hBuff, int *left, int *right); | ||
proc _GetVolume@12 stdcall, str:dword, pleft:dword,pright:dword | proc _GetVolume@12 stdcall, str:dword, pleft:dword,pright:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndout.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall WaveOut(SNDBUF hBuff,void *buff, int size); | ||
_WaveOut@12: ;str:dword, src:dword, size:dword | _WaveOut@12: ;str:dword, src:dword, size:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndreset.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall ResetBuffer(SNDBUF hBuff, unsigned int flags); | ||
_ResetBuffer@8: ;str:dword, flags:dword | _ResetBuffer@8: ;str:dword, flags:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndsetfmt.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall SetFormat(SNDBUF hBuff, unsigned int format); | ||
_SetFormat@8: ;str:dword, fmt:dword | _SetFormat@8: ;str:dword, fmt:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | Устанавливает новый формат звукового буфера. Применимо для PCM_OUT и PCM_STATIC буферов. | |
+ | == sndsetmvol.asm == | ||
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall SetMasterVol(int vol); | ||
_SetMasterVol@4: ;vol:dword | _SetMasterVol@4: ;vol:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndsetpan.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall SetPan(SNDBUF hBuff, int pan); | ||
_SetPan@8: ;str:dword, pan:dword | _SetPan@8: ;str:dword, pan:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | Устанавливает баланс левого и правого каналов. Баланс задаётся в сотых долях децибела в диапазоне -10000 - 10000, где | |
+ | -10000 - тишина в правом канале | ||
+ | 10000 - тишина в левом канале | ||
+ | 0 - нормальный баланс каналов | ||
+ | == sndsetpos.asm == | ||
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall SetBufferPos(SNDBUF hBuff, int offset); | ||
_SetBufferPos@8: ;str:dword, offs:dword | _SetBufferPos@8: ;str:dword, offs:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == sndsetvol.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall SetVolume(SNDBUF hBuff, int left, int right); | ||
_SetVolume@12: ;str:dword, lvol:dword,rvol:dword | _SetVolume@12: ;str:dword, lvol:dword,rvol:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | Устанавливает уровень громкости для правого и левого каналов. Уровень задаётся как ослабление сигнала в сотых долях децибела в диапазоне 0 - -10000, где | |
+ | 0 - максимальная громкость | ||
+ | -10000 (-100dB) - полная тишина | ||
+ | == stopbuf.asm == | ||
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
+ | ; int _stdcall StopBuffer(SNDBUF hBuff); | ||
_StopBuffer@4: ;str:dword | _StopBuffer@4: ;str:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
− | + | == wavhdr.asm == | |
<syntaxhighlight lang="asm"> | <syntaxhighlight lang="asm"> | ||
proc _test_wav@4 stdcall, hdr:dword | proc _test_wav@4 stdcall, hdr:dword | ||
</syntaxhighlight> | </syntaxhighlight> | ||
+ | |||
+ | = Примеры = | ||
+ | |||
+ | == Инициализация == | ||
+ | <syntaxhighlight lang="c"> | ||
+ | #include <sound.h> | ||
+ | |||
+ | int err; | ||
+ | int version =-1; | ||
+ | |||
+ | if((err = InitSound(&version)) !=0 ){ | ||
+ | goto epic_fail; | ||
+ | }; | ||
+ | |||
+ | if( (SOUND_VERSION>(version&0xFFFF)) || | ||
+ | (SOUND_VERSION<(version >> 16))){ | ||
+ | goto epic_fail; | ||
+ | } | ||
+ | </syntaxhighlight> | ||
+ | |||
+ | == Звуковые буферы == | ||
+ | |||
+ | Создаём звуковой буфер. | ||
+ | Есть три вида буферов - статические (PCM_STATIC), потоковые (PCM_OUT) и кольцевые (PCM_RING). Самый простой для программирования - потоковый. Статический буфер не сильно отличается от буфера в DirectSound. SetBuffer заполняет буфер, GetBufferPos и SetBufferPos получают и устанавливают текущую позицию в буфере. Кольцевой буфер позволяет выводить звук с минимальной задержкой. Это аналог Direct Sound буфера с событиями, поделённого на две части. | ||
+ | |||
+ | <syntaxhighlight lang="c"> | ||
+ | SNDBUF hBuff; | ||
+ | void* buffer; //семплы в формате snd_format | ||
+ | int buffer_size; // размер буфера в байтах | ||
+ | |||
+ | if((err = CreateBuffer(snd_format|PCM_OUT, 0, &hBuff)) != 0) | ||
+ | { | ||
+ | goto epic_fail; | ||
+ | }; | ||
+ | выводим звук | ||
+ | WaveOut(hBuff,buffer,buffer_size); | ||
+ | |||
+ | |||
+ | Для статического буфера размером 1Mб | ||
+ | if((err = CreateBuffer(snd_format|PCM_STATIC, 1024*1024, &hBuff)) != 0) | ||
+ | { | ||
+ | goto epic_fail; | ||
+ | }; | ||
+ | |||
+ | заполняем буфер | ||
+ | int offset; // смещение от начала звукового буфера | ||
+ | SetBuffer(hBuff, buffer, offset, buffer_size); | ||
+ | |||
+ | выводим звук асинхронно - функция возвращает управление немедленно | ||
+ | if((err = PlayBuffer(hBuff, 0)) !=0 ){ | ||
+ | goto exit_whith_error; | ||
+ | }; | ||
+ | синхронно - поток блокируется пока весь буфер не будет воспроизведён | ||
+ | if((err = PlayBuffer(hBuff, PLAY_SYNC)) !=0 ){ | ||
+ | goto exit_whith_error; | ||
+ | }; | ||
+ | </syntaxhighlight> | ||
+ | |||
+ | === Применение === | ||
+ | |||
+ | # Статический буфер: простая звуковая сигнализация, озвучка интерфейса и т.п. Позволяет одновременно использовать звуковые данные в разных форматах. | ||
+ | # Потоковый буфер: различные аудиоплееры. Программа загружает большие объёмы звуковых данных из сети, накопителей или генерирует их в реальном времени. | ||
+ | # Кольцевой буфер: игры и другие приложения с повышенными требованиями к синхронности аудио- и видеоряда. | ||
[[Category: Библиотеки]] | [[Category: Библиотеки]] |
Revision as of 11:29, 14 June 2012
Изначально Колибри унаследовала от Менуэт только звуковой драйвер для SoundBlaster, встроенный в ядро. Позже в (2005-2006) была написана полноценная звуковая подсистема Infinity, автор Сергей Семёнов aka Serge.
К сожалению какой либо внятной документации по Infinity нет, есть только исходники и файлы SDK.
Звуковая система Infinity содержит следующие сервисы:
SRV_GETVERSION equ 0
SND_CREATE_BUFF equ 1
SND_DESTROY_BUFF equ 2
SND_SETFORMAT equ 3
SND_GETFORMAT equ 4
SND_RESET equ 5
SND_SETPOS equ 6
SND_GETPOS equ 7
SND_SETBUFF equ 8
SND_OUT equ 9
SND_PLAY equ 10
SND_STOP equ 11
SND_SETVOLUME equ 12
SND_GETVOLUME equ 13
SND_SETPAN equ 14
SND_GETPAN equ 15
SND_GETBUFFSIZE equ 16
SND_GETFREESPACE equ 17
SND_SETTIMEBASE equ 18
SND_GETTIMESTAMP equ 19
SDK содержит следующие вспомогательные библиотеки:
init.asm
; int _stdcall InitSound(int *version);
_InitSound@4: ;p_ver:dword
; int _stdcall CreateBuffer(unsigned int format,int size,SNDBUF *buf);
_CreateBuffer@12: ;format:dword,size:dword,p_str:dword
; int _stdcall DestroyBuffer(SNDBUF hBuff);
_DestroyBuffer@4: ;str:dword
setbuf.asm
; int _stdcall SetBuffer(SNDBUF hBuff,void* buff, int offs, int size);
_SetBuffer@16: ;str:dword, src:dword, offs:dword, size:dword
; int _stdcall PlayBuffer(SNDBUF hBuff,unsigned int flags);
_PlayBuffer@8: ;str:dword,flags:dword
sndgetfmt.asm
; int _stdcall GetFormat(SNDBUF hBuff, unsigned int *format);
_GetFormat@8: ;str:dword, p_fmt:dword
sndgetmvol.asm
; int _stdcall GetMasterVol(int* vol);
proc _GetMasterVol@4 stdcall, pvol:dword
proc _GetDevInfo@8 stdcall, hSrv:dword, p_info:dword
sndgetpan.asm
; int _stdcall GetPan(SNDBUF hBuff, int *pan);
_GetPan@8: ;str:dword, p_pan:dword
sndgetpos.asm
; int _stdcall GetBufferPos(SNDBUF hBuff, int *offset);
_GetBufferPos@8: ;str:dword, p_pos:dword
sndgetsize.asm
; int _stdcall GetBufferSize(SNDBUF hBuff, int *size);
_GetBufferSize@8: ;str:dword, p_size:dword
; int _stdcall GetBufferFree(SNDBUF hBuff, int *free);
_GetBufferFree@8: ;str:dword, p_free:dword
sndgetvol.asm
; int _stdcall GetVolume(SNDBUF hBuff, int *left, int *right);
proc _GetVolume@12 stdcall, str:dword, pleft:dword,pright:dword
sndout.asm
; int _stdcall WaveOut(SNDBUF hBuff,void *buff, int size);
_WaveOut@12: ;str:dword, src:dword, size:dword
sndreset.asm
; int _stdcall ResetBuffer(SNDBUF hBuff, unsigned int flags);
_ResetBuffer@8: ;str:dword, flags:dword
sndsetfmt.asm
; int _stdcall SetFormat(SNDBUF hBuff, unsigned int format);
_SetFormat@8: ;str:dword, fmt:dword
Устанавливает новый формат звукового буфера. Применимо для PCM_OUT и PCM_STATIC буферов.
sndsetmvol.asm
; int _stdcall SetMasterVol(int vol);
_SetMasterVol@4: ;vol:dword
sndsetpan.asm
; int _stdcall SetPan(SNDBUF hBuff, int pan);
_SetPan@8: ;str:dword, pan:dword
Устанавливает баланс левого и правого каналов. Баланс задаётся в сотых долях децибела в диапазоне -10000 - 10000, где -10000 - тишина в правом канале 10000 - тишина в левом канале 0 - нормальный баланс каналов
sndsetpos.asm
; int _stdcall SetBufferPos(SNDBUF hBuff, int offset);
_SetBufferPos@8: ;str:dword, offs:dword
sndsetvol.asm
; int _stdcall SetVolume(SNDBUF hBuff, int left, int right);
_SetVolume@12: ;str:dword, lvol:dword,rvol:dword
Устанавливает уровень громкости для правого и левого каналов. Уровень задаётся как ослабление сигнала в сотых долях децибела в диапазоне 0 - -10000, где 0 - максимальная громкость -10000 (-100dB) - полная тишина
stopbuf.asm
; int _stdcall StopBuffer(SNDBUF hBuff);
_StopBuffer@4: ;str:dword
wavhdr.asm
proc _test_wav@4 stdcall, hdr:dword
Примеры
Инициализация
#include <sound.h>
int err;
int version =-1;
if((err = InitSound(&version)) !=0 ){
goto epic_fail;
};
if( (SOUND_VERSION>(version&0xFFFF)) ||
(SOUND_VERSION<(version >> 16))){
goto epic_fail;
}
Звуковые буферы
Создаём звуковой буфер. Есть три вида буферов - статические (PCM_STATIC), потоковые (PCM_OUT) и кольцевые (PCM_RING). Самый простой для программирования - потоковый. Статический буфер не сильно отличается от буфера в DirectSound. SetBuffer заполняет буфер, GetBufferPos и SetBufferPos получают и устанавливают текущую позицию в буфере. Кольцевой буфер позволяет выводить звук с минимальной задержкой. Это аналог Direct Sound буфера с событиями, поделённого на две части.
SNDBUF hBuff;
void* buffer; //семплы в формате snd_format
int buffer_size; // размер буфера в байтах
if((err = CreateBuffer(snd_format|PCM_OUT, 0, &hBuff)) != 0)
{
goto epic_fail;
};
выводим звук
WaveOut(hBuff,buffer,buffer_size);
Для статического буфера размером 1Mб
if((err = CreateBuffer(snd_format|PCM_STATIC, 1024*1024, &hBuff)) != 0)
{
goto epic_fail;
};
заполняем буфер
int offset; // смещение от начала звукового буфера
SetBuffer(hBuff, buffer, offset, buffer_size);
выводим звук асинхронно - функция возвращает управление немедленно
if((err = PlayBuffer(hBuff, 0)) !=0 ){
goto exit_whith_error;
};
синхронно - поток блокируется пока весь буфер не будет воспроизведён
if((err = PlayBuffer(hBuff, PLAY_SYNC)) !=0 ){
goto exit_whith_error;
};
Применение
- Статический буфер: простая звуковая сигнализация, озвучка интерфейса и т.п. Позволяет одновременно использовать звуковые данные в разных форматах.
- Потоковый буфер: различные аудиоплееры. Программа загружает большие объёмы звуковых данных из сети, накопителей или генерирует их в реальном времени.
- Кольцевой буфер: игры и другие приложения с повышенными требованиями к синхронности аудио- и видеоряда.