Merge branch 'music-cleanup' into music-sdlmixerx

This commit is contained in:
mazmazz 2018-08-26 14:04:54 -04:00
commit ed6ec14797
19 changed files with 1191 additions and 1104 deletions

View file

@ -55,90 +55,87 @@ void I_SetSfxVolume(INT32 volume)
(void)volume; (void)volume;
} }
// /// ------------------------
// MUSIC I/O // MUSIC SYSTEM
// /// ------------------------
UINT8 music_started = 0; UINT8 music_started = 0;
UINT8 digmusic_started = 0;
void I_InitMusic(void){} void I_InitMusic(void){}
void I_ShutdownMusic(void){} void I_ShutdownMusic(void){}
void I_PauseSong(INT32 handle) /// ------------------------
// MUSIC PROPERTIES
/// ------------------------
musictype_t I_SongType(void)
{ {
(void)handle; return MU_NONE;
} }
void I_ResumeSong(INT32 handle) boolean I_SongPlaying(void)
{ {
(void)handle; return false;
} }
// boolean I_SongPaused(void)
// MIDI I/O
//
UINT8 midimusic_started = 0;
void I_InitMIDIMusic(void){}
void I_ShutdownMIDIMusic(void){}
void I_SetMIDIMusicVolume(INT32 volume)
{ {
(void)volume; return false;
} }
INT32 I_RegisterSong(void *data, size_t len) /// ------------------------
{ // MUSIC EFFECTS
(void)data; /// ------------------------
(void)len;
return -1;
}
boolean I_PlaySong(INT32 handle, INT32 looping)
{
(void)handle;
(void)looping;
return false;
}
void I_StopSong(INT32 handle)
{
(void)handle;
}
void I_UnRegisterSong(INT32 handle)
{
(void)handle;
}
//
// DIGMUSIC I/O
//
UINT8 digmusic_started = 0;
void I_InitDigMusic(void){}
void I_ShutdownDigMusic(void){}
boolean I_StartDigSong(const char *musicname, INT32 looping)
{
(void)musicname;
(void)looping;
return false;
}
void I_StopDigSong(void){}
void I_SetDigMusicVolume(INT32 volume)
{
(void)volume;
}
boolean I_SetSongSpeed(float speed) boolean I_SetSongSpeed(float speed)
{ {
(void)speed; (void)speed;
return false; return false;
} }
/// ------------------------
// MUSIC PLAYBACK
/// ------------------------
UINT8 midimusic_started = 0;
boolean I_LoadSong(char *data, size_t len)
{
(void)data;
(void)len;
return -1;
}
void I_UnloadSong()
{
}
boolean I_PlaySong(boolean looping)
{
(void)handle;
(void)looping;
return false;
}
void I_StopSong(void)
{
(void)handle;
}
void I_PauseSong(void)
{
(void)handle;
}
void I_ResumeSong(void)
{
(void)handle;
}
void I_SetMusicVolume(INT32 volume)
{
(void)volume;
}

View file

@ -112,13 +112,10 @@ INT32 postimgparam;
postimg_t postimgtype2 = postimg_none; postimg_t postimgtype2 = postimg_none;
INT32 postimgparam2; INT32 postimgparam2;
boolean nomidimusic = false, nosound = false; // These variables are in effect
boolean nodigimusic = false; // No fmod-based music // whether the respective sound system is disabled
// or they're init'ed, but the player just toggled them
// These variables are only true if boolean midi_disabled = false;
// the respective sound system is initialized
// and active, but no sounds/music should play.
boolean music_disabled = false;
boolean sound_disabled = false; boolean sound_disabled = false;
boolean digital_disabled = false; boolean digital_disabled = false;
@ -1192,27 +1189,27 @@ void D_SRB2Main(void)
// setting up sound // setting up sound
if (dedicated) if (dedicated)
{ {
nosound = true; sound_disabled = true;
nomidimusic = nodigimusic = true; midi_disabled = digital_disabled = true;
} }
else else
{ {
CONS_Printf("S_Init(): Setting up sound.\n"); CONS_Printf("S_InitSfxChannels(): Setting up sound channels.\n");
} }
if (M_CheckParm("-nosound")) if (M_CheckParm("-nosound"))
nosound = true; sound_disabled = true;
if (M_CheckParm("-nomusic")) // combines -nomidimusic and -nodigmusic if (M_CheckParm("-nomusic")) // combines -nomidimusic and -nodigmusic
nomidimusic = nodigimusic = true; midi_disabled = digital_disabled = true;
else else
{ {
if (M_CheckParm("-nomidimusic")) if (M_CheckParm("-nomidimusic"))
nomidimusic = true; ; // WARNING: DOS version initmusic in I_StartupSound midi_disabled = true; ; // WARNING: DOS version initmusic in I_StartupSound
if (M_CheckParm("-nodigmusic")) if (M_CheckParm("-nodigmusic"))
nodigimusic = true; // WARNING: DOS version initmusic in I_StartupSound digital_disabled = true; // WARNING: DOS version initmusic in I_StartupSound
} }
I_StartupSound(); I_StartupSound();
I_InitMusic(); I_InitMusic();
S_Init(cv_soundvolume.value, cv_digmusicvolume.value, cv_midimusicvolume.value); S_InitSfxChannels(cv_soundvolume.value);
CONS_Printf("ST_Init(): Init status bar.\n"); CONS_Printf("ST_Init(): Init status bar.\n");
ST_Init(); ST_Init();

View file

@ -4057,11 +4057,9 @@ static void Command_RestartAudio_f(void)
// These must be called or no sound and music until manually set. // These must be called or no sound and music until manually set.
I_SetSfxVolume(cv_soundvolume.value); I_SetSfxVolume(cv_soundvolume.value);
I_SetDigMusicVolume(cv_digmusicvolume.value); S_SetMusicVolume(cv_digmusicvolume.value, cv_midimusicvolume.value);
I_SetMIDIMusicVolume(cv_midimusicvolume.value);
if (Playing()) // Gotta make sure the player is in a level if (Playing()) // Gotta make sure the player is in a level
P_RestoreMusic(&players[consoleplayer]); P_RestoreMusic(&players[consoleplayer]);
} }
/** Quits a game and returns to the title screen. /** Quits a game and returns to the title screen.

View file

@ -134,21 +134,12 @@ FUNCINLINE static ATTRINLINE int Volset(int vol)
void I_SetSfxVolume(INT32 volume) void I_SetSfxVolume(INT32 volume)
{ {
if (nosound) if (sound_disabled)
return; return;
set_volume (Volset(volume),-1); set_volume (Volset(volume),-1);
} }
void I_SetMIDIMusicVolume(INT32 volume)
{
if (nomidimusic)
return;
// Now set volume on output device.
set_volume (-1, Volset(volume));
}
// //
// Starting a sound means adding it // Starting a sound means adding it
// to the current list of active sounds // to the current list of active sounds
@ -169,7 +160,7 @@ INT32 I_StartSound ( sfxenum_t id,
{ {
int voice; int voice;
if (nosound) if (sound_disabled)
return 0; return 0;
// UNUSED // UNUSED
@ -190,7 +181,7 @@ void I_StopSound (INT32 handle)
// an setting the channel to zero. // an setting the channel to zero.
int voice=handle & (VIRTUAL_VOICES-1); int voice=handle & (VIRTUAL_VOICES-1);
if (nosound) if (sound_disabled)
return; return;
if (voice_check(voice)==S_sfx[handle>>VOICESSHIFT].data) if (voice_check(voice)==S_sfx[handle>>VOICESSHIFT].data)
@ -199,7 +190,7 @@ void I_StopSound (INT32 handle)
INT32 I_SoundIsPlaying(INT32 handle) INT32 I_SoundIsPlaying(INT32 handle)
{ {
if (nosound) if (sound_disabled)
return FALSE; return FALSE;
if (voice_check(handle & (VIRTUAL_VOICES-1))==S_sfx[handle>>VOICESSHIFT].data) if (voice_check(handle & (VIRTUAL_VOICES-1))==S_sfx[handle>>VOICESSHIFT].data)
@ -229,7 +220,7 @@ void I_UpdateSoundParams( INT32 handle,
int voice=handle & (VIRTUAL_VOICES-1); int voice=handle & (VIRTUAL_VOICES-1);
int numsfx=handle>>VOICESSHIFT; int numsfx=handle>>VOICESSHIFT;
if (nosound) if (sound_disabled)
return; return;
if (voice_check(voice)==S_sfx[numsfx].data) if (voice_check(voice)==S_sfx[numsfx].data)
@ -270,17 +261,17 @@ void I_StartupSound(void)
char err[255]; char err[255];
#endif #endif
if (nosound) if (sound_disabled)
sfxcard=DIGI_NONE; sfxcard=DIGI_NONE;
else else
sfxcard=DIGI_AUTODETECT; sfxcard=DIGI_AUTODETECT;
if (nomidimusic) if (midi_disabled)
midicard=MIDI_NONE; midicard=MIDI_NONE;
else else
midicard=MIDI_AUTODETECT; //DetectMusicCard(); midicard=MIDI_AUTODETECT; //DetectMusicCard();
nodigimusic=true; //Alam: No OGG/MP3/IT/MOD support digital_disabled=true; //Alam: No OGG/MP3/IT/MOD support
// Secure and configure sound device first. // Secure and configure sound device first.
CONS_Printf("I_StartupSound: "); CONS_Printf("I_StartupSound: ");
@ -293,8 +284,8 @@ void I_StartupSound(void)
{ {
sprintf (err,"Sound init error : %s\n",allegro_error); sprintf (err,"Sound init error : %s\n",allegro_error);
CONS_Error (err); CONS_Error (err);
nosound=true; sound_disabled=true;
nomidimusic=true; midi_disabled=true;
} }
else else
{ {
@ -321,7 +312,11 @@ static MIDI* currsong; //im assuming only 1 song will be played at once
static int islooping=0; static int islooping=0;
static int musicdies=-1; static int musicdies=-1;
UINT8 music_started=0; UINT8 music_started=0;
boolean songpaused=false;
/// ------------------------
// MUSIC SYSTEM
/// ------------------------
/* load_midi_mem: /* load_midi_mem:
* Loads a standard MIDI file from memory, returning a pointer to * Loads a standard MIDI file from memory, returning a pointer to
@ -389,116 +384,66 @@ static MIDI *load_midi_mem(char *mempointer,int *e)
return midi; return midi;
} }
void I_InitMIDIMusic(void) void I_InitMusic(void)
{ {
if (nomidimusic) if (midi_disabled)
return; return;
I_AddExitFunc(I_ShutdownMusic); I_AddExitFunc(I_ShutdownMusic);
music_started = true; music_started = true;
} songpaused = false;
void I_ShutdownMIDIMusic(void)
{
if ( !music_started )
return;
I_StopSong(1);
music_started=false;
}
void I_InitDigMusic(void)
{
// CONS_Printf("Digital music not yet supported under DOS.\n");
}
void I_ShutdownDigMusic(void)
{
// CONS_Printf("Digital music not yet supported under DOS.\n");
}
void I_InitMusic(void)
{
if (!nodigimusic)
I_InitDigMusic();
if (!nomidimusic)
I_InitMIDIMusic();
} }
void I_ShutdownMusic(void) void I_ShutdownMusic(void)
{ {
I_ShutdownMIDIMusic(); if ( !music_started )
I_ShutdownDigMusic(); return;
I_StopSong();
music_started=false;
} }
boolean I_PlaySong(INT32 handle, INT32 looping) /// ------------------------
{ // MUSIC PROPERTIES
handle = 0; /// ------------------------
if (nomidimusic)
return false;
islooping = looping; musictype_t I_SongType(void)
musicdies = gametic + NEWTICRATE*30; {
if (play_midi(currsong,looping)==0) if (currsong)
return true; return MU_MID;
else
return MU_NONE;
}
boolean I_SongPlaying()
{
return (boolean)currsong;
}
boolean I_SongPaused()
{
return songpaused;
}
/// ------------------------
// MUSIC EFFECTS
/// ------------------------
boolean I_SetSongSpeed(float speed)
{
(void)speed;
return false; return false;
} }
void I_PauseSong (INT32 handle) /// ------------------------
{ // MUSIC PLAYBACK
handle = 0; /// ------------------------
if (nomidimusic)
return;
midi_pause(); boolean I_LoadSong(char *data, size_t len)
}
void I_ResumeSong (INT32 handle)
{
handle = 0;
if (nomidimusic)
return;
midi_resume();
}
void I_StopSong(INT32 handle)
{
handle = 0;
if (nomidimusic)
return;
islooping = 0;
musicdies = 0;
stop_midi();
}
// Is the song playing?
#if 0
int I_QrySongPlaying(int handle)
{
if (nomidimusic)
return 0;
//return islooping || musicdies > gametic;
return (midi_pos==-1);
}
#endif
void I_UnRegisterSong(INT32 handle)
{
handle = 0;
if (nomidimusic)
return;
//destroy_midi(currsong);
}
INT32 I_RegisterSong(void *data, size_t len)
{ {
int e = len; //Alam: For error int e = len; //Alam: For error
if (nomidimusic) if (midi_disabled)
return 0; return 0;
if (memcmp(data,"MThd",4)==0) // support mid file in WAD !!! if (memcmp(data,"MThd",4)==0) // support mid file in WAD !!!
@ -520,32 +465,81 @@ INT32 I_RegisterSong(void *data, size_t len)
return 1; return 1;
} }
/// \todo Add OGG/MP3 support for dos void I_UnloadSong(void)
boolean I_StartDigSong(const char *musicname, INT32 looping)
{ {
musicname = NULL; handle = 0;
looping = 0; if (midi_disabled)
//CONS_Printf("I_StartDigSong: Not yet supported under DOS.\n"); return;
//destroy_midi(currsong);
}
boolean I_PlaySong(boolean looping)
{
handle = 0;
if (midi_disabled)
return false;
islooping = looping;
musicdies = gametic + NEWTICRATE*30;
if (play_midi(currsong,looping)==0)
return true;
return false; return false;
} }
void I_StopDigSong(void) void I_StopSong(void)
{ {
// CONS_Printf("I_StopDigSong: Not yet supported under DOS.\n"); handle = 0;
if (midi_disabled)
return;
islooping = 0;
musicdies = 0;
stop_midi();
songpaused = false;
} }
void I_SetDigMusicVolume(INT32 volume) void I_PauseSong (INT32 handle)
{ {
volume = 0; handle = 0;
if (nodigimusic) if (midi_disabled)
return;
midi_pause();
songpaused = true;
}
void I_ResumeSong (INT32 handle)
{
handle = 0;
if (midi_disabled)
return;
midi_resume();
songpaused = false;
}
void I_SetMusicVolume(INT32 volume)
{
if (midi_disabled)
return; return;
// Now set volume on output device. // Now set volume on output device.
// CONS_Printf("Digital music not yet supported under DOS.\n"); set_volume (-1, Volset(volume));
} }
boolean I_SetSongSpeed(float speed) boolean I_SetSongTrack(INT32 track)
{ {
(void)speed; (void)track;
return false; return false;
} }
// Is the song playing?
#if 0
int I_QrySongPlaying(int handle)
{
if (midi_disabled)
return 0;
//return islooping || musicdies > gametic;
return (midi_pos==-1);
}
#endif

View file

@ -90,10 +90,7 @@ extern boolean fromlevelselect;
// Internal parameters for sound rendering. // Internal parameters for sound rendering.
// ======================================== // ========================================
extern boolean nomidimusic; // defined in d_main.c extern boolean midi_disabled;
extern boolean nosound;
extern boolean nodigimusic;
extern boolean music_disabled;
extern boolean sound_disabled; extern boolean sound_disabled;
extern boolean digital_disabled; extern boolean digital_disabled;

View file

@ -57,82 +57,36 @@ void I_SetSfxVolume(UINT8 volume)
(void)volume; (void)volume;
} }
// /// ------------------------
// MUSIC I/O // MUSIC SYSTEM
// /// ------------------------
void I_InitMusic(void){} void I_InitMusic(void){}
void I_ShutdownMusic(void){} void I_ShutdownMusic(void){}
void I_PauseSong(INT32 handle) /// ------------------------
// MUSIC PROPERTIES
/// ------------------------
musictype_t I_SongType(void)
{ {
(void)handle; return MU_NONE;
} }
void I_ResumeSong(INT32 handle) boolean I_SongPlaying(void)
{ {
(void)handle;
}
//
// MIDI I/O
//
void I_InitMIDIMusic(void){}
void I_ShutdownMIDIMusic(void){}
void I_SetMIDIMusicVolume(UINT8 volume)
{
(void)volume;
}
INT32 I_RegisterSong(void *data, size_t len)
{
(void)data;
(void)len;
return -1;
}
boolean I_PlaySong(INT32 handle, boolean looping)
{
(void)handle;
(void)looping;
return false; return false;
} }
void I_StopSong(INT32 handle) boolean I_SongPaused(void)
{ {
(void)handle;
}
void I_UnRegisterSong(INT32 handle)
{
(void)handle;
}
//
// DIGMUSIC I/O
//
void I_InitDigMusic(void){}
void I_ShutdownDigMusic(void){}
boolean I_StartDigSong(const char *musicname, boolean looping)
{
(void)musicname;
(void)looping;
return false; return false;
} }
void I_StopDigSong(void){} /// ------------------------
// MUSIC EFFECTS
void I_SetDigMusicVolume(UINT8 volume) /// ------------------------
{
(void)volume;
}
boolean I_SetSongSpeed(float speed) boolean I_SetSongSpeed(float speed)
{ {
@ -140,6 +94,49 @@ boolean I_SetSongSpeed(float speed)
return false; return false;
} }
/// ------------------------
// MUSIC PLAYBACK
/// ------------------------
boolean I_LoadSong(char *data, size_t len)
{
(void)data;
(void)len;
return -1;
}
void I_UnloadSong(void)
{
(void)handle;
}
boolean I_PlaySong(boolean looping)
{
(void)handle;
(void)looping;
return false;
}
void I_StopSong(void)
{
(void)handle;
}
void I_PauseSong(void)
{
(void)handle;
}
void I_ResumeSong(void)
{
(void)handle;
}
void I_SetMusicVolume(UINT8 volume)
{
(void)volume;
}
boolean I_SetSongTrack(int track) boolean I_SetSongTrack(int track)
{ {
(void)track; (void)track;

View file

@ -361,7 +361,7 @@ INT32 HW3S_I_StartSound(const void *origin_p, source3D_data_t *source_parm, chan
if (splitscreen) listenmobj2 = players[secondarydisplayplayer].mo; if (splitscreen) listenmobj2 = players[secondarydisplayplayer].mo;
if (nosound) if (sound_disabled)
return -1; return -1;
sfx = &S_sfx[sfx_id]; sfx = &S_sfx[sfx_id];

View file

@ -18,6 +18,21 @@
#include "sounds.h" #include "sounds.h"
#include "command.h" #include "command.h"
// copied from SDL mixer, plus GME
typedef enum {
MU_NONE,
MU_CMD,
MU_WAV,
MU_MOD,
MU_MID,
MU_OGG,
MU_MP3,
MU_MP3_MAD_UNUSED, // use MU_MP3 instead
MU_FLAC,
MU_MODPLUG_UNUSED, // use MU_MOD instead
MU_GME
} musictype_t;
/** \brief Sound subsystem runing and waiting /** \brief Sound subsystem runing and waiting
*/ */
extern UINT8 sound_started; extern UINT8 sound_started;
@ -51,9 +66,9 @@ void I_StartupSound(void);
*/ */
void I_ShutdownSound(void); void I_ShutdownSound(void);
// /// ------------------------
// SFX I/O /// SFX I/O
// /// ------------------------
/** \brief Starts a sound in a particular sound channel. /** \brief Starts a sound in a particular sound channel.
\param id sfxid \param id sfxid
@ -105,9 +120,10 @@ void I_UpdateSoundParams(INT32 handle, UINT8 vol, UINT8 sep, UINT8 pitch);
*/ */
void I_SetSfxVolume(UINT8 volume); void I_SetSfxVolume(UINT8 volume);
// /// ------------------------
// MUSIC I/O // MUSIC SYSTEM
// /// ------------------------
/** \brief Init the music systems /** \brief Init the music systems
*/ */
void I_InitMusic(void); void I_InitMusic(void);
@ -116,41 +132,23 @@ void I_InitMusic(void);
*/ */
void I_ShutdownMusic(void); void I_ShutdownMusic(void);
/** \brief PAUSE game handling. /// ------------------------
// MUSIC PROPERTIES
/// ------------------------
\param handle song handle musictype_t I_SongType(void);
boolean I_SongPlaying(void);
boolean I_SongPaused(void);
\return void /// ------------------------
*/ // MUSIC EFFECTS
void I_PauseSong(INT32 handle); /// ------------------------
/** \brief RESUME game handling boolean I_SetSongSpeed(float speed);
\param handle song handle /// ------------------------
// MUSIC PLAYBACK
\return void /// ------------------------
*/
void I_ResumeSong(INT32 handle);
//
// MIDI I/O
//
/** \brief Startup the MIDI music system
*/
void I_InitMIDIMusic(void);
/** \brief Shutdown the MIDI music system
*/
void I_ShutdownMIDIMusic(void);
/** \brief The I_SetMIDIMusicVolume function
\param volume volume to set at
\return void
*/
void I_SetMIDIMusicVolume(UINT8 volume);
/** \brief Registers a song handle to song data. /** \brief Registers a song handle to song data.
@ -161,7 +159,16 @@ void I_SetMIDIMusicVolume(UINT8 volume);
\todo Remove this \todo Remove this
*/ */
INT32 I_RegisterSong(void *data, size_t len); boolean I_LoadSong(char *data, size_t len);
/** \brief See ::I_LoadSong, then think backwards
\param handle song handle
\sa I_LoadSong
\todo remove midi handle
*/
void I_UnloadSong(void);
/** \brief Called by anything that wishes to start music /** \brief Called by anything that wishes to start music
@ -172,7 +179,7 @@ INT32 I_RegisterSong(void *data, size_t len);
\todo pass music name, not handle \todo pass music name, not handle
*/ */
boolean I_PlaySong(INT32 handle, boolean looping); boolean I_PlaySong(boolean looping);
/** \brief Stops a song over 3 seconds /** \brief Stops a song over 3 seconds
@ -181,58 +188,37 @@ boolean I_PlaySong(INT32 handle, boolean looping);
/todo drop handle /todo drop handle
*/ */
void I_StopSong(INT32 handle); void I_StopSong(void);
/** \brief See ::I_RegisterSong, then think backwards /** \brief PAUSE game handling.
\param handle song handle \param handle song handle
\sa I_RegisterSong \return void
\todo remove midi handle
*/ */
void I_UnRegisterSong(INT32 handle); void I_PauseSong(void);
// /** \brief RESUME game handling
// DIGMUSIC I/O
//
/** \brief Startup the music system \param handle song handle
\return void
*/ */
void I_InitDigMusic(void); void I_ResumeSong(void);
/** \brief Shutdown the music system /** \brief The I_SetMusicVolume function
*/
void I_ShutdownDigMusic(void);
boolean I_SetSongSpeed(float speed);
boolean I_SetSongTrack(INT32 track);
/** \brief The I_StartDigSong function
\param musicname music lump name
\param looping if true, loop the song
\return if true, song playing
*/
boolean I_StartDigSong(const char *musicname, boolean looping);
/** \brief stop non-MIDI song
*/
void I_StopDigSong(void);
/** \brief The I_SetDigMusicVolume function
\param volume volume to set at \param volume volume to set at
\return void \return void
*/ */
void I_SetDigMusicVolume(UINT8 volume); void I_SetMusicVolume(UINT8 volume);
// boolean I_SetSongTrack(INT32 track);
// CD MUSIC I/O
//
/// ------------------------
// CD MUSIC I/O
/// ------------------------
/** \brief cd music interface /** \brief cd music interface
*/ */

View file

@ -3825,7 +3825,7 @@ msgid "Music lump is not MID music format\n"
msgstr "" msgstr ""
#: win32/win_snd.c:2128 #: win32/win_snd.c:2128
msgid "I_RegisterSong: StreamBufferSetup FAILED" msgid "I_LoadSong: StreamBufferSetup FAILED"
msgstr "" msgstr ""
#: win32/win_sys.c:892 #: win32/win_sys.c:892

View file

@ -4021,7 +4021,7 @@ msgid "Music lump is not MID music format\n"
msgstr "" msgstr ""
#: win32/win_snd.c:2126 #: win32/win_snd.c:2126
msgid "I_RegisterSong: StreamBufferSetup FAILED" msgid "I_LoadSong: StreamBufferSetup FAILED"
msgstr "" msgstr ""
#: win32/win_sys.c:894 #: win32/win_sys.c:894

View file

@ -9350,7 +9350,7 @@ static void M_SoundMenu(INT32 choice)
{ {
(void)choice; (void)choice;
OP_SoundOptionsMenu[6].status = ((nosound || sound_disabled) ? IT_GRAYEDOUT : (IT_STRING | IT_CVAR)); OP_SoundOptionsMenu[6].status = (sound_disabled ? IT_GRAYEDOUT : (IT_STRING | IT_CVAR));
M_SetupNextMenu(&OP_SoundOptionsDef); M_SetupNextMenu(&OP_SoundOptionsDef);
} }
@ -9363,25 +9363,25 @@ void M_DrawSoundMenu(void)
V_DrawRightAlignedString(BASEVIDWIDTH - currentMenu->x, V_DrawRightAlignedString(BASEVIDWIDTH - currentMenu->x,
currentMenu->y+currentMenu->menuitems[0].alphaKey, currentMenu->y+currentMenu->menuitems[0].alphaKey,
(nosound ? V_REDMAP : V_YELLOWMAP), (sound_disabled ? V_REDMAP : V_YELLOWMAP),
((nosound || sound_disabled) ? offstring : onstring)); (sound_disabled ? offstring : onstring));
V_DrawRightAlignedString(BASEVIDWIDTH - currentMenu->x, V_DrawRightAlignedString(BASEVIDWIDTH - currentMenu->x,
currentMenu->y+currentMenu->menuitems[2].alphaKey, currentMenu->y+currentMenu->menuitems[2].alphaKey,
(nodigimusic ? V_REDMAP : V_YELLOWMAP), (digital_disabled ? V_REDMAP : V_YELLOWMAP),
((nodigimusic || digital_disabled) ? offstring : onstring)); (digital_disabled ? offstring : onstring));
V_DrawRightAlignedString(BASEVIDWIDTH - currentMenu->x, V_DrawRightAlignedString(BASEVIDWIDTH - currentMenu->x,
currentMenu->y+currentMenu->menuitems[4].alphaKey, currentMenu->y+currentMenu->menuitems[4].alphaKey,
(nomidimusic ? V_REDMAP : V_YELLOWMAP), (midi_disabled ? V_REDMAP : V_YELLOWMAP),
((nomidimusic || music_disabled) ? offstring : onstring)); (midi_disabled ? offstring : onstring));
if (itemOn == 0) if (itemOn == 0)
lengthstring = ((nosound || sound_disabled) ? 3 : 2); lengthstring = (sound_disabled ? 3 : 2);
else if (itemOn == 2) else if (itemOn == 2)
lengthstring = ((nodigimusic || digital_disabled) ? 3 : 2); lengthstring = (digital_disabled ? 3 : 2);
else if (itemOn == 4) else if (itemOn == 4)
lengthstring = ((nomidimusic || music_disabled) ? 3 : 2); lengthstring = (midi_disabled ? 3 : 2);
else else
return; return;
@ -9416,12 +9416,12 @@ static void M_ToggleSFX(INT32 choice)
break; break;
} }
if (nosound) if (sound_disabled)
{ {
nosound = false; sound_disabled = false;
I_StartupSound(); I_StartupSound();
if (nosound) return; if (sound_disabled) return;
S_Init(cv_soundvolume.value, cv_digmusicvolume.value, cv_midimusicvolume.value); S_InitSfxChannels(cv_soundvolume.value);
S_StartSound(NULL, sfx_strpst); S_StartSound(NULL, sfx_strpst);
OP_SoundOptionsMenu[6].status = IT_STRING | IT_CVAR; OP_SoundOptionsMenu[6].status = IT_STRING | IT_CVAR;
//M_StartMessage(M_GetText("SFX Enabled\n"), NULL, MM_NOTHING); //M_StartMessage(M_GetText("SFX Enabled\n"), NULL, MM_NOTHING);
@ -9469,12 +9469,11 @@ static void M_ToggleDigital(INT32 choice)
break; break;
} }
if (nodigimusic) if (digital_disabled)
{ {
nodigimusic = false; digital_disabled = false;
I_InitDigMusic(); I_InitMusic();
if (nodigimusic) return; if (digital_disabled) return;
S_Init(cv_soundvolume.value, cv_digmusicvolume.value, cv_midimusicvolume.value);
S_StopMusic(); S_StopMusic();
if (Playing()) if (Playing())
P_RestoreMusic(&players[consoleplayer]); P_RestoreMusic(&players[consoleplayer]);
@ -9484,21 +9483,27 @@ static void M_ToggleDigital(INT32 choice)
} }
else else
{ {
if (digital_disabled) digital_disabled = true;
if (S_MusicType() != MU_MID)
{ {
digital_disabled = false; if (midi_disabled)
if (Playing()) S_StopMusic();
P_RestoreMusic(&players[consoleplayer]);
else else
S_ChangeMusicInternal("_clear", false); {
//M_StartMessage(M_GetText("Digital Music Enabled\n"), NULL, MM_NOTHING); char mmusic[7];
} UINT16 mflags;
else boolean looping;
{
digital_disabled = true; if (S_MusicInfo(mmusic, &mflags, &looping) && S_MIDIExists(mmusic))
S_StopMusic(); {
//M_StartMessage(M_GetText("Digital Music Disabled\n"), NULL, MM_NOTHING); S_StopMusic();
S_ChangeMusic(mmusic, mflags, looping);
}
else
S_StopMusic();
}
} }
//M_StartMessage(M_GetText("Digital Music Disabled\n"), NULL, MM_NOTHING);
} }
} }
@ -9516,6 +9521,12 @@ static void M_ToggleMIDI(INT32 choice)
itemOn--; itemOn--;
return; return;
case KEY_LEFTARROW:
case KEY_RIGHTARROW:
if (S_MusicType() != MU_MID && S_MusicType() != MU_NONE)
S_StartSound(NULL, sfx_menu1);
break;
case KEY_ESCAPE: case KEY_ESCAPE:
if (currentMenu->prevMenu) if (currentMenu->prevMenu)
M_SetupNextMenu(currentMenu->prevMenu); M_SetupNextMenu(currentMenu->prevMenu);
@ -9526,12 +9537,11 @@ static void M_ToggleMIDI(INT32 choice)
break; break;
} }
if (nomidimusic) if (midi_disabled)
{ {
nomidimusic = false; midi_disabled = false;
I_InitMIDIMusic(); I_InitMusic();
if (nomidimusic) return; if (midi_disabled) return;
S_Init(cv_soundvolume.value, cv_digmusicvolume.value, cv_midimusicvolume.value);
if (Playing()) if (Playing())
P_RestoreMusic(&players[consoleplayer]); P_RestoreMusic(&players[consoleplayer]);
else else
@ -9540,21 +9550,27 @@ static void M_ToggleMIDI(INT32 choice)
} }
else else
{ {
if (music_disabled) midi_disabled = true;
if (S_MusicType() == MU_MID)
{ {
music_disabled = false; if (digital_disabled)
if (Playing()) S_StopMusic();
P_RestoreMusic(&players[consoleplayer]);
else else
S_ChangeMusicInternal("_clear", false); {
//M_StartMessage(M_GetText("MIDI Music Enabled\n"), NULL, MM_NOTHING); char mmusic[7];
} UINT16 mflags;
else boolean looping;
{
music_disabled = true; if (S_MusicInfo(mmusic, &mflags, &looping) && S_DigExists(mmusic))
S_StopMusic(); {
//M_StartMessage(M_GetText("MIDI Music Disabled\n"), NULL, MM_NOTHING); S_StopMusic();
S_ChangeMusic(mmusic, mflags, looping);
}
else
S_StopMusic();
}
} }
//M_StartMessage(M_GetText("MIDI Music Disabled\n"), NULL, MM_NOTHING);
} }
} }

View file

@ -9172,7 +9172,7 @@ void P_PrecipitationEffects(void)
if (!playeringame[displayplayer] || !players[displayplayer].mo) if (!playeringame[displayplayer] || !players[displayplayer].mo)
return; return;
if (nosound || sound_disabled) if (sound_disabled)
return; // Sound off? D'aw, no fun. return; // Sound off? D'aw, no fun.
if (players[displayplayer].mo->subsector->sector->ceilingpic == skyflatnum) if (players[displayplayer].mo->subsector->sector->ceilingpic == skyflatnum)

View file

@ -230,7 +230,7 @@ void S_RegisterSoundStuff(void)
{ {
if (dedicated) if (dedicated)
{ {
nosound = true; sound_disabled = true;
return; return;
} }
@ -494,7 +494,7 @@ void S_StartSoundAtVolume(const void *origin_p, sfxenum_t sfx_id, INT32 volume)
mobj_t *listenmobj = players[displayplayer].mo; mobj_t *listenmobj = players[displayplayer].mo;
mobj_t *listenmobj2 = NULL; mobj_t *listenmobj2 = NULL;
if (sound_disabled || !sound_started || nosound) if (sound_disabled || !sound_started)
return; return;
// Don't want a sound? Okay then... // Don't want a sound? Okay then...
@ -824,7 +824,7 @@ void S_UpdateSounds(void)
goto notinlevel; goto notinlevel;
} }
if (dedicated || nosound) if (dedicated || sound_disabled)
return; return;
if (players[displayplayer].awayviewtics) if (players[displayplayer].awayviewtics)
@ -1283,6 +1283,43 @@ void S_StartSoundName(void *mo, const char *soundname)
S_StartSound(mo, soundnum); S_StartSound(mo, soundnum);
} }
//
// Initializes sound stuff, including volume
// Sets channels, SFX volume,
// allocates channel buffer, sets S_sfx lookup.
//
void S_InitSfxChannels(INT32 sfxVolume)
{
INT32 i;
if (dedicated)
return;
S_SetSfxVolume(sfxVolume);
SetChannelsNum();
// Note that sounds have not been cached (yet).
for (i = 1; i < NUMSFX; i++)
{
S_sfx[i].usefulness = -1; // for I_GetSfx()
S_sfx[i].lumpnum = LUMPERROR;
}
// precache sounds if requested by cmdline, or precachesound var true
if (!sound_disabled && (M_CheckParm("-precachesound") || precachesound.value))
{
// Initialize external data (all sounds) at start, keep static.
CONS_Printf(M_GetText("Loading sounds... "));
for (i = 1; i < NUMSFX; i++)
if (S_sfx[i].name)
S_sfx[i].data = I_GetSfx(&S_sfx[i]);
CONS_Printf(M_GetText(" pre-cached all sound data\n"));
}
}
/// ------------------------ /// ------------------------
/// Music /// Music
/// ------------------------ /// ------------------------
@ -1309,75 +1346,145 @@ const char *compat_special_music_slots[16] =
}; };
#endif #endif
#define music_playing (music_name[0]) // String is empty if no music is playing
static char music_name[7]; // up to 6-character name static char music_name[7]; // up to 6-character name
static lumpnum_t music_lumpnum; // lump number of music (used??) static UINT16 music_flags;
static void *music_data; // music raw data static boolean music_looping;
static INT32 music_handle; // once registered, the handle for the music
static boolean mus_paused = 0; // whether songs are mus_paused /// ------------------------
/// Music Status
/// ------------------------
static boolean S_MIDIMusic(const char *mname, boolean looping) boolean S_DigMusicDisabled(void)
{
return digital_disabled;
}
boolean S_MIDIMusicDisabled(void)
{
return midi_disabled;
}
boolean S_MusicDisabled(void)
{
return (midi_disabled && digital_disabled);
}
boolean S_MusicPlaying(void)
{
return I_SongPlaying();
}
boolean S_MusicPaused(void)
{
return I_SongPaused();
}
musictype_t S_MusicType(void)
{
return I_SongType();
}
boolean S_MusicInfo(char *mname, UINT16 *mflags, boolean *looping)
{
if (!I_SongPlaying())
return false;
strncpy(mname, music_name, 7);
mname[6] = 0;
*mflags = music_flags;
*looping = music_looping;
return (boolean)mname[0];
}
boolean S_MusicExists(const char *mname, boolean checkMIDI, boolean checkDigi)
{
return (
(checkDigi ? W_CheckNumForName(va("O_%s", mname)) != LUMPERROR : false)
|| (checkMIDI ? W_CheckNumForName(va("D_%s", mname)) != LUMPERROR : false)
);
}
/// ------------------------
/// Music Effects
/// ------------------------
boolean S_SpeedMusic(float speed)
{
return I_SetSongSpeed(speed);
}
/// ------------------------
/// Music Playback
/// ------------------------
static boolean S_LoadMusic(const char *mname)
{ {
lumpnum_t mlumpnum; lumpnum_t mlumpnum;
void *mdata; void *mdata;
INT32 mhandle;
if (nomidimusic || music_disabled) if (S_MusicDisabled())
return false; // didn't search.
if (W_CheckNumForName(va("d_%s", mname)) == LUMPERROR)
return false; return false;
mlumpnum = W_GetNumForName(va("d_%s", mname));
if (!S_DigMusicDisabled() && S_DigExists(mname))
mlumpnum = W_GetNumForName(va("o_%s", mname));
else if (!S_MIDIMusicDisabled() && S_MIDIExists(mname))
mlumpnum = W_GetNumForName(va("d_%s", mname));
else if (S_DigMusicDisabled() && S_DigExists(mname))
{
CONS_Alert(CONS_NOTICE, "Digital music is disabled!\n");
return false;
}
else if (S_MIDIMusicDisabled() && S_MIDIExists(mname))
{
CONS_Alert(CONS_NOTICE, "MIDI music is disabled!\n");
return false;
}
else
{
CONS_Alert(CONS_ERROR, M_GetText("Music lump %.6s not found!\n"), mname);
return false;
}
// load & register it // load & register it
mdata = W_CacheLumpNum(mlumpnum, PU_MUSIC); mdata = W_CacheLumpNum(mlumpnum, PU_MUSIC);
mhandle = I_RegisterSong(mdata, W_LumpLength(mlumpnum));
#ifdef MUSSERV if (I_LoadSong(mdata, W_LumpLength(mlumpnum)))
if (msg_id != -1)
{ {
struct musmsg msg_buffer; strncpy(music_name, mname, 7);
music_name[6] = 0;
msg_buffer.msg_type = 6; return true;
memset(msg_buffer.msg_text, 0, sizeof (msg_buffer.msg_text));
sprintf(msg_buffer.msg_text, "d_%s", mname);
msgsnd(msg_id, (struct msgbuf*)&msg_buffer, sizeof (msg_buffer.msg_text), IPC_NOWAIT);
} }
#endif else
// play it
if (!I_PlaySong(mhandle, looping))
return false; return false;
strncpy(music_name, mname, 7);
music_name[6] = 0;
music_lumpnum = mlumpnum;
music_data = mdata;
music_handle = mhandle;
return true;
} }
static boolean S_DigMusic(const char *mname, boolean looping) static void S_UnloadMusic(void)
{ {
if (nodigimusic || digital_disabled) I_UnloadSong();
return false; // try midi music_name[0] = 0;
music_flags = 0;
music_looping = false;
}
if (!I_StartDigSong(mname, looping)) static boolean S_PlayMusic(boolean looping)
{
if (S_MusicDisabled())
return false; return false;
strncpy(music_name, mname, 7); if (!I_PlaySong(looping))
music_name[6] = 0; {
music_lumpnum = LUMPERROR; S_UnloadMusic();
music_data = NULL; return false;
music_handle = 0; }
S_InitMusicVolume(); // switch between digi and sequence volume
return true; return true;
} }
void S_ChangeMusic(const char *mmusic, UINT16 mflags, boolean looping) void S_ChangeMusic(const char *mmusic, UINT16 mflags, boolean looping)
{ {
if ((nomidimusic || music_disabled) && (nodigimusic || digital_disabled)) if (S_MusicDisabled())
return; return;
// No Music (empty string) // No Music (empty string)
@ -1387,43 +1494,41 @@ void S_ChangeMusic(const char *mmusic, UINT16 mflags, boolean looping)
return; return;
} }
if (strncmp(music_name, mmusic, 6)) if (strnicmp(music_name, newmusic, 6))
{ {
S_StopMusic(); // shutdown old music S_StopMusic(); // shutdown old music
if (!S_DigMusic(mmusic, looping) && !S_MIDIMusic(mmusic, looping))
if (!S_LoadMusic(mmusic))
return;
music_flags = mflags;
music_looping = looping;
if (!S_PlayMusic(looping))
{ {
CONS_Alert(CONS_ERROR, M_GetText("Music lump %.6s not found!\n"), mmusic); CONS_Alert(CONS_ERROR, "Music cannot be played!\n");
return; return;
} }
} }
I_SetSongTrack(mflags & MUSIC_TRACKMASK); I_SetSongTrack(mflags & MUSIC_TRACKMASK);
} }
boolean S_SpeedMusic(float speed)
{
return I_SetSongSpeed(speed);
}
void S_StopMusic(void) void S_StopMusic(void)
{ {
if (!music_playing) if (!I_SongPlaying())
return; return;
if (mus_paused) if (I_SongPaused())
I_ResumeSong(music_handle); I_ResumeSong();
if (!nodigimusic)
I_StopDigSong();
S_SpeedMusic(1.0f); S_SpeedMusic(1.0f);
I_StopSong(music_handle); I_StopSong();
I_UnRegisterSong(music_handle); I_UnloadSong();
#ifndef HAVE_SDL //SDL uses RWOPS #ifndef HAVE_SDL //SDL uses RWOPS
Z_ChangeTag(music_data, PU_CACHE); Z_ChangeTag(music_data, PU_CACHE);
#endif #endif
music_data = NULL;
music_name[0] = 0; music_name[0] = 0;
if (cv_closedcaptioning.value) if (cv_closedcaptioning.value)
@ -1433,81 +1538,70 @@ void S_StopMusic(void)
} }
} }
void S_SetDigMusicVolume(INT32 volume) //
// Stop and resume music, during game PAUSE.
//
void S_PauseAudio(void)
{ {
if (volume < 0 || volume > 31) if (I_SongPlaying() && !I_SongPaused())
CONS_Alert(CONS_WARNING, "musicvolume should be between 0-31\n"); I_PauseSong();
CV_SetValue(&cv_digmusicvolume, volume&31); // pause cd music
actualdigmusicvolume = cv_digmusicvolume.value; //check for change of var #if (defined (__unix__) && !defined (MSDOS)) || defined (UNIXCOMMON) || defined (HAVE_SDL)
I_PauseCD();
#ifdef DJGPPDOS #else
I_SetDigMusicVolume(31); // Trick for buggy dos drivers. Win32 doesn't need this. I_StopCD();
#endif #endif
I_SetDigMusicVolume(volume&31);
} }
void S_SetMIDIMusicVolume(INT32 volume) void S_ResumeAudio(void)
{ {
if (volume < 0 || volume > 31) if (I_SongPlaying() && I_SongPaused())
CONS_Alert(CONS_WARNING, "musicvolume should be between 0-31\n"); I_ResumeSong();
CV_SetValue(&cv_midimusicvolume, volume&0x1f); // resume cd music
I_ResumeCD();
}
void S_SetMusicVolume(INT32 digvolume, INT32 seqvolume)
{
if (digvolume < 0)
digvolume = cv_digmusicvolume.value;
if (seqvolume < 0)
seqvolume = cv_midimusicvolume.value;
if (digvolume < 0 || digvolume > 31)
CONS_Alert(CONS_WARNING, "digmusicvolume should be between 0-31\n");
CV_SetValue(&cv_digmusicvolume, digvolume&31);
actualdigmusicvolume = cv_digmusicvolume.value; //check for change of var
if (seqvolume < 0 || seqvolume > 31)
CONS_Alert(CONS_WARNING, "midimusicvolume should be between 0-31\n");
CV_SetValue(&cv_midimusicvolume, seqvolume&31);
actualmidimusicvolume = cv_midimusicvolume.value; //check for change of var actualmidimusicvolume = cv_midimusicvolume.value; //check for change of var
#ifdef DJGPPDOS #ifdef DJGPPDOS
I_SetMIDIMusicVolume(31); // Trick for buggy dos drivers. Win32 doesn't need this. digvolume = seqvolume = 31;
#endif #endif
I_SetMIDIMusicVolume(volume&0x1f);
switch(I_SongType())
{
case MU_MID:
//case MU_MOD:
//case MU_GME:
I_SetMusicVolume(seqvolume&31);
break;
default:
I_SetMusicVolume(digvolume&31);
break;
}
} }
/// ------------------------ /// ------------------------
/// Init & Others /// Init & Others
/// ------------------------ /// ------------------------
//
// Initializes sound stuff, including volume
// Sets channels, SFX and music volume,
// allocates channel buffer, sets S_sfx lookup.
//
void S_Init(INT32 sfxVolume, INT32 digMusicVolume, INT32 midiMusicVolume)
{
INT32 i;
if (dedicated)
return;
S_SetSfxVolume(sfxVolume);
S_SetDigMusicVolume(digMusicVolume);
S_SetMIDIMusicVolume(midiMusicVolume);
SetChannelsNum();
// no sounds are playing, and they are not mus_paused
mus_paused = 0;
// Note that sounds have not been cached (yet).
for (i = 1; i < NUMSFX; i++)
{
S_sfx[i].usefulness = -1; // for I_GetSfx()
S_sfx[i].lumpnum = LUMPERROR;
}
// precache sounds if requested by cmdline, or precachesound var true
if (!nosound && (M_CheckParm("-precachesound") || precachesound.value))
{
// Initialize external data (all sounds) at start, keep static.
CONS_Printf(M_GetText("Loading sounds... "));
for (i = 1; i < NUMSFX; i++)
if (S_sfx[i].name)
S_sfx[i].data = I_GetSfx(&S_sfx[i]);
CONS_Printf(M_GetText(" pre-cached all sound data\n"));
}
}
// //
// Per level startup code. // Per level startup code.
// Kills playing sounds at start of level, // Kills playing sounds at start of level,
@ -1522,46 +1616,7 @@ void S_Start(void)
mapmusflags = (mapheaderinfo[gamemap-1]->mustrack & MUSIC_TRACKMASK); mapmusflags = (mapheaderinfo[gamemap-1]->mustrack & MUSIC_TRACKMASK);
} }
mus_paused = 0;
if (cv_resetmusic.value) if (cv_resetmusic.value)
S_StopMusic(); S_StopMusic();
S_ChangeMusic(mapmusname, mapmusflags, true); S_ChangeMusic(mapmusname, mapmusflags, true);
} }
//
// Stop and resume music, during game PAUSE.
//
void S_PauseAudio(void)
{
if (!nodigimusic)
I_PauseSong(0);
if (music_playing && !mus_paused)
{
I_PauseSong(music_handle);
mus_paused = true;
}
// pause cd music
#if (defined (__unix__) && !defined (MSDOS)) || defined (UNIXCOMMON) || defined (HAVE_SDL)
I_PauseCD();
#else
I_StopCD();
#endif
}
void S_ResumeAudio(void)
{
if (!nodigimusic)
I_ResumeSong(0);
else
if (music_playing && mus_paused)
{
I_ResumeSong(music_handle);
mus_paused = false;
}
// resume cd music
I_ResumeCD();
}

View file

@ -14,6 +14,7 @@
#ifndef __S_SOUND__ #ifndef __S_SOUND__
#define __S_SOUND__ #define __S_SOUND__
#include "i_sound.h" // musictype_t
#include "sounds.h" #include "sounds.h"
#include "m_fixed.h" #include "m_fixed.h"
#include "command.h" #include "command.h"
@ -97,9 +98,9 @@ void S_RegisterSoundStuff(void);
// //
// Initializes sound stuff, including volume // Initializes sound stuff, including volume
// Sets channels, SFX and music volume, allocates channel buffer, sets S_sfx lookup. // Sets channels, SFX, allocates channel buffer, sets S_sfx lookup.
// //
void S_Init(INT32 sfxVolume, INT32 digMusicVolume, INT32 midiMusicVolume); void S_InitSfxChannels(INT32 sfxVolume);
// //
// Per level startup code. // Per level startup code.
@ -125,6 +126,33 @@ void S_StartSoundAtVolume(const void *origin, sfxenum_t sound_id, INT32 volume);
// Stop sound for thing at <origin> // Stop sound for thing at <origin>
void S_StopSound(void *origin); void S_StopSound(void *origin);
//
// Music Status
//
boolean S_DigMusicDisabled(void);
boolean S_MIDIMusicDisabled(void);
boolean S_MusicDisabled(void);
boolean S_MusicPlaying(void);
boolean S_MusicPaused(void);
musictype_t S_MusicType(void);
boolean S_MusicInfo(char *mname, UINT16 *mflags, boolean *looping);
boolean S_MusicExists(const char *mname, boolean checkMIDI, boolean checkDigi);
#define S_DigExists(a) S_MusicExists(a, false, true)
#define S_MIDIExists(a) S_MusicExists(a, true, false)
//
// Music Properties
//
// Set Speed of Music
boolean S_SpeedMusic(float speed);
//
// Music Routines
//
// Start music track, arbitrary, given its name, and set whether looping // Start music track, arbitrary, given its name, and set whether looping
// note: music flags 12 bits for tracknum (gme, other formats with more than one track) // note: music flags 12 bits for tracknum (gme, other formats with more than one track)
// 13-15 aren't used yet // 13-15 aren't used yet
@ -132,9 +160,6 @@ void S_StopSound(void *origin);
#define S_ChangeMusicInternal(a,b) S_ChangeMusic(a,0,b) #define S_ChangeMusicInternal(a,b) S_ChangeMusic(a,0,b)
void S_ChangeMusic(const char *mmusic, UINT16 mflags, boolean looping); void S_ChangeMusic(const char *mmusic, UINT16 mflags, boolean looping);
// Set Speed of Music
boolean S_SpeedMusic(float speed);
// Stops the music. // Stops the music.
void S_StopMusic(void); void S_StopMusic(void);
@ -149,9 +174,11 @@ void S_UpdateSounds(void);
FUNCMATH fixed_t S_CalculateSoundDistance(fixed_t px1, fixed_t py1, fixed_t pz1, fixed_t px2, fixed_t py2, fixed_t pz2); FUNCMATH fixed_t S_CalculateSoundDistance(fixed_t px1, fixed_t py1, fixed_t pz1, fixed_t px2, fixed_t py2, fixed_t pz2);
void S_SetDigMusicVolume(INT32 volume);
void S_SetMIDIMusicVolume(INT32 volume);
void S_SetSfxVolume(INT32 volume); void S_SetSfxVolume(INT32 volume);
void S_SetMusicVolume(INT32 digvolume, INT32 seqvolume);
#define S_SetDigMusicVolume(a) S_SetMusicVolume(a,-1)
#define S_SetMIDIMusicVolume(a) S_SetMusicVolume(-1,a)
#define S_InitMusicVolume() S_SetMusicVolume(-1,-1)
INT32 S_OriginPlaying(void *origin); INT32 S_OriginPlaying(void *origin);
INT32 S_IdPlaying(sfxenum_t id); INT32 S_IdPlaying(sfxenum_t id);

View file

@ -566,7 +566,7 @@ static void Impl_HandleWindowEvent(SDL_WindowEvent evt)
// Tell game we got focus back, resume music if necessary // Tell game we got focus back, resume music if necessary
window_notinfocus = false; window_notinfocus = false;
if (!paused) if (!paused)
I_ResumeSong(0); //resume it I_ResumeSong(); //resume it
if (!firsttimeonmouse) if (!firsttimeonmouse)
{ {
@ -578,7 +578,7 @@ static void Impl_HandleWindowEvent(SDL_WindowEvent evt)
{ {
// Tell game we lost focus, pause music // Tell game we lost focus, pause music
window_notinfocus = true; window_notinfocus = true;
I_PauseSong(0); I_PauseSong();
if (!disable_mouse) if (!disable_mouse)
{ {

View file

@ -62,9 +62,8 @@
UINT8 sound_started = false; UINT8 sound_started = false;
static boolean midimode;
static Mix_Music *music; static Mix_Music *music;
static UINT8 music_volume, midi_volume, sfx_volume; static UINT8 music_volume, sfx_volume;
static float loop_point; static float loop_point;
static boolean songpaused; static boolean songpaused;
@ -73,6 +72,10 @@ static Music_Emu *gme;
static INT32 current_track; static INT32 current_track;
#endif #endif
/// ------------------------
/// Audio System
/// ------------------------
void I_StartupSound(void) void I_StartupSound(void)
{ {
I_Assert(!sound_started); I_Assert(!sound_started);
@ -87,9 +90,8 @@ void I_StartupSound(void)
return; return;
} }
midimode = false;
music = NULL; music = NULL;
music_volume = midi_volume = sfx_volume = 0; music_volume = sfx_volume = 0;
#if SDL_MIXER_VERSION_ATLEAST(1,2,11) #if SDL_MIXER_VERSION_ATLEAST(1,2,11)
Mix_Init(MIX_INIT_FLAC|MIX_INIT_MOD|MIX_INIT_MP3|MIX_INIT_OGG); Mix_Init(MIX_INIT_FLAC|MIX_INIT_MOD|MIX_INIT_MP3|MIX_INIT_OGG);
@ -130,6 +132,10 @@ FUNCMATH void I_UpdateSound(void)
{ {
} }
/// ------------------------
/// SFX
/// ------------------------
// this is as fast as I can possibly make it. // this is as fast as I can possibly make it.
// sorry. more asm needed. // sorry. more asm needed.
static Mix_Chunk *ds2chunk(void *stream) static Mix_Chunk *ds2chunk(void *stream)
@ -432,11 +438,10 @@ void I_SetSfxVolume(UINT8 volume)
sfx_volume = volume; sfx_volume = volume;
} }
// /// ------------------------
// Music /// Music Hooks
// /// ------------------------
// Music hooks
static void music_loop(void) static void music_loop(void)
{ {
Mix_PlayMusic(music, 0); Mix_PlayMusic(music, 0);
@ -464,46 +469,21 @@ static void mix_gme(void *udata, Uint8 *stream, int len)
} }
#endif #endif
/// ------------------------
/// Music System
/// ------------------------
FUNCMATH void I_InitMusic(void) FUNCMATH void I_InitMusic(void)
{ {
}
void I_ShutdownMusic(void)
{
I_ShutdownDigMusic();
I_ShutdownMIDIMusic();
}
void I_PauseSong(INT32 handle)
{
(void)handle;
Mix_PauseMusic();
songpaused = true;
}
void I_ResumeSong(INT32 handle)
{
(void)handle;
Mix_ResumeMusic();
songpaused = false;
}
//
// Digital Music
//
void I_InitDigMusic(void)
{
#ifdef HAVE_LIBGME #ifdef HAVE_LIBGME
gme = NULL; gme = NULL;
current_track = -1; current_track = -1;
#endif #endif
} }
void I_ShutdownDigMusic(void) void I_ShutdownMusic(void)
{ {
if (midimode)
return;
#ifdef HAVE_LIBGME #ifdef HAVE_LIBGME
if (gme) if (gme)
{ {
@ -519,24 +499,77 @@ void I_ShutdownDigMusic(void)
music = NULL; music = NULL;
} }
boolean I_StartDigSong(const char *musicname, boolean looping) /// ------------------------
{ /// Music Properties
char *data; /// ------------------------
size_t len;
lumpnum_t lumpnum = W_CheckNumForName(va("O_%s",musicname));
musictype_t I_SongType(void)
{
#ifdef HAVE_LIBGME
if (gme)
return MU_GME;
else
#endif
if (!music)
return MU_NONE;
else if (Mix_GetMusicType(music) == MUS_MID)
return MU_MID;
else if (Mix_GetMusicType(music) == MUS_MOD || Mix_GetMusicType(music) == MUS_MODPLUG_UNUSED)
return MU_MOD;
else if (Mix_GetMusicType(music) == MUS_MP3 || Mix_GetMusicType(music) == MUS_MP3_MAD_UNUSED)
return MU_MP3;
else
return (musictype_t)Mix_GetMusicType(music);
}
boolean I_SongPlaying(void)
{
return (
#ifdef HAVE_LIBGME
(I_SongType() == MU_GME && gme) ||
#endif
(boolean)music
);
}
boolean I_SongPaused(void)
{
return songpaused;
}
/// ------------------------
/// Music Effects
/// ------------------------
boolean I_SetSongSpeed(float speed)
{
if (speed > 250.0f)
speed = 250.0f; //limit speed up to 250x
#ifdef HAVE_LIBGME
if (gme)
{
SDL_LockAudio();
gme_set_tempo(gme, speed);
SDL_UnlockAudio();
return true;
}
#else
(void)speed;
#endif
return false;
}
/// ------------------------
/// Music Playback
/// ------------------------
boolean I_LoadSong(char *data, size_t len)
{
I_Assert(!music); I_Assert(!music);
#ifdef HAVE_LIBGME #ifdef HAVE_LIBGME
I_Assert(!gme); I_Assert(!gme);
#endif #endif
if (lumpnum == LUMPERROR)
return false;
midimode = false;
data = (char *)W_CacheLumpNum(lumpnum, PU_MUSIC);
len = W_LumpLength(lumpnum);
#ifdef HAVE_LIBGME #ifdef HAVE_LIBGME
if ((UINT8)data[0] == 0x1F if ((UINT8)data[0] == 0x1F
&& (UINT8)data[1] == 0x8B) && (UINT8)data[1] == 0x8B)
@ -627,10 +660,7 @@ boolean I_StartDigSong(const char *musicname, boolean looping)
else if (!gme_open_data(data, len, &gme, 44100)) else if (!gme_open_data(data, len, &gme, 44100))
{ {
gme_equalizer_t eq = {GME_TREBLE, GME_BASS, 0,0,0,0,0,0,0,0}; gme_equalizer_t eq = {GME_TREBLE, GME_BASS, 0,0,0,0,0,0,0,0};
gme_start_track(gme, 0);
current_track = 0;
gme_set_equalizer(gme, &eq); gme_set_equalizer(gme, &eq);
Mix_HookMusic(mix_gme, gme);
return true; return true;
} }
#endif #endif
@ -639,48 +669,73 @@ boolean I_StartDigSong(const char *musicname, boolean looping)
if (!music) if (!music)
{ {
CONS_Alert(CONS_ERROR, "Mix_LoadMUS_RW: %s\n", Mix_GetError()); CONS_Alert(CONS_ERROR, "Mix_LoadMUS_RW: %s\n", Mix_GetError());
return true; return false;
} }
// Find the OGG loop point. // Find the OGG loop point.
loop_point = 0.0f; loop_point = 0.0f;
if (looping)
const char *key1 = "LOOP";
const char *key2 = "POINT=";
const char *key3 = "MS=";
const size_t key1len = strlen(key1);
const size_t key2len = strlen(key2);
const size_t key3len = strlen(key3);
char *p = data;
while ((UINT32)(p - data) < len)
{ {
const char *key1 = "LOOP"; if (strncmp(p++, key1, key1len))
const char *key2 = "POINT="; continue;
const char *key3 = "MS="; p += key1len-1; // skip OOP (the L was skipped in strncmp)
const size_t key1len = strlen(key1); if (!strncmp(p, key2, key2len)) // is it LOOPPOINT=?
const size_t key2len = strlen(key2);
const size_t key3len = strlen(key3);
char *p = data;
while ((UINT32)(p - data) < len)
{ {
if (strncmp(p++, key1, key1len)) p += key2len; // skip POINT=
continue; loop_point = (float)((44.1L+atoi(p)) / 44100.0L); // LOOPPOINT works by sample count.
p += key1len-1; // skip OOP (the L was skipped in strncmp) // because SDL_Mixer is USELESS and can't even tell us
if (!strncmp(p, key2, key2len)) // is it LOOPPOINT=? // something simple like the frequency of the streaming music,
{ // we are unfortunately forced to assume that ALL MUSIC is 44100hz.
p += key2len; // skip POINT= // This means a lot of tracks that are only 22050hz for a reasonable downloadable file size will loop VERY badly.
loop_point = (float)((44.1L+atoi(p)) / 44100.0L); // LOOPPOINT works by sample count.
// because SDL_Mixer is USELESS and can't even tell us
// something simple like the frequency of the streaming music,
// we are unfortunately forced to assume that ALL MUSIC is 44100hz.
// This means a lot of tracks that are only 22050hz for a reasonable downloadable file size will loop VERY badly.
}
else if (!strncmp(p, key3, key3len)) // is it LOOPMS=?
{
p += key3len; // skip MS=
loop_point = (float)(atoi(p) / 1000.0L); // LOOPMS works by real time, as miliseconds.
// Everything that uses LOOPMS will work perfectly with SDL_Mixer.
}
// Neither?! Continue searching.
} }
else if (!strncmp(p, key3, key3len)) // is it LOOPMS=?
{
p += key3len; // skip MS=
loop_point = (float)(atoi(p) / 1000.0L); // LOOPMS works by real time, as miliseconds.
// Everything that uses LOOPMS will work perfectly with SDL_Mixer.
}
// Neither?! Continue searching.
} }
return true;
}
void I_UnloadSong(void)
{
// \todo unhook looper
//var_cleanup();
//Mix_FreeMusic(music);
//music = NULL;
I_StopSong();
}
boolean I_PlaySong(boolean looping)
{
#ifdef HAVE_LIBGME
if (gme)
{
gme_start_track(gme, 0);
current_track = 0;
Mix_HookMusic(mix_gme, gme);
return true;
}
else
#endif
if (!music)
return false;
if (Mix_PlayMusic(music, looping && loop_point == 0.0f ? -1 : 0) == -1) if (Mix_PlayMusic(music, looping && loop_point == 0.0f ? -1 : 0) == -1)
{ {
CONS_Alert(CONS_ERROR, "Mix_PlayMusic: %s\n", Mix_GetError()); CONS_Alert(CONS_ERROR, "Mix_PlayMusic: %s\n", Mix_GetError());
return true; return false;
} }
Mix_VolumeMusic((UINT32)music_volume*128/31); Mix_VolumeMusic((UINT32)music_volume*128/31);
@ -692,10 +747,8 @@ boolean I_StartDigSong(const char *musicname, boolean looping)
return true; return true;
} }
void I_StopDigSong(void) void I_StopSong(void)
{ {
if (midimode)
return;
#ifdef HAVE_LIBGME #ifdef HAVE_LIBGME
if (gme) if (gme)
{ {
@ -713,30 +766,33 @@ void I_StopDigSong(void)
music = NULL; music = NULL;
} }
void I_SetDigMusicVolume(UINT8 volume) void I_PauseSong(void)
{ {
music_volume = volume; Mix_PauseMusic();
if (midimode || !music) songpaused = true;
return;
Mix_VolumeMusic((UINT32)volume*128/31);
} }
boolean I_SetSongSpeed(float speed) void I_ResumeSong(void)
{ {
if (speed > 250.0f) Mix_ResumeMusic();
speed = 250.0f; //limit speed up to 250x songpaused = false;
#ifdef HAVE_LIBGME }
if (gme)
{ void I_SetMusicVolume(UINT8 volume)
SDL_LockAudio(); {
gme_set_tempo(gme, speed); if (!I_SongPlaying())
SDL_UnlockAudio(); return;
return true;
} #ifdef _WIN32
#else if (I_SongType() == MU_MID)
(void)speed; // HACK: Until we stop using native MIDI,
// disable volume changes
music_volume = 31;
else
#endif #endif
return false; music_volume = volume;
Mix_VolumeMusic((UINT32)music_volume*128/31);
} }
boolean I_SetSongTrack(int track) boolean I_SetSongTrack(int track)
@ -770,82 +826,4 @@ boolean I_SetSongTrack(int track)
return false; return false;
} }
//
// MIDI Music
//
FUNCMATH void I_InitMIDIMusic(void)
{
}
void I_ShutdownMIDIMusic(void)
{
if (!midimode || !music)
return;
Mix_FreeMusic(music);
music = NULL;
}
void I_SetMIDIMusicVolume(UINT8 volume)
{
// HACK: Until we stop using native MIDI,
// disable volume changes
(void)volume;
midi_volume = 31;
//midi_volume = volume;
if (!midimode || !music)
return;
Mix_VolumeMusic((UINT32)midi_volume*128/31);
}
INT32 I_RegisterSong(void *data, size_t len)
{
Mix_SetMidiPlayer(MIDI_OPNMIDI);
music = Mix_LoadMUS_RW(SDL_RWFromMem(data, len), SDL_FALSE);
if (!music)
{
CONS_Alert(CONS_ERROR, "Mix_LoadMUS_RW: %s\n", Mix_GetError());
return -1;
}
return 1337;
}
boolean I_PlaySong(INT32 handle, boolean looping)
{
(void)handle;
midimode = true;
if (Mix_PlayMusic(music, looping ? -1 : 0) == -1)
{
CONS_Alert(CONS_ERROR, "Mix_PlayMusic: %s\n", Mix_GetError());
return false;
}
Mix_VolumeMusic((UINT32)midi_volume*128/31);
return true;
}
void I_StopSong(INT32 handle)
{
if (!midimode || !music)
return;
(void)handle;
Mix_HaltMusic();
}
void I_UnRegisterSong(INT32 handle)
{
if (!midimode || !music)
return;
(void)handle;
Mix_FreeMusic(music);
music = NULL;
}
#endif #endif

View file

@ -194,8 +194,8 @@ static srb2audio_t localdata;
static void Snd_LockAudio(void) //Alam: Lock audio data and uninstall audio callback static void Snd_LockAudio(void) //Alam: Lock audio data and uninstall audio callback
{ {
if (Snd_Mutex) SDL_LockMutex(Snd_Mutex); if (Snd_Mutex) SDL_LockMutex(Snd_Mutex);
else if (nosound) return; else if (sound_disabled) return;
else if (nomidimusic && nodigimusic else if (midi_disabled && digital_disabled
#ifdef HW3SOUND #ifdef HW3SOUND
&& hws_mode == HWS_DEFAULT_MODE && hws_mode == HWS_DEFAULT_MODE
#endif #endif
@ -208,8 +208,8 @@ static void Snd_LockAudio(void) //Alam: Lock audio data and uninstall audio call
static void Snd_UnlockAudio(void) //Alam: Unlock audio data and reinstall audio callback static void Snd_UnlockAudio(void) //Alam: Unlock audio data and reinstall audio callback
{ {
if (Snd_Mutex) SDL_UnlockMutex(Snd_Mutex); if (Snd_Mutex) SDL_UnlockMutex(Snd_Mutex);
else if (nosound) return; else if (sound_disabled) return;
else if (nomidimusic && nodigimusic else if (midi_disabled && digital_disabled
#ifdef HW3SOUND #ifdef HW3SOUND
&& hws_mode == HWS_DEFAULT_MODE && hws_mode == HWS_DEFAULT_MODE
#endif #endif
@ -493,7 +493,7 @@ static inline void I_SetChannels(void)
INT32 *steptablemid = steptable + 128; INT32 *steptablemid = steptable + 128;
if (nosound) if (sound_disabled)
return; return;
// This table provides step widths for pitch parameters. // This table provides step widths for pitch parameters.
@ -609,7 +609,7 @@ INT32 I_StartSound(sfxenum_t id, UINT8 vol, UINT8 sep, UINT8 pitch, UINT8 priori
(void)priority; (void)priority;
(void)pitch; (void)pitch;
if (nosound) if (sound_disabled)
return 0; return 0;
if (S_sfx[id].data == NULL) return -1; if (S_sfx[id].data == NULL) return -1;
@ -1136,7 +1136,7 @@ static INT32 Init3DSDriver(const char *soName)
void I_ShutdownSound(void) void I_ShutdownSound(void)
{ {
if (nosound || !sound_started) if (sound_disabled || !sound_started)
return; return;
CONS_Printf("I_ShutdownSound: "); CONS_Printf("I_ShutdownSound: ");
@ -1150,7 +1150,7 @@ void I_ShutdownSound(void)
} }
#endif #endif
if (nomidimusic && nodigimusic) if (midi_disabled && digital_disabled)
SDL_CloseAudio(); SDL_CloseAudio();
CONS_Printf("%s", M_GetText("shut down\n")); CONS_Printf("%s", M_GetText("shut down\n"));
sound_started = false; sound_started = false;
@ -1170,7 +1170,7 @@ void I_StartupSound(void)
const char *sdrv_name = NULL; const char *sdrv_name = NULL;
#endif #endif
#ifndef HAVE_MIXER #ifndef HAVE_MIXER
nomidimusic = nodigimusic = true; midi_disabled = digital_disabled = true;
#endif #endif
memset(channels, 0, sizeof (channels)); //Alam: Clean it memset(channels, 0, sizeof (channels)); //Alam: Clean it
@ -1213,7 +1213,7 @@ void I_StartupSound(void)
audio.samples /= 2; audio.samples /= 2;
} }
if (nosound) if (sound_disabled)
return; return;
#ifdef HW3SOUND #ifdef HW3SOUND
@ -1261,7 +1261,7 @@ void I_StartupSound(void)
{ {
snddev_t snddev; snddev_t snddev;
//nosound = true; //sound_disabled = true;
//I_AddExitFunc(I_ShutdownSound); //I_AddExitFunc(I_ShutdownSound);
snddev.bps = 16; snddev.bps = 16;
snddev.sample_rate = audio.freq; snddev.sample_rate = audio.freq;
@ -1288,7 +1288,7 @@ void I_StartupSound(void)
if (!musicStarted && SDL_OpenAudio(&audio, &audio) < 0) if (!musicStarted && SDL_OpenAudio(&audio, &audio) < 0)
{ {
CONS_Printf("%s", M_GetText(" couldn't open audio with desired format\n")); CONS_Printf("%s", M_GetText(" couldn't open audio with desired format\n"));
nosound = true; sound_disabled = true;
return; return;
} }
else else
@ -1313,10 +1313,37 @@ void I_StartupSound(void)
// MUSIC API. // MUSIC API.
// //
void I_ShutdownMIDIMusic(void) musictype_t I_SongType(void)
{ {
nomidimusic = false; #ifdef HAVE_MIXER
if (nodigimusic) I_ShutdownMusic(); #ifdef HAVE_LIBGME
if (gme)
return MU_GME;
else
#endif
if (!music)
return MU_NONE;
else if (Mix_GetMusicType(music) == MUS_MID)
return MU_MID;
else if (Mix_GetMusicType(music) == MUS_MOD || Mix_GetMusicType(music) == MUS_MODPLUG_UNUSED)
return MU_MOD;
else if (Mix_GetMusicType(music) == MUS_MP3 || Mix_GetMusicType(music) == MUS_MP3_MAD_UNUSED)
return MU_MP3;
else
return (musictype_t)Mix_GetMusicType(music);
#else
return MU_NONE
#endif
}
boolean I_SongPlaying(void)
{
return music_started;
}
boolean I_SongPaused(void)
{
return Mix_PausedMusic();
} }
#ifdef HAVE_LIBGME #ifdef HAVE_LIBGME
@ -1330,12 +1357,6 @@ static void I_ShutdownGMEMusic(void)
} }
#endif #endif
void I_ShutdownDigMusic(void)
{
nodigimusic = false;
if (nomidimusic) I_ShutdownMusic();
}
#ifdef HAVE_MIXER #ifdef HAVE_MIXER
static boolean LoadSong(void *data, size_t lumplength, size_t selectpos) static boolean LoadSong(void *data, size_t lumplength, size_t selectpos)
{ {
@ -1427,38 +1448,9 @@ static boolean LoadSong(void *data, size_t lumplength, size_t selectpos)
} }
#endif #endif
/// ------------------------
void I_ShutdownMusic(void) // MUSIC SYSTEM
{ /// ------------------------
#ifdef HAVE_MIXER
if ((nomidimusic && nodigimusic) || !musicStarted)
return;
CONS_Printf("%s", M_GetText("I_ShutdownMusic: "));
I_UnRegisterSong(0);
I_StopDigSong();
Mix_CloseAudio();
#ifdef MIX_INIT
Mix_Quit();
#endif
CONS_Printf("%s", M_GetText("shut down\n"));
musicStarted = SDL_FALSE;
if (Msc_Mutex)
SDL_DestroyMutex(Msc_Mutex);
Msc_Mutex = NULL;
#endif
}
void I_InitMIDIMusic(void)
{
if (nodigimusic) I_InitMusic();
}
void I_InitDigMusic(void)
{
if (nomidimusic) I_InitMusic();
}
void I_InitMusic(void) void I_InitMusic(void)
{ {
@ -1532,7 +1524,7 @@ void I_InitMusic(void)
if (Mix_OpenAudio(audio.freq, audio.format, audio.channels, audio.samples) < 0) //open_music(&audio) if (Mix_OpenAudio(audio.freq, audio.format, audio.channels, audio.samples) < 0) //open_music(&audio)
{ {
CONS_Printf(M_GetText(" Unable to open music: %s\n"), Mix_GetError()); CONS_Printf(M_GetText(" Unable to open music: %s\n"), Mix_GetError());
nomidimusic = nodigimusic = true; midi_disabled = digital_disabled = true;
if (sound_started if (sound_started
#ifdef HW3SOUND #ifdef HW3SOUND
&& hws_mode == HWS_DEFAULT_MODE && hws_mode == HWS_DEFAULT_MODE
@ -1542,7 +1534,7 @@ void I_InitMusic(void)
if (SDL_OpenAudio(&audio, NULL) < 0) //retry if (SDL_OpenAudio(&audio, NULL) < 0) //retry
{ {
CONS_Printf("%s", M_GetText(" couldn't open audio with desired format\n")); CONS_Printf("%s", M_GetText(" couldn't open audio with desired format\n"));
nosound = true; sound_disabled = true;
sound_started = false; sound_started = false;
} }
else else
@ -1573,11 +1565,106 @@ void I_InitMusic(void)
#endif #endif
} }
boolean I_PlaySong(INT32 handle, boolean looping) void I_ShutdownMusic(void)
{ {
(void)handle;
#ifdef HAVE_MIXER #ifdef HAVE_MIXER
if (nomidimusic || !musicStarted || !music[handle]) if ((midi_disabled && digital_disabled) || !musicStarted)
return;
CONS_Printf("%s", M_GetText("I_ShutdownMusic: "));
I_UnloadSong();
I_StopSong();
Mix_CloseAudio();
#ifdef MIX_INIT
Mix_Quit();
#endif
CONS_Printf("%s", M_GetText("shut down\n"));
musicStarted = SDL_FALSE;
if (Msc_Mutex)
SDL_DestroyMutex(Msc_Mutex);
Msc_Mutex = NULL;
#endif
}
/// ------------------------
// MUSIC PROPERTIES
/// ------------------------
musictype_t I_SongType(void)
{
return MU_NONE;
}
boolean I_SongPlaying(void)
{
return false;
}
boolean I_SongPaused(void)
{
return false;
}
/// ------------------------
// MUSIC EFFECTS
/// ------------------------
boolean I_SetSongSpeed(float speed)
{
(void)speed;
return false;
}
/// ------------------------
// MUSIC PLAYBACK
// \todo Merge Digital and MIDI
/// ------------------------
boolean I_LoadSong(char *data, size_t len)
{
#ifdef HAVE_MIXER
if (midi_disabled || !musicStarted)
return false;
if (!LoadSong(data, len, 0))
return false;
if (music[0])
return true;
CONS_Printf(M_GetText("Couldn't load MIDI: %s\n"), Mix_GetError());
#else
(void)len;
(void)data;
#endif
return false;
}
void I_UnloadSong(void)
{
#ifdef HAVE_MIXER
if (midi_disabled || !musicStarted)
return;
Mix_HaltMusic();
while (Mix_PlayingMusic())
;
if (music[handle])
Mix_FreeMusic(music[handle]);
music[handle] = NULL;
LoadSong(NULL, 0, handle);
#else
(void)handle;
#endif
}
boolean I_PlaySong(boolean looping)
{
#ifdef HAVE_MIXER
if (!musicStarted || !music[handle])
return false; return false;
#ifdef MIXER_POS #ifdef MIXER_POS
@ -1598,6 +1685,28 @@ boolean I_PlaySong(INT32 handle, boolean looping)
return false; return false;
} }
void I_StopSong(void)
{
I_StopGME();
#ifdef HAVE_MIXER
if (digital_disabled)
return;
#ifdef MIXER_POS
if (canlooping)
Mix_HookMusicFinished(NULL);
#endif
Mix_HaltMusic();
while (Mix_PlayingMusic())
;
if (music[1])
Mix_FreeMusic(music[1]);
music[1] = NULL;
LoadSong(NULL, 0, 1);
}
static void I_PauseGME(void) static void I_PauseGME(void)
{ {
#ifdef HAVE_LIBGME #ifdef HAVE_LIBGME
@ -1605,12 +1714,12 @@ static void I_PauseGME(void)
#endif #endif
} }
void I_PauseSong(INT32 handle) void I_PauseSong(void)
{ {
(void)handle; (void)handle;
I_PauseGME(); I_PauseGME();
#ifdef HAVE_MIXER #ifdef HAVE_MIXER
if ((nomidimusic && nodigimusic) || !musicStarted) if ((midi_disabled && digital_disabled) || !musicStarted)
return; return;
Mix_PauseMusic(); Mix_PauseMusic();
@ -1625,12 +1734,12 @@ static void I_ResumeGME(void)
#endif #endif
} }
void I_ResumeSong(INT32 handle) void I_ResumeSong(void)
{ {
(void)handle; (void)handle;
I_ResumeGME(); I_ResumeGME();
#ifdef HAVE_MIXER #ifdef HAVE_MIXER
if ((nomidimusic && nodigimusic) || !musicStarted) if ((midi_disabled && digital_disabled) || !musicStarted)
return; return;
Mix_VolumeMusic(musicvol); Mix_VolumeMusic(musicvol);
@ -1639,60 +1748,10 @@ void I_ResumeSong(INT32 handle)
#endif #endif
} }
void I_StopSong(INT32 handle) void I_SetMusicVolume(UINT8 volume)
{
(void)handle;
#ifdef HAVE_MIXER
if (nomidimusic || !musicStarted)
return;
Mix_FadeOutMusic(MIDIfade);
#endif
}
void I_UnRegisterSong(INT32 handle)
{ {
#ifdef HAVE_MIXER #ifdef HAVE_MIXER
if ((midi_disabled && digital_disabled) || !musicStarted)
if (nomidimusic || !musicStarted)
return;
Mix_HaltMusic();
while (Mix_PlayingMusic())
;
if (music[handle])
Mix_FreeMusic(music[handle]);
music[handle] = NULL;
LoadSong(NULL, 0, handle);
#else
(void)handle;
#endif
}
INT32 I_RegisterSong(void *data, size_t len)
{
#ifdef HAVE_MIXER
if (nomidimusic || !musicStarted)
return false;
if (!LoadSong(data, len, 0))
return false;
if (music[0])
return true;
CONS_Printf(M_GetText("Couldn't load MIDI: %s\n"), Mix_GetError());
#else
(void)len;
(void)data;
#endif
return false;
}
void I_SetMIDIMusicVolume(UINT8 volume)
{
#ifdef HAVE_MIXER
if ((nomidimusic && nodigimusic) || !musicStarted)
return; return;
if (Msc_Mutex) SDL_LockMutex(Msc_Mutex); if (Msc_Mutex) SDL_LockMutex(Msc_Mutex);
@ -1704,6 +1763,18 @@ void I_SetMIDIMusicVolume(UINT8 volume)
#endif #endif
} }
boolean I_SetSongTrack(int track)
{
(void)track;
return false;
}
/// ------------------------
// MUSIC LOADING AND CLEANUP
// \todo Split logic between loading and playing,
// then move to Playback section
/// ------------------------
#ifdef HAVE_LIBGME #ifdef HAVE_LIBGME
static void I_CleanupGME(void *userdata) static void I_CleanupGME(void *userdata)
{ {
@ -1779,14 +1850,14 @@ boolean I_StartDigSong(const char *musicname, boolean looping)
return true; return true;
#ifdef HAVE_MIXER #ifdef HAVE_MIXER
if (nodigimusic) if (digital_disabled)
return false; return false;
snprintf(filename, sizeof filename, "o_%s", musicname); snprintf(filename, sizeof filename, "o_%s", musicname);
lumpnum = W_CheckNumForName(filename); lumpnum = W_CheckNumForName(filename);
I_StopDigSong(); I_StopSong();
if (lumpnum == LUMPERROR) if (lumpnum == LUMPERROR)
{ {
@ -1938,47 +2009,6 @@ static void I_StopGME(void)
#endif #endif
} }
void I_StopDigSong(void)
{
I_StopGME();
#ifdef HAVE_MIXER
if (nodigimusic)
return;
#ifdef MIXER_POS
if (canlooping)
Mix_HookMusicFinished(NULL);
#endif
Mix_HaltMusic();
while (Mix_PlayingMusic())
;
if (music[1])
Mix_FreeMusic(music[1]);
music[1] = NULL;
LoadSong(NULL, 0, 1);
#endif
}
void I_SetDigMusicVolume(UINT8 volume)
{
I_SetMIDIMusicVolume(volume);
}
boolean I_SetSongSpeed(float speed)
{
(void)speed;
return false;
}
boolean I_SetSongTrack(int track)
{
(void)track;
return false;
}
#ifdef MIXER_POS #ifdef MIXER_POS
static void SDLCALL I_FinishMusic(void) static void SDLCALL I_FinishMusic(void)
{ {

View file

@ -110,9 +110,9 @@ static LRESULT CALLBACK MainWndproc(HWND hWnd, UINT message, WPARAM wParam, LPAR
// pause music when alt-tab // pause music when alt-tab
if (appActive && !paused) if (appActive && !paused)
I_ResumeSong(0); I_ResumeSong();
else if (!paused) else if (!paused)
I_PauseSong(0); I_PauseSong();
{ {
HANDLE ci = GetStdHandle(STD_INPUT_HANDLE); HANDLE ci = GetStdHandle(STD_INPUT_HANDLE);
DWORD mode; DWORD mode;

View file

@ -42,7 +42,6 @@
static FMOD_SYSTEM *fsys; static FMOD_SYSTEM *fsys;
static FMOD_SOUND *music_stream; static FMOD_SOUND *music_stream;
static FMOD_CHANNEL *music_channel; static FMOD_CHANNEL *music_channel;
static boolean midimode;
static UINT8 music_volume, midi_volume, sfx_volume; static UINT8 music_volume, midi_volume, sfx_volume;
static INT32 current_track; static INT32 current_track;
@ -440,9 +439,9 @@ void I_SetSfxVolume(UINT8 volume)
sfx_volume = volume; sfx_volume = volume;
} }
// /// ------------------------
// MUSIC // MUSIC SYSTEM
// /// ------------------------
void I_InitMusic(void) void I_InitMusic(void)
{ {
@ -450,35 +449,103 @@ void I_InitMusic(void)
void I_ShutdownMusic(void) void I_ShutdownMusic(void)
{ {
I_ShutdownDigMusic(); I_StopSong();
I_ShutdownMIDIMusic();
} }
void I_PauseSong(INT32 handle) /// ------------------------
// MUSIC PROPERTIES
/// ------------------------
musictype_t I_SongType(void)
{ {
UNREFERENCED_PARAMETER(handle); #ifdef HAVE_LIBGME
if (gme)
return MU_GME;
#endif
if (!music_stream)
return MU_NONE;
FMOD_SOUND_TYPE type;
if (FMOD_Sound_GetFormat(music_stream, &type, NULL, NULL, NULL) == FMOD_OK)
{
switch(type)
{
case FMOD_SOUND_TYPE_WAV:
return MU_WAV;
case FMOD_SOUND_TYPE_MOD:
return MU_MOD;
case FMOD_SOUND_TYPE_MID:
return MU_MID;
case FMOD_SOUND_TYPE_OGGVORBIS:
return MU_OGG;
case FMOD_SOUND_TYPE_MP3:
return MU_MP3;
case FMOD_SOUND_TYPE_FLAC:
return MU_FLAC;
default:
return MU_NONE;
}
}
else
return MU_NONE;
}
boolean I_SongPlaying(void)
{
return (boolean)music_stream;
}
boolean I_SongPaused(void)
{
boolean fmpaused = false;
if (music_stream) if (music_stream)
FMR_MUSIC(FMOD_Channel_SetPaused(music_channel, true)); FMOD_Channel_GetPaused(music_channel, &fmpaused);
return fmpaused;
} }
void I_ResumeSong(INT32 handle) /// ------------------------
// MUSIC EFFECTS
/// ------------------------
boolean I_SetSongSpeed(float speed)
{ {
UNREFERENCED_PARAMETER(handle); FMOD_RESULT e;
if (music_stream) float frequency;
FMR_MUSIC(FMOD_Channel_SetPaused(music_channel, false)); if (!music_stream)
return false;
if (speed > 250.0f)
speed = 250.0f; //limit speed up to 250x
#ifdef HAVE_LIBGME
// Try to set GME speed
if (gme)
{
gme_set_tempo(gme, speed);
return true;
}
#endif
// Try to set Mod/Midi speed
e = FMOD_Sound_SetMusicSpeed(music_stream, speed);
if (e == FMOD_ERR_FORMAT)
{
// Just change pitch instead for Ogg/etc.
FMR(FMOD_Sound_GetDefaults(music_stream, &frequency, NULL, NULL, NULL));
FMR_MUSIC(FMOD_Channel_SetFrequency(music_channel, speed*frequency));
}
else
FMR_MUSIC(e);
return true;
} }
void I_InitDigMusic(void) /// ------------------------
{ // MUSIC PLAYBACK
} /// ------------------------
void I_ShutdownDigMusic(void) boolean I_LoadSong(char *data, size_t len)
{
if (!midimode)
I_StopDigSong();
}
boolean I_StartDigSong(const char *musicname, boolean looping)
{ {
char *data; char *data;
size_t len; size_t len;
@ -490,10 +557,7 @@ boolean I_StartDigSong(const char *musicname, boolean looping)
lumpnum = W_CheckNumForName(va("D_%s",musicname)); lumpnum = W_CheckNumForName(va("D_%s",musicname));
if (lumpnum == LUMPERROR) if (lumpnum == LUMPERROR)
return false; return false;
midimode = true;
} }
else
midimode = false;
data = (char *)W_CacheLumpNum(lumpnum, PU_MUSIC); data = (char *)W_CacheLumpNum(lumpnum, PU_MUSIC);
len = W_LumpLength(lumpnum); len = W_LumpLength(lumpnum);
@ -603,8 +667,6 @@ boolean I_StartDigSong(const char *musicname, boolean looping)
{ {
gme_equalizer_t gmeq = {GME_TREBLE, GME_BASS, 0,0,0,0,0,0,0,0}; gme_equalizer_t gmeq = {GME_TREBLE, GME_BASS, 0,0,0,0,0,0,0,0};
Z_Free(data); // We don't need this anymore. Z_Free(data); // We don't need this anymore.
gme_start_track(gme, 0);
current_track = 0;
gme_set_equalizer(gme,&gmeq); gme_set_equalizer(gme,&gmeq);
fmt.format = FMOD_SOUND_FORMAT_PCM16; fmt.format = FMOD_SOUND_FORMAT_PCM16;
fmt.defaultfrequency = 44100; fmt.defaultfrequency = 44100;
@ -613,6 +675,102 @@ boolean I_StartDigSong(const char *musicname, boolean looping)
fmt.decodebuffersize = (44100 * 2) / 35; fmt.decodebuffersize = (44100 * 2) / 35;
fmt.pcmreadcallback = GMEReadCallback; fmt.pcmreadcallback = GMEReadCallback;
fmt.userdata = gme; fmt.userdata = gme;
return true;
}
#endif
fmt.length = len;
FMOD_RESULT e = FMOD_System_CreateStream(fsys, data, FMOD_OPENMEMORY_POINT|(looping ? FMOD_LOOP_NORMAL : 0), &fmt, &music_stream);
if (e != FMOD_OK)
{
if (e == FMOD_ERR_FORMAT)
CONS_Alert(CONS_WARNING, "Failed to play music lump %s due to invalid format.\n", W_CheckNameForNum(lumpnum));
else
FMR(e);
return false;
}
// Try to find a loop point in streaming music formats (ogg, mp3)
FMOD_RESULT e;
FMOD_TAG tag;
unsigned int loopstart, loopend;
// A proper LOOPPOINT is its own tag, stupid.
e = FMOD_Sound_GetTag(music_stream, "LOOPPOINT", 0, &tag);
if (e != FMOD_ERR_TAGNOTFOUND)
{
FMR(e);
loopstart = atoi((char *)tag.data); // assumed to be a string data tag.
FMR(FMOD_Sound_GetLoopPoints(music_stream, NULL, FMOD_TIMEUNIT_PCM, &loopend, FMOD_TIMEUNIT_PCM));
if (loopstart > 0)
FMR(FMOD_Sound_SetLoopPoints(music_stream, loopstart, FMOD_TIMEUNIT_PCM, loopend, FMOD_TIMEUNIT_PCM));
return true;
}
// todo
// if(music type == MIDI)
// {
// FMR(FMOD_Sound_SetMode(music_stream, FMOD_LOOP_NORMAL));
// return true;
// }
// Use LOOPMS for time in miliseconds.
e = FMOD_Sound_GetTag(music_stream, "LOOPMS", 0, &tag);
if (e != FMOD_ERR_TAGNOTFOUND)
{
FMR(e);
loopstart = atoi((char *)tag.data); // assumed to be a string data tag.
FMR(FMOD_Sound_GetLoopPoints(music_stream, NULL, FMOD_TIMEUNIT_MS, &loopend, FMOD_TIMEUNIT_PCM));
if (loopstart > 0)
FMR(FMOD_Sound_SetLoopPoints(music_stream, loopstart, FMOD_TIMEUNIT_MS, loopend, FMOD_TIMEUNIT_PCM));
return true;
}
// Try to fetch it from the COMMENT tag, like A.J. Freda
e = FMOD_Sound_GetTag(music_stream, "COMMENT", 0, &tag);
if (e != FMOD_ERR_TAGNOTFOUND)
{
char *loopText;
// Handle any errors that arose, first
FMR(e);
// Figure out where the number starts
loopText = strstr((char *)tag.data,"LOOPPOINT=");
if (loopText != NULL)
{
// Skip the "LOOPPOINT=" part.
loopText += 10;
// Convert it to our looppoint
// FMOD seems to ensure the tag is properly NULL-terminated.
// atoi will stop when it reaches anything that's not a number.
loopstart = atoi(loopText);
// Now do the rest like above
FMR(FMOD_Sound_GetLoopPoints(music_stream, NULL, FMOD_TIMEUNIT_PCM, &loopend, FMOD_TIMEUNIT_PCM));
if (loopstart > 0)
FMR(FMOD_Sound_SetLoopPoints(music_stream, loopstart, FMOD_TIMEUNIT_PCM, loopend, FMOD_TIMEUNIT_PCM));
}
return true;
}
// No special loop point
return true;
}
void I_UnloadSong(void)
{
UNREFERENCED_PARAMETER(handle);
if (music_stream)
FMR(FMOD_Sound_Release(music_stream));
music_stream = NULL;
}
boolean I_PlaySong(boolean looping)
{
#ifdef HAVE_LIBGME
if (gme)
{
gme_start_track(gme, 0);
current_track = 0;
FMR(FMOD_System_CreateStream(fsys, NULL, FMOD_OPENUSER | (looping ? FMOD_LOOP_NORMAL : 0), &fmt, &music_stream)); FMR(FMOD_System_CreateStream(fsys, NULL, FMOD_OPENUSER | (looping ? FMOD_LOOP_NORMAL : 0), &fmt, &music_stream));
FMR(FMOD_System_PlaySound(fsys, FMOD_CHANNEL_FREE, music_stream, false, &music_channel)); FMR(FMOD_System_PlaySound(fsys, FMOD_CHANNEL_FREE, music_stream, false, &music_channel));
FMR(FMOD_Channel_SetVolume(music_channel, music_volume / 31.0)); FMR(FMOD_Channel_SetVolume(music_channel, music_volume / 31.0));
@ -621,139 +779,55 @@ boolean I_StartDigSong(const char *musicname, boolean looping)
} }
#endif #endif
fmt.length = len;
{
FMOD_RESULT e = FMOD_System_CreateStream(fsys, data, FMOD_OPENMEMORY_POINT|(looping ? FMOD_LOOP_NORMAL : 0), &fmt, &music_stream);
if (e != FMOD_OK)
{
if (e == FMOD_ERR_FORMAT)
CONS_Alert(CONS_WARNING, "Failed to play music lump %s due to invalid format.\n", W_CheckNameForNum(lumpnum));
else
FMR(e);
return false;
}
}
FMR(FMOD_System_PlaySound(fsys, FMOD_CHANNEL_FREE, music_stream, false, &music_channel)); FMR(FMOD_System_PlaySound(fsys, FMOD_CHANNEL_FREE, music_stream, false, &music_channel));
if (midimode) if (I_SongType() != MU_MID)
FMR(FMOD_Channel_SetVolume(music_channel, midi_volume / 31.0)); FMR(FMOD_Channel_SetVolume(music_channel, midi_volume / 31.0));
else else
FMR(FMOD_Channel_SetVolume(music_channel, music_volume / 31.0)); FMR(FMOD_Channel_SetVolume(music_channel, music_volume / 31.0));
FMR(FMOD_Channel_SetPriority(music_channel, 0)); FMR(FMOD_Channel_SetPriority(music_channel, 0));
current_track = 0; current_track = 0;
// Try to find a loop point in streaming music formats (ogg, mp3)
if (looping)
{
FMOD_RESULT e;
FMOD_TAG tag;
unsigned int loopstart, loopend;
// A proper LOOPPOINT is its own tag, stupid.
e = FMOD_Sound_GetTag(music_stream, "LOOPPOINT", 0, &tag);
if (e != FMOD_ERR_TAGNOTFOUND)
{
FMR(e);
loopstart = atoi((char *)tag.data); // assumed to be a string data tag.
FMR(FMOD_Sound_GetLoopPoints(music_stream, NULL, FMOD_TIMEUNIT_PCM, &loopend, FMOD_TIMEUNIT_PCM));
if (loopstart > 0)
FMR(FMOD_Sound_SetLoopPoints(music_stream, loopstart, FMOD_TIMEUNIT_PCM, loopend, FMOD_TIMEUNIT_PCM));
return true;
}
// Use LOOPMS for time in miliseconds.
e = FMOD_Sound_GetTag(music_stream, "LOOPMS", 0, &tag);
if (e != FMOD_ERR_TAGNOTFOUND)
{
FMR(e);
loopstart = atoi((char *)tag.data); // assumed to be a string data tag.
FMR(FMOD_Sound_GetLoopPoints(music_stream, NULL, FMOD_TIMEUNIT_MS, &loopend, FMOD_TIMEUNIT_PCM));
if (loopstart > 0)
FMR(FMOD_Sound_SetLoopPoints(music_stream, loopstart, FMOD_TIMEUNIT_MS, loopend, FMOD_TIMEUNIT_PCM));
return true;
}
// Try to fetch it from the COMMENT tag, like A.J. Freda
e = FMOD_Sound_GetTag(music_stream, "COMMENT", 0, &tag);
if (e != FMOD_ERR_TAGNOTFOUND)
{
char *loopText;
// Handle any errors that arose, first
FMR(e);
// Figure out where the number starts
loopText = strstr((char *)tag.data,"LOOPPOINT=");
if (loopText != NULL)
{
// Skip the "LOOPPOINT=" part.
loopText += 10;
// Convert it to our looppoint
// FMOD seems to ensure the tag is properly NULL-terminated.
// atoi will stop when it reaches anything that's not a number.
loopstart = atoi(loopText);
// Now do the rest like above
FMR(FMOD_Sound_GetLoopPoints(music_stream, NULL, FMOD_TIMEUNIT_PCM, &loopend, FMOD_TIMEUNIT_PCM));
if (loopstart > 0)
FMR(FMOD_Sound_SetLoopPoints(music_stream, loopstart, FMOD_TIMEUNIT_PCM, loopend, FMOD_TIMEUNIT_PCM));
}
return true;
}
}
// No special loop point, but we're playing so it's all good.
return true; return true;
} }
void I_StopDigSong(void) void I_StopSong(void)
{ {
if (music_stream)
FMR(FMOD_Sound_Release(music_stream));
music_stream = NULL;
#ifdef HAVE_LIBGME #ifdef HAVE_LIBGME
if (gme) if (gme)
gme_delete(gme); gme_delete(gme);
gme = NULL; gme = NULL;
#endif #endif
current_track = -1; current_track = -1;
I_UnloadSong();
} }
void I_SetDigMusicVolume(UINT8 volume) void I_PauseSong(void)
{ {
// volume is 0 to 31. UNREFERENCED_PARAMETER(handle);
music_volume = volume; if (music_stream)
if (!midimode && music_stream) FMR_MUSIC(FMOD_Channel_SetPaused(music_channel, true));
FMR_MUSIC(FMOD_Channel_SetVolume(music_channel, volume / 31.0));
} }
boolean I_SetSongSpeed(float speed) void I_ResumeSong(void)
{
UNREFERENCED_PARAMETER(handle);
if (music_stream)
FMR_MUSIC(FMOD_Channel_SetPaused(music_channel, false));
}
void I_SetMusicVolume(UINT8 volume)
{ {
FMOD_RESULT e;
float frequency;
if (!music_stream) if (!music_stream)
return false; return;
if (speed > 250.0f)
speed = 250.0f; //limit speed up to 250x
#ifdef HAVE_LIBGME // volume is 0 to 31.
// Try to set GME speed if (I_SongType() == MU_MID)
if (gme) music_volume = 31; // windows bug hack
{
gme_set_tempo(gme, speed);
return true;
}
#endif
// Try to set Mod/Midi speed
e = FMOD_Sound_SetMusicSpeed(music_stream, speed);
if (e == FMOD_ERR_FORMAT)
{
// Just change pitch instead for Ogg/etc.
FMR(FMOD_Sound_GetDefaults(music_stream, &frequency, NULL, NULL, NULL));
FMR_MUSIC(FMOD_Channel_SetFrequency(music_channel, speed*frequency));
}
else else
FMR_MUSIC(e); music_volume = volume;
return true; FMR_MUSIC(FMOD_Channel_SetVolume(music_channel, music_volume / 31.0));
} }
boolean I_SetSongTrack(INT32 track) boolean I_SetSongTrack(INT32 track)
@ -800,62 +874,3 @@ boolean I_SetSongTrack(INT32 track)
} }
return false; return false;
} }
//
// Fuck MIDI. ... Okay fine, you can have your silly D_-only mode.
//
void I_InitMIDIMusic(void)
{
}
void I_ShutdownMIDIMusic(void)
{
if (midimode)
I_StopSong(0);
}
void I_SetMIDIMusicVolume(UINT8 volume)
{
// volume is 0 to 31.
midi_volume = volume;
if (midimode && music_stream)
FMR_MUSIC(FMOD_Channel_SetVolume(music_channel, volume / 31.0));
}
INT32 I_RegisterSong(void *data, size_t len)
{
FMOD_CREATESOUNDEXINFO fmt;
memset(&fmt, 0, sizeof(FMOD_CREATESOUNDEXINFO));
fmt.cbsize = sizeof(FMOD_CREATESOUNDEXINFO);
fmt.length = len;
FMR(FMOD_System_CreateStream(fsys, (char *)data, FMOD_OPENMEMORY_POINT, &fmt, &music_stream));
return 1337;
}
boolean I_PlaySong(INT32 handle, boolean looping)
{
if (1337 == handle)
{
midimode = true;
if (looping)
FMR(FMOD_Sound_SetMode(music_stream, FMOD_LOOP_NORMAL));
FMR(FMOD_System_PlaySound(fsys, FMOD_CHANNEL_FREE, music_stream, false, &music_channel));
FMR_MUSIC(FMOD_Channel_SetVolume(music_channel, midi_volume / 31.0));
FMR_MUSIC(FMOD_Channel_SetPriority(music_channel, 0));
}
return true;
}
void I_StopSong(INT32 handle)
{
I_UnRegisterSong(handle);
}
void I_UnRegisterSong(INT32 handle)
{
UNREFERENCED_PARAMETER(handle);
if (music_stream)
FMR(FMOD_Sound_Release(music_stream));
music_stream = NULL;
}