--- a/hedgewars/uSound.pas Sun Oct 28 14:08:13 2018 +0100
+++ b/hedgewars/uSound.pas Tue Oct 30 23:08:43 2018 +0100
@@ -62,14 +62,15 @@
// Plays the sound snd [from a given voicepack],
// if keepPlaying is given and true,
// then the sound's playback won't be interrupted if asked to play again.
-procedure PlaySound(snd: TSound);
-procedure PlaySound(snd: TSound; keepPlaying: boolean);
-procedure PlaySound(snd: TSound; keepPlaying: boolean; ignoreMask: boolean);
-procedure PlaySound(snd: TSound; keepPlaying, ignoreMask, soundAsMusic: boolean);
-procedure PlaySoundV(snd: TSound; voicepack: PVoicepack);
-procedure PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying: boolean);
-procedure PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying, ignoreMask: boolean);
-procedure PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying, ignoreMask, soundAsMusic: boolean);
+// Returns true if sound was found and is played, false otherwise.
+function PlaySound(snd: TSound): boolean;
+function PlaySound(snd: TSound; keepPlaying: boolean): boolean;
+function PlaySound(snd: TSound; keepPlaying: boolean; ignoreMask: boolean): boolean;
+function PlaySound(snd: TSound; keepPlaying, ignoreMask, soundAsMusic: boolean): boolean;
+function PlaySoundV(snd: TSound; voicepack: PVoicepack): boolean;
+function PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying: boolean): boolean;
+function PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying, ignoreMask: boolean): boolean;
+function PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying, ignoreMask, soundAsMusic: boolean): boolean;
// Plays/stops a sound to replace the main background music temporarily.
procedure PlayMusicSound(snd: TSound);
@@ -89,8 +90,11 @@
procedure StopSoundChan(chn: LongInt);
procedure StopSoundChan(chn, fadems: LongInt);
+// Add voice to the voice queue
procedure AddVoice(snd: TSound; voicepack: PVoicepack);
-procedure AddVoice(snd: TSound; voicepack: PVoicepack; ignoreMask: boolean);
+procedure AddVoice(snd: TSound; voicepack: PVoicepack; ignoreMask, isFallback: boolean);
+
+// Actually play next voice
procedure PlayNextVoice;
@@ -125,6 +129,7 @@
var Volume: LongInt;
SoundTimerTicks: Longword;
+ LastVoiceFailed: boolean;
implementation
uses uVariables, uConsole, uCommands, uDebug, uPhysFSLayer;
@@ -140,14 +145,14 @@
isAutoDampening: boolean;
isSEBackup: boolean;
VoiceList : array[0..7] of TVoice = (
- ( snd: sndNone; voicepack: nil),
- ( snd: sndNone; voicepack: nil),
- ( snd: sndNone; voicepack: nil),
- ( snd: sndNone; voicepack: nil),
- ( snd: sndNone; voicepack: nil),
- ( snd: sndNone; voicepack: nil),
- ( snd: sndNone; voicepack: nil),
- ( snd: sndNone; voicepack: nil));
+ ( snd: sndNone; voicepack: nil; isFallback: false),
+ ( snd: sndNone; voicepack: nil; isFallback: false),
+ ( snd: sndNone; voicepack: nil; isFallback: false),
+ ( snd: sndNone; voicepack: nil; isFallback: false),
+ ( snd: sndNone; voicepack: nil; isFallback: false),
+ ( snd: sndNone; voicepack: nil; isFallback: false),
+ ( snd: sndNone; voicepack: nil; isFallback: false),
+ ( snd: sndNone; voicepack: nil; isFallback: false));
Soundz: array[TSound] of record
FileName: string[31];
Path, AltPath : TPathType;
@@ -499,45 +504,47 @@
GetFallbackV := sndNone;
end;
-procedure PlaySound(snd: TSound);
+function PlaySound(snd: TSound): boolean;
begin
- PlaySoundV(snd, nil, false, false, false);
+ PlaySound:= PlaySoundV(snd, nil, false, false, false);
end;
-procedure PlaySound(snd: TSound; keepPlaying: boolean);
+function PlaySound(snd: TSound; keepPlaying: boolean): boolean;
begin
- PlaySoundV(snd, nil, keepPlaying, false, false);
+ PlaySound:= PlaySoundV(snd, nil, keepPlaying, false, false);
end;
-procedure PlaySound(snd: TSound; keepPlaying: boolean; ignoreMask: boolean);
+function PlaySound(snd: TSound; keepPlaying: boolean; ignoreMask: boolean): boolean;
begin
- PlaySoundV(snd, nil, keepPlaying, ignoreMask, false);
+ PlaySound:= PlaySoundV(snd, nil, keepPlaying, ignoreMask, false);
end;
-procedure PlaySound(snd: TSound; keepPlaying: boolean; ignoreMask, soundAsMusic: boolean);
+function PlaySound(snd: TSound; keepPlaying: boolean; ignoreMask, soundAsMusic: boolean): boolean;
begin
- PlaySoundV(snd, nil, keepPlaying, ignoreMask, soundAsMusic);
+ PlaySound:= PlaySoundV(snd, nil, keepPlaying, ignoreMask, soundAsMusic);
end;
-procedure PlaySoundV(snd: TSound; voicepack: PVoicepack);
+function PlaySoundV(snd: TSound; voicepack: PVoicepack): boolean;
begin
- PlaySoundV(snd, voicepack, false, false, false);
+ PlaySoundV:= PlaySoundV(snd, voicepack, false, false, false);
end;
-procedure PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying: boolean);
+function PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying: boolean): boolean;
begin
- PlaySoundV(snd, voicepack, keepPlaying, false, false);
+ PlaySoundV:= PlaySoundV(snd, voicepack, keepPlaying, false, false);
end;
-procedure PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying, ignoreMask: boolean);
+function PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying, ignoreMask: boolean): boolean;
begin
- PlaySoundV(snd, voicepack, keepPlaying, ignoreMask, false);
+ PlaySoundV:= PlaySoundV(snd, voicepack, keepPlaying, ignoreMask, false);
end;
-procedure PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying, ignoreMask, soundAsMusic: boolean);
+function PlaySoundV(snd: TSound; voicepack: PVoicepack; keepPlaying, ignoreMask, soundAsMusic: boolean): boolean;
var s:shortstring;
rwops: PSDL_RWops;
begin
+ s:= cPathz[Soundz[snd].Path] + '/' + voicepack^.name + '/' + Soundz[snd].FileName;
+ PlaySoundV:= false;
if ((not isSoundEnabled) and (not (soundAsMusic and isMusicEnabled))) or fastUntilLag then
exit;
@@ -576,7 +583,8 @@
else
WriteLnToConsole(msgOK)
end;
- lastChan[snd]:= Mix_PlayChannelTimed(-1, voicepack^.chunks[snd], 0, -1)
+ lastChan[snd]:= Mix_PlayChannelTimed(-1, voicepack^.chunks[snd], 0, -1);
+ PlaySoundV:= true;
end
else
begin
@@ -597,7 +605,8 @@
if SDLCheck(defVoicepack^.chunks[snd] <> nil, 'Mix_LoadWAV_RW', true) then exit;
WriteLnToConsole(msgOK);
end;
- lastChan[snd]:= Mix_PlayChannelTimed(-1, defVoicepack^.chunks[snd], 0, -1)
+ lastChan[snd]:= Mix_PlayChannelTimed(-1, defVoicepack^.chunks[snd], 0, -1);
+ PlaySoundV:= true;
end;
end;
@@ -615,10 +624,23 @@
procedure AddVoice(snd: TSound; voicepack: PVoicepack);
begin
- AddVoice(snd, voicepack, false);
+ AddVoice(snd, voicepack, false, false);
end;
-procedure AddVoice(snd: TSound; voicepack: PVoicepack; ignoreMask: boolean);
+{
+AddVoice: Add a voice to the voice queue.
+* snd: Sound ID
+* voicepack: Hedgehog voicepack
+* ignoreMask: If true, the sound will be played anyway if masked by Lua
+* isFallback: If true, this sound is added as fallback if the sound previously added to the
+ queue was not found. Useful to make sure a voice is always played, even if
+ a voicepack is incomplete.
+ Example:
+ AddVoice(sndRevenge, voiceAttacker);
+ AddVoice(sndRegret, voiceVictim, false, true);
+ --> plays sndRegret if sndRevenge could not be played.
+}
+procedure AddVoice(snd: TSound; voicepack: PVoicepack; ignoreMask, isFallback: boolean);
var i : LongInt;
begin
@@ -646,11 +668,13 @@
begin
VoiceList[i].snd:= snd;
VoiceList[i].voicepack:= voicepack;
+ VoiceList[i].isFallback:= isFallback;
end
end;
procedure PlayNextVoice;
var i : LongInt;
+ played : boolean;
begin
if (not isSoundEnabled) or fastUntilLag or ((LastVoice.snd <> sndNone) and (lastChan[LastVoice.snd] <> -1) and (Mix_Playing(lastChan[LastVoice.snd]) <> 0)) then
exit;
@@ -658,14 +682,19 @@
while (i<High(VoiceList)) and (VoiceList[i].snd = sndNone) do
inc(i);
- if (VoiceList[i].snd <> sndNone) then
+ played:= false;
+ if (VoiceList[i].snd <> sndNone) and ((not VoiceList[i].isFallback) or LastVoiceFailed) then
begin
LastVoice.snd:= VoiceList[i].snd;
LastVoice.voicepack:= VoiceList[i].voicepack;
+ LastVoice.isFallback:= VoiceList[i].isFallback;
VoiceList[i].snd:= sndNone;
- PlaySoundV(LastVoice.snd, LastVoice.voicepack)
+ played:= PlaySoundV(LastVoice.snd, LastVoice.voicepack);
+ // Remember if sound was not played.
+ LastVoiceFailed:= (not played);
end
- else LastVoice.snd:= sndNone;
+ else
+ LastVoice.snd:= sndNone;
end;
function LoopSound(snd: TSound): LongInt;
@@ -965,6 +994,7 @@
Volume:= 0;
SoundTimerTicks:= 0;
defVoicepack:= AskForVoicepack('Default');
+ LastVoiceFailed:= false;
for i:= Low(TSound) to High(TSound) do
lastChan[i]:= -1;