mirror of
https://github.com/vcmi/vcmi.git
synced 2025-08-15 20:03:15 +02:00
Sound patch from Ubuntux #11: Add music infrastruture + some musics in various places
[With mine minor fixes and updated MSVC project] vcmi_music.diff
This commit is contained in:
@@ -1785,6 +1785,7 @@ void CBattleInterface::battleFinished(const BattleResult& br)
|
||||
CGI->curh->changeGraphic(0,0);
|
||||
|
||||
SDL_Rect temp_rect = genRect(561, 470, (screen->w - 800)/2 + 165, (screen->h - 600)/2 + 19);
|
||||
CGI->mush->stopMusic();
|
||||
resWindow = new CBattleReslutWindow(br, temp_rect, this);
|
||||
LOCPLINT->pushInt(resWindow);
|
||||
}
|
||||
@@ -2787,30 +2788,36 @@ CBattleReslutWindow::CBattleReslutWindow(const BattleResult &br, const SDL_Rect
|
||||
case 0: //normal victory
|
||||
if((br.winner == 0 && weAreAttacker) || (br.winner == 1 && !weAreAttacker)) //we've won
|
||||
{
|
||||
CGI->mush->playMusic(musicBase::winBattle);
|
||||
CSDL_Ext::printAtMiddle(CGI->generaltexth->allTexts[304], 235, 235, GEOR13, zwykly, background);
|
||||
}
|
||||
else
|
||||
{
|
||||
CGI->mush->playMusic(musicBase::loseCombat);
|
||||
CSDL_Ext::printAtMiddle(CGI->generaltexth->allTexts[311], 235, 235, GEOR13, zwykly, background);
|
||||
}
|
||||
break;
|
||||
case 1: //flee
|
||||
if((br.winner == 0 && weAreAttacker) || (br.winner == 1 && !weAreAttacker)) //we've won
|
||||
{
|
||||
CGI->mush->playMusic(musicBase::winBattle);
|
||||
CSDL_Ext::printAtMiddle(CGI->generaltexth->allTexts[303], 235, 235, GEOR13, zwykly, background);
|
||||
}
|
||||
else
|
||||
{
|
||||
CGI->mush->playMusic(musicBase::retreatBattle);
|
||||
CSDL_Ext::printAtMiddle(CGI->generaltexth->allTexts[310], 235, 235, GEOR13, zwykly, background);
|
||||
}
|
||||
break;
|
||||
case 2: //surrender
|
||||
if((br.winner == 0 && weAreAttacker) || (br.winner == 1 && !weAreAttacker)) //we've won
|
||||
{
|
||||
CGI->mush->playMusic(musicBase::winBattle);
|
||||
CSDL_Ext::printAtMiddle(CGI->generaltexth->allTexts[302], 235, 235, GEOR13, zwykly, background);
|
||||
}
|
||||
else
|
||||
{
|
||||
CGI->mush->playMusic(musicBase::surrenderBattle);
|
||||
CSDL_Ext::printAtMiddle(CGI->generaltexth->allTexts[309], 235, 235, GEOR13, zwykly, background);
|
||||
}
|
||||
break;
|
||||
|
@@ -433,30 +433,39 @@ CCastleInterface::CCastleInterface(const CGTownInstance * Town)
|
||||
{
|
||||
case 0:
|
||||
defname = "HALLCSTL.DEF";
|
||||
musicID = musicBase::castleTown;
|
||||
break;
|
||||
case 1:
|
||||
defname = "HALLRAMP.DEF";
|
||||
musicID = musicBase::rampartTown;
|
||||
break;
|
||||
case 2:
|
||||
defname = "HALLTOWR.DEF";
|
||||
musicID = musicBase::towerTown;
|
||||
break;
|
||||
case 3:
|
||||
defname = "HALLINFR.DEF";
|
||||
musicID = musicBase::infernoTown;
|
||||
break;
|
||||
case 4:
|
||||
defname = "HALLNECR.DEF";
|
||||
musicID = musicBase::necroTown;
|
||||
break;
|
||||
case 5:
|
||||
defname = "HALLDUNG.DEF";
|
||||
musicID = musicBase::dungeonTown;
|
||||
break;
|
||||
case 6:
|
||||
defname = "HALLSTRN.DEF";
|
||||
musicID = musicBase::strongHoldTown;
|
||||
break;
|
||||
case 7:
|
||||
defname = "HALLFORT.DEF";
|
||||
musicID = musicBase::fortressTown;
|
||||
break;
|
||||
case 8:
|
||||
defname = "HALLELEM.DEF";
|
||||
musicID = musicBase::elemTown;
|
||||
break;
|
||||
default:
|
||||
throw new std::string("Wrong town subID");
|
||||
@@ -492,6 +501,7 @@ void CCastleInterface::close()
|
||||
LOCPLINT->adventureInt->select(town->visitingHero);
|
||||
LOCPLINT->castleInt = NULL;
|
||||
LOCPLINT->popIntTotally(this);
|
||||
CGI->mush->stopMusic(5000);
|
||||
}
|
||||
|
||||
void CCastleInterface::splitF()
|
||||
|
@@ -85,6 +85,8 @@ public:
|
||||
AdventureMapButton *exit;
|
||||
AdventureMapButton *split;
|
||||
|
||||
musicBase::musicID musicID;
|
||||
|
||||
std::vector<CBuildingRect*> buildings; //building id, building def, structure struct, border, filling
|
||||
|
||||
CCastleInterface(const CGTownInstance * Town);
|
||||
|
4
CMT.cpp
4
CMT.cpp
@@ -147,8 +147,8 @@ int main(int argc, char** argv)
|
||||
CPreGame * cpg = new CPreGame(); //main menu and submenus
|
||||
tlog0<<"Initialization CPreGame (together): "<<tmh.getDif()<<std::endl;
|
||||
tlog0<<"Initialization of VCMI (together): "<<total.getDif()<<std::endl;
|
||||
cpg->mush = mush;
|
||||
|
||||
mush->playMusic(musicBase::mainMenu, -1);
|
||||
StartInfo *options = new StartInfo(cpg->runLoop());
|
||||
|
||||
if(screen->w != conf.cc.resx || screen->h != conf.cc.resy)
|
||||
@@ -187,6 +187,7 @@ int main(int argc, char** argv)
|
||||
THC tlog0<<"\tConnecting to the server: "<<tmh.getDif()<<std::endl;
|
||||
cl.newGame(c,options);
|
||||
client = &cl;
|
||||
mush->stopMusic();
|
||||
boost::thread t(boost::bind(&CClient::run,&cl));
|
||||
}
|
||||
else //load game
|
||||
@@ -195,6 +196,7 @@ int main(int argc, char** argv)
|
||||
boost::algorithm::erase_last(fname,".vlgm1");
|
||||
cl.load(fname);
|
||||
client = &cl;
|
||||
mush->stopMusic();
|
||||
boost::thread t(boost::bind(&CClient::run,&cl));
|
||||
}
|
||||
|
||||
|
@@ -4,7 +4,6 @@
|
||||
#include "global.h"
|
||||
#include <SDL_ttf.h>
|
||||
#include <SDL.h>
|
||||
#include "CPreGame.h"
|
||||
|
||||
/*
|
||||
* CMessage.h, part of VCMI engine
|
||||
|
@@ -1837,6 +1837,7 @@ void CPlayerInterface::heroCreated(const CGHeroInstance * hero)
|
||||
void CPlayerInterface::openTownWindow(const CGTownInstance * town)
|
||||
{
|
||||
castleInt = new CCastleInterface(town);
|
||||
CGI->mush->playMusic(castleInt->musicID, -1);
|
||||
LOCPLINT->pushInt(castleInt);
|
||||
}
|
||||
|
||||
@@ -2197,6 +2198,7 @@ void CPlayerInterface::battleStart(CCreatureSet *army1, CCreatureSet *army2, int
|
||||
|
||||
boost::unique_lock<boost::recursive_mutex> un(*pim);
|
||||
battleInt = new CBattleInterface(army1, army2, hero1, hero2, genRect(600, 800, (conf.cc.resx - 800)/2, (conf.cc.resy - 600)/2));
|
||||
CGI->mush->playMusicFromSet(CGI->mush->battleMusics, -1);
|
||||
pushInt(battleInt);
|
||||
}
|
||||
|
||||
|
@@ -22,7 +22,7 @@
|
||||
#include <boost/bind.hpp>
|
||||
#include <cstdlib>
|
||||
#include "lib/Connection.h"
|
||||
|
||||
#include "hch/CMusicHandler.h"
|
||||
/*
|
||||
* CPreGame.cpp, part of VCMI engine
|
||||
*
|
||||
@@ -1973,7 +1973,7 @@ void CPreGame::scenHandleEv(SDL_Event& sEvent)
|
||||
{
|
||||
if (isItIn(&btns[i]->pos,sEvent.motion.x,sEvent.motion.y))
|
||||
{
|
||||
mush->playSound(soundBase::button);
|
||||
CGI->mush->playSound(soundBase::button);
|
||||
btns[i]->press(true);
|
||||
ourScenSel->pressed=(Button*)btns[i];
|
||||
}
|
||||
@@ -1982,7 +1982,7 @@ void CPreGame::scenHandleEv(SDL_Event& sEvent)
|
||||
&& (sEvent.button.x>55) && (sEvent.button.x<372))
|
||||
{
|
||||
int py = ((sEvent.button.y-121)/25)+ourScenSel->mapsel.slid->whereAreWe;
|
||||
mush->playSound(soundBase::button);
|
||||
CGI->mush->playSound(soundBase::button);
|
||||
ourScenSel->mapsel.select(ourScenSel->mapsel.whichWL(py));
|
||||
}
|
||||
|
||||
@@ -2237,7 +2237,7 @@ StartInfo CPreGame::runLoop()
|
||||
current->highlighted=5;
|
||||
}
|
||||
if (current->highlighted)
|
||||
mush->playSound(soundBase::button);
|
||||
CGI->mush->playSound(soundBase::button);
|
||||
}
|
||||
else if ((sEvent.type==SDL_MOUSEBUTTONUP) && (sEvent.button.button == SDL_BUTTON_LEFT))
|
||||
{
|
||||
|
@@ -6,7 +6,6 @@
|
||||
#include "StartInfo.h"
|
||||
#include "CMessage.h"
|
||||
#include "map.h"
|
||||
#include "hch/CMusicHandler.h"
|
||||
#include <boost/function.hpp>
|
||||
#include <boost/bind.hpp>
|
||||
#include <cstdlib>
|
||||
@@ -21,6 +20,7 @@
|
||||
*
|
||||
*/
|
||||
|
||||
struct CMusicHandler;
|
||||
class CPreGame;
|
||||
class CDefHandler;
|
||||
extern CPreGame * CPG;
|
||||
@@ -256,7 +256,6 @@ public:
|
||||
bool first; //hasn't we showed the scensel
|
||||
int fromnewgame; //1 - new game; 0 - load game; 2 - save game
|
||||
std::vector<Slider *> interested;
|
||||
CMusicHandler * mush;
|
||||
std::vector<HighButton *> btns;
|
||||
SDL_Rect * currentMessage;
|
||||
SDL_Surface * behindCurMes;
|
||||
|
@@ -464,6 +464,10 @@
|
||||
RelativePath="..\CMessage.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\hch\CMusicBase.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\hch\CMusicHandler.h"
|
||||
>
|
||||
|
82
hch/CMusicBase.h
Normal file
82
hch/CMusicBase.h
Normal file
@@ -0,0 +1,82 @@
|
||||
#ifndef __CMUSICBASE_H__
|
||||
#define __CMUSICBASE_H__
|
||||
|
||||
// Use some magic to keep the list of files and their code name in sync.
|
||||
|
||||
#define VCMI_MUSIC_LIST \
|
||||
VCMI_MUSIC_ID(AITheme0) VCMI_MUSIC_FILE("AITheme0.mp3") \
|
||||
VCMI_MUSIC_ID(AITheme1) VCMI_MUSIC_FILE("AITHEME1.MP3") \
|
||||
VCMI_MUSIC_ID(AITheme2) VCMI_MUSIC_FILE("AITHEME2.MP3") \
|
||||
VCMI_MUSIC_ID(bladeABCampaign) VCMI_MUSIC_FILE("BladeABCampaign.mp3") \
|
||||
VCMI_MUSIC_ID(bladeDBCampaign) VCMI_MUSIC_FILE("BladeDBCampaign.mp3") \
|
||||
VCMI_MUSIC_ID(bladeDSCampaign) VCMI_MUSIC_FILE("BladeDSCampaign.mp3") \
|
||||
VCMI_MUSIC_ID(bladeFLCampaign) VCMI_MUSIC_FILE("BladeFLCampaign.mp3") \
|
||||
VCMI_MUSIC_ID(bladeFWCampaign) VCMI_MUSIC_FILE("BladeFWCampaign.mp3") \
|
||||
VCMI_MUSIC_ID(bladePFCampaign) VCMI_MUSIC_FILE("BladePFCampaign.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic01) VCMI_MUSIC_FILE("CampainMusic01.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic02) VCMI_MUSIC_FILE("CampainMusic02.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic03) VCMI_MUSIC_FILE("CampainMusic03.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic04) VCMI_MUSIC_FILE("CampainMusic04.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic05) VCMI_MUSIC_FILE("CampainMusic05.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic06) VCMI_MUSIC_FILE("CampainMusic06.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic07) VCMI_MUSIC_FILE("CampainMusic07.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic08) VCMI_MUSIC_FILE("CampainMusic08.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic09) VCMI_MUSIC_FILE("CampainMusic09.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic10) VCMI_MUSIC_FILE("CampainMusic10.mp3") \
|
||||
VCMI_MUSIC_ID(campainMusic11) VCMI_MUSIC_FILE("CampainMusic11.mp3") \
|
||||
VCMI_MUSIC_ID(combat1) VCMI_MUSIC_FILE("COMBAT01.MP3") \
|
||||
VCMI_MUSIC_ID(combat2) VCMI_MUSIC_FILE("COMBAT02.MP3") \
|
||||
VCMI_MUSIC_ID(combat3) VCMI_MUSIC_FILE("COMBAT03.MP3") \
|
||||
VCMI_MUSIC_ID(combat4) VCMI_MUSIC_FILE("COMBAT04.MP3") \
|
||||
VCMI_MUSIC_ID(castleTown) VCMI_MUSIC_FILE("CstleTown.mp3") \
|
||||
VCMI_MUSIC_ID(defendCastle) VCMI_MUSIC_FILE("Defend Castle.mp3") \
|
||||
VCMI_MUSIC_ID(dirt) VCMI_MUSIC_FILE("DIRT.MP3") \
|
||||
VCMI_MUSIC_ID(dungeonTown) VCMI_MUSIC_FILE("DUNGEON.MP3") \
|
||||
VCMI_MUSIC_ID(elemTown) VCMI_MUSIC_FILE("ElemTown.mp3") \
|
||||
VCMI_MUSIC_ID(evilTheme) VCMI_MUSIC_FILE("EvilTheme.mp3") \
|
||||
VCMI_MUSIC_ID(fortressTown) VCMI_MUSIC_FILE("FortressTown.mp3") \
|
||||
VCMI_MUSIC_ID(goodTheme) VCMI_MUSIC_FILE("GoodTheme.mp3") \
|
||||
VCMI_MUSIC_ID(grass) VCMI_MUSIC_FILE("GRASS.MP3") \
|
||||
VCMI_MUSIC_ID(infernoTown) VCMI_MUSIC_FILE("InfernoTown.mp3") \
|
||||
VCMI_MUSIC_ID(lava) VCMI_MUSIC_FILE("LAVA.MP3") \
|
||||
VCMI_MUSIC_ID(loopLepr) VCMI_MUSIC_FILE("LoopLepr.mp3") \
|
||||
VCMI_MUSIC_ID(loseCampain) VCMI_MUSIC_FILE("Lose Campain.mp3") \
|
||||
VCMI_MUSIC_ID(loseCastle) VCMI_MUSIC_FILE("LoseCastle.mp3") \
|
||||
VCMI_MUSIC_ID(loseCombat) VCMI_MUSIC_FILE("LoseCombat.mp3") \
|
||||
VCMI_MUSIC_ID(mainMenu) VCMI_MUSIC_FILE("MAINMENU.MP3") \
|
||||
VCMI_MUSIC_ID(mainMenuWoG) VCMI_MUSIC_FILE("MainMenuWoG.mp3") \
|
||||
VCMI_MUSIC_ID(necroTown) VCMI_MUSIC_FILE("necroTown.mp3") \
|
||||
VCMI_MUSIC_ID(neutralTheme) VCMI_MUSIC_FILE("NeutralTheme.mp3") \
|
||||
VCMI_MUSIC_ID(rampartTown) VCMI_MUSIC_FILE("RAMPART.MP3") \
|
||||
VCMI_MUSIC_ID(retreatBattle) VCMI_MUSIC_FILE("Retreat Battle.mp3") \
|
||||
VCMI_MUSIC_ID(rough) VCMI_MUSIC_FILE("ROUGH.MP3") \
|
||||
VCMI_MUSIC_ID(sand) VCMI_MUSIC_FILE("SAND.MP3") \
|
||||
VCMI_MUSIC_ID(secretTheme) VCMI_MUSIC_FILE("SecretTheme.mp3") \
|
||||
VCMI_MUSIC_ID(snow) VCMI_MUSIC_FILE("SNOW.MP3") \
|
||||
VCMI_MUSIC_ID(strongHoldTown) VCMI_MUSIC_FILE("StrongHold.mp3") \
|
||||
VCMI_MUSIC_ID(surrenderBattle) VCMI_MUSIC_FILE("Surrender Battle.mp3") \
|
||||
VCMI_MUSIC_ID(swamp) VCMI_MUSIC_FILE("SWAMP.MP3") \
|
||||
VCMI_MUSIC_ID(towerTown) VCMI_MUSIC_FILE("TowerTown.mp3") \
|
||||
VCMI_MUSIC_ID(ultimateLose) VCMI_MUSIC_FILE("UltimateLose.mp3") \
|
||||
VCMI_MUSIC_ID(underground) VCMI_MUSIC_FILE("Underground.mp3") \
|
||||
VCMI_MUSIC_ID(water) VCMI_MUSIC_FILE("WATER.MP3") \
|
||||
VCMI_MUSIC_ID(winBattle) VCMI_MUSIC_FILE("Win Battle.mp3") \
|
||||
VCMI_MUSIC_ID(winScenario) VCMI_MUSIC_FILE("Win Scenario.mp3" )
|
||||
|
||||
class musicBase
|
||||
{
|
||||
public:
|
||||
// Make a list of enums
|
||||
#define VCMI_MUSIC_ID(x) x,
|
||||
#define VCMI_MUSIC_FILE(y)
|
||||
enum musicID {
|
||||
music_todo=0, // temp entry until code is fixed
|
||||
VCMI_MUSIC_LIST
|
||||
};
|
||||
#undef VCMI_MUSIC_ID
|
||||
#undef VCMI_MUSIC_FILE
|
||||
};
|
||||
|
||||
#endif // __CMUSICBASE_H__
|
||||
|
||||
|
@@ -24,7 +24,12 @@
|
||||
|
||||
using namespace boost::assign;
|
||||
|
||||
boost::bimap<soundBase::soundID, std::string> sounds;
|
||||
static boost::bimap<soundBase::soundID, std::string> sounds;
|
||||
|
||||
// Not pretty, but there's only one music handler object in the game.
|
||||
static void musicFinishedCallbackC(void) {
|
||||
CGI->mush->musicFinishedCallback();
|
||||
}
|
||||
|
||||
CMusicHandler::~CMusicHandler()
|
||||
{
|
||||
@@ -42,6 +47,20 @@ CMusicHandler::~CMusicHandler()
|
||||
Mix_FreeChunk(it->second);
|
||||
}
|
||||
|
||||
Mix_HookMusicFinished(NULL);
|
||||
|
||||
musicMutex.lock();
|
||||
|
||||
if (currentMusic) {
|
||||
Mix_HaltMusic();
|
||||
Mix_FreeMusic(currentMusic);
|
||||
}
|
||||
|
||||
if (nextMusic)
|
||||
Mix_FreeMusic(nextMusic);
|
||||
|
||||
musicMutex.unlock();
|
||||
|
||||
Mix_CloseAudio();
|
||||
}
|
||||
|
||||
@@ -75,51 +94,23 @@ void CMusicHandler::initMusics()
|
||||
soundBase::horseSubterranean, soundBase::horseLava,
|
||||
soundBase::horseWater, soundBase::horseRock;
|
||||
|
||||
//AITheme0 = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "AITheme0.mp3");
|
||||
//AITheme1 = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "AITHEME1.mp3");
|
||||
//AITheme2 = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "AITHEME2.mp3");
|
||||
//buildTown = Mix_LoadWAV("MP3" PATHSEPARATOR "BUILDTWN.wav");
|
||||
//combat1 = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "COMBAT01.mp3");
|
||||
//combat2 = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "COMBAT02.mp3");
|
||||
//combat3 = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "COMBAT03.mp3");
|
||||
//combat4 = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "COMBAT04.mp3");
|
||||
//castleTown = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "CstleTown.mp3");
|
||||
//defendCastle = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "Defend Castle.mp3");
|
||||
//dirt = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "DIRT.mp3");
|
||||
//dungeon = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "DUNGEON.mp3");
|
||||
//elemTown = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "ElemTown.mp3");
|
||||
//evilTheme = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "EvilTheme.mp3");
|
||||
//fortressTown = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "FortressTown.mp3");
|
||||
//goodTheme = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "GoodTheme.mp3");
|
||||
//grass = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "GRASS.mp3");
|
||||
//infernoTown = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "InfernoTown.mp3");
|
||||
//lava = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "LAVA.mp3");
|
||||
//loopLepr = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "LoopLepr.mp3");
|
||||
//loseCampain = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "Lose Campain.mp3");
|
||||
//loseCastle = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "LoseCastle.mp3");
|
||||
//loseCombat = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "LoseCombat.mp3");
|
||||
//mainMenu = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "MAINMENU.mp3");
|
||||
//mainMenuWoG = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "MainMenuWoG.mp3");
|
||||
//necroTown = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "necroTown.mp3");
|
||||
//neutralTheme = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "NeutralTheme.mp3");
|
||||
//rampart = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "RAMPART.mp3");
|
||||
//retreatBattle = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "Retreat Battle.mp3");
|
||||
//rough = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "ROUGH.mp3");
|
||||
//sand = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "SAND.mp3");
|
||||
//secretTheme = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "SecretTheme.mp3");
|
||||
//snow = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "SNOW.mp3");
|
||||
//stronghold = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "StrongHold.mp3");
|
||||
//surrenderBattle = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "Surrender Battle.mp3");
|
||||
//swamp = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "SWAMP.mp3");
|
||||
//towerTown = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "TowerTown.mp3");
|
||||
//ultimateLose = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "UltimateLose.mp3");
|
||||
//underground = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "Underground.mp3");
|
||||
//water = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "WATER.mp3");
|
||||
//winBattle = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "Win Battle.mp3");
|
||||
//winScenario = Mix_LoadMUS(DATA_DIR "MP3" PATHSEPARATOR "Win Scenario.mp3");
|
||||
// Map music IDs
|
||||
#define VCMI_MUSIC_ID(x) ( musicBase::x ,
|
||||
#define VCMI_MUSIC_FILE(y) y )
|
||||
musics = map_list_of
|
||||
VCMI_MUSIC_LIST;
|
||||
#undef VCMI_MUSIC_NAME
|
||||
#undef VCMI_MUSIC_FILE
|
||||
|
||||
Mix_HookMusicFinished(musicFinishedCallbackC);
|
||||
|
||||
// Vector for helper
|
||||
battleMusics += musicBase::combat1, musicBase::combat2,
|
||||
musicBase::combat3, musicBase::combat4;
|
||||
|
||||
// Load sounds
|
||||
sndh = new CSndHandler(std::string(DATA_DIR "Data" PATHSEPARATOR "Heroes3.snd"));
|
||||
nextMusic = NULL;
|
||||
}
|
||||
|
||||
// Allocate an SDL chunk and cache it.
|
||||
@@ -260,4 +251,75 @@ void CMusicHandler::stopSound( int handler )
|
||||
{
|
||||
if (handler != -1)
|
||||
Mix_HaltChannel(handler);
|
||||
}
|
||||
|
||||
// Plays a music
|
||||
// loop: -1 always repeats, 0=do not play, 1+=number of loops
|
||||
void CMusicHandler::playMusic(musicBase::musicID musicID, int loop)
|
||||
{
|
||||
if (!sndh)
|
||||
return;
|
||||
|
||||
std::string filename = DATA_DIR "Mp3" PATHSEPARATOR;
|
||||
filename += musics[musicID];
|
||||
|
||||
musicMutex.lock();
|
||||
|
||||
if (nextMusic) {
|
||||
// There's already a music queued, so remove it
|
||||
Mix_FreeMusic(nextMusic);
|
||||
nextMusic = NULL;
|
||||
}
|
||||
|
||||
if (currentMusic) {
|
||||
// A music is already playing. Stop it and the callback will
|
||||
// start the new one
|
||||
nextMusic = Mix_LoadMUS(filename.c_str());
|
||||
nextMusicLoop = loop;
|
||||
Mix_FadeOutMusic(1000);
|
||||
} else {
|
||||
currentMusic = Mix_LoadMUS(filename.c_str());
|
||||
if (Mix_PlayMusic(currentMusic, loop) == -1)
|
||||
tlog1 << "Unable to play sound file " << musicID << "(" << Mix_GetError() << ")" << std::endl;
|
||||
}
|
||||
|
||||
musicMutex.unlock();
|
||||
}
|
||||
|
||||
// Helper. Randomly select a music from an array and play it
|
||||
void CMusicHandler::playMusicFromSet(std::vector<musicBase::musicID> &music_vec, int loop)
|
||||
{
|
||||
playMusic(music_vec[rand() % music_vec.size()], loop);
|
||||
}
|
||||
|
||||
// Stop and free the current music
|
||||
void CMusicHandler::stopMusic(int fade_ms)
|
||||
{
|
||||
musicMutex.lock();
|
||||
|
||||
if (currentMusic) {
|
||||
Mix_FadeOutMusic(fade_ms);
|
||||
}
|
||||
|
||||
musicMutex.unlock();
|
||||
}
|
||||
|
||||
// Called by SDL when a music finished.
|
||||
void CMusicHandler::musicFinishedCallback(void)
|
||||
{
|
||||
musicMutex.lock();
|
||||
|
||||
if (currentMusic) {
|
||||
Mix_FreeMusic(currentMusic);
|
||||
currentMusic = NULL;
|
||||
}
|
||||
|
||||
if (nextMusic) {
|
||||
currentMusic = nextMusic;
|
||||
nextMusic = NULL;
|
||||
if (Mix_PlayMusic(currentMusic, nextMusicLoop) == -1)
|
||||
tlog1 << "Unable to play music (" << Mix_GetError() << ")" << std::endl;
|
||||
}
|
||||
|
||||
musicMutex.unlock();
|
||||
}
|
@@ -1,7 +1,11 @@
|
||||
#ifndef __CMUSICHANDLER_H__
|
||||
#define __CMUSICHANDLER_H__
|
||||
|
||||
#include <boost/thread/mutex.hpp>
|
||||
|
||||
#include "CSoundBase.h"
|
||||
#include "CMusicBase.h"
|
||||
|
||||
|
||||
/*
|
||||
* CMusicHandler.h, part of VCMI engine
|
||||
@@ -13,12 +17,16 @@
|
||||
*
|
||||
*/
|
||||
|
||||
struct Mix_Chunk;
|
||||
class CSndHandler;
|
||||
struct _Mix_Music;
|
||||
typedef struct _Mix_Music Mix_Music;
|
||||
struct Mix_Chunk;
|
||||
|
||||
class CMusicHandler
|
||||
{
|
||||
private:
|
||||
bool audioInit;
|
||||
|
||||
CSndHandler *sndh;
|
||||
soundBase::soundID getSoundID(std::string &fileName);
|
||||
|
||||
@@ -26,10 +34,16 @@ private:
|
||||
|
||||
Mix_Chunk *GetSoundChunk(soundBase::soundID soundID);
|
||||
|
||||
bool audioInit;
|
||||
// Because we use the SDL music callback, our music variables must
|
||||
// be protected
|
||||
boost::mutex musicMutex;
|
||||
Mix_Music *currentMusic;
|
||||
Mix_Music *nextMusic;
|
||||
int nextMusicLoop;
|
||||
|
||||
public:
|
||||
CMusicHandler(): sndh(NULL), audioInit(false) {};
|
||||
CMusicHandler(): audioInit(false), sndh(NULL), currentMusic(NULL) {};
|
||||
|
||||
~CMusicHandler();
|
||||
|
||||
void initMusics();
|
||||
@@ -43,6 +57,15 @@ public:
|
||||
// Sets
|
||||
std::vector<soundBase::soundID> pickup_sounds;
|
||||
std::vector<soundBase::soundID> horseSounds;
|
||||
|
||||
// Musics
|
||||
std::map<musicBase::musicID, std::string> musics;
|
||||
std::vector<musicBase::musicID> battleMusics;
|
||||
|
||||
void playMusic(musicBase::musicID musicID, int loop=1);
|
||||
void playMusicFromSet(std::vector<musicBase::musicID> &music_vec, int loop=1);
|
||||
void stopMusic(int fade_ms=1000);
|
||||
void musicFinishedCallback(void);
|
||||
};
|
||||
|
||||
#endif // __CMUSICHANDLER_H__
|
||||
|
Reference in New Issue
Block a user