hedgewars/uSound.pas
changeset 2948 3f21a9dc93d0
parent 2905 f3c79f7193a9
child 3038 4e48c276a468
equal deleted inserted replaced
2947:803b277e4894 2948:3f21a9dc93d0
    21 unit uSound;
    21 unit uSound;
    22 interface
    22 interface
    23 uses SDLh, uConsts;
    23 uses SDLh, uConsts;
    24 
    24 
    25 type PVoicepack = ^TVoicepack;
    25 type PVoicepack = ^TVoicepack;
    26 	TVoicepack = record
    26     TVoicepack = record
    27 		name: shortstring;
    27         name: shortstring;
    28 		chunks: array [TSound] of PMixChunk;
    28         chunks: array [TSound] of PMixChunk;
    29 		end;
    29         end;
    30 
    30 
    31 var MusicFN: shortstring;
    31 var MusicFN: shortstring;
    32 
    32 
    33 procedure init_uSound;
    33 procedure init_uSound;
    34 procedure free_uSound;
    34 procedure free_uSound;
    62 function  AskForVoicepack(name: shortstring): Pointer;
    62 function  AskForVoicepack(name: shortstring): Pointer;
    63 var i: Longword;
    63 var i: Longword;
    64 begin
    64 begin
    65 i:= 0;
    65 i:= 0;
    66 while (voicepacks[i].name <> name) and (voicepacks[i].name <> '') do
    66 while (voicepacks[i].name <> name) and (voicepacks[i].name <> '') do
    67 	begin
    67     begin
    68 	inc(i);
    68     inc(i);
    69 	TryDo(i <= cMaxTeams, 'Engine bug: AskForVoicepack i > cMaxTeams', true)
    69     TryDo(i <= cMaxTeams, 'Engine bug: AskForVoicepack i > cMaxTeams', true)
    70 	end;
    70     end;
    71 
    71 
    72 voicepacks[i].name:= name;
    72 voicepacks[i].name:= name;
    73 AskForVoicepack:= @voicepacks[i]
    73 AskForVoicepack:= @voicepacks[i]
    74 end;
    74 end;
    75 
    75 
    76 procedure InitSound;
    76 procedure InitSound;
    77 var i: TSound;
    77 var i: TSound;
    78 begin
    78 begin
    79 	if not isSoundEnabled then exit;
    79     if not isSoundEnabled then exit;
    80 	WriteToConsole('Init sound...');
    80     WriteToConsole('Init sound...');
    81 	isSoundEnabled:= SDL_InitSubSystem(SDL_INIT_AUDIO) >= 0;
    81     isSoundEnabled:= SDL_InitSubSystem(SDL_INIT_AUDIO) >= 0;
    82 
    82 
    83 	if isSoundEnabled then
    83     if isSoundEnabled then
    84 		isSoundEnabled:= Mix_OpenAudio(44100, $8010, 2, 1024) = 0;
    84         isSoundEnabled:= Mix_OpenAudio(44100, $8010, 2, 1024) = 0;
    85 
    85 
    86 	if isSoundEnabled then
    86     if isSoundEnabled then
    87 		WriteLnToConsole(msgOK)
    87         WriteLnToConsole(msgOK)
    88 	else
    88     else
    89 		WriteLnToConsole(msgFailed);
    89         WriteLnToConsole(msgFailed);
    90 
    90 
    91 	Mix_AllocateChannels(Succ(chanTPU));
    91     Mix_AllocateChannels(Succ(chanTPU));
    92 	if isMusicEnabled then
    92     if isMusicEnabled then
    93 		Mix_VolumeMusic(50);
    93         Mix_VolumeMusic(50);
    94 	for i:= Low(TSound) to High(TSound) do
    94     for i:= Low(TSound) to High(TSound) do
    95 		lastChan[i]:= -1;
    95         lastChan[i]:= -1;
    96 
    96 
    97 	Volume:= 0;
    97     Volume:= 0;
    98 	ChangeVolume(cInitVolume)
    98     ChangeVolume(cInitVolume)
    99 end;
    99 end;
   100 
   100 
   101 procedure ReleaseSound;
   101 procedure ReleaseSound;
   102 var i: TSound;
   102 var i: TSound;
   103 	t: Longword;
   103     t: Longword;
   104 begin
   104 begin
   105 for t:= 0 to cMaxTeams do
   105 for t:= 0 to cMaxTeams do
   106 	if voicepacks[t].name <> '' then
   106     if voicepacks[t].name <> '' then
   107 		for i:= Low(TSound) to High(TSound) do
   107         for i:= Low(TSound) to High(TSound) do
   108 			if voicepacks[t].chunks[i] <> nil then
   108             if voicepacks[t].chunks[i] <> nil then
   109 				Mix_FreeChunk(voicepacks[t].chunks[i]);
   109                 Mix_FreeChunk(voicepacks[t].chunks[i]);
   110 
   110 
   111 Mix_FreeMusic(Mus);
   111 Mix_FreeMusic(Mus);
   112 Mix_CloseAudio();
   112 Mix_CloseAudio();
   113 end;
   113 end;
   114 
   114 
   115 procedure SoundLoad;
   115 procedure SoundLoad;
   116 var i: TSound;
   116 var i: TSound;
   117 	s: shortstring;
   117     s: shortstring;
   118 	t: Longword;
   118     t: Longword;
   119 begin
   119 begin
   120 	if not isSoundEnabled then exit;
   120     if not isSoundEnabled then exit;
   121 
   121 
   122 {$IFDEF SDL_MIXER_NEWER}
   122 {$IFDEF SDL_MIXER_NEWER}
   123 	WriteToConsole('Init SDL_mixer... ');
   123     WriteToConsole('Init SDL_mixer... ');
   124 	SDLTry(Mix_Init(MIX_INIT_OGG) <> 0, true);
   124     SDLTry(Mix_Init(MIX_INIT_OGG) <> 0, true);
   125 	WriteLnToConsole(msgOK);
   125     WriteLnToConsole(msgOK);
   126 {$ENDIF}
   126 {$ENDIF}
   127 
   127 
   128 	defVoicepack:= AskForVoicepack('Default');
   128     defVoicepack:= AskForVoicepack('Default');
   129 
   129 
   130 for i:= Low(TSound) to High(TSound) do
   130 for i:= Low(TSound) to High(TSound) do
   131 	if (Soundz[i].Path <> ptVoices) and (Soundz[i].FileName <> '') then
   131     if (Soundz[i].Path <> ptVoices) and (Soundz[i].FileName <> '') then
   132 		begin
   132         begin
   133 		s:= Pathz[Soundz[i].Path] + '/' + Soundz[i].FileName;
   133         s:= Pathz[Soundz[i].Path] + '/' + Soundz[i].FileName;
   134 		WriteToConsole(msgLoading + s + ' ');
   134         WriteToConsole(msgLoading + s + ' ');
   135 		defVoicepack^.chunks[i]:= Mix_LoadWAV_RW(SDL_RWFromFile(Str2PChar(s), 'rb'), 1);
   135         defVoicepack^.chunks[i]:= Mix_LoadWAV_RW(SDL_RWFromFile(Str2PChar(s), 'rb'), 1);
   136 		TryDo(defVoicepack^.chunks[i] <> nil, msgFailed, true);
   136         TryDo(defVoicepack^.chunks[i] <> nil, msgFailed, true);
   137 		WriteLnToConsole(msgOK);
   137         WriteLnToConsole(msgOK);
   138 		end;
   138         end;
   139 
   139 
   140 for t:= 0 to cMaxTeams do
   140 for t:= 0 to cMaxTeams do
   141 	if voicepacks[t].name <> '' then
   141     if voicepacks[t].name <> '' then
   142 		for i:= Low(TSound) to High(TSound) do
   142         for i:= Low(TSound) to High(TSound) do
   143 			if (Soundz[i].Path = ptVoices) and (Soundz[i].FileName <> '') then
   143             if (Soundz[i].Path = ptVoices) and (Soundz[i].FileName <> '') then
   144 				begin
   144                 begin
   145 				s:= Pathz[Soundz[i].Path] + '/' + voicepacks[t].name + '/' + Soundz[i].FileName;
   145                 s:= Pathz[Soundz[i].Path] + '/' + voicepacks[t].name + '/' + Soundz[i].FileName;
   146 				WriteToConsole(msgLoading + s + ' ');
   146                 WriteToConsole(msgLoading + s + ' ');
   147 				voicepacks[t].chunks[i]:= Mix_LoadWAV_RW(SDL_RWFromFile(Str2PChar(s), 'rb'), 1);
   147                 voicepacks[t].chunks[i]:= Mix_LoadWAV_RW(SDL_RWFromFile(Str2PChar(s), 'rb'), 1);
   148 				if voicepacks[t].chunks[i] = nil then
   148                 if voicepacks[t].chunks[i] = nil then
   149 					WriteLnToConsole(msgFailed)
   149                     WriteLnToConsole(msgFailed)
   150 				else
   150                 else
   151 					WriteLnToConsole(msgOK)
   151                     WriteLnToConsole(msgOK)
   152 				end;
   152                 end;
   153 {$IFDEF SDL_MIXER_NEWER}
   153 {$IFDEF SDL_MIXER_NEWER}
   154 	Mix_Quit();
   154     Mix_Quit();
   155 {$ENDIF}	
   155 {$ENDIF}    
   156 end;
   156 end;
   157 
   157 
   158 procedure PlaySound(snd: TSound);
   158 procedure PlaySound(snd: TSound);
   159 begin
   159 begin
   160 	PlaySound(snd, nil);
   160     PlaySound(snd, nil);
   161 end;
   161 end;
   162 
   162 
   163 procedure PlaySound(snd: TSound; voicepack: PVoicepack);
   163 procedure PlaySound(snd: TSound; voicepack: PVoicepack);
   164 begin
   164 begin
   165 if (not isSoundEnabled) or fastUntilLag then exit;
   165 if (not isSoundEnabled) or fastUntilLag then exit;
   166 
   166 
   167 if (voicepack <> nil) and (voicepack^.chunks[snd] <> nil) then
   167 if (voicepack <> nil) and (voicepack^.chunks[snd] <> nil) then
   168 	lastChan[snd]:= Mix_PlayChannelTimed(-1, voicepack^.chunks[snd], 0, -1)
   168     lastChan[snd]:= Mix_PlayChannelTimed(-1, voicepack^.chunks[snd], 0, -1)
   169 else
   169 else
   170 	lastChan[snd]:= Mix_PlayChannelTimed(-1, defVoicepack^.chunks[snd], 0, -1)
   170     lastChan[snd]:= Mix_PlayChannelTimed(-1, defVoicepack^.chunks[snd], 0, -1)
   171 end;
   171 end;
   172 
   172 
   173 function LoopSound(snd: TSound): LongInt;
   173 function LoopSound(snd: TSound): LongInt;
   174 begin
   174 begin
   175 	LoopSound:= LoopSound(snd, nil)
   175     LoopSound:= LoopSound(snd, nil)
   176 end;
   176 end;
   177 
   177 
   178 function LoopSound(snd: TSound; voicepack: PVoicepack): LongInt;
   178 function LoopSound(snd: TSound; voicepack: PVoicepack): LongInt;
   179 begin
   179 begin
   180 if (not isSoundEnabled) or fastUntilLag then
   180 if (not isSoundEnabled) or fastUntilLag then
   181 	begin
   181     begin
   182 	LoopSound:= -1;
   182     LoopSound:= -1;
   183 	exit
   183     exit
   184 	end;
   184     end;
   185 
   185 
   186 if (voicepack <> nil) and (voicepack^.chunks[snd] <> nil) then
   186 if (voicepack <> nil) and (voicepack^.chunks[snd] <> nil) then
   187 	LoopSound:= Mix_PlayChannelTimed(-1, voicepack^.chunks[snd], -1, -1)
   187     LoopSound:= Mix_PlayChannelTimed(-1, voicepack^.chunks[snd], -1, -1)
   188 else
   188 else
   189 	LoopSound:= Mix_PlayChannelTimed(-1, defVoicepack^.chunks[snd], -1, -1)
   189     LoopSound:= Mix_PlayChannelTimed(-1, defVoicepack^.chunks[snd], -1, -1)
   190 end;
   190 end;
   191 
   191 
   192 procedure StopSound(snd: TSound);
   192 procedure StopSound(snd: TSound);
   193 begin
   193 begin
   194 if not isSoundEnabled then exit;
   194 if not isSoundEnabled then exit;
   195 if (lastChan[snd] <> -1) and (Mix_Playing(lastChan[snd]) <> 0) then
   195 if (lastChan[snd] <> -1) and (Mix_Playing(lastChan[snd]) <> 0) then
   196 	begin
   196     begin
   197 	Mix_HaltChannel(lastChan[snd]);
   197     Mix_HaltChannel(lastChan[snd]);
   198 	lastChan[snd]:= -1;
   198     lastChan[snd]:= -1;
   199 	end;
   199     end;
   200 end;
   200 end;
   201 
   201 
   202 procedure StopSound(chn: LongInt);
   202 procedure StopSound(chn: LongInt);
   203 begin
   203 begin
   204 if not isSoundEnabled then exit;
   204 if not isSoundEnabled then exit;
   207 
   207 
   208 procedure PlayMusic;
   208 procedure PlayMusic;
   209 var s: shortstring;
   209 var s: shortstring;
   210 begin
   210 begin
   211 if (not isSoundEnabled)
   211 if (not isSoundEnabled)
   212 	or (MusicFN = '')
   212     or (MusicFN = '')
   213 	or (not isMusicEnabled) then exit;
   213     or (not isMusicEnabled) then exit;
   214 
   214 
   215 s:= PathPrefix + '/Music/' + MusicFN;
   215 s:= PathPrefix + '/Music/' + MusicFN;
   216 WriteToConsole(msgLoading + s + ' ');
   216 WriteToConsole(msgLoading + s + ' ');
   217 
   217 
   218 Mus:= Mix_LoadMUS(Str2PChar(s));
   218 Mus:= Mix_LoadMUS(Str2PChar(s));
   223 end;
   223 end;
   224 
   224 
   225 function ChangeVolume(voldelta: LongInt): LongInt;
   225 function ChangeVolume(voldelta: LongInt): LongInt;
   226 begin
   226 begin
   227 if not isSoundEnabled then
   227 if not isSoundEnabled then
   228 	exit(0);
   228     exit(0);
   229 
   229 
   230 inc(Volume, voldelta);
   230 inc(Volume, voldelta);
   231 if Volume < 0 then Volume:= 0;
   231 if Volume < 0 then Volume:= 0;
   232 Mix_Volume(-1, Volume);
   232 Mix_Volume(-1, Volume);
   233 Volume:= Mix_Volume(-1, -1);
   233 Volume:= Mix_Volume(-1, -1);
   249 Mix_ResumeMusic(Mus);
   249 Mix_ResumeMusic(Mus);
   250 end;
   250 end;
   251 
   251 
   252 procedure init_uSound;
   252 procedure init_uSound;
   253 begin
   253 begin
   254 	MusicFN:='';
   254     MusicFN:='';
   255 end;
   255 end;
   256 
   256 
   257 procedure free_uSound;
   257 procedure free_uSound;
   258 begin
   258 begin
   259 
   259