aboutsummaryrefslogtreecommitdiff
path: root/engines/gob
diff options
context:
space:
mode:
Diffstat (limited to 'engines/gob')
-rw-r--r--engines/gob/dataio.cpp18
-rw-r--r--engines/gob/dataio.h3
-rw-r--r--engines/gob/demos/demoplayer.cpp4
-rw-r--r--engines/gob/detection.cpp1081
-rw-r--r--engines/gob/draw.cpp10
-rw-r--r--engines/gob/draw_v1.cpp40
-rw-r--r--engines/gob/draw_v2.cpp76
-rw-r--r--engines/gob/expression.cpp1144
-rw-r--r--engines/gob/expression.h178
-rw-r--r--engines/gob/game.cpp669
-rw-r--r--engines/gob/game.h132
-rw-r--r--engines/gob/game_fascin.cpp1
-rw-r--r--engines/gob/game_v1.cpp318
-rw-r--r--engines/gob/game_v2.cpp315
-rw-r--r--engines/gob/game_v6.cpp254
-rw-r--r--engines/gob/global.cpp28
-rw-r--r--engines/gob/global.h76
-rw-r--r--engines/gob/gob.cpp45
-rw-r--r--engines/gob/gob.h4
-rw-r--r--engines/gob/init.cpp58
-rw-r--r--engines/gob/inter.cpp152
-rw-r--r--engines/gob/inter.h341
-rw-r--r--engines/gob/inter_bargon.cpp684
-rw-r--r--engines/gob/inter_fascin.cpp690
-rw-r--r--engines/gob/inter_v1.cpp1690
-rw-r--r--engines/gob/inter_v2.cpp1279
-rw-r--r--engines/gob/inter_v3.cpp702
-rw-r--r--engines/gob/inter_v4.cpp707
-rw-r--r--engines/gob/inter_v5.cpp785
-rw-r--r--engines/gob/inter_v6.cpp787
-rw-r--r--engines/gob/map_v1.cpp11
-rw-r--r--engines/gob/map_v2.cpp21
-rw-r--r--engines/gob/map_v4.cpp21
-rw-r--r--engines/gob/module.mk5
-rw-r--r--engines/gob/mult.cpp8
-rw-r--r--engines/gob/mult_v1.cpp25
-rw-r--r--engines/gob/mult_v2.cpp67
-rw-r--r--engines/gob/parse.cpp1499
-rw-r--r--engines/gob/parse.h128
-rw-r--r--engines/gob/resources.cpp706
-rw-r--r--engines/gob/resources.h207
-rw-r--r--engines/gob/save/savefile.h2
-rw-r--r--engines/gob/save/saveload.cpp2
-rw-r--r--engines/gob/save/saveload_v3.cpp8
-rw-r--r--engines/gob/save/saveload_v4.cpp6
-rw-r--r--engines/gob/scenery.cpp396
-rw-r--r--engines/gob/script.cpp522
-rw-r--r--engines/gob/script.h169
-rw-r--r--engines/gob/sound/adlib.cpp522
-rw-r--r--engines/gob/sound/adlib.h84
-rw-r--r--engines/gob/sound/bgatmosphere.cpp1
-rw-r--r--engines/gob/sound/bgatmosphere.h3
-rw-r--r--engines/gob/sound/cdrom.cpp3
-rw-r--r--engines/gob/sound/cdrom.h4
-rw-r--r--engines/gob/sound/infogrames.cpp4
-rw-r--r--engines/gob/sound/protracker.cpp2
-rw-r--r--engines/gob/sound/protracker.h1
-rw-r--r--engines/gob/sound/sound.cpp194
-rw-r--r--engines/gob/sound/sound.h26
-rw-r--r--engines/gob/sound/soundblaster.cpp1
-rw-r--r--engines/gob/sound/soundblaster.h3
-rw-r--r--engines/gob/sound/sounddesc.cpp50
-rw-r--r--engines/gob/sound/sounddesc.h17
-rw-r--r--engines/gob/sound/soundmixer.cpp1
-rw-r--r--engines/gob/sound/soundmixer.h4
-rw-r--r--engines/gob/totfile.cpp135
-rw-r--r--engines/gob/totfile.h80
-rw-r--r--engines/gob/util.cpp6
-rw-r--r--engines/gob/util.h1
-rw-r--r--engines/gob/videoplayer.cpp6
70 files changed, 7196 insertions, 10026 deletions
diff --git a/engines/gob/dataio.cpp b/engines/gob/dataio.cpp
index a37586aee6..f59fa80e8d 100644
--- a/engines/gob/dataio.cpp
+++ b/engines/gob/dataio.cpp
@@ -239,7 +239,7 @@ int16 DataIO::getChunk(const char *chunkName) {
}
dataDesc = _dataFiles[file];
- for (int16 chunk = 0; chunk < _numDataChunks[file]; chunk++, dataDesc++) {
+ for (uint16 chunk = 0; chunk < _numDataChunks[file]; chunk++, dataDesc++) {
if (scumm_stricmp(chunkName, dataDesc->chunkName) != 0)
continue;
@@ -334,7 +334,6 @@ uint32 DataIO::getChunkPos(int16 handle) const {
int32 DataIO::getChunkSize(const char *chunkName) {
int16 file;
- int16 chunk;
struct ChunkDesc *dataDesc;
int16 slot;
int32 realSize;
@@ -344,7 +343,7 @@ int32 DataIO::getChunkSize(const char *chunkName) {
return -1;
dataDesc = _dataFiles[file];
- for (chunk = 0; chunk < _numDataChunks[file]; chunk++, dataDesc++) {
+ for (uint16 chunk = 0; chunk < _numDataChunks[file]; chunk++, dataDesc++) {
if (scumm_stricmp(chunkName, dataDesc->chunkName) != 0)
continue;
@@ -488,6 +487,16 @@ int16 DataIO::openData(const char *path) {
return file_open(path);
}
+bool DataIO::existData(const char *path) {
+ int16 handle = openData(path);
+
+ if (handle < 0)
+ return false;
+
+ closeData(handle);
+ return true;
+}
+
DataStream *DataIO::openAsStream(int16 handle, bool dispose) {
uint32 curPos = getPos(handle);
seekData(handle, 0, SEEK_END);
@@ -575,6 +584,9 @@ byte *DataIO::getData(const char *path) {
}
DataStream *DataIO::getDataStream(const char *path) {
+ if (!path || (path[0] == '\0') || !existData(path))
+ return 0;
+
uint32 size = getDataSize(path);
byte *data = getData(path);
diff --git a/engines/gob/dataio.h b/engines/gob/dataio.h
index c67dc89df8..1f55cac90d 100644
--- a/engines/gob/dataio.h
+++ b/engines/gob/dataio.h
@@ -80,6 +80,7 @@ public:
byte *getUnpackedData(const char *name);
void closeData(int16 handle);
int16 openData(const char *path);
+ bool existData(const char *path);
DataStream *openAsStream(int16 handle, bool dispose = false);
int32 getDataSize(const char *name);
@@ -92,7 +93,7 @@ public:
protected:
Common::File _filesHandles[MAX_FILES];
struct ChunkDesc *_dataFiles[MAX_DATA_FILES];
- int16 _numDataChunks[MAX_DATA_FILES];
+ uint16 _numDataChunks[MAX_DATA_FILES];
int16 _dataFileHandles[MAX_DATA_FILES];
bool _dataFileItk[MAX_DATA_FILES];
int32 _chunkPos[MAX_SLOT_COUNT * MAX_DATA_FILES];
diff --git a/engines/gob/demos/demoplayer.cpp b/engines/gob/demos/demoplayer.cpp
index ede90af333..0229bb7515 100644
--- a/engines/gob/demos/demoplayer.cpp
+++ b/engines/gob/demos/demoplayer.cpp
@@ -123,7 +123,9 @@ void DemoPlayer::init() {
void DemoPlayer::clearScreen() {
debugC(1, kDebugDemo, "Clearing the screen");
- _vm->_video->clearScreen();
+ _vm->_video->clearSurf(*_vm->_draw->_backSurface);
+ _vm->_draw->forceBlit();
+ _vm->_video->retrace();
}
void DemoPlayer::playVideo(const char *fileName) {
diff --git a/engines/gob/detection.cpp b/engines/gob/detection.cpp
index af64a53b60..9426c01ef2 100644
--- a/engines/gob/detection.cpp
+++ b/engines/gob/detection.cpp
@@ -61,13 +61,14 @@ static const PlainGameDescriptor gobGames[] = {
{"woodruff", "The Bizarre Adventures of Woodruff and the Schnibble"},
{"dynasty", "The Last Dynasty"},
{"urban", "Urban Runner"},
- {"archi", "Playtoon 1 - Uncle Archibald"},
- {"spirou", "Playtoon 2 - The Case of the Counterfeit Collaborator"},
- {"chato", "Playtoon 3 - The Secret of the Castle"},
- {"manda", "Playtoon 4 - The Mandarine Prince"},
- {"wakan", "Playtoon 5 - The Stone of Wakan"},
- {"playtnck2", "Playtoon Construction Kit 2 - Les chevaliers"},
- {"bambou", "Playtoon Limited Edition - Bambou le sauveur de la jungle"},
+ {"playtoons1", "Playtoons 1 - Uncle Archibald"},
+ {"playtoons2", "Playtoons 2 - The Case of the Counterfeit Collaborator"},
+ {"playtoons3", "Playtoons 3 - The Secret of the Castle"},
+ {"playtoons4", "Playtoons 4 - The Mandarine Prince"},
+ {"playtoons5", "Playtoons 5 - The Stone of Wakan"},
+ {"playtnck1", "Playtoons Construction Kit 1 - Monsters"},
+ {"playtnck2", "Playtoons Construction Kit 2 - Knights"},
+ {"bambou", "Playtoons Limited Edition - Bambou le sauveur de la jungle"},
{"fascination", "Fascination"},
{"geisha", "Geisha"},
{"adibou4", "Adibou v4"},
@@ -84,6 +85,7 @@ static const ADObsoleteGameID obsoleteGameIDsTable[] = {
namespace Gob {
using Common::GUIO_NOSPEECH;
+using Common::GUIO_NOSUBTITLES;
using Common::GUIO_NONE;
static const GOBGameDescription gameDescriptions[] = {
@@ -95,7 +97,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesEGA,
@@ -109,7 +111,7 @@ static const GOBGameDescription gameDescriptions[] = {
RU_RUS,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesEGA,
@@ -123,7 +125,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesNone,
@@ -137,7 +139,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesAdlib,
@@ -151,7 +153,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -165,7 +167,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -179,7 +181,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -193,7 +195,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -207,7 +209,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -221,7 +223,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -235,7 +237,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -249,7 +251,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -263,7 +265,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -277,7 +279,63 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob1cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "40d4a53818f4fce3f5997d02c3fafe73", 4049248),
+ HU_HUN,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob1cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "40d4a53818f4fce3f5997d02c3fafe73", 4049248),
+ FR_FRA,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob1cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "40d4a53818f4fce3f5997d02c3fafe73", 4049248),
+ ES_ESP,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob1cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "40d4a53818f4fce3f5997d02c3fafe73", 4049248),
+ IT_ITA,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -291,7 +349,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformAmiga,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesNone,
@@ -305,7 +363,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesNone,
@@ -319,7 +377,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesNone,
@@ -333,7 +391,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesNone,
@@ -347,7 +405,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesNone,
@@ -361,7 +419,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesAdlib,
@@ -375,7 +433,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesAdlib,
@@ -389,7 +447,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesAdlib,
@@ -403,7 +461,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesAdlib,
@@ -417,13 +475,13 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesAdlib,
0, 0, 0
},
- {
+ { // Supplied by Hkz on #scummvm
{
"gob1",
"",
@@ -435,7 +493,151 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformWindows,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ { // Supplied by Hkz on #scummvm
+ {
+ "gob1",
+ "",
+ {
+ {"intro.stk", 0, "f5f028ee39c456fa51fa63b606583918", 313472},
+ {"musmac1.mid", 0, "4f66903b33df8a20edd4c748809c0b56", 8161},
+ {0, 0, 0, 0}
+ },
+ IT_ITA,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ { // Supplied by Hkz on #scummvm
+ {
+ "gob1",
+ "",
+ {
+ {"intro.stk", 0, "f5f028ee39c456fa51fa63b606583918", 313472},
+ {"musmac1.mid", 0, "4f66903b33df8a20edd4c748809c0b56", 8161},
+ {0, 0, 0, 0}
+ },
+ EN_GRB,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ { // Supplied by Hkz on #scummvm
+ {
+ "gob1",
+ "",
+ {
+ {"intro.stk", 0, "f5f028ee39c456fa51fa63b606583918", 313472},
+ {"musmac1.mid", 0, "4f66903b33df8a20edd4c748809c0b56", 8161},
+ {0, 0, 0, 0}
+ },
+ DE_DEU,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ { // Supplied by Hkz on #scummvm
+ {
+ "gob1",
+ "",
+ {
+ {"intro.stk", 0, "f5f028ee39c456fa51fa63b606583918", 313472},
+ {"musmac1.mid", 0, "4f66903b33df8a20edd4c748809c0b56", 8161},
+ {0, 0, 0, 0}
+ },
+ ES_ESP,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "gob1",
+ "",
+ {
+ {"intro.stk", 0, "e157cb59c6d330ca70d12ab0ef1dd12b", 288972},
+ {"musmac1.mid", 0, "4f66903b33df8a20edd4c748809c0b56", 8161},
+ {0, 0, 0, 0}
+ },
+ EN_GRB,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "gob1",
+ "",
+ {
+ {"intro.stk", 0, "e157cb59c6d330ca70d12ab0ef1dd12b", 288972},
+ {"musmac1.mid", 0, "4f66903b33df8a20edd4c748809c0b56", 8161},
+ {0, 0, 0, 0}
+ },
+ FR_FRA,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "gob1",
+ "",
+ {
+ {"intro.stk", 0, "e157cb59c6d330ca70d12ab0ef1dd12b", 288972},
+ {"musmac1.mid", 0, "4f66903b33df8a20edd4c748809c0b56", 8161},
+ {0, 0, 0, 0}
+ },
+ ES_ESP,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob1,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "gob1",
+ "",
+ {
+ {"intro.stk", 0, "e157cb59c6d330ca70d12ab0ef1dd12b", 288972},
+ {"musmac1.mid", 0, "4f66903b33df8a20edd4c748809c0b56", 8161},
+ {0, 0, 0, 0}
+ },
+ IT_ITA,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesAdlib,
@@ -453,7 +655,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformWindows,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesAdlib,
@@ -467,7 +669,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesNone,
@@ -481,7 +683,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesNone,
@@ -495,7 +697,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesNone,
@@ -509,7 +711,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformAtariST,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesNone,
@@ -527,7 +729,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -545,7 +747,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -559,7 +761,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -573,7 +775,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -587,7 +789,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -601,7 +803,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -615,7 +817,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -629,7 +831,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -643,7 +845,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -657,7 +859,7 @@ static const GOBGameDescription gameDescriptions[] = {
RU_RUS,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -671,7 +873,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -685,7 +887,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesCD,
@@ -699,7 +901,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesCD,
@@ -713,7 +915,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesCD,
@@ -727,7 +929,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesCD,
@@ -741,7 +943,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesCD,
@@ -755,7 +957,77 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob2,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob2cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "5ba85a4769a1ab03a283dd694588d526", 5006236),
+ HU_HUN,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob2,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob2cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "5ba85a4769a1ab03a283dd694588d526", 5006236),
+ FR_FRA,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob2,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob2cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "5ba85a4769a1ab03a283dd694588d526", 5006236),
+ DE_DEU,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob2,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob2cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "5ba85a4769a1ab03a283dd694588d526", 5006236),
+ ES_ESP,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob2,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob2cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "5ba85a4769a1ab03a283dd694588d526", 5006236),
+ IT_ITA,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesCD,
@@ -769,7 +1041,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -783,7 +1055,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -797,7 +1069,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformAmiga,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesNone,
@@ -811,7 +1083,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformAmiga,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesNone,
@@ -829,7 +1101,43 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformWindows,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob2,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "gob2",
+ "",
+ {
+ {"intro.stk", 0, "25a99827cd59751a80bed9620fb677a0", 893302},
+ {"musmac1.mid", 0, "834e55205b710d0af5f14a6f2320dd8e", 8661},
+ {0, 0, 0, 0}
+ },
+ EN_USA,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob2,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "gob2",
+ "",
+ {
+ {"intro.stk", 0, "25a99827cd59751a80bed9620fb677a0", 893302},
+ {"musmac1.mid", 0, "834e55205b710d0af5f14a6f2320dd8e", 8661},
+ {0, 0, 0, 0}
+ },
+ FR_FRA,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -847,7 +1155,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformWindows,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -865,7 +1173,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesNone,
@@ -879,7 +1187,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesNone,
@@ -893,7 +1201,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesNone,
@@ -907,7 +1215,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesNone,
@@ -925,7 +1233,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesNone,
@@ -943,7 +1251,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformAtariST,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesNone,
@@ -957,7 +1265,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformAtariST,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesNone,
@@ -971,7 +1279,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesAdlib,
@@ -985,7 +1293,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesAdlib,
@@ -999,7 +1307,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesAdlib,
@@ -1013,7 +1321,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesAdlib,
@@ -1027,7 +1335,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesAdlib,
@@ -1041,7 +1349,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesAdlib,
@@ -1055,7 +1363,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesAdlib,
@@ -1069,7 +1377,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWeen,
kFeaturesAdlib,
@@ -1083,7 +1391,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeBargon,
kFeaturesNone,
@@ -1097,7 +1405,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformAtariST,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeBargon,
kFeaturesNone,
@@ -1111,7 +1419,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeBargon,
kFeaturesNone,
@@ -1125,7 +1433,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeBargon,
kFeaturesNone,
@@ -1139,7 +1447,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeBargon,
kFeaturesNone,
@@ -1153,7 +1461,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeBargon,
kFeaturesNone,
@@ -1167,7 +1475,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeBargon,
kFeaturesNone,
@@ -1181,7 +1489,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib | kFeaturesEGA,
@@ -1195,7 +1503,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib | kFeaturesEGA,
@@ -1209,7 +1517,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib | kFeaturesEGA,
@@ -1223,7 +1531,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib | kFeaturesEGA,
@@ -1237,7 +1545,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib | kFeaturesEGA,
@@ -1255,7 +1563,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesNone,
@@ -1269,7 +1577,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -1283,7 +1591,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -1297,7 +1605,7 @@ static const GOBGameDescription gameDescriptions[] = {
HB_ISR,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -1311,7 +1619,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -1325,7 +1633,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -1339,7 +1647,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -1357,7 +1665,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -1371,7 +1679,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1385,7 +1693,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1399,7 +1707,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1413,7 +1721,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1427,7 +1735,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1441,7 +1749,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1455,7 +1763,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1469,7 +1777,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1483,7 +1791,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1497,7 +1805,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1511,7 +1819,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1525,7 +1833,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -1536,10 +1844,38 @@ static const GOBGameDescription gameDescriptions[] = {
"lostintime",
"",
AD_ENTRY1s("intro.stk", "0ddf39cea1ec30ecc8bfe444ebd7b845", 4207330),
- UNK_LANG,
+ EN_GRB,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeLostInTime,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "lostintime",
+ "",
+ AD_ENTRY1s("intro.stk", "0ddf39cea1ec30ecc8bfe444ebd7b845", 4207330),
+ FR_FRA,
kPlatformWindows,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeLostInTime,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "lostintime",
+ "",
+ AD_ENTRY1s("intro.stk", "0ddf39cea1ec30ecc8bfe444ebd7b845", 4207330),
+ ES_ESP,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -1553,7 +1889,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES
},
kGameTypeFascination,
kFeaturesCD,
@@ -1567,7 +1903,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeFascination,
kFeaturesAdlib,
@@ -1581,14 +1917,13 @@ static const GOBGameDescription gameDescriptions[] = {
HB_ISR,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeFascination,
kFeaturesAdlib,
"intro.stk", 0, 0
},
- //Provided by Sanguine
- {
+ { // Supplied by sanguine
{
"fascination",
"VGA 3 disks edition",
@@ -1596,7 +1931,21 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeFascination,
+ kFeaturesAdlib,
+ "disk0.stk", 0, 0
+ },
+ { // Supplied by windlepoons in bug report #2809247
+ {
+ "fascination",
+ "VGA 3 disks edition",
+ AD_ENTRY1s("disk0.stk", "3a24e60a035250189643c86a9ceafb97", 1062480),
+ DE_DEU,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeFascination,
kFeaturesAdlib,
@@ -1610,7 +1959,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeFascination,
kFeaturesAdlib,
@@ -1624,7 +1973,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeFascination,
kFeaturesNone,
@@ -1638,7 +1987,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeFascination,
kFeaturesNone,
@@ -1652,7 +2001,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeFascination,
kFeaturesNone,
@@ -1666,7 +2015,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeFascination,
kFeaturesNone,
@@ -1680,7 +2029,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGeisha,
kFeaturesNone,
@@ -1694,7 +2043,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGeisha,
kFeaturesNone,
@@ -1708,7 +2057,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -1722,7 +2071,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -1736,7 +2085,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1750,7 +2099,7 @@ static const GOBGameDescription gameDescriptions[] = {
HB_ISR,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1764,7 +2113,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1782,7 +2131,43 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformWindows,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob3,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "gob3",
+ "",
+ {
+ {"intro.stk", 0, "16b014bf32dbd6ab4c5163c44f56fed1", 445104},
+ {"musmac1.mid", 0, "948c546cad3a9de5bff3fe4107c82bf1", 6404},
+ {0, 0, 0, 0}
+ },
+ FR_FRA,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob3,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "gob3",
+ "",
+ {
+ {"intro.stk", 0, "16b014bf32dbd6ab4c5163c44f56fed1", 445104},
+ {"musmac1.mid", 0, "948c546cad3a9de5bff3fe4107c82bf1", 6404},
+ {0, 0, 0, 0}
+ },
+ EN_GRB,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1800,7 +2185,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1814,7 +2199,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1828,7 +2213,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1842,7 +2227,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1856,7 +2241,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1870,7 +2255,7 @@ static const GOBGameDescription gameDescriptions[] = {
RU_RUS,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1884,7 +2269,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1898,7 +2283,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -1912,7 +2297,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesNone,
@@ -1926,7 +2311,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformAmiga,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesNone,
@@ -1940,7 +2325,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesCD,
@@ -1954,7 +2339,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesCD,
@@ -1968,7 +2353,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesCD,
@@ -1982,7 +2367,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesCD,
@@ -1996,7 +2381,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesCD,
@@ -2010,7 +2395,63 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob3,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob3cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "bfd7d4c6fedeb2cfcc8baa4d5ddb1f74", 616220),
+ HU_HUN,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob3,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob3cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "bfd7d4c6fedeb2cfcc8baa4d5ddb1f74", 616220),
+ FR_FRA,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob3,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob3cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "bfd7d4c6fedeb2cfcc8baa4d5ddb1f74", 616220),
+ DE_DEU,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeGob3,
+ kFeaturesCD,
+ 0, 0, 0
+ },
+ { // Supplied by goodoldgeorg in bug report #2810082
+ {
+ "gob3cd",
+ "v1.02",
+ AD_ENTRY1s("intro.stk", "bfd7d4c6fedeb2cfcc8baa4d5ddb1f74", 616220),
+ ES_ESP,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesCD,
@@ -2024,7 +2465,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -2038,7 +2479,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -2052,7 +2493,7 @@ static const GOBGameDescription gameDescriptions[] = {
UNK_LANG,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -2066,7 +2507,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformPC,
ADGF_DEMO,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -2084,7 +2525,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformWindows,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -2098,7 +2539,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeInca2,
kFeaturesCD,
@@ -2112,7 +2553,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeInca2,
kFeaturesCD,
@@ -2126,7 +2567,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeInca2,
kFeaturesCD,
@@ -2140,7 +2581,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeInca2,
kFeaturesCD,
@@ -2154,7 +2595,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeInca2,
kFeaturesCD,
@@ -2168,7 +2609,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeInca2,
kFeaturesAdlib,
@@ -2182,7 +2623,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeInca2,
kFeaturesAdlib,
@@ -2196,7 +2637,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeInca2,
kFeaturesAdlib,
@@ -2210,7 +2651,63 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformWindows,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeInca2,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "inca2",
+ "",
+ AD_ENTRY1s("intro.stk", "d33011df8758ac64ca3dca77c7719001", 908612),
+ DE_DEU,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeInca2,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "inca2",
+ "",
+ AD_ENTRY1s("intro.stk", "d33011df8758ac64ca3dca77c7719001", 908612),
+ IT_ITA,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeInca2,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "inca2",
+ "",
+ AD_ENTRY1s("intro.stk", "d33011df8758ac64ca3dca77c7719001", 908612),
+ ES_ESP,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeInca2,
+ kFeaturesAdlib,
+ 0, 0, 0
+ },
+ {
+ {
+ "inca2",
+ "",
+ AD_ENTRY1s("intro.stk", "d33011df8758ac64ca3dca77c7719001", 908612),
+ FR_FRA,
+ kPlatformWindows,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeInca2,
kFeaturesAdlib,
@@ -2237,7 +2734,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeInca2,
kFeaturesAdlib | kFeaturesBATDemo,
@@ -2251,7 +2748,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2265,7 +2762,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2279,7 +2776,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2293,7 +2790,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2307,7 +2804,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2321,7 +2818,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2335,7 +2832,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2349,7 +2846,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2363,7 +2860,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2377,7 +2874,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2391,7 +2888,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2405,7 +2902,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2419,7 +2916,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2433,7 +2930,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2447,7 +2944,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2461,7 +2958,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2475,7 +2972,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2489,7 +2986,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2503,7 +3000,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2517,7 +3014,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_GRB,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2531,7 +3028,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2545,7 +3042,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2559,7 +3056,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2573,7 +3070,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2587,7 +3084,7 @@ static const GOBGameDescription gameDescriptions[] = {
PL_POL,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -2605,7 +3102,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640 | kFeaturesSCNDemo,
@@ -2619,7 +3116,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeDynasty,
kFeatures640,
@@ -2633,7 +3130,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeDynasty,
kFeatures640,
@@ -2647,7 +3144,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeDynasty,
kFeatures640,
@@ -2661,7 +3158,21 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypeDynasty,
+ kFeatures640,
+ 0, 0, 0
+ },
+ {
+ {
+ "dynasty",
+ "",
+ AD_ENTRY1s("intro.stk", "bdbdac8919200a5e71ffb9fb0709f704", 2446652),
+ DE_DEU,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeDynasty,
kFeatures640,
@@ -2717,7 +3228,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_USA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeUrban,
kFeatures640,
@@ -2731,7 +3242,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeUrban,
kFeatures640,
@@ -2745,7 +3256,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeUrban,
kFeatures640,
@@ -2759,7 +3270,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeUrban,
kFeatures640,
@@ -2786,7 +3297,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "archi",
+ "playtoons1",
"",
{
{"playtoon.stk", 0, "8c98e9a11be9bb203a55e8c6e68e519b", 25574338},
@@ -2796,7 +3307,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -2804,8 +3315,8 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "archi",
- "Pack mes histoires animées",
+ "playtoons1",
+ "Pack mes histoires anim\xE9""es",
{
{"playtoon.stk", 0, "55f0293202963854192e39474e214f5f", 30448474},
{"archi.stk", 0, "8d44b2a0d4e3139471213f9f0ed21e81", 5524674},
@@ -2814,7 +3325,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -2822,7 +3333,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "archi",
+ "playtoons1",
"",
{
{"playtoon.stk", 0, "c5ca2a288cdaefca9556cd9ae4b579cf", 25158926},
@@ -2832,7 +3343,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -2840,7 +3351,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "archi",
+ "playtoons1",
"Non-Interactive Demo",
{
{"play123.scn", 0, "4689a31f543915e488c3bc46ea358add", 258},
@@ -2855,7 +3366,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640 | kFeaturesSCNDemo,
@@ -2863,7 +3374,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "archi",
+ "playtoons1",
"Non-Interactive Demo",
{
{"e.scn", 0, "8a0db733c3f77be86e74e8242e5caa61", 124},
@@ -2873,7 +3384,7 @@ static const GOBGameDescription gameDescriptions[] = {
EN_ANY,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640 | kFeaturesSCNDemo,
@@ -2881,7 +3392,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "archi",
+ "playtoons1",
"Non-Interactive Demo",
{
{"i.scn", 0, "8b3294474d39970463663edd22341730", 285},
@@ -2895,7 +3406,7 @@ static const GOBGameDescription gameDescriptions[] = {
IT_ITA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640 | kFeaturesSCNDemo,
@@ -2903,7 +3414,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "archi",
+ "playtoons1",
"Non-Interactive Demo",
{
{"s.scn", 0, "1f527010626b5490761f16ba7a6f639a", 251},
@@ -2916,7 +3427,7 @@ static const GOBGameDescription gameDescriptions[] = {
ES_ESP,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640 | kFeaturesSCNDemo,
@@ -2924,7 +3435,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "spirou",
+ "playtoons2",
"",
{
{"playtoon.stk", 0, "55a85036dd93cce93532d8f743d90074", 17467154},
@@ -2934,7 +3445,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -2942,7 +3453,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "spirou",
+ "playtoons2",
"",
{
{"playtoon.stk", 0, "c5ca2a288cdaefca9556cd9ae4b579cf", 25158926},
@@ -2952,7 +3463,7 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -2960,7 +3471,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "chato",
+ "playtoons3",
"",
{
{"playtoon.stk", 0, "8c98e9a11be9bb203a55e8c6e68e519b", 25574338},
@@ -2970,7 +3481,25 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypePlaytoon,
+ kFeatures640,
+ "intro2.stk", 0, 0
+ },
+ {
+ {
+ "playtoons3",
+ "",
+ {
+ {"playtoon.stk", 0, "9e513e993a5b0e2496add3f50c08764b", 30448506},
+ {"chato.stk", 0, "8fc8d0da5b3e758908d1d7298d497d0b", 6041026},
+ {0, 0, 0, 0}
+ },
+ EN_ANY,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -2978,8 +3507,8 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "chato",
- "Pack mes histoires animées",
+ "playtoons3",
+ "Pack mes histoires anim\xE9""es",
{
{"playtoon.stk", 0, "55f0293202963854192e39474e214f5f", 30448474},
{"chato.stk", 0, "4fa4ed96a427c344e9f916f9f236598d", 6033793},
@@ -2988,7 +3517,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -2996,7 +3525,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "chato",
+ "playtoons3",
"",
{
{"playtoon.stk", 0, "c5ca2a288cdaefca9556cd9ae4b579cf", 25158926},
@@ -3006,7 +3535,26 @@ static const GOBGameDescription gameDescriptions[] = {
DE_DEU,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypePlaytoon,
+ kFeatures640,
+ "intro2.stk", 0, 0
+ },
+
+ {
+ {
+ "playtoons4",
+ "",
+ {
+ {"playtoon.stk", 0, "b7f5afa2dc1b0f75970b7c07d175db1b", 24340406},
+ {"manda.stk", 0, "92529e0b927191d9898a34c2892e9a3a", 6485072},
+ {0, 0, 0, 0}
+ },
+ FR_FRA,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -3014,7 +3562,7 @@ static const GOBGameDescription gameDescriptions[] = {
},
{
{
- "wakan",
+ "playtoons5",
"",
{
{"playtoon.stk", 0, "55f0293202963854192e39474e214f5f", 30448474},
@@ -3024,7 +3572,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -3042,11 +3590,29 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeBambou,
kFeatures640,
- 0, 0, 0
+ "intro.stk", "intro.tot", 0
+ },
+ {
+ {
+ "playtnck1",
+ "",
+ {
+ {"playtoon.stk", 0, "5f9aae29265f1f105ad8ec195dff81de", 68382024},
+ {"dan.itk", 0, "906d67b3e438d5e95ec7ea9e781a94f3", 3000320},
+ {0, 0, 0, 0}
+ },
+ FR_FRA,
+ kPlatformPC,
+ ADGF_NO_FLAGS,
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
+ },
+ kGameTypePlaytnCk,
+ kFeatures640,
+ "intro2.stk", 0, 0
},
{
{
@@ -3054,12 +3620,13 @@ static const GOBGameDescription gameDescriptions[] = {
"",
{
{"playtoon.stk", 0, "5f9aae29265f1f105ad8ec195dff81de", 68382024},
+ {"dan.itk", 0, "74eeb075bd2cb47b243349730264af01", 3213312},
{0, 0, 0, 0}
},
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytnCk,
kFeatures640,
@@ -3073,7 +3640,7 @@ static const GOBGameDescription gameDescriptions[] = {
FR_FRA,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NONE
},
kGameTypeAdibou4,
kFeatures640,
@@ -3207,7 +3774,7 @@ static const GOBGameDescription gameDescriptions[] = {
{
{
"adibouunknown",
- "ADIBÙ 2 Ambiente",
+ "ADIB\xD9 2 Ambiente",
AD_ENTRY1s("intro.stk", "092707829555f27706920e4cacf1fada", 8737958),
IT_ITA,
kPlatformPC,
@@ -3221,7 +3788,7 @@ static const GOBGameDescription gameDescriptions[] = {
{
{
"adibouunknown",
- "ADIBÙ prima elementare : Imparo a leggere e a contare",
+ "ADIB\xD9 prima elementare : Imparo a leggere e a contare",
{
{"intro.stk", 0, "092707829555f27706920e4cacf1fada", 8737958},
{"appbou2.itk", 0, "f7bf045f6bdce5a7607c720e36704f33", 200005632},
@@ -3239,7 +3806,7 @@ static const GOBGameDescription gameDescriptions[] = {
{
{
"adibouunknown",
- "ADIBOU présente La Magie (STK2.1/OBC)",
+ "ADIBOU pr\xE9sente La Magie (STK2.1/OBC)",
{
{"adibou.stk", 0, "977d2449d398f3df23238d718fca35b5", 61097},
{"magic.stk", 0, "9776765dead3e338a32c43bf344b5819", 302664},
@@ -3320,7 +3887,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesNone,
@@ -3334,7 +3901,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob1,
kFeaturesCD,
@@ -3348,7 +3915,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -3362,7 +3929,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesAdlib,
@@ -3376,7 +3943,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob2,
kFeaturesCD,
@@ -3390,7 +3957,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeBargon,
kFeaturesNone,
@@ -3404,7 +3971,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesAdlib,
@@ -3418,7 +3985,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGob3,
kFeaturesCD,
@@ -3432,7 +3999,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeWoodruff,
kFeatures640,
@@ -3446,7 +4013,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -3460,7 +4027,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformMacintosh,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesAdlib,
@@ -3474,7 +4041,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeLostInTime,
kFeaturesCD,
@@ -3488,7 +4055,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NONE
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeUrban,
kFeaturesCD,
@@ -3496,13 +4063,13 @@ static const GOBGameDescription fallbackDescs[] = {
},
{
{
- "archi",
+ "playtoons1",
"unknown",
AD_ENTRY1(0, 0),
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -3510,13 +4077,13 @@ static const GOBGameDescription fallbackDescs[] = {
},
{
{
- "spirou",
+ "playtoons2",
"unknown",
AD_ENTRY1(0, 0),
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -3524,13 +4091,13 @@ static const GOBGameDescription fallbackDescs[] = {
},
{
{
- "chato",
+ "playtoons3",
"unknown",
AD_ENTRY1(0, 0),
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -3538,13 +4105,13 @@ static const GOBGameDescription fallbackDescs[] = {
},
{
{
- "manda",
+ "playtoons4",
"unknown",
AD_ENTRY1(0, 0),
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -3552,13 +4119,13 @@ static const GOBGameDescription fallbackDescs[] = {
},
{
{
- "wakan",
+ "playtoons5",
"unknown",
AD_ENTRY1(0, 0),
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytoon,
kFeatures640,
@@ -3572,7 +4139,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypePlaytnCk,
kFeatures640,
@@ -3586,7 +4153,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeBambou,
kFeatures640,
@@ -3600,7 +4167,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeFascination,
kFeaturesNone,
@@ -3614,7 +4181,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeGeisha,
kFeaturesNone,
@@ -3628,7 +4195,7 @@ static const GOBGameDescription fallbackDescs[] = {
UNK_LANG,
kPlatformPC,
ADGF_NO_FLAGS,
- GUIO_NOSPEECH
+ GUIO_NOSUBTITLES | GUIO_NOSPEECH
},
kGameTypeAdibou4,
kFeatures640,
diff --git a/engines/gob/draw.cpp b/engines/gob/draw.cpp
index 8619e08e8b..b3e5e7418c 100644
--- a/engines/gob/draw.cpp
+++ b/engines/gob/draw.cpp
@@ -30,6 +30,7 @@
#include "gob/global.h"
#include "gob/util.h"
#include "gob/game.h"
+#include "gob/script.h"
#include "gob/inter.h"
#include "gob/video.h"
#include "gob/palanim.h"
@@ -389,11 +390,10 @@ void Draw::printTextCentered(int16 id, int16 left, int16 top, int16 right,
adjustCoords(1, &left, &top);
adjustCoords(1, &right, &bottom);
- if (READ_LE_UINT16(_vm->_game->_totFileData + 0x7E) != 0) {
- byte *storedIP = _vm->_global->_inter_execPtr;
+ uint16 centerOffset = _vm->_game->_script->getFunctionOffset(TOTFile::kFunctionCenter);
+ if (centerOffset != 0) {
+ _vm->_game->_script->call(centerOffset);
- _vm->_global->_inter_execPtr = _vm->_game->_totFileData +
- READ_LE_UINT16(_vm->_game->_totFileData + 0x7E);
WRITE_VAR(17, (uint32) id);
WRITE_VAR(18, (uint32) left);
WRITE_VAR(19, (uint32) top);
@@ -401,7 +401,7 @@ void Draw::printTextCentered(int16 id, int16 left, int16 top, int16 right,
WRITE_VAR(21, (uint32) (bottom - top + 1));
_vm->_inter->funcBlock(0);
- _vm->_global->_inter_execPtr = storedIP;
+ _vm->_game->_script->pop();
}
if (str[0] == '\0')
diff --git a/engines/gob/draw_v1.cpp b/engines/gob/draw_v1.cpp
index de71f20142..94ee32a031 100644
--- a/engines/gob/draw_v1.cpp
+++ b/engines/gob/draw_v1.cpp
@@ -32,6 +32,7 @@
#include "gob/global.h"
#include "gob/util.h"
#include "gob/game.h"
+#include "gob/resources.h"
#include "gob/scenery.h"
#include "gob/inter.h"
#include "gob/sound/sound.h"
@@ -173,12 +174,12 @@ void Draw_v1::printTotText(int16 id) {
_vm->_sound->cdPlayMultMusic();
- if (!_vm->_game->_totTextData || !_vm->_game->_totTextData->dataPtr)
+ TextItem *textItem = _vm->_game->_resources->getTextItem(id);
+ if (!textItem)
return;
- dataPtr = _vm->_game->_totTextData->dataPtr +
- _vm->_game->_totTextData->items[id].offset;
- ptr = dataPtr;
+ dataPtr = textItem->getData();
+ ptr = dataPtr;
destX = READ_LE_UINT16(ptr) & 0x7FFF;
destY = READ_LE_UINT16(ptr + 2);
@@ -312,7 +313,9 @@ void Draw_v1::printTotText(int16 id) {
}
}
+ delete textItem;
_renderFlags = savedFlags;
+
if (_renderFlags & RENDERFLAG_COLLISIONS)
_vm->_game->checkCollisions(0, 0, 0, 0);
@@ -323,11 +326,10 @@ void Draw_v1::printTotText(int16 id) {
}
void Draw_v1::spriteOperation(int16 operation) {
- uint16 id;
- byte *dataBuf;
int16 len;
int16 x, y;
int16 perLine;
+ Resource *resource;
if (_sourceSurface >= 100)
_sourceSurface -= 80;
@@ -396,30 +398,20 @@ void Draw_v1::spriteOperation(int16 operation) {
break;
case DRAW_LOADSPRITE:
- id = _spriteLeft;
- if (id >= 30000) {
- dataBuf =
- _vm->_game->loadExtData(id, &_spriteRight, &_spriteBottom);
- _vm->_video->drawPackedSprite(dataBuf,
- _spriteRight, _spriteBottom,
- _destSpriteX, _destSpriteY,
- _transparency, *_spritesArray[_destSurface]);
- dirtiedRect(_destSurface, _destSpriteX, _destSpriteY,
- _destSpriteX + _spriteRight - 1, _destSpriteY + _spriteBottom - 1);
- delete[] dataBuf;
- break;
- }
+ resource = _vm->_game->_resources->getResource((uint16) _spriteLeft,
+ &_spriteRight, &_spriteBottom);
- if (!(dataBuf = _vm->_game->loadTotResource(id, 0, &_spriteRight, &_spriteBottom)))
+ if (!resource)
break;
- _vm->_video->drawPackedSprite(dataBuf,
- _spriteRight, _spriteBottom,
- _destSpriteX, _destSpriteY,
- _transparency, *_spritesArray[_destSurface]);
+ _vm->_video->drawPackedSprite(resource->getData(),
+ _spriteRight, _spriteBottom, _destSpriteX, _destSpriteY,
+ _transparency, *_spritesArray[_destSurface]);
dirtiedRect(_destSurface, _destSpriteX, _destSpriteY,
_destSpriteX + _spriteRight - 1, _destSpriteY + _spriteBottom - 1);
+
+ delete resource;
break;
case DRAW_PRINTTEXT:
diff --git a/engines/gob/draw_v2.cpp b/engines/gob/draw_v2.cpp
index 4bb8120e3a..2843456f42 100644
--- a/engines/gob/draw_v2.cpp
+++ b/engines/gob/draw_v2.cpp
@@ -32,6 +32,8 @@
#include "gob/global.h"
#include "gob/util.h"
#include "gob/game.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/scenery.h"
#include "gob/inter.h"
#include "gob/video.h"
@@ -205,12 +207,6 @@ void Draw_v2::printTotText(int16 id) {
id &= 0xFFF;
- if (!_vm->_game->_totTextData || !_vm->_game->_totTextData->dataPtr ||
- (id >= _vm->_game->_totTextData->itemsCount) ||
- (_vm->_game->_totTextData->items[id].offset == -1) ||
- (_vm->_game->_totTextData->items[id].size == 0))
- return;
-
_vm->validateLanguage();
// WORKAROUND: In the scripts of some Gobliins 2 versions, the dialog text IDs
@@ -234,13 +230,18 @@ void Draw_v2::printTotText(int16 id) {
}
- size = _vm->_game->_totTextData->items[id].size;
- dataPtr = _vm->_game->_totTextData->dataPtr +
- _vm->_game->_totTextData->items[id].offset;
- ptr = dataPtr;
+ TextItem *textItem = _vm->_game->_resources->getTextItem(id);
+ if (!textItem)
+ return;
- if ((_renderFlags & RENDERFLAG_SKIPOPTIONALTEXT) && (ptr[1] & 0x80))
+ size = textItem->getSize();
+ dataPtr = textItem->getData();
+ ptr = dataPtr;
+
+ if ((_renderFlags & RENDERFLAG_SKIPOPTIONALTEXT) && (ptr[1] & 0x80)) {
+ delete textItem;
return;
+ }
if (_renderFlags & RENDERFLAG_DOUBLECOORDS) {
destX = (READ_LE_UINT16(ptr) & 0x7FFF) * 2;
@@ -328,7 +329,7 @@ void Draw_v2::printTotText(int16 id) {
ptrEnd = ptr;
while (((ptrEnd - dataPtr) < size) && (*ptrEnd != 1)) {
// Converting to unknown commands/characters to spaces
- if ((_vm->_game->_totFileData[0x29] < 0x32) && (*ptrEnd > 3) && (*ptrEnd < 32))
+ if ((_vm->_game->_script->getVersionMinor() < 2) && (*ptrEnd > 3) && (*ptrEnd < 32))
*ptrEnd = 32;
switch (*ptrEnd) {
@@ -524,7 +525,7 @@ void Draw_v2::printTotText(int16 id) {
case 10:
str[0] = (char) 255;
WRITE_LE_UINT16((uint16 *) (str + 1),
- ptr - _vm->_game->_totTextData->dataPtr);
+ ptr - _vm->_game->_resources->getTexts());
str[3] = 0;
ptr++;
for (int i = *ptr++; i > 0; i--) {
@@ -597,7 +598,9 @@ void Draw_v2::printTotText(int16 id) {
}
}
+ delete textItem;
_renderFlags = savedFlags;
+
if (!(_renderFlags & RENDERFLAG_COLLISIONS))
return;
@@ -610,14 +613,13 @@ void Draw_v2::printTotText(int16 id) {
}
void Draw_v2::spriteOperation(int16 operation) {
- uint16 id;
- byte *dataBuf;
int16 len;
int16 x, y;
SurfaceDescPtr sourceSurf, destSurf;
bool deltaVeto;
int16 left;
int16 ratio;
+ Resource *resource;
// Always assigned to -1 in Game::loadTotFile()
int16 someHandle = -1;
@@ -705,6 +707,11 @@ void Draw_v2::spriteOperation(int16 operation) {
sourceSurf = _spritesArray[_sourceSurface];
destSurf = _spritesArray[_destSurface];
+ if (!destSurf) {
+ warning("Can't do operation %d on surface %d: nonexistent", operation, _destSurface);
+ return;
+ }
+
switch (operation) {
case DRAW_BLITSURF:
case DRAW_DRAWLETTER:
@@ -755,41 +762,20 @@ void Draw_v2::spriteOperation(int16 operation) {
break;
case DRAW_LOADSPRITE:
- id = _spriteLeft;
-
- if ((id >= 30000) || (_vm->_game->_lomHandle >= 0)) {
- dataBuf = 0;
+ resource = _vm->_game->_resources->getResource((uint16) _spriteLeft,
+ &_spriteRight, &_spriteBottom);
- if (_vm->_game->_lomHandle >= 0)
- warning("Urban Stub: LOADSPRITE %d, LOM", id);
- else
- dataBuf = _vm->_game->loadExtData(id, &_spriteRight, &_spriteBottom);
-
- if (!dataBuf)
- break;
-
- _vm->_video->drawPackedSprite(dataBuf,
- _spriteRight, _spriteBottom, _destSpriteX, _destSpriteY,
- _transparency, *_spritesArray[_destSurface]);
-
- dirtiedRect(_destSurface, _destSpriteX, _destSpriteY,
- _destSpriteX + _spriteRight - 1, _destSpriteY + _spriteBottom - 1);
-
- delete[] dataBuf;
+ if (!resource)
break;
- }
- // Load from .TOT resources
- if (!(dataBuf = _vm->_game->loadTotResource(id, 0, &_spriteRight, &_spriteBottom)))
- break;
-
- _vm->_video->drawPackedSprite(dataBuf,
- _spriteRight, _spriteBottom,
- _destSpriteX, _destSpriteY,
- _transparency, *_spritesArray[_destSurface]);
+ _vm->_video->drawPackedSprite(resource->getData(),
+ _spriteRight, _spriteBottom, _destSpriteX, _destSpriteY,
+ _transparency, *_spritesArray[_destSurface]);
dirtiedRect(_destSurface, _destSpriteX, _destSpriteY,
_destSpriteX + _spriteRight - 1, _destSpriteY + _spriteBottom - 1);
+
+ delete resource;
break;
case DRAW_PRINTTEXT:
@@ -802,7 +788,7 @@ void Draw_v2::spriteOperation(int16 operation) {
if (((int8) _textToPrint[0]) == -1) {
_vm->validateLanguage();
- dataBuf = _vm->_game->_totTextData->dataPtr + _textToPrint[1] + 1;
+ byte *dataBuf = _vm->_game->_resources->getTexts() + _textToPrint[1] + 1;
len = *dataBuf++;
for (int i = 0; i < len; i++, dataBuf += 2) {
_vm->_video->drawLetter(READ_LE_UINT16(dataBuf), _destSpriteX,
diff --git a/engines/gob/expression.cpp b/engines/gob/expression.cpp
new file mode 100644
index 0000000000..61376b2212
--- /dev/null
+++ b/engines/gob/expression.cpp
@@ -0,0 +1,1144 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/endian.h"
+
+#include "gob/gob.h"
+#include "gob/expression.h"
+#include "gob/global.h"
+#include "gob/game.h"
+#include "gob/script.h"
+#include "gob/inter.h"
+
+namespace Gob {
+
+Expression::Stack::Stack(size_t size) {
+ opers = new byte[size];
+ values = new int32[size];
+ memset(opers , 0, size * sizeof(byte ));
+ memset(values, 0, size * sizeof(int32));
+}
+
+Expression::Stack::~Stack() {
+ delete[] opers;
+ delete[] values;
+}
+
+Expression::StackFrame::StackFrame(const Stack &stack) {
+ opers = stack.opers - 1;
+ values = stack.values - 1;
+ pos = -1;
+}
+
+void Expression::StackFrame::push(int count) {
+ opers += count;
+ values += count;
+ pos += count;
+}
+
+void Expression::StackFrame::pop(int count) {
+ opers -= count;
+ values -= count;
+ pos -= count;
+}
+
+Expression::Expression(GobEngine *vm) : _vm(vm) {
+ _resultStr[0] = 0;
+ _resultInt = 0;
+}
+
+int32 Expression::encodePtr(byte *ptr, int type) {
+ int32 offset = 0;
+
+ switch (type) {
+ case kExecPtr:
+ offset = _vm->_game->_script->getOffset(ptr);
+ break;
+ case kInterVar:
+ offset = ptr - ((byte *) _vm->_inter->_variables->getAddressOff8(0));
+ break;
+ case kResStr:
+ offset = ptr - ((byte *) _resultStr);
+ break;
+ default:
+ error("Expression::encodePtr(): Unknown pointer type");
+ }
+ assert((offset & 0xF0000000) == 0);
+ return (type << 28) | offset;
+}
+
+byte *Expression::decodePtr(int32 n) {
+ byte *ptr;
+
+ switch (n >> 28) {
+ case kExecPtr:
+ return _vm->_game->_script->getData((n & 0x0FFFFFFF));
+ case kInterVar:
+ ptr = (byte *) _vm->_inter->_variables->getAddressOff8(0);
+ break;
+ case kResStr:
+ ptr = (byte *) _resultStr;
+ break;
+ default:
+ error("Expression::decodePtr(): Unknown pointer type");
+ }
+ return ptr + (n & 0x0FFFFFFF);
+}
+
+void Expression::skipExpr(char stopToken) {
+ int16 dimCount;
+ byte operation;
+ int16 num;
+ int16 dim;
+
+ num = 0;
+ while (true) {
+ operation = _vm->_game->_script->readByte();
+
+ if ((operation >= 14) && (operation <= OP_FUNC)) {
+ switch (operation) {
+ case 14:
+ _vm->_game->_script->skip(4);
+ if (_vm->_game->_script->peekByte() == 97)
+ _vm->_game->_script->skip(1);
+ break;
+
+ case OP_LOAD_VAR_INT16:
+ case OP_LOAD_VAR_INT8:
+ case OP_LOAD_IMM_INT16:
+ case OP_LOAD_VAR_INT32:
+ case OP_LOAD_VAR_INT32_AS_INT16:
+ _vm->_game->_script->skip(2);
+ break;
+
+ case OP_LOAD_IMM_INT32:
+ _vm->_game->_script->skip(4);
+ break;
+
+ case OP_LOAD_IMM_INT8:
+ _vm->_game->_script->skip(1);
+ break;
+
+ case OP_LOAD_IMM_STR:
+ _vm->_game->_script->skip(strlen(_vm->_game->_script->peekString()) + 1);
+ break;
+
+ case OP_LOAD_VAR_STR:
+ _vm->_game->_script->skip(2);
+ if (_vm->_game->_script->peekByte() == 13) {
+ _vm->_game->_script->skip(1);
+ skipExpr(OP_END_MARKER);
+ }
+ break;
+
+ case 15:
+ _vm->_game->_script->skip(2);
+
+ case OP_ARRAY_INT8:
+ case OP_ARRAY_INT32:
+ case OP_ARRAY_INT16:
+ case OP_ARRAY_STR:
+ dimCount = _vm->_game->_script->peekByte(2);
+ // skip header and dimensions
+ _vm->_game->_script->skip(3 + dimCount);
+ // skip indices
+ for (dim = 0; dim < dimCount; dim++)
+ skipExpr(OP_END_MARKER);
+
+ if ((operation == OP_ARRAY_STR) && (_vm->_game->_script->peekByte() == 13)) {
+ _vm->_game->_script->skip(1);
+ skipExpr(OP_END_MARKER);
+ }
+ break;
+
+ case OP_FUNC:
+ _vm->_game->_script->skip(1);
+ skipExpr(OP_END_EXPR);
+ }
+ continue;
+ } // if ((operation >= OP_ARRAY_INT8) && (operation <= OP_FUNC))
+
+ if (operation == OP_BEGIN_EXPR) {
+ num++;
+ continue;
+ }
+
+ if ((operation == OP_NOT) || ((operation >= OP_NEG) && (operation <= 8)))
+ continue;
+
+ if ((operation >= OP_OR) && (operation <= OP_NEQ))
+ continue;
+
+ if (operation == OP_END_EXPR)
+ num--;
+
+ if (operation != stopToken)
+ continue;
+
+ if ((stopToken != OP_END_EXPR) || (num < 0))
+ return;
+ }
+}
+
+void Expression::printExpr(char stopToken) {
+ // Expression printing disabled by default
+ return;
+
+ int32 savedPos = _vm->_game->_script->pos();
+ printExpr_internal(stopToken);
+
+ // restore IP to start of expression
+ _vm->_game->_script->seek(savedPos);
+}
+
+void Expression::printExpr_internal(char stopToken) {
+ int16 dimCount;
+ byte operation;
+ int16 num;
+ int16 dim;
+ byte *arrDesc;
+ byte func;
+
+ num = 0;
+ while (true) {
+ operation = _vm->_game->_script->readByte();
+
+ if ((operation >= OP_ARRAY_INT8) && (operation <= OP_FUNC)) {
+ // operands
+
+ switch (operation) {
+ case OP_LOAD_VAR_INT16: // int16 variable load
+ debugN(5, "var16_%d", _vm->_game->_script->readUint16());
+ break;
+
+ case OP_LOAD_VAR_INT8: // int8 variable load:
+ debugN(5, "var8_%d", _vm->_game->_script->readUint16());
+ break;
+
+ case OP_LOAD_IMM_INT32: // int32/uint32 immediate
+ debugN(5, "%d", _vm->_game->_script->readInt32());
+ break;
+
+ case OP_LOAD_IMM_INT16: // int16 immediate
+ debugN(5, "%d", _vm->_game->_script->readInt16());
+ break;
+
+ case OP_LOAD_IMM_INT8: // int8 immediate
+ debugN(5, "%d", _vm->_game->_script->readInt8());
+ break;
+
+ case OP_LOAD_IMM_STR: // string immediate
+ debugN(5, "\42%s\42", _vm->_game->_script->readString());
+ break;
+
+ case OP_LOAD_VAR_INT32:
+ case OP_LOAD_VAR_INT32_AS_INT16:
+ debugN(5, "var_%d", _vm->_game->_script->readUint16());
+ break;
+
+ case OP_LOAD_VAR_STR: // string variable load
+ debugN(5, "(&var_%d)", _vm->_game->_script->readUint16());
+ if (_vm->_game->_script->peekByte() == 13) {
+ _vm->_game->_script->skip(1);
+ debugN(5, "{");
+ printExpr_internal(OP_END_MARKER); // this also prints the closing }
+ }
+ break;
+
+ case OP_ARRAY_INT8: // int8 array access
+ case OP_ARRAY_INT32: // int32 array access
+ case OP_ARRAY_INT16: // int16 array access
+ case OP_ARRAY_STR: // string array access
+ debugN(5, "\n");
+ if (operation == OP_ARRAY_STR)
+ debugN(5, "(&");
+
+ debugN(5, "var_%d[", _vm->_game->_script->readInt16());
+ dimCount = _vm->_game->_script->readByte();
+ arrDesc = _vm->_game->_script->getData() + _vm->_game->_script->pos();
+ _vm->_game->_script->skip(dimCount);
+ for (dim = 0; dim < dimCount; dim++) {
+ printExpr_internal(OP_END_MARKER);
+ debugN(5, " of %d", (int16) arrDesc[dim]);
+ if (dim != dimCount - 1)
+ debugN(5, ",");
+ }
+ debugN(5, "]");
+ if (operation == OP_ARRAY_STR)
+ debugN(5, ")");
+
+ if ((operation == OP_ARRAY_STR) && (_vm->_game->_script->peekByte() == 13)) {
+ _vm->_game->_script->skip(1);
+ debugN(5, "{");
+ printExpr_internal(OP_END_MARKER); // this also prints the closing }
+ }
+ break;
+
+ case OP_FUNC: // function
+ func = _vm->_game->_script->readByte();
+ if (func == FUNC_SQR)
+ debugN(5, "sqr(");
+ else if (func == FUNC_RAND)
+ debugN(5, "rand(");
+ else if (func == FUNC_ABS)
+ debugN(5, "abs(");
+ else if ((func == FUNC_SQRT1) || (func == FUNC_SQRT2) || (func == FUNC_SQRT3))
+ debugN(5, "sqrt(");
+ else
+ debugN(5, "id(");
+ printExpr_internal(OP_END_EXPR);
+ break;
+ }
+ continue;
+ } // if ((operation >= OP_ARRAY_INT8) && (operation <= OP_FUNC))
+
+ // operators
+ switch (operation) {
+ case OP_BEGIN_EXPR:
+ debugN(5, "(");
+ break;
+
+ case OP_NOT:
+ debugN(5, "!");
+ break;
+
+ case OP_END_EXPR:
+ debugN(5, ")");
+ break;
+
+ case OP_NEG:
+ debugN(5, "-");
+ break;
+
+ case OP_ADD:
+ debugN(5, "+");
+ break;
+
+ case OP_SUB:
+ debugN(5, "-");
+ break;
+
+ case OP_BITOR:
+ debugN(5, "|");
+ break;
+
+ case OP_MUL:
+ debugN(5, "*");
+ break;
+
+ case OP_DIV:
+ debugN(5, "/");
+ break;
+
+ case OP_MOD:
+ debugN(5, "%%");
+ break;
+
+ case OP_BITAND:
+ debugN(5, "&");
+ break;
+
+ case OP_OR:
+ debugN(5, "||");
+ break;
+
+ case 31:
+ debugN(5, "&&");
+ break;
+
+ case OP_LESS:
+ debugN(5, "<");
+ break;
+
+ case OP_LEQ:
+ debugN(5, "<=");
+ break;
+
+ case OP_GREATER:
+ debugN(5, ">");
+ break;
+
+ case OP_GEQ:
+ debugN(5, ">=");
+ break;
+
+ case OP_EQ:
+ debugN(5, "==");
+ break;
+
+ case OP_NEQ:
+ debugN(5, "!=");
+ break;
+
+ case 99:
+ debugN(5, "\n");
+ break;
+
+ case OP_END_MARKER:
+ debugN(5, "}");
+ if (stopToken != OP_END_MARKER) {
+ debugN(5, "Closing paren without opening?");
+ }
+ break;
+
+ default:
+ debugN(5, "<%d>", (int16) operation);
+ error("Expression::printExpr(): invalid operator in expression");
+ break;
+ }
+
+ if (operation == OP_BEGIN_EXPR) {
+ num++;
+ continue;
+ }
+
+ if ((operation == OP_NOT) || ((operation >= OP_NEG) && (operation <= 8)))
+ continue;
+
+ if ((operation >= OP_OR) && (operation <= OP_NEQ))
+ continue;
+
+ if (operation == OP_END_EXPR)
+ num--;
+
+ if (operation == stopToken) {
+ if ((stopToken != OP_END_EXPR) || (num < 0)) {
+ return;
+ }
+ }
+ }
+}
+
+
+void Expression::printVarIndex() {
+ byte *arrDesc;
+ int16 dim;
+ int16 dimCount;
+ int16 operation;
+ int16 temp;
+
+ int32 pos = _vm->_game->_script->pos();
+
+ operation = _vm->_game->_script->readByte();
+ switch (operation) {
+ case OP_LOAD_VAR_INT32:
+ case OP_LOAD_VAR_STR:
+ temp = _vm->_game->_script->readUint16() * 4;
+ debugN(5, "&var_%d", temp);
+ if ((operation == OP_LOAD_VAR_STR) && (_vm->_game->_script->peekByte() == 13)) {
+ _vm->_game->_script->skip(1);
+ debugN(5, "+");
+ printExpr(OP_END_MARKER);
+ }
+ break;
+
+ case OP_ARRAY_INT32:
+ case OP_ARRAY_STR:
+ debugN(5, "&var_%d[", _vm->_game->_script->readUint16());
+ dimCount = _vm->_game->_script->readByte();
+ arrDesc = _vm->_game->_script->getData() + _vm->_game->_script->pos();
+ _vm->_game->_script->skip(dimCount);
+ for (dim = 0; dim < dimCount; dim++) {
+ printExpr(OP_END_MARKER);
+ debugN(5, " of %d", (int16) arrDesc[dim]);
+ if (dim != dimCount - 1)
+ debugN(5, ",");
+ }
+ debugN(5, "]");
+
+ if ((operation == OP_ARRAY_STR) && (_vm->_game->_script->peekByte() == 13)) {
+ _vm->_game->_script->skip(1);
+ debugN(5, "+");
+ printExpr(OP_END_MARKER);
+ }
+ break;
+
+ default:
+ debugN(5, "var_0");
+ break;
+ }
+ debugN(5, "\n");
+
+ _vm->_game->_script->seek(pos);
+ return;
+}
+
+int Expression::cmpHelper(const StackFrame &stackFrame) {
+ byte type = stackFrame.opers[-3];
+ int cmpTemp = 0;
+
+ if (type == OP_LOAD_IMM_INT16) {
+ cmpTemp = (int)stackFrame.values[-3] - (int)stackFrame.values[-1];
+ } else if (type == OP_LOAD_IMM_STR) {
+ if ((char *)decodePtr(stackFrame.values[-3]) != _resultStr) {
+ strcpy(_resultStr, (char *)decodePtr(stackFrame.values[-3]));
+ stackFrame.values[-3] = encodePtr((byte *) _resultStr, kResStr);
+ }
+ cmpTemp = strcmp(_resultStr, (char *)decodePtr(stackFrame.values[-1]));
+ }
+
+ return cmpTemp;
+}
+
+bool Expression::getVarBase(uint32 &varBase, bool mindStop,
+ uint16 *size, uint16 *type) {
+
+ varBase = 0;
+
+ byte operation = _vm->_game->_script->peekByte();
+ while ((operation == 14) || (operation == 15)) {
+ _vm->_game->_script->skip(1);
+
+ if (operation == 14) {
+ // Add a direct offset
+
+ varBase += _vm->_game->_script->readInt16() * 4;
+
+ if (size)
+ *size = _vm->_game->_script->peekUint16();
+ if (type)
+ *type = 14;
+
+ _vm->_game->_script->skip(2);
+
+ debugC(2, kDebugExpression, "varBase: %d, by %d", varBase, operation);
+
+ if (_vm->_game->_script->peekByte() != 97) {
+ if (mindStop)
+ return true;
+ } else
+ _vm->_game->_script->skip(1);
+
+ } else if (operation == 15) {
+ // Add an offset from an array
+
+ varBase += _vm->_game->_script->readInt16() * 4;
+
+ uint16 offset1 = _vm->_game->_script->readUint16();
+
+ if (size)
+ *size = offset1;
+ if (type)
+ *type = 15;
+
+ uint8 dimCount = _vm->_game->_script->readByte();
+ byte *dimArray = _vm->_game->_script->getData() + _vm->_game->_script->pos();
+
+ _vm->_game->_script->skip(dimCount);
+
+ uint16 offset2 = 0;
+ for (int i = 0; i < dimCount; i++) {
+ int16 dim = CLIP<int>(parseValExpr(OP_END_MARKER), 0, dimArray[i] - 1);
+
+ offset2 = offset2 * dimArray[i] + dim;
+ }
+
+ varBase += offset2 * offset1 * 4;
+
+ debugC(2, kDebugExpression, "varBase: %d, by %d", varBase, operation);
+
+ if (_vm->_game->_script->peekByte() != 97) {
+ if (mindStop)
+ return true;
+ } else
+ _vm->_game->_script->skip(1);
+ }
+
+ operation = _vm->_game->_script->peekByte();
+ }
+
+ return false;
+}
+
+int16 Expression::parseVarIndex(uint16 *size, uint16 *type) {
+ int16 temp2;
+ byte *arrDesc;
+ int16 dim;
+ int16 dimCount;
+ int16 operation;
+ int16 temp;
+ int16 offset;
+ int16 val;
+ uint32 varBase;
+
+ if (getVarBase(varBase, true, size, type))
+ return varBase;
+
+ operation = _vm->_game->_script->readByte();
+
+ if (size)
+ *size = 0;
+ if (type)
+ *type = operation;
+
+ debugC(5, kDebugExpression, "var parse = %d", operation);
+ switch (operation) {
+ case OP_ARRAY_INT8:
+ case OP_ARRAY_INT32:
+ case OP_ARRAY_INT16:
+ case OP_ARRAY_STR:
+ temp = _vm->_game->_script->readInt16();
+ dimCount = _vm->_game->_script->readByte();
+ arrDesc = _vm->_game->_script->getData() + _vm->_game->_script->pos();
+ _vm->_game->_script->skip(dimCount);
+ offset = 0;
+ for (dim = 0; dim < dimCount; dim++) {
+ temp2 = parseValExpr(OP_END_MARKER);
+ offset = arrDesc[dim] * offset + temp2;
+ }
+ if (operation == OP_ARRAY_INT8)
+ return varBase + temp + offset;
+ if (operation == OP_ARRAY_INT32)
+ return varBase + (temp + offset) * 4;
+ if (operation == OP_ARRAY_INT16)
+ return varBase + (temp + offset) * 2;
+ temp *= 4;
+ offset *= 4;
+ if (_vm->_game->_script->peekByte() == 13) {
+ _vm->_game->_script->skip(1);
+ temp += parseValExpr(OP_END_MARKER);
+ }
+ return varBase + offset * _vm->_global->_inter_animDataSize + temp;
+
+ case OP_LOAD_VAR_INT16:
+ return varBase + _vm->_game->_script->readInt16() * 2;
+
+ case OP_LOAD_VAR_INT8:
+ return varBase + _vm->_game->_script->readInt16();
+
+ case OP_LOAD_VAR_INT32:
+ case OP_LOAD_VAR_INT32_AS_INT16:
+ case OP_LOAD_VAR_STR:
+ temp = _vm->_game->_script->readInt16() * 4;
+ debugC(5, kDebugExpression, "oper = %d", _vm->_game->_script->peekInt16());
+ if ((operation == OP_LOAD_VAR_STR) && (_vm->_game->_script->peekByte() == 13)) {
+ _vm->_game->_script->skip(1);
+ val = parseValExpr(OP_END_MARKER);
+ temp += val;
+ debugC(5, kDebugExpression, "parse subscript = %d", val);
+ }
+ return varBase + temp;
+
+ default:
+ return 0;
+ }
+}
+
+int16 Expression::parseValExpr(byte stopToken) {
+ parseExpr(stopToken, 0);
+
+ return _resultInt;
+}
+
+// Load a value according to the operation
+void Expression::loadValue(byte operation, uint32 varBase, const StackFrame &stackFrame) {
+ int16 dimCount;
+ int16 temp;
+ int16 temp2;
+ int16 offset;
+ int16 dim;
+ byte *arrDescPtr;
+ int32 prevPrevVal;
+ int32 prevVal;
+ int32 curVal;
+
+ switch (operation) {
+ case OP_ARRAY_INT8:
+ case OP_ARRAY_INT32:
+ case OP_ARRAY_INT16:
+ case OP_ARRAY_STR:
+ *stackFrame.opers = (operation == OP_ARRAY_STR) ? OP_LOAD_IMM_STR : OP_LOAD_IMM_INT16;
+ temp = _vm->_game->_script->readInt16();
+ dimCount = _vm->_game->_script->readByte();
+ arrDescPtr = _vm->_game->_script->getData() + _vm->_game->_script->pos();
+ _vm->_game->_script->skip(dimCount);
+ offset = 0;
+ for (dim = 0; dim < dimCount; dim++) {
+ temp2 = parseValExpr(OP_END_MARKER);
+ offset = offset * arrDescPtr[dim] + temp2;
+ }
+ if (operation == OP_ARRAY_INT8)
+ *stackFrame.values = (int8) READ_VARO_UINT8(varBase + temp + offset);
+ else if (operation == OP_ARRAY_INT32)
+ *stackFrame.values = READ_VARO_UINT32(varBase + temp * 4 + offset * 4);
+ else if (operation == OP_ARRAY_INT16)
+ *stackFrame.values = (int16) READ_VARO_UINT16(varBase + temp * 2 + offset * 2);
+ else if (operation == OP_ARRAY_STR) {
+ *stackFrame.values = encodePtr(_vm->_inter->_variables->getAddressOff8(
+ varBase + temp * 4 + offset * _vm->_global->_inter_animDataSize * 4),
+ kInterVar);
+ if (_vm->_game->_script->peekByte() == 13) {
+ _vm->_game->_script->skip(1);
+ temp2 = parseValExpr(OP_END_MARKER);
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ *stackFrame.values = READ_VARO_UINT8(varBase + temp * 4 +
+ offset * 4 * _vm->_global->_inter_animDataSize + temp2);
+ }
+ }
+ break;
+
+ case OP_LOAD_VAR_INT16:
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ *stackFrame.values = (int16) READ_VARO_UINT16(varBase + _vm->_game->_script->readInt16() * 2);
+ break;
+
+ case OP_LOAD_VAR_INT8:
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ *stackFrame.values = (int8) READ_VARO_UINT8(varBase + _vm->_game->_script->readInt16());
+ break;
+
+ case OP_LOAD_IMM_INT32:
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ *stackFrame.values = _vm->_game->_script->readInt32();
+ break;
+
+ case OP_LOAD_IMM_INT16:
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ *stackFrame.values = _vm->_game->_script->readInt16();
+ break;
+
+ case OP_LOAD_IMM_INT8:
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ *stackFrame.values = _vm->_game->_script->readInt8();
+ break;
+
+ case OP_LOAD_IMM_STR:
+ *stackFrame.opers = OP_LOAD_IMM_STR;
+ *stackFrame.values = encodePtr((byte *) _vm->_game->_script->readString(), kExecPtr);
+ break;
+
+ case OP_LOAD_VAR_INT32:
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ *stackFrame.values = READ_VARO_UINT32(varBase + _vm->_game->_script->readInt16() * 4);
+ break;
+
+ case OP_LOAD_VAR_INT32_AS_INT16:
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ *stackFrame.values = (int16) READ_VARO_UINT16(varBase + _vm->_game->_script->readInt16() * 4);
+ break;
+
+ case OP_LOAD_VAR_STR:
+ *stackFrame.opers = OP_LOAD_IMM_STR;
+ temp = _vm->_game->_script->readInt16() * 4;
+ *stackFrame.values = encodePtr(_vm->_inter->_variables->getAddressOff8(varBase + temp), kInterVar);
+ if (_vm->_game->_script->peekByte() == 13) {
+ _vm->_game->_script->skip(1);
+ temp += parseValExpr(OP_END_MARKER);
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ *stackFrame.values = READ_VARO_UINT8(varBase + temp);
+ }
+ break;
+
+ case OP_FUNC:
+ operation = _vm->_game->_script->readByte();
+ parseExpr(OP_END_EXPR, 0);
+
+ switch (operation) {
+ case FUNC_SQRT1:
+ case FUNC_SQRT2:
+ case FUNC_SQRT3:
+ curVal = 1;
+ prevVal = 1;
+
+ do {
+ prevPrevVal = prevVal;
+ prevVal = curVal;
+ curVal = (curVal + _resultInt / curVal) / 2;
+ } while ((curVal != prevVal) && (curVal != prevPrevVal));
+ _resultInt = curVal;
+ break;
+
+ case FUNC_SQR:
+ _resultInt =
+ _resultInt * _resultInt;
+ break;
+
+ case FUNC_ABS:
+ if (_resultInt < 0)
+ _resultInt = -_resultInt;
+ break;
+
+ case FUNC_RAND:
+ _resultInt =
+ _vm->_util->getRandom(_resultInt);
+ break;
+ }
+
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ *stackFrame.values = _resultInt;
+ break;
+ }
+}
+
+void Expression::simpleArithmetic1(StackFrame &stackFrame) {
+ switch (stackFrame.opers[-1]) {
+ case OP_ADD:
+ if (stackFrame.opers[-2] == OP_LOAD_IMM_STR) {
+ if ((char *) decodePtr(stackFrame.values[-2]) != _resultStr) {
+ strcpy(_resultStr, (char *) decodePtr(stackFrame.values[-2]));
+ stackFrame.values[-2] = encodePtr((byte *) _resultStr, kResStr);
+ }
+ strcat(_resultStr, (char *) decodePtr(stackFrame.values[0]));
+ stackFrame.pop(2);
+ }
+ break;
+
+ case OP_MUL:
+ stackFrame.values[-2] *= stackFrame.values[0];
+ stackFrame.pop(2);
+ break;
+
+ case OP_DIV:
+ stackFrame.values[-2] /= stackFrame.values[0];
+ stackFrame.pop(2);
+ break;
+
+ case OP_MOD:
+ stackFrame.values[-2] %= stackFrame.values[0];
+ stackFrame.pop(2);
+ break;
+
+ case OP_BITAND:
+ stackFrame.values[-2] &= stackFrame.values[0];
+ stackFrame.pop(2);
+ break;
+ }
+}
+
+void Expression::simpleArithmetic2(StackFrame &stackFrame) {
+ if (stackFrame.pos > 1) {
+ if (stackFrame.opers[-2] == OP_NEG) {
+ stackFrame.opers[-2] = OP_LOAD_IMM_INT16;
+ stackFrame.values[-2] = -stackFrame.values[-1];
+ stackFrame.pop();
+ } else if (stackFrame.opers[-2] == OP_NOT) {
+ stackFrame.opers[-2] = (stackFrame.opers[-1] == GOB_FALSE) ? GOB_TRUE : GOB_FALSE;
+ stackFrame.pop();
+ }
+ }
+
+ if (stackFrame.pos > 2) {
+ switch (stackFrame.opers[-2]) {
+ case OP_MUL:
+ stackFrame.values[-3] *= stackFrame.values[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_DIV:
+ stackFrame.values[-3] /= stackFrame.values[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_MOD:
+ stackFrame.values[-3] %= stackFrame.values[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_BITAND:
+ stackFrame.values[-3] &= stackFrame.values[-1];
+ stackFrame.pop(2);
+ break;
+ }
+ }
+
+}
+
+// Complex arithmetics with brackets
+bool Expression::complexArithmetic(Stack &stack, StackFrame &stackFrame, int16 brackStart) {
+ switch (stackFrame.opers[-2]) {
+ case OP_ADD:
+ if (stack.opers[brackStart] == OP_LOAD_IMM_INT16) {
+ stack.values[brackStart] += stackFrame.values[-1];
+ } else if (stack.opers[brackStart] == OP_LOAD_IMM_STR) {
+ if ((char *) decodePtr(stack.values[brackStart]) != _resultStr) {
+ strcpy(_resultStr, (char *) decodePtr(stack.values[brackStart]));
+ stack.values[brackStart] =
+ encodePtr((byte *) _resultStr, kResStr);
+ }
+ strcat(_resultStr, (char *) decodePtr(stackFrame.values[-1]));
+ }
+ stackFrame.pop(2);
+ break;
+
+ case OP_SUB:
+ stack.values[brackStart] -= stackFrame.values[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_BITOR:
+ stack.values[brackStart] |= stackFrame.values[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_MUL:
+ stackFrame.values[-3] *= stackFrame.values[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_DIV:
+ stackFrame.values[-3] /= stackFrame.values[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_MOD:
+ stackFrame.values[-3] %= stackFrame.values[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_BITAND:
+ stackFrame.values[-3] &= stackFrame.values[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_OR:
+ // (x OR false) == x
+ // (x OR true) == true
+ if (stackFrame.opers[-3] == GOB_FALSE)
+ stackFrame.opers[-3] = stackFrame.opers[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_AND:
+ // (x AND false) == false
+ // (x AND true) == x
+ if (stackFrame.opers[-3] == GOB_TRUE)
+ stackFrame.opers[-3] = stackFrame.opers[-1];
+ stackFrame.pop(2);
+ break;
+
+ case OP_LESS:
+ stackFrame.opers[-3] = (cmpHelper(stackFrame) < 0) ? GOB_TRUE : GOB_FALSE;
+ stackFrame.pop(2);
+ break;
+
+ case OP_LEQ:
+ stackFrame.opers[-3] = (cmpHelper(stackFrame) <= 0) ? GOB_TRUE : GOB_FALSE;
+ stackFrame.pop(2);
+ break;
+
+ case OP_GREATER:
+ stackFrame.opers[-3] = (cmpHelper(stackFrame) > 0) ? GOB_TRUE : GOB_FALSE;
+ stackFrame.pop(2);
+ break;
+
+ case OP_GEQ:
+ stackFrame.opers[-3] = (cmpHelper(stackFrame) >= 0) ? GOB_TRUE : GOB_FALSE;
+ stackFrame.pop(2);
+ break;
+
+ case OP_EQ:
+ stackFrame.opers[-3] = (cmpHelper(stackFrame) == 0) ? GOB_TRUE : GOB_FALSE;
+ stackFrame.pop(2);
+ break;
+
+ case OP_NEQ:
+ stackFrame.opers[-3] = (cmpHelper(stackFrame) != 0) ? GOB_TRUE : GOB_FALSE;
+ stackFrame.pop(2);
+ break;
+
+ default:
+ return true;
+ }
+
+ return false;
+}
+
+// Assign the result to the appropriate _result variable
+void Expression::getResult(byte operation, int32 value, byte *type) {
+ if (type != 0)
+ *type = operation;
+
+ switch (operation) {
+ case OP_NOT:
+ if (type != 0)
+ *type ^= 1;
+ break;
+
+ case OP_LOAD_IMM_INT16:
+ _resultInt = value;
+ break;
+
+ case OP_LOAD_IMM_STR:
+ if ((char *) decodePtr(value) != _resultStr)
+ strcpy(_resultStr, (char *) decodePtr(value));
+ break;
+
+ case OP_LOAD_VAR_INT32:
+ case OP_LOAD_VAR_INT32_AS_INT16:
+ break;
+
+ default:
+ _resultInt = 0;
+ if (type != 0)
+ *type = OP_LOAD_IMM_INT16;
+ break;
+ }
+}
+
+int16 Expression::parseExpr(byte stopToken, byte *type) {
+ Stack stack;
+ StackFrame stackFrame(stack);
+ byte operation;
+ bool escape;
+ int16 brackStart;
+ uint32 varBase;
+
+ while (true) {
+ getVarBase(varBase);
+
+ stackFrame.push();
+
+ operation = _vm->_game->_script->readByte();
+ if ((operation >= OP_ARRAY_INT8) && (operation <= OP_FUNC)) {
+
+ loadValue(operation, varBase, stackFrame);
+
+ if ((stackFrame.pos > 0) && ((stackFrame.opers[-1] == OP_NEG) || (stackFrame.opers[-1] == OP_NOT))) {
+ stackFrame.pop();
+
+ if (*stackFrame.opers == OP_NEG) {
+ *stackFrame.opers = OP_LOAD_IMM_INT16;
+ stackFrame.values[0] = -stackFrame.values[1];
+ } else
+ *stackFrame.opers = (stackFrame.opers[1] == GOB_FALSE) ? GOB_TRUE : GOB_FALSE;
+ }
+
+ if (stackFrame.pos <= 0)
+ continue;
+
+ simpleArithmetic1(stackFrame);
+
+ continue;
+ } // (op >= OP_ARRAY_INT8) && (op <= OP_FUNC)
+
+ if ((operation == stopToken) || (operation == OP_OR) ||
+ (operation == OP_AND) || (operation == OP_END_EXPR)) {
+ while (stackFrame.pos >= 2) {
+ escape = false;
+ if ((stackFrame.opers[-2] == OP_BEGIN_EXPR) &&
+ ((operation == OP_END_EXPR) || (operation == stopToken))) {
+ stackFrame.opers[-2] = stackFrame.opers[-1];
+ if ((stackFrame.opers[-2] == OP_LOAD_IMM_INT16) || (stackFrame.opers[-2] == OP_LOAD_IMM_STR))
+ stackFrame.values[-2] = stackFrame.values[-1];
+
+ stackFrame.pop();
+
+ simpleArithmetic2(stackFrame);
+
+ if (operation != stopToken)
+ break;
+ } // if ((stackFrame.opers[-2] == OP_BEGIN_EXPR) && ...)
+
+ for (brackStart = (stackFrame.pos - 2); (brackStart > 0) &&
+ (stack.opers[brackStart] < OP_OR) && (stack.opers[brackStart] != OP_BEGIN_EXPR);
+ brackStart--)
+ ;
+
+ if ((stack.opers[brackStart] >= OP_OR) || (stack.opers[brackStart] == OP_BEGIN_EXPR))
+ brackStart++;
+
+ if (complexArithmetic(stack, stackFrame, brackStart))
+ break;
+
+ } // while (stackFrame.pos >= 2)
+
+ if ((operation == OP_OR) || (operation == OP_AND)) {
+ if (stackFrame.opers[-1] == OP_LOAD_IMM_INT16) {
+ if (stackFrame.values[-1] != 0)
+ stackFrame.opers[-1] = GOB_TRUE;
+ else
+ stackFrame.opers[-1] = GOB_FALSE;
+ }
+
+ if (((operation == OP_OR) && (stackFrame.opers[-1] == GOB_TRUE)) ||
+ ((operation == OP_AND) && (stackFrame.opers[-1] == GOB_FALSE))) {
+ if ((stackFrame.pos > 1) && (stackFrame.opers[-2] == OP_BEGIN_EXPR)) {
+ skipExpr(OP_END_EXPR);
+ stackFrame.opers[-2] = stackFrame.opers[-1];
+ stackFrame.pop(2);
+ } else {
+ skipExpr(stopToken);
+ }
+ operation = _vm->_game->_script->peekByte(-1);
+ if ((stackFrame.pos > 0) && (stackFrame.opers[-1] == OP_NOT)) {
+ if (stackFrame.opers[0] == GOB_FALSE)
+ stackFrame.opers[-1] = GOB_TRUE;
+ else
+ stackFrame.opers[-1] = GOB_FALSE;
+
+ stackFrame.pop();
+ }
+ } else
+ stackFrame.opers[0] = operation;
+ } else
+ stackFrame.pop();
+
+ if (operation != stopToken)
+ continue;
+
+ getResult(stack.opers[0], stack.values[0], type);
+
+ return 0;
+ } // (operation == stopToken) || (operation == OP_OR) || (operation == OP_AND) || (operation == OP_END_EXPR)
+
+ if ((operation < OP_NEG) || (operation > OP_NOT)) {
+ if ((operation < OP_LESS) || (operation > OP_NEQ))
+ continue;
+
+ if (stackFrame.pos > 2) {
+ if (stackFrame.opers[-2] == OP_ADD) {
+ if (stackFrame.opers[-3] == OP_LOAD_IMM_INT16) {
+ stackFrame.values[-3] += stackFrame.values[-1];
+ } else if (stackFrame.opers[-3] == OP_LOAD_IMM_STR) {
+ if ((char *) decodePtr(stackFrame.values[-3]) != _resultStr) {
+ strcpy(_resultStr, (char *) decodePtr(stackFrame.values[-3]));
+ stackFrame.values[-3] = encodePtr((byte *) _resultStr, kResStr);
+ }
+ strcat(_resultStr, (char *) decodePtr(stackFrame.values[-1]));
+ }
+ stackFrame.pop(2);
+
+ } else if (stackFrame.opers[-2] == OP_SUB) {
+ stackFrame.values[-3] -= stackFrame.values[-1];
+ stackFrame.pop(2);
+ } else if (stackFrame.opers[-2] == OP_BITOR) {
+ stackFrame.values[-3] |= stackFrame.values[-1];
+ stackFrame.pop(2);
+ }
+ }
+ }
+ *stackFrame.opers = operation;
+ }
+}
+
+int32 Expression::getResultInt() {
+ return _resultInt;
+}
+
+char *Expression::getResultStr() {
+ return _resultStr;
+}
+
+} // End of namespace Gob
diff --git a/engines/gob/expression.h b/engines/gob/expression.h
new file mode 100644
index 0000000000..894704e2a9
--- /dev/null
+++ b/engines/gob/expression.h
@@ -0,0 +1,178 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#ifndef GOB_EXPRESSION_H
+#define GOB_EXPRESSION_H
+
+#include "common/scummsys.h"
+
+namespace Gob {
+
+class GobEngine;
+
+enum {
+ OP_NEG = 1,
+ OP_ADD = 2,
+ OP_SUB = 3,
+ OP_BITOR = 4,
+ OP_MUL = 5,
+ OP_DIV = 6,
+ OP_MOD = 7,
+ OP_BITAND = 8,
+ OP_BEGIN_EXPR = 9,
+ OP_END_EXPR = 10,
+ OP_NOT = 11,
+
+ OP_END_MARKER = 12, // Marks end of an array or string
+
+
+ OP_ARRAY_INT8 = 16,
+ OP_LOAD_VAR_INT16 = 17,
+ OP_LOAD_VAR_INT8 = 18,
+ OP_LOAD_IMM_INT32 = 19,
+ OP_LOAD_IMM_INT16 = 20,
+ OP_LOAD_IMM_INT8 = 21,
+ OP_LOAD_IMM_STR = 22,
+ OP_LOAD_VAR_INT32 = 23,
+ OP_LOAD_VAR_INT32_AS_INT16 = 24,
+ OP_LOAD_VAR_STR = 25,
+ OP_ARRAY_INT32 = 26,
+ OP_ARRAY_INT16 = 27,
+ OP_ARRAY_STR = 28,
+
+ OP_FUNC = 29,
+
+ OP_OR = 30, // Logical OR
+ OP_AND = 31, // Logical AND
+ OP_LESS = 32,
+ OP_LEQ = 33,
+ OP_GREATER = 34,
+ OP_GEQ = 35,
+ OP_EQ = 36,
+ OP_NEQ = 37
+};
+
+enum {
+ FUNC_SQRT1 = 0,
+ FUNC_SQRT2 = 1,
+ FUNC_SQRT3 = 6,
+
+ FUNC_SQR = 5,
+ FUNC_ABS = 7,
+ FUNC_RAND = 10
+};
+
+enum {
+ TYPE_IMM_INT8 = OP_LOAD_IMM_INT8, // 21
+ TYPE_IMM_INT32 = OP_LOAD_IMM_INT32, // 19
+ TYPE_IMM_INT16 = OP_LOAD_IMM_INT16, // 20
+ TYPE_IMM_STR = OP_LOAD_IMM_STR, // 22
+ TYPE_VAR_INT8 = OP_LOAD_VAR_INT8, // 18
+ TYPE_VAR_INT16 = OP_LOAD_VAR_INT16, // 17
+ TYPE_VAR_INT32 = OP_LOAD_VAR_INT32, // 23
+ TYPE_VAR_STR = OP_LOAD_VAR_STR, // 25
+ TYPE_ARRAY_INT8 = OP_ARRAY_INT8, // 16
+ TYPE_ARRAY_INT16 = OP_ARRAY_INT16, // 27
+ TYPE_ARRAY_INT32 = OP_ARRAY_INT32, // 26
+ TYPE_ARRAY_STR = OP_ARRAY_STR, // 28
+ TYPE_VAR_INT32_AS_INT16 = OP_LOAD_VAR_INT32_AS_INT16 // 24
+};
+
+enum {
+ // FIXME: The following two 'truth values' are stored inside the list
+ // of "operators". So they somehow coincide with OP_LOAD_VAR_INT32
+ // and OP_LOAD_VAR_INT32_AS_INT16. I haven't yet quite understood
+ // how, resp. what that means. You have been warned.
+ GOB_TRUE = 24,
+ GOB_FALSE = 23
+};
+
+class Expression {
+public:
+ Expression(GobEngine *vm);
+ virtual ~Expression() {}
+
+ void skipExpr(char stopToken);
+ void printExpr(char stopToken);
+ void printVarIndex(void);
+
+ int16 parseVarIndex(uint16 *size = 0, uint16 *type = 0);
+ int16 parseValExpr(byte stopToken = 99);
+ int16 parseExpr(byte stopToken, byte *type);
+
+ int32 getResultInt();
+ char *getResultStr();
+
+private:
+ class Stack {
+ public:
+ byte *opers;
+ int32 *values;
+
+ Stack(size_t size = 20);
+ ~Stack();
+ };
+ class StackFrame {
+ public:
+ byte *opers;
+ int32 *values;
+ int16 pos;
+
+ StackFrame(const Stack &stack);
+
+ void push(int count = 1);
+ void pop(int count = 1);
+ };
+
+ enum PointerType {
+ kExecPtr = 0,
+ kInterVar = 1,
+ kResStr = 2
+ };
+
+ GobEngine *_vm;
+
+ int32 _resultInt;
+ char _resultStr[200];
+
+ int32 encodePtr(byte *ptr, int type);
+ byte *decodePtr(int32 n);
+
+ void printExpr_internal(char stopToken);
+
+ bool getVarBase(uint32 &varBase, bool mindStop = false,
+ uint16 *size = 0, uint16 *type = 0);
+ int cmpHelper(const StackFrame &stackFrame);
+ void loadValue(byte operation, uint32 varBase, const StackFrame &stackFrame);
+
+ void simpleArithmetic1(StackFrame &stackFrame);
+ void simpleArithmetic2(StackFrame &stackFrame);
+ bool complexArithmetic(Stack &stack, StackFrame &stackFrame, int16 brackStart);
+ void getResult(byte operation, int32 value, byte *type);
+};
+
+} // End of namespace Gob
+
+#endif // GOB_EXPRESSION_H
diff --git a/engines/gob/game.cpp b/engines/gob/game.cpp
index 09addc3900..5771ee9f76 100644
--- a/engines/gob/game.cpp
+++ b/engines/gob/game.cpp
@@ -31,8 +31,10 @@
#include "gob/global.h"
#include "gob/util.h"
#include "gob/dataio.h"
+#include "gob/variables.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/inter.h"
-#include "gob/parse.h"
#include "gob/draw.h"
#include "gob/mult.h"
#include "gob/videoplayer.h"
@@ -40,21 +42,139 @@
namespace Gob {
+Environments::Environments(GobEngine *vm) : _vm(vm) {
+ _environments = new Environment[kEnvironmentCount];
+
+ for (uint i = 0; i < kEnvironmentCount; i++) {
+ Environment &e = _environments[i];
+
+ e.cursorHotspotX = 0;
+ e.cursorHotspotY = 0;
+ e.variables = 0;
+ e.script = 0;
+ e.resources = 0;
+ e.curTotFile[0] = '\0';
+ }
+}
+
+Environments::~Environments() {
+ clear();
+
+ delete[] _environments;
+}
+
+void Environments::clear() {
+ // Deleting unique variables, script and resources
+
+ for (uint i = 0; i < kEnvironmentCount; i++) {
+ if (_environments[i].variables == _vm->_inter->_variables)
+ continue;
+
+ if (!has(_environments[i].variables, i + 1))
+ delete _environments[i].variables;
+ }
+
+ for (uint i = 0; i < kEnvironmentCount; i++) {
+ if (_environments[i].script == _vm->_game->_script)
+ continue;
+
+ if (!has(_environments[i].script, i + 1))
+ delete _environments[i].script;
+ }
+
+ for (uint i = 0; i < kEnvironmentCount; i++) {
+ if (_environments[i].resources == _vm->_game->_resources)
+ continue;
+
+ if (!has(_environments[i].resources, i + 1))
+ delete _environments[i].resources;
+ }
+}
+
+void Environments::set(uint8 env) {
+ if (env >= kEnvironmentCount)
+ return;
+
+ Environment &e = _environments[env];
+
+ // If it already has a unique script or resource assigned, delete them
+ if ((e.script != _vm->_game->_script) && !has(e.script, 0, env))
+ delete e.script;
+ if ((e.resources != _vm->_game->_resources) && !has(e.resources, 0, env))
+ delete e.resources;
+
+ e.cursorHotspotX = _vm->_draw->_cursorHotspotXVar;
+ e.cursorHotspotY = _vm->_draw->_cursorHotspotYVar;
+ e.script = _vm->_game->_script;
+ e.resources = _vm->_game->_resources;
+ e.variables = _vm->_inter->_variables;
+ strncpy(e.curTotFile, _vm->_game->_curTotFile, 14);
+}
+
+void Environments::get(uint8 env) const {
+ if (env >= kEnvironmentCount)
+ return;
+
+ const Environment &e = _environments[env];
+
+ _vm->_draw->_cursorHotspotXVar = e.cursorHotspotX;
+ _vm->_draw->_cursorHotspotYVar = e.cursorHotspotY;
+ _vm->_game->_script = e.script;
+ _vm->_game->_resources = e.resources;
+ _vm->_inter->_variables = e.variables;
+ strncpy(_vm->_game->_curTotFile, e.curTotFile, 14);
+}
+
+const char *Environments::getTotFile(uint8 env) const {
+ if (env >= kEnvironmentCount)
+ return "";
+
+ return _environments[env].curTotFile;
+}
+
+bool Environments::has(Variables *variables, uint8 startEnv, int16 except) const {
+ for (uint i = startEnv; i < kEnvironmentCount; i++) {
+ if ((except >= 0) && (((uint16) except) == i))
+ continue;
+
+ if (_environments[i].variables == variables)
+ return true;
+ }
+
+ return false;
+}
+
+bool Environments::has(Script *script, uint8 startEnv, int16 except) const {
+ for (uint i = startEnv; i < kEnvironmentCount; i++) {
+ if ((except >= 0) && (((uint16) except) == i))
+ continue;
+
+ if (_environments[i].script == script)
+ return true;
+ }
+
+ return false;
+}
+
+bool Environments::has(Resources *resources, uint8 startEnv, int16 except) const {
+ for (uint i = startEnv; i < kEnvironmentCount; i++) {
+ if ((except >= 0) && (((uint16) except) == i))
+ continue;
+
+ if (_environments[i].resources == resources)
+ return true;
+ }
+
+ return false;
+}
+
+
Game::Game(GobEngine *vm) : _vm(vm) {
- _extTable = 0;
- _totFileData = 0;
- _totResourceTable = 0;
- _imFileData = 0;
- _extHandle = 0;
- _lomHandle = -1;
_collisionAreas = 0;
_shouldPushColls = 0;
_captureCount = 0;
- _foundTotLoc = false;
- _totTextData = 0;
-
_collStackSize = 0;
for (int i = 0; i < 5; i++) {
@@ -63,7 +183,6 @@ Game::Game(GobEngine *vm) : _vm(vm) {
}
_curTotFile[0] = 0;
- _curExtFile[0] = 0;
_totToLoad[0] = 0;
_startTimeKey = 0;
@@ -85,138 +204,20 @@ Game::Game(GobEngine *vm) : _vm(vm) {
_noCd = false;
_tempStr[0] = 0;
- _curImaFile[0] = 0;
_collStr[0] = 0;
- _backupedCount = 0;
- _curBackupPos = 0;
+ _numEnvironments = 0;
+ _curEnvironment = 0;
- for (int i = 0; i < 5; i++) {
- _cursorHotspotXArray[i] = 0;
- _cursorHotspotYArray[i] = 0;
- _totTextDataArray[i] = 0;
- _totFileDataArray[i] = 0;
- _totResourceTableArray[i] = 0;
- _extTableArray[i] = 0;
- _extHandleArray[i] = 0;
- _imFileDataArray[i] = 0;
- _variablesArray[i] = 0;
- _curTotFileArray[i][0] = 0;
- }
+ _environments = new Environments(_vm);
+ _script = new Script(_vm);
+ _resources = new Resources(_vm);
}
Game::~Game() {
- delete[] _vm->_game->_totFileData;
- if (_vm->_game->_totTextData) {
- if (_vm->_game->_totTextData->items)
- delete[] _vm->_game->_totTextData->items;
- delete _vm->_game->_totTextData;
- }
- if (_vm->_game->_totResourceTable) {
- delete[] _vm->_game->_totResourceTable->items;
- delete _vm->_game->_totResourceTable;
- }
-}
-
-byte *Game::loadExtData(int16 itemId, int16 *pResWidth,
- int16 *pResHeight, uint32 *dataSize) {
- int16 commonHandle;
- int16 itemsCount;
- int32 offset;
- uint32 size;
- uint32 realSize;
- ExtItem *item;
- bool isPacked;
- int16 handle;
- int32 tableSize;
- char path[20];
- byte *dataBuf;
- byte *packedBuf;
- byte *dataPtr;
-
- itemId -= 30000;
- if (_extTable == 0)
- return 0;
-
- commonHandle = -1;
- itemsCount = _extTable->itemsCount;
- item = &_extTable->items[itemId];
- tableSize = szGame_ExtTable + szGame_ExtItem * itemsCount;
-
- offset = item->offset;
- size = item->size;
- isPacked = (item->width & 0x8000) != 0;
-
- if ((pResWidth != 0) && (pResHeight != 0)) {
- *pResWidth = item->width & 0x7FFF;
-
- if (*pResWidth & 0x4000)
- size += 1 << 16;
- if (*pResWidth & 0x2000)
- size += 2 << 16;
- if (*pResWidth & 0x1000)
- size += 4 << 16;
-
- *pResWidth &= 0xFFF;
-
- *pResHeight = item->height;
- debugC(7, kDebugFileIO, "loadExtData(%d, %d, %d)",
- itemId, *pResWidth, *pResHeight);
- }
-
- debugC(7, kDebugFileIO, "loadExtData(%d, 0, 0)", itemId);
-
- if (item->height == 0)
- size += (item->width & 0x7FFF) << 16;
-
- debugC(7, kDebugFileIO, "size: %d off: %d", size, offset);
- if (offset < 0) {
- offset = -(offset + 1);
- tableSize = 0;
- _vm->_dataIO->closeData(_extHandle);
- strcpy(path, "commun.ex1");
- path[strlen(path) - 1] = *(_totFileData + 0x3C) + '0';
- commonHandle = _vm->_dataIO->openData(path);
- handle = commonHandle;
- } else
- handle = _extHandle;
-
- DataStream *stream = _vm->_dataIO->openAsStream(handle);
-
- debugC(7, kDebugFileIO, "off: %d size: %d", offset, tableSize);
- stream->seek(offset + tableSize);
- realSize = size;
- if (isPacked)
- dataBuf = new byte[size + 2];
- else
- dataBuf = new byte[size];
-
- dataPtr = dataBuf;
- while (size > 32000) {
- // BUG: huge->far conversion. Need normalization?
- stream->read(dataPtr, 32000);
- size -= 32000;
- dataPtr += 32000;
- }
- stream->read(dataPtr, size);
-
- delete stream;
- if (commonHandle != -1) {
- _vm->_dataIO->closeData(commonHandle);
- _extHandle = _vm->_dataIO->openData(_curExtFile);
- }
-
- if (isPacked) {
- packedBuf = dataBuf;
- realSize = READ_LE_UINT32(packedBuf);
- dataBuf = new byte[realSize];
- _vm->_dataIO->unpackData(packedBuf, dataBuf);
- delete[] packedBuf;
- }
-
- if (dataSize)
- *dataSize = realSize;
- return dataBuf;
+ delete _environments;
+ delete _script;
+ delete _resources;
}
void Game::freeCollision(int16 id) {
@@ -281,39 +282,9 @@ void Game::capturePop(char doDraw) {
_vm->_draw->freeSprite(30 + _captureCount);
}
-byte *Game::loadTotResource(int16 id,
- int16 *dataSize, int16 *width, int16 *height) {
-
- TotResItem *itemPtr;
- int32 offset;
-
- if (id >= _vm->_game->_totResourceTable->itemsCount) {
- warning("Trying to load non-existent TOT resource (%s, %d/%d)",
- _curTotFile, id, _totResourceTable->itemsCount - 1);
- return 0;
- }
-
- itemPtr = &_totResourceTable->items[id];
- offset = itemPtr->offset;
-
- if (dataSize)
- *dataSize = itemPtr->size;
- if (width)
- *width = itemPtr->width;
- if (height)
- *height = itemPtr->height;
-
- if (offset < 0) {
- offset = (-offset - 1) * 4;
- return _imFileData + (int32) READ_LE_UINT32(_imFileData + offset);
- } else
- return _totResourceTable->dataPtr + szGame_TotResTable +
- szGame_TotResItem * _totResourceTable->itemsCount + offset;
-}
-
void Game::freeSoundSlot(int16 slot) {
if (slot == -1)
- slot = _vm->_parse->parseValExpr();
+ slot = _vm->_game->_script->readValExpr();
_vm->_sound->sampleFree(_vm->_sound->sampleGetBySlot(slot));
}
@@ -416,104 +387,6 @@ int16 Game::adjustKey(int16 key) {
return key - 0x20;
}
-int32 Game::loadTotFile(const char *path) {
- int16 handle;
- int32 size;
-
- _lomHandle = -1;
-
- size = -1;
- handle = _vm->_dataIO->openData(path);
- if (handle >= 0) {
-
- if (!scumm_stricmp(path + strlen(path) - 3, "LOM")) {
- warning("Urban Stub: loadTotFile %s", path);
-
- _lomHandle = handle;
-
- DataStream *stream = _vm->_dataIO->openAsStream(handle);
-
- stream->seek(48);
- size = stream->readUint32LE();
- stream->seek(0);
-
- _totFileData = new byte[size];
- stream->read(_totFileData, size);
-
- delete stream;
- } else {
- _vm->_dataIO->closeData(handle);
- size = _vm->_dataIO->getDataSize(path);
- _totFileData = _vm->_dataIO->getData(path);
- }
-
- } else {
- Common::MemoryReadStream *videoExtraData = _vm->_vidPlayer->getExtraData(path);
-
- if (videoExtraData) {
- warning("Found \"%s\" in video file", path);
-
- size = videoExtraData->size();
- _totFileData = new byte[size];
- videoExtraData->read(_totFileData, size);
- delete videoExtraData;
- } else
- _totFileData = 0;
- }
-
- return size;
-}
-
-void Game::loadExtTable(void) {
- int16 count;
-
- // Function is correct. [sev]
-
- _extHandle = _vm->_dataIO->openData(_curExtFile);
- if (_extHandle < 0)
- return;
-
- DataStream *stream = _vm->_dataIO->openAsStream(_extHandle);
- count = stream->readUint16LE();
-
- stream->seek(0);
- _extTable = new ExtTable;
- _extTable->items = 0;
- if (count)
- _extTable->items = new ExtItem[count];
-
- _extTable->itemsCount = stream->readUint16LE();
- _extTable->unknown = stream->readByte();
-
- for (int i = 0; i < count; i++) {
- _extTable->items[i].offset = stream->readUint32LE();
- _extTable->items[i].size = stream->readUint16LE();
- _extTable->items[i].width = stream->readUint16LE();
- _extTable->items[i].height = stream->readUint16LE();
- }
-
- delete stream;
-}
-
-void Game::loadImFile(void) {
- char path[20];
- int16 handle;
-
- if ((_totFileData[0x3D] != 0) && (_totFileData[0x3B] == 0))
- return;
-
- strcpy(path, "commun.im1");
- if (_totFileData[0x3B] != 0)
- path[strlen(path) - 1] = '0' + _totFileData[0x3B];
-
- handle = _vm->_dataIO->openData(path);
- if (handle < 0)
- return;
-
- _vm->_dataIO->closeData(handle);
- _imFileData = _vm->_dataIO->getData(path);
-}
-
void Game::start(void) {
_collisionAreas = new Collision[250];
memset(_collisionAreas, 0, 250 * sizeof(Collision));
@@ -533,27 +406,17 @@ void Game::start(void) {
void Game::totSub(int8 flags, const char *newTotFile) {
int8 curBackupPos;
- if (_backupedCount >= 5)
+ if (_numEnvironments >= Environments::kEnvironmentCount)
return;
- _cursorHotspotXArray[_backupedCount] = _vm->_draw->_cursorHotspotXVar;
- _cursorHotspotYArray[_backupedCount] = _vm->_draw->_cursorHotspotYVar;
- _totTextDataArray[_backupedCount] = _totTextData;
- _totFileDataArray[_backupedCount] = _totFileData;
- _totResourceTableArray[_backupedCount] = _totResourceTable;
- _extTableArray[_backupedCount] = _extTable;
- _extHandleArray[_backupedCount] = _extHandle;
- _imFileDataArray[_backupedCount] = _imFileData;
- _variablesArray[_backupedCount] = _vm->_inter->_variables;
- strcpy(_curTotFileArray[_backupedCount], _curTotFile);
-
- curBackupPos = _curBackupPos;
- _backupedCount++;
- _curBackupPos = _backupedCount;
-
- _totTextData = 0;
- _totFileData = 0;
- _totResourceTable = 0;
+ _environments->set(_numEnvironments);
+
+ curBackupPos = _curEnvironment;
+ _numEnvironments++;
+ _curEnvironment = _numEnvironments;
+
+ _script = new Script(_vm);
+ _resources = new Resources(_vm);
if (flags & 1)
_vm->_inter->_variables = 0;
@@ -563,8 +426,10 @@ void Game::totSub(int8 flags, const char *newTotFile) {
// else
strcat(_curTotFile, ".TOT");
- if (_vm->_inter->_terminate != 0)
+ if (_vm->_inter->_terminate != 0) {
+ clearUnusedEnvironment();
return;
+ }
pushCollisions(0);
@@ -582,197 +447,64 @@ void Game::totSub(int8 flags, const char *newTotFile) {
_vm->_inter->delocateVars();
}
- _backupedCount--;
- _curBackupPos = curBackupPos;
-
- _vm->_draw->_cursorHotspotXVar = _cursorHotspotXArray[_backupedCount];
- _vm->_draw->_cursorHotspotYVar = _cursorHotspotYArray[_backupedCount];
- _totTextData = _totTextDataArray[_backupedCount];
- _totFileData = _totFileDataArray[_backupedCount];
- _totResourceTable = _totResourceTableArray[_backupedCount];
- _extTable = _extTableArray[_backupedCount];
- _extHandle = _extHandleArray[_backupedCount];
- _imFileData = _imFileDataArray[_backupedCount];
- _vm->_inter->_variables = _variablesArray[_backupedCount];
- strcpy(_curTotFile, _curTotFileArray[_backupedCount]);
- strcpy(_curExtFile, _curTotFile);
- _curExtFile[strlen(_curExtFile) - 4] = '\0';
- strcat(_curExtFile, ".EXT");
+ clearUnusedEnvironment();
+
+ _numEnvironments--;
+ _curEnvironment = curBackupPos;
+ _environments->get(_numEnvironments);
}
void Game::switchTotSub(int16 index, int16 skipPlay) {
int16 backupedCount;
int16 curBackupPos;
- if ((_backupedCount - index) < 1)
+ if ((_numEnvironments - index) < 1)
+ return;
+
+ int16 newPos = _curEnvironment - index - ((index >= 0) ? 1 : 0);
+ if (newPos >= Environments::kEnvironmentCount)
return;
- int16 newPos = _curBackupPos - index - ((index >= 0) ? 1 : 0);
// WORKAROUND: Some versions don't make the MOVEMENT menu item unselectable
// in the dreamland screen, resulting in a crash when it's clicked.
if ((_vm->getGameType() == kGameTypeGob2) && (index == -1) && (skipPlay == 7) &&
- !scumm_stricmp(_curTotFileArray[newPos], "gob06.tot"))
+ !scumm_stricmp(_environments->getTotFile(newPos), "gob06.tot"))
return;
- curBackupPos = _curBackupPos;
- backupedCount = _backupedCount;
- if (_curBackupPos == _backupedCount) {
- _cursorHotspotXArray[_backupedCount] = _vm->_draw->_cursorHotspotXVar;
- _cursorHotspotYArray[_backupedCount] = _vm->_draw->_cursorHotspotYVar;
- _totTextDataArray[_backupedCount] = _totTextData;
- _totFileDataArray[_backupedCount] = _totFileData;
- _totResourceTableArray[_backupedCount] = _totResourceTable;
- _extTableArray[_backupedCount] = _extTable;
- _extHandleArray[_backupedCount] = _extHandle;
- _imFileDataArray[_backupedCount] = _imFileData;
- _variablesArray[_backupedCount] = _vm->_inter->_variables;
- strcpy(_curTotFileArray[_backupedCount], _curTotFile);
- _backupedCount++;
- }
- _curBackupPos -= index;
- if (index >= 0)
- _curBackupPos--;
-
- _vm->_draw->_cursorHotspotXVar = _cursorHotspotXArray[_curBackupPos];
- _vm->_draw->_cursorHotspotYVar = _cursorHotspotYArray[_curBackupPos];
- _totTextData = _totTextDataArray[_curBackupPos];
- _totFileData = _totFileDataArray[_curBackupPos];
- _totResourceTable = _totResourceTableArray[_curBackupPos];
- _imFileData = _imFileDataArray[_curBackupPos];
- _extTable = _extTableArray[_curBackupPos];
- _extHandle = _extHandleArray[_curBackupPos];
- _vm->_inter->_variables = _variablesArray[_curBackupPos];
- strcpy(_curTotFile, _curTotFileArray[_curBackupPos]);
- strcpy(_curExtFile, _curTotFile);
- _curExtFile[strlen(_curExtFile) - 4] = '\0';
- strcat(_curExtFile, ".EXT");
-
- if (_vm->_inter->_terminate != 0)
- return;
+ curBackupPos = _curEnvironment;
+ backupedCount = _numEnvironments;
+ if (_curEnvironment == _numEnvironments)
+ _environments->set(_numEnvironments++);
- _vm->_game->pushCollisions(0);
- _vm->_game->playTot(skipPlay);
+ _curEnvironment -= index;
+ if (index >= 0)
+ _curEnvironment--;
- if (_vm->_inter->_terminate != 2)
- _vm->_inter->_terminate = 0;
+ clearUnusedEnvironment();
- _vm->_game->popCollisions();
-
- _curBackupPos = curBackupPos;
- _backupedCount = backupedCount;
- _vm->_draw->_cursorHotspotXVar = _cursorHotspotXArray[_curBackupPos];
- _vm->_draw->_cursorHotspotYVar = _cursorHotspotYArray[_curBackupPos];
- _totTextData = _totTextDataArray[_curBackupPos];
- _totFileData = _totFileDataArray[_curBackupPos];
- _totResourceTable = _totResourceTableArray[_curBackupPos];
- _extTable = _extTableArray[_curBackupPos];
- _extHandle = _extHandleArray[_curBackupPos];
- _imFileData = _imFileDataArray[_curBackupPos];
- _vm->_inter->_variables = _variablesArray[_curBackupPos];
- strcpy(_curTotFile, _curTotFileArray[_curBackupPos]);
- strcpy(_curExtFile, _curTotFile);
- _curExtFile[strlen(_curExtFile) - 4] = '\0';
- strcat(_curExtFile, ".EXT");
-}
+ _environments->get(_curEnvironment);
-int16 Game::openLocTextFile(char *locTextFile, int language) {
- int n;
-
- n = strlen(locTextFile);
- if (n < 4)
- return -1;
-
- locTextFile[n - 4] = 0;
- switch (language) {
- case 0:
- strcat(locTextFile, ".dat");
- break;
- case 1:
- strcat(locTextFile, ".all");
- break;
- case 3:
- strcat(locTextFile, ".esp");
- break;
- case 4:
- strcat(locTextFile, ".ita");
- break;
- case 5:
- strcat(locTextFile, ".usa");
- break;
- case 6:
- strcat(locTextFile, ".ndl");
- break;
- case 7:
- strcat(locTextFile, ".kor");
- break;
- case 8:
- strcat(locTextFile, ".isr");
- break;
- default:
- strcat(locTextFile, ".ang");
- break;
+ if (_vm->_inter->_terminate != 0) {
+ clearUnusedEnvironment();
+ return;
}
- return _vm->_dataIO->openData(locTextFile);
-}
-
-byte *Game::loadLocTexts(int32 *dataSize) {
- char locTextFile[20];
- int16 handle;
- int i;
-
- strcpy(locTextFile, _curTotFile);
-
- handle = openLocTextFile(locTextFile, _vm->_global->_languageWanted);
- if (handle >= 0) {
-
- _foundTotLoc = true;
- _vm->_global->_language = _vm->_global->_languageWanted;
-
- } else if (!_foundTotLoc) {
- bool found = false;
-
- if (_vm->_global->_languageWanted == 2) {
- handle = openLocTextFile(locTextFile, 5);
- if (handle >= 0) {
- _vm->_global->_language = 5;
- found = true;
- }
- } else if (_vm->_global->_languageWanted == 5) {
- handle = openLocTextFile(locTextFile, 2);
- if (handle >= 0) {
- _vm->_global->_language = 2;
- found = true;
- }
- }
- if (!found) {
- for (i = 0; i < 10; i++) {
- handle = openLocTextFile(locTextFile, i);
- if (handle >= 0) {
- _vm->_global->_language = i;
- break;
- }
- }
- }
-
- }
+ pushCollisions(0);
+ playTot(skipPlay);
- debugC(1, kDebugFileIO, "Using language %d for %s",
- _vm->_global->_language, _curTotFile);
+ if (_vm->_inter->_terminate != 2)
+ _vm->_inter->_terminate = 0;
- if (handle >= 0) {
- _vm->_dataIO->closeData(handle);
+ popCollisions();
- if (dataSize)
- *dataSize = _vm->_dataIO->getDataSize(locTextFile);
+ clearUnusedEnvironment();
- return _vm->_dataIO->getData(locTextFile);
- }
- return 0;
+ _curEnvironment = curBackupPos;
+ _numEnvironments = backupedCount;
+ _environments->get(_curEnvironment);
}
void Game::setCollisions(byte arg_0) {
- byte *savedIP;
uint16 left;
uint16 top;
uint16 width;
@@ -783,12 +515,12 @@ void Game::setCollisions(byte arg_0) {
if (((collArea->id & 0xC000) != 0x8000) || (collArea->funcSub == 0))
continue;
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData + collArea->funcSub;
- left = _vm->_parse->parseValExpr();
- top = _vm->_parse->parseValExpr();
- width = _vm->_parse->parseValExpr();
- height = _vm->_parse->parseValExpr();
+ _script->call(collArea->funcSub);
+
+ left = _script->readValExpr();
+ top = _script->readValExpr();
+ width = _script->readValExpr();
+ height = _script->readValExpr();
if ((_vm->_draw->_renderFlags & RENDERFLAG_CAPTUREPOP) &&
(left != 0xFFFF)) {
left += _vm->_draw->_backDeltaX;
@@ -807,16 +539,15 @@ void Game::setCollisions(byte arg_0) {
collArea->top = top;
collArea->right = left + width - 1;
collArea->bottom = top + height - 1;
- _vm->_global->_inter_execPtr = savedIP;
+
+ _script->pop();
}
}
void Game::collSub(uint16 offset) {
- byte *savedIP;
int16 collStackSize;
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData + offset;
+ _script->call(offset);
_shouldPushColls = 1;
collStackSize = _collStackSize;
@@ -827,7 +558,9 @@ void Game::collSub(uint16 offset) {
popCollisions();
_shouldPushColls = 0;
- _vm->_global->_inter_execPtr = savedIP;
+
+ _script->pop();
+
setCollisions();
}
@@ -852,4 +585,16 @@ void Game::collAreaSub(int16 index, int8 enter) {
}
}
+void Game::clearUnusedEnvironment() {
+ if (!_environments->has(_script)) {
+ delete _script;
+ _script = 0;
+ }
+ if (!_environments->has(_resources)) {
+ delete _resources;
+ _resources = 0;
+ }
+
+}
+
} // End of namespace Gob
diff --git a/engines/gob/game.h b/engines/gob/game.h
index 3264288a32..ead4a56492 100644
--- a/engines/gob/game.h
+++ b/engines/gob/game.h
@@ -26,10 +26,45 @@
#ifndef GOB_GAME_H
#define GOB_GAME_H
-#include "gob/variables.h"
-
namespace Gob {
+class Script;
+class Resources;
+class Variables;
+
+class Environments {
+public:
+ static const uint8 kEnvironmentCount = 5;
+
+ Environments(GobEngine *vm);
+ ~Environments();
+
+ void set(uint8 env);
+ void get(uint8 env) const;
+
+ const char *getTotFile(uint8 env) const;
+
+ bool has(Variables *variables, uint8 startEnv = 0, int16 except = -1) const;
+ bool has(Script *script , uint8 startEnv = 0, int16 except = -1) const;
+ bool has(Resources *resources, uint8 startEnv = 0, int16 except = -1) const;
+
+ void clear();
+
+private:
+ struct Environment {
+ int16 cursorHotspotX;
+ int16 cursorHotspotY;
+ char curTotFile[14];
+ Variables *variables;
+ Script *script;
+ Resources *resources;
+ };
+
+ GobEngine *_vm;
+
+ Environment *_environments;
+};
+
class Game {
public:
@@ -46,20 +81,7 @@ public:
uint16 funcEnter;
uint16 funcLeave;
uint16 funcSub;
- byte *totFileData;
- } PACKED_STRUCT;
-
-#define szGame_TotTextItem (2 + 2)
- struct TotTextItem {
- int16 offset;
- int16 size;
- } PACKED_STRUCT;
-
-#define szGame_TotTextTable (2)
- struct TotTextTable {
- int16 itemsCount;
- TotTextItem *items;
- byte *dataPtr;
+ Script *script;
} PACKED_STRUCT;
struct InputDesc {
@@ -74,18 +96,10 @@ public:
Collision *_collisionAreas;
Collision *_collStack[5];
- bool _foundTotLoc;
- TotTextTable *_totTextData;
+ Script *_script;
+ Resources *_resources;
char _curTotFile[14];
- char _curExtFile[14];
-
- byte *_imFileData;
- byte *_totFileData;
-
- int16 _extHandle;
- int16 _lomHandle;
-
char _totToLoad[20];
int32 _startTimeKey;
@@ -100,9 +114,6 @@ public:
Game(GobEngine *vm);
virtual ~Game();
- byte *loadExtData(int16 dataId, int16 *pResWidth, int16 *pResHeight, uint32 *dataSize = 0);
- byte *loadTotResource(int16 id, int16 *dataSize = 0, int16 *width = 0, int16 *height = 0);
-
void capturePush(int16 left, int16 top, int16 width, int16 height);
void capturePop(char doDraw);
@@ -142,42 +153,6 @@ public:
virtual void popCollisions(void) = 0;
protected:
-#include "common/pack-start.h" // START STRUCT PACKING
-
-#define szGame_TotResItem (4 + 2 + 2 + 2)
- struct TotResItem {
- int32 offset; // if > 0, then offset from end of resource table.
- // If < 0, then -offset-1 is index in .IM file table
- int16 size;
- int16 width;
- int16 height;
- } PACKED_STRUCT;
-
-#define szGame_TotResTable (2 + 1)
- struct TotResTable {
- int16 itemsCount;
- byte unknown;
- TotResItem *items;
- byte *dataPtr;
- } PACKED_STRUCT;
-
-#define szGame_ExtItem (4 + 2 + 2 + 2)
- struct ExtItem {
- int32 offset; // offset from the table end
- uint16 size;
- int16 width; // width & 0x7FFF: width, width & 0x8000: pack flag
- int16 height; // not zero
- } PACKED_STRUCT;
-
-#define szGame_ExtTable (2 + 1)
- struct ExtTable {
- int16 itemsCount;
- byte unknown;
- ExtItem *items;
- } PACKED_STRUCT;
-
-#include "common/pack-end.h" // END STRUCT PACKING
-
int16 _lastCollKey;
int16 _lastCollAreaIndex;
int16 _lastCollId;
@@ -190,10 +165,6 @@ protected:
char _tempStr[256];
- TotResTable *_totResourceTable;
- ExtTable *_extTable;
- char _curImaFile[18];
-
int16 _collStackSize;
int16 _collStackElemSizes[5];
@@ -206,35 +177,22 @@ protected:
char _collStr[256];
// For totSub()
- int8 _backupedCount;
- int8 _curBackupPos;
- int16 _cursorHotspotXArray[5];
- int16 _cursorHotspotYArray[5];
- TotTextTable *_totTextDataArray[5];
- byte *_totFileDataArray[5];
- TotResTable *_totResourceTableArray[5];
- ExtTable *_extTableArray[5];
- int16 _extHandleArray[5];
- byte *_imFileDataArray[5];
- Variables *_variablesArray[5];
- char _curTotFileArray[5][14];
+ int8 _curEnvironment;
+ int8 _numEnvironments;
+ Environments *_environments;
GobEngine *_vm;
virtual int16 adjustKey(int16 key);
- byte *loadLocTexts(int32 *dataSize = 0);
- int32 loadTotFile(const char *path);
- void loadExtTable(void);
- void loadImFile(void);
-
void collAreaSub(int16 index, int8 enter);
- int16 openLocTextFile(char *locTextFile, int language);
virtual void setCollisions(byte arg_0 = 1);
virtual void collSub(uint16 offset);
virtual int16 checkMousePoint(int16 all, int16 *resId, int16 *resIndex) = 0;
+
+ void clearUnusedEnvironment();
};
class Game_v1 : public Game {
diff --git a/engines/gob/game_fascin.cpp b/engines/gob/game_fascin.cpp
index 8e77141ce6..38ad03f0f8 100644
--- a/engines/gob/game_fascin.cpp
+++ b/engines/gob/game_fascin.cpp
@@ -35,7 +35,6 @@
#include "gob/goblin.h"
#include "gob/inter.h"
#include "gob/mult.h"
-#include "gob/parse.h"
#include "gob/scenery.h"
#include "gob/video.h"
#include "gob/videoplayer.h"
diff --git a/engines/gob/game_v1.cpp b/engines/gob/game_v1.cpp
index ad24d7d9c6..87dc78e3b1 100644
--- a/engines/gob/game_v1.cpp
+++ b/engines/gob/game_v1.cpp
@@ -32,11 +32,12 @@
#include "gob/global.h"
#include "gob/util.h"
#include "gob/dataio.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/draw.h"
#include "gob/inter.h"
#include "gob/mult.h"
#include "gob/video.h"
-#include "gob/parse.h"
#include "gob/scenery.h"
#include "gob/sound/sound.h"
@@ -49,12 +50,12 @@ void Game_v1::playTot(int16 skipPlay) {
int16 _captureCounter;
int16 breakFrom;
int16 nestLevel;
- int32 variablesCount;
int16 *oldNestLevel = _vm->_inter->_nestLevel;
int16 *oldBreakFrom = _vm->_inter->_breakFromLevel;
int16 *oldCaptureCounter = _vm->_scenery->_pCaptureCounter;
- byte *savedIP = _vm->_global->_inter_execPtr;
+
+ _script->push();
_vm->_inter->_nestLevel = &nestLevel;
_vm->_inter->_breakFromLevel = &breakFrom;
@@ -93,86 +94,23 @@ void Game_v1::playTot(int16 skipPlay) {
for (int i = 0; i < 20; i++)
freeSoundSlot(i);
- _totTextData = 0;
- _totResourceTable = 0;
- _imFileData = 0;
- _extTable = 0;
- _extHandle = -1;
-
_totToLoad[0] = 0;
- if ((_curTotFile[0] == 0) && (_totFileData == 0))
+ if ((_curTotFile[0] == 0) && !_script->isLoaded())
break;
- loadTotFile(_curTotFile);
- if (_totFileData == 0) {
+ if (!_script->load(_curTotFile)) {
_vm->_draw->blitCursor();
break;
}
- strcpy(_curImaFile, _curTotFile);
- strcpy(_curExtFile, _curTotFile);
-
- _curImaFile[strlen(_curImaFile) - 4] = 0;
- strcat(_curImaFile, ".ima");
-
- _curExtFile[strlen(_curExtFile) - 4] = 0;
- strcat(_curExtFile, ".ext");
-
- debugC(4, kDebugFileIO, "IMA: %s", _curImaFile);
- debugC(4, kDebugFileIO, "EXT: %s", _curExtFile);
-
- byte *filePtr = _totFileData + 0x30;
-
- _totTextData = 0;
- if (READ_LE_UINT32(filePtr) != (uint32) -1) {
- _totTextData = new TotTextTable;
- _totTextData->dataPtr =
- (_totFileData + READ_LE_UINT32(_totFileData + 0x30));
- Common::MemoryReadStream totTextData(_totTextData->dataPtr,
- 4294967295U);
-
- _totTextData->itemsCount = totTextData.readSint16LE();
-
- _totTextData->items = new TotTextItem[_totTextData->itemsCount];
- for (int i = 0; i < _totTextData->itemsCount; ++i) {
- _totTextData->items[i].offset = totTextData.readSint16LE();
- _totTextData->items[i].size = totTextData.readSint16LE();
- }
- }
-
- filePtr = _totFileData + 0x34;
- _totResourceTable = 0;
- if (READ_LE_UINT32(filePtr) != (uint32) -1) {
- _totResourceTable = new TotResTable;
- _totResourceTable->dataPtr =
- _totFileData + READ_LE_UINT32( _totFileData + 0x34);
- Common::MemoryReadStream totResTable(_totResourceTable->dataPtr,
- 4294967295U);
-
- _totResourceTable->itemsCount = totResTable.readSint16LE();
- _totResourceTable->unknown = totResTable.readByte();
-
- _totResourceTable->items =
- new TotResItem[_totResourceTable->itemsCount];
- for (int i = 0; i < _totResourceTable->itemsCount; ++i) {
- _totResourceTable->items[i].offset = totResTable.readSint32LE();
- _totResourceTable->items[i].size = totResTable.readSint16LE();
- _totResourceTable->items[i].width = totResTable.readSint16LE();
- _totResourceTable->items[i].height = totResTable.readSint16LE();
- }
- }
-
- loadImFile();
- loadExtTable();
+ _resources->load(_curTotFile);
- _vm->_global->_inter_animDataSize =
- READ_LE_UINT16(_totFileData + 0x38);
+ _vm->_global->_inter_animDataSize = _script->getAnimDataSize();
if (!_vm->_inter->_variables)
- _vm->_inter->allocateVars(READ_LE_UINT16(_totFileData + 0x2C));
+ _vm->_inter->allocateVars(_script->getVariablesCount() & 0xFFFF);
- _vm->_global->_inter_execPtr = _totFileData;
- _vm->_global->_inter_execPtr += READ_LE_UINT32(_totFileData + 0x64);
+ _script->seek(_script->getFunctionOffset(TOTFile::kFunctionStart));
_vm->_inter->renewTimeInVars();
@@ -182,39 +120,16 @@ void Game_v1::playTot(int16 skipPlay) {
WRITE_VAR(16, _vm->_global->_language);
_vm->_inter->callSub(2);
+ _script->setFinished(false);
if (_totToLoad[0] != 0)
_vm->_inter->_terminate = 0;
- variablesCount = READ_LE_UINT32(_totFileData + 0x2C);
_vm->_draw->blitInvalidated();
- delete[] _totFileData;
- _totFileData = 0;
-
- if (_totTextData) {
- delete[] _totTextData->items;
- delete _totTextData;
- }
- _totTextData = 0;
-
- if (_totResourceTable) {
- delete[] _totResourceTable->items;
- delete _totResourceTable;
- }
- _totResourceTable = 0;
-
- delete[] _imFileData;
- _imFileData = 0;
- if (_extTable)
- delete[] _extTable->items;
- delete _extTable;
- _extTable = 0;
+ _script->unload();
- if (_extHandle >= 0)
- _vm->_dataIO->closeData(_extHandle);
-
- _extHandle = -1;
+ _resources->unload();
for (int i = 0; i < *_vm->_scenery->_pCaptureCounter; i++)
capturePop(0);
@@ -241,7 +156,8 @@ void Game_v1::playTot(int16 skipPlay) {
_vm->_inter->_nestLevel = oldNestLevel;
_vm->_inter->_breakFromLevel = oldBreakFrom;
_vm->_scenery->_pCaptureCounter = oldCaptureCounter;
- _vm->_global->_inter_execPtr = savedIP;
+
+ _script->pop();
}
void Game_v1::clearCollisions() {
@@ -279,7 +195,7 @@ int16 Game_v1::addNewCollision(int16 id, uint16 left, uint16 top,
ptr->funcEnter = funcEnter;
ptr->funcLeave = funcLeave;
ptr->funcSub = funcSub;
- ptr->totFileData = 0;
+ ptr->script = 0;
return i;
}
@@ -331,7 +247,6 @@ void Game_v1::popCollisions(void) {
int16 Game_v1::checkCollisions(byte handleMouse, int16 deltaTime,
int16 *pResId, int16 *pResIndex) {
- byte *savedIP;
int16 resIndex;
int16 key;
int16 oldIndex;
@@ -357,12 +272,9 @@ int16 Game_v1::checkCollisions(byte handleMouse, int16 deltaTime,
_lastCollKey = checkMousePoint(1, &_lastCollId, &_lastCollAreaIndex);
if ((_lastCollKey != 0) && ((_lastCollId & 0x8000) != 0)) {
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData +
- _collisionAreas[_lastCollAreaIndex].funcEnter;
-
+ _script->call(_collisionAreas[_lastCollAreaIndex].funcEnter);
_vm->_inter->funcBlock(0);
- _vm->_global->_inter_execPtr = savedIP;
+ _script->pop();
}
}
@@ -423,12 +335,10 @@ int16 Game_v1::checkCollisions(byte handleMouse, int16 deltaTime,
if ((_lastCollKey != 0) &&
(_collisionAreas[_lastCollAreaIndex].funcLeave != 0)) {
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData +
- _collisionAreas[_lastCollAreaIndex].funcLeave;
+ _script->call(_collisionAreas[_lastCollAreaIndex].funcLeave);
_vm->_inter->funcBlock(0);
- _vm->_global->_inter_execPtr = savedIP;
+ _script->pop();
}
_lastCollKey = 0;
@@ -463,12 +373,11 @@ int16 Game_v1::checkCollisions(byte handleMouse, int16 deltaTime,
if ((_lastCollKey != 0) &&
(_collisionAreas[_lastCollAreaIndex].funcLeave != 0)) {
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData +
- _collisionAreas[_lastCollAreaIndex].funcLeave;
+ _script->call(_collisionAreas[_lastCollAreaIndex].funcLeave);
_vm->_inter->funcBlock(0);
- _vm->_global->_inter_execPtr = savedIP;
+ _script->pop();
+
}
_lastCollKey = 0;
return key;
@@ -476,24 +385,22 @@ int16 Game_v1::checkCollisions(byte handleMouse, int16 deltaTime,
if ((_lastCollKey != 0) &&
(_collisionAreas[_lastCollAreaIndex].funcLeave != 0)) {
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData +
- _collisionAreas[_lastCollAreaIndex].funcLeave;
+ _script->call(_collisionAreas[_lastCollAreaIndex].funcLeave);
_vm->_inter->funcBlock(0);
- _vm->_global->_inter_execPtr = savedIP;
+ _script->pop();
+
}
_lastCollKey =
checkMousePoint(1, &_lastCollId, &_lastCollAreaIndex);
if ((_lastCollKey != 0) && ((_lastCollId & 0x8000) != 0)) {
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData +
- _collisionAreas[_lastCollAreaIndex].funcEnter;
+ _script->call(_collisionAreas[_lastCollAreaIndex].funcEnter);
_vm->_inter->funcBlock(0);
- _vm->_global->_inter_execPtr = savedIP;
+ _script->pop();
+
}
} else {
@@ -507,23 +414,22 @@ int16 Game_v1::checkCollisions(byte handleMouse, int16 deltaTime,
if (key != _lastCollKey) {
if ((_lastCollKey != 0) && ((oldId & 0x8000) != 0)) {
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData +
- _collisionAreas[oldIndex].funcLeave;
+ _script->call(_collisionAreas[oldIndex].funcLeave);
_vm->_inter->funcBlock(0);
- _vm->_global->_inter_execPtr = savedIP;
+ _script->pop();
+
}
_lastCollKey = key;
if ((_lastCollKey != 0) && ((_lastCollId & 0x8000) != 0)) {
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData +
- _collisionAreas[_lastCollAreaIndex].funcEnter;
+ _script->call(_collisionAreas[_lastCollAreaIndex].funcEnter);
_vm->_inter->funcBlock(0);
- _vm->_global->_inter_execPtr = savedIP;
+ _script->pop();
+
}
+
}
}
}
@@ -588,7 +494,6 @@ void Game_v1::collisionsBlock(void) {
int16 array[250];
byte count;
int16 collResId;
- byte *startIP;
int16 curCmd;
int16 cmd;
int16 cmdHigh;
@@ -615,27 +520,27 @@ void Game_v1::collisionsBlock(void) {
int16 collStackPos;
Collision *collPtr;
uint32 timeKey;
- byte *savedIP;
if (_shouldPushColls)
pushCollisions(1);
collResId = -1;
- _vm->_global->_inter_execPtr++;
- count = *_vm->_global->_inter_execPtr++;
- _handleMouse = _vm->_global->_inter_execPtr[0];
- deltaTime = 1000 * _vm->_global->_inter_execPtr[1];
- descIndex2 = _vm->_global->_inter_execPtr[2];
- stackPos2 = _vm->_global->_inter_execPtr[3];
- descIndex = _vm->_global->_inter_execPtr[4];
+ _script->skip(1);
+ count = _script->readByte();
+ _handleMouse = _script->readByte();
+ deltaTime = 1000 * _script->readByte();
+ descIndex2 = _script->readByte();
+ stackPos2 = _script->readByte();
+ descIndex = _script->readByte();
if ((stackPos2 != 0) || (descIndex != 0))
deltaTime /= 100;
timeVal = deltaTime;
- _vm->_global->_inter_execPtr += 6;
+ _script->skip(1);
+
+ uint32 startPos = _script->pos();
- startIP = _vm->_global->_inter_execPtr;
WRITE_VAR(16, 0);
var_22 = 0;
index = 0;
@@ -643,26 +548,25 @@ void Game_v1::collisionsBlock(void) {
for (curCmd = 0; curCmd < count; curCmd++) {
array[curCmd] = 0;
- cmd = *_vm->_global->_inter_execPtr++;
+ cmd = _script->readByte();
if ((cmd & 0x40) != 0) {
cmd -= 0x40;
- cmdHigh = *_vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr++;
+ cmdHigh = _script->readByte();
cmdHigh <<= 8;
} else
cmdHigh = 0;
if ((cmd & 0x80) != 0) {
- left = _vm->_parse->parseValExpr();
- top = _vm->_parse->parseValExpr();
- width = _vm->_parse->parseValExpr();
- height = _vm->_parse->parseValExpr();
+ left = _script->readValExpr();
+ top = _script->readValExpr();
+ width = _script->readValExpr();
+ height = _script->readValExpr();
} else {
- left = _vm->_inter->load16();
- top = _vm->_inter->load16();
- width = _vm->_inter->load16();
- height = _vm->_inter->load16();
+ left = _script->readUint16();
+ top = _script->readUint16();
+ width = _script->readUint16();
+ height = _script->readUint16();
}
cmd &= 0x7F;
@@ -680,16 +584,16 @@ void Game_v1::collisionsBlock(void) {
_vm->_util->clearKeyBuf();
var_22 = 1;
- key = _vm->_parse->parseVarIndex();
- descArray[index].fontIndex = _vm->_inter->load16();
- descArray[index].backColor = *_vm->_global->_inter_execPtr++;
- descArray[index].frontColor = *_vm->_global->_inter_execPtr++;
+ key = _script->readVarIndex();
+ descArray[index].fontIndex = _script->readInt16();
+ descArray[index].backColor = _script->readByte();
+ descArray[index].frontColor = _script->readByte();
if ((cmd < 5) || (cmd > 8)) {
descArray[index].ptr = 0;
} else {
- descArray[index].ptr = _vm->_global->_inter_execPtr + 2;
- _vm->_global->_inter_execPtr += _vm->_inter->load16();
+ descArray[index].ptr = _script->getData() + _script->pos() + 2;
+ _script->skip(_script->readInt16());
}
if (left == 0xFFFF)
@@ -698,12 +602,9 @@ void Game_v1::collisionsBlock(void) {
if ((cmd & 1) == 0) {
addNewCollision(curCmd + 0x8000, left, top, left + width *
_vm->_draw->_fonts[descArray[index].fontIndex]->itemWidth - 1,
- top + height - 1, cmd, key, 0,
- _vm->_global->_inter_execPtr - _totFileData);
+ top + height - 1, cmd, key, 0, _script->pos());
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
} else {
addNewCollision(curCmd + 0x8000, left, top, left + width *
_vm->_draw->_fonts[descArray[index].fontIndex]->itemWidth - 1,
@@ -713,18 +614,15 @@ void Game_v1::collisionsBlock(void) {
break;
case 21:
- key = _vm->_inter->load16();
- array[curCmd] = _vm->_inter->load16();
- flags = _vm->_inter->load16() & 3;
+ key = _script->readInt16();
+ array[curCmd] = _script->readInt16();
+ flags = _script->readInt16() & 3;
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
- (flags << 4) + cmdHigh + 2, key,
- _vm->_global->_inter_execPtr - _totFileData, 0);
+ (flags << 4) + cmdHigh + 2, key, _script->pos(), 0);
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 20:
@@ -732,61 +630,48 @@ void Game_v1::collisionsBlock(void) {
// Fall through to case 2
case 2:
- key = _vm->_inter->load16();
- array[curCmd] = _vm->_inter->load16();
- flags = _vm->_inter->load16() & 3;
+ key = _script->readInt16();
+ array[curCmd] = _script->readInt16();
+ flags = _script->readInt16() & 3;
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1,
top + height - 1,
- (flags << 4) + cmdHigh + 2, key, 0,
- _vm->_global->_inter_execPtr - _totFileData);
+ (flags << 4) + cmdHigh + 2, key, 0, _script->pos());
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 0:
- _vm->_global->_inter_execPtr += 6;
- startIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(6);
+ startPos = _script->pos();
+ _script->skip(_script->peekUint16(2) + 2);
key = curCmd + 0xA000;
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
cmd + cmdHigh, key,
- startIP - _totFileData,
- _vm->_global->_inter_execPtr - _totFileData);
+ startPos, _script->pos());
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 1:
- key = _vm->_inter->load16();
- array[curCmd] = _vm->_inter->load16();
- flags = _vm->_inter->load16() & 3;
-
- startIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ key = _script->readInt16();
+ array[curCmd] = _script->readInt16();
+ flags = _script->readInt16() & 3;
+
+ startPos = _script->pos();
+ _script->skip(_script->peekUint16(2) + 2);
if (key == 0)
key = curCmd + 0xA000;
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
(flags << 4) + cmd + cmdHigh, key,
- startIP - _totFileData,
- _vm->_global->_inter_execPtr - _totFileData);
+ startPos, _script->pos());
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
}
}
@@ -895,9 +780,11 @@ void Game_v1::collisionsBlock(void) {
if (collPtr->funcLeave != 0) {
timeKey = _vm->_util->getTimeKey();
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr =
- _totFileData + collPtr->funcLeave;
+
+ uint32 savedPos = _script->pos();
+
+ _script->seek(collPtr->funcLeave);
+
_shouldPushColls = 1;
savedCollStackSize = _collStackSize;
_vm->_inter->funcBlock(0);
@@ -906,7 +793,8 @@ void Game_v1::collisionsBlock(void) {
popCollisions();
_shouldPushColls = 0;
- _vm->_global->_inter_execPtr = savedIP;
+
+ _script->seek(savedPos);
deltaTime = timeVal -
(_vm->_util->getTimeKey() - timeKey);
@@ -986,9 +874,9 @@ void Game_v1::collisionsBlock(void) {
WRITE_VAR(16, array[(uint16) _activeCollResId & ~0x8000]);
if (_collisionAreas[_activeCollIndex].funcEnter != 0) {
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData +
- _collisionAreas[_activeCollIndex].funcEnter;
+ uint32 savedPos = _script->pos();
+
+ _script->seek(_collisionAreas[_activeCollIndex].funcEnter);
_shouldPushColls = 1;
@@ -997,7 +885,8 @@ void Game_v1::collisionsBlock(void) {
if (collStackPos != _collStackSize)
popCollisions();
_shouldPushColls = 0;
- _vm->_global->_inter_execPtr = savedIP;
+
+ _script->seek(savedPos);
}
WRITE_VAR(16, 0);
@@ -1071,10 +960,8 @@ void Game_v1::collisionsBlock(void) {
WRITE_VAR(17, 1);
}
- savedIP = 0;
if (!_vm->_inter->_terminate) {
- savedIP = _totFileData +
- _collisionAreas[_activeCollIndex].funcLeave;
+ _script->seek(_collisionAreas[_activeCollIndex].funcLeave);
WRITE_VAR(2, _vm->_global->_inter_mouseX);
WRITE_VAR(3, _vm->_global->_inter_mouseY);
@@ -1082,12 +969,11 @@ void Game_v1::collisionsBlock(void) {
if (VAR(16) == 0)
WRITE_VAR(16, array[(uint16) _activeCollResId & ~0x8000]);
- }
+ } else
+ _script->setFinished(true);
for (curCmd = 0; curCmd < count; curCmd++)
freeCollision(curCmd + 0x8000);
-
- _vm->_global->_inter_execPtr = savedIP;
}
int16 Game_v1::multiEdit(int16 time, int16 index, int16 *pCurPos,
diff --git a/engines/gob/game_v2.cpp b/engines/gob/game_v2.cpp
index e9656efa32..08184e73d0 100644
--- a/engines/gob/game_v2.cpp
+++ b/engines/gob/game_v2.cpp
@@ -32,11 +32,12 @@
#include "gob/global.h"
#include "gob/util.h"
#include "gob/dataio.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/draw.h"
#include "gob/goblin.h"
#include "gob/inter.h"
#include "gob/mult.h"
-#include "gob/parse.h"
#include "gob/scenery.h"
#include "gob/video.h"
#include "gob/videoplayer.h"
@@ -55,15 +56,12 @@ void Game_v2::playTot(int16 skipPlay) {
int16 _captureCounter;
int16 breakFrom;
int16 nestLevel;
- int32 totSize;
- byte *filePtr;
- byte *savedIP;
- bool totTextLoc;
oldNestLevel = _vm->_inter->_nestLevel;
oldBreakFrom = _vm->_inter->_breakFromLevel;
oldCaptureCounter = _vm->_scenery->_pCaptureCounter;
- savedIP = _vm->_global->_inter_execPtr;
+
+ _script->push();
_vm->_inter->_nestLevel = &nestLevel;
_vm->_inter->_breakFromLevel = &breakFrom;
@@ -94,125 +92,30 @@ void Game_v2::playTot(int16 skipPlay) {
} else
_vm->_inter->initControlVars(0);
- _totTextData = 0;
- _totResourceTable = 0;
- _imFileData = 0;
- _extTable = 0;
- _extHandle = -1;
-
_vm->_draw->_cursorHotspotXVar = -1;
_totToLoad[0] = 0;
- if ((_curTotFile[0] == 0) && (_totFileData == 0))
+ if ((_curTotFile[0] == 0) && (!_script->isLoaded()))
break;
- totSize = loadTotFile(_curTotFile);
-
if (skipPlay == -2) {
_vm->_vidPlayer->primaryClose();
skipPlay = 0;
}
- if (_totFileData == 0) {
+ if (!_script->load(_curTotFile)) {
_vm->_draw->blitCursor();
_vm->_inter->_terminate = 2;
break;
}
- strcpy(_curImaFile, _curTotFile);
- strcpy(_curExtFile, _curTotFile);
-
- _curImaFile[strlen(_curImaFile) - 4] = 0;
- strcat(_curImaFile, ".ima");
-
- _curExtFile[strlen(_curExtFile) - 4] = 0;
- strcat(_curExtFile, ".ext");
-
- debugC(4, kDebugFileIO, "IMA: %s", _curImaFile);
- debugC(4, kDebugFileIO, "EXT: %s", _curExtFile);
-
- filePtr = _totFileData + 0x30;
-
- _totTextData = 0;
- totTextLoc = false;
- if (READ_LE_UINT32(filePtr) != (uint32) -1) {
- _totTextData = new TotTextTable;
-
- int32 size;
-
- if (READ_LE_UINT32(filePtr) == 0) {
- _totTextData->dataPtr = loadLocTexts(&size);
- totTextLoc = true;
- } else {
- _totTextData->dataPtr =
- (_totFileData + READ_LE_UINT32(_totFileData + 0x30));
- size = totSize;
- _vm->_global->_language = _vm->_global->_languageWanted;
- }
-
- _totTextData->items = 0;
- if (_totTextData->dataPtr != 0) {
- Common::MemoryReadStream totTextData(_totTextData->dataPtr,
- 4294967295U);
- _totTextData->itemsCount = totTextData.readSint16LE() & 0x3FFF;
-
- _totTextData->items = new TotTextItem[_totTextData->itemsCount];
- for (int i = 0; i < _totTextData->itemsCount; ++i) {
- _totTextData->items[i].offset = totTextData.readSint16LE();
- _totTextData->items[i].size = totTextData.readSint16LE();
- }
- }
- }
-
- filePtr = _totFileData + 0x34;
- _totResourceTable = 0;
- int32 resSize;
- if (READ_LE_UINT32(filePtr) != (uint32) -1) {
- _totResourceTable = new TotResTable;
- _totResourceTable->dataPtr =
- _totFileData + READ_LE_UINT32(_totFileData + 0x34);
- Common::MemoryReadStream totResTable(_totResourceTable->dataPtr,
- 4294967295U);
-
- _totResourceTable->itemsCount = totResTable.readSint16LE();
- resSize = _totResourceTable->itemsCount * szGame_TotResItem + szGame_TotResTable;
- if (totSize > (resSize + 0x34)) {
- _totResourceTable->unknown = totResTable.readByte();
-
- _totResourceTable->items =
- new TotResItem[_totResourceTable->itemsCount];
- for (int i = 0; i < _totResourceTable->itemsCount; ++i) {
- _totResourceTable->items[i].offset = totResTable.readSint32LE();
- _totResourceTable->items[i].size = totResTable.readSint16LE();
- _totResourceTable->items[i].width = totResTable.readSint16LE();
- _totResourceTable->items[i].height = totResTable.readSint16LE();
- }
- }
- else {
- // WORKAROUND: In the original asm, _totResourceTable is
- // only assigned in playTot and evaluated later, right
- // before using it. In the Gobliins 2 demo, there is a
- // dummy tot that loads another tot, overwriting the dummy
- // pointer with the real one.
- debugC(1, kDebugFileIO,
- "Attempted to load invalid resource table (size = %d, totSize = %d)",
- resSize, totSize);
- delete _totResourceTable;
- _totResourceTable = 0;
- }
- }
-
- loadImFile();
- loadExtTable();
+ _resources->load(_curTotFile);
- _vm->_global->_inter_animDataSize =
- READ_LE_UINT16(_totFileData + 0x38);
+ _vm->_global->_inter_animDataSize = _script->getAnimDataSize();
if (!_vm->_inter->_variables)
- _vm->_inter->allocateVars(READ_LE_UINT16(_totFileData + 0x2C));
+ _vm->_inter->allocateVars(_script->getVariablesCount() & 0xFFFF);
- _vm->_global->_inter_execPtr = _totFileData;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_totFileData + 0x64);
+ _script->seek(_script->getFunctionOffset(TOTFile::kFunctionStart));
_vm->_inter->renewTimeInVars();
@@ -227,35 +130,10 @@ void Game_v2::playTot(int16 skipPlay) {
_vm->_inter->_terminate = 0;
_vm->_draw->blitInvalidated();
- delete[] _totFileData;
- _totFileData = 0;
-
- if (_totTextData) {
- delete[] _totTextData->items;
- if (totTextLoc)
- delete[] _totTextData->dataPtr;
- delete _totTextData;
- }
- _totTextData = 0;
- if (_totResourceTable) {
- delete[] _totResourceTable->items;
- delete _totResourceTable;
- }
- _totResourceTable = 0;
-
- delete[] _imFileData;
- _imFileData = 0;
-
- if (_extTable)
- delete[] _extTable->items;
- delete _extTable;
- _extTable = 0;
-
- if (_extHandle >= 0)
- _vm->_dataIO->closeData(_extHandle);
+ _script->unload();
- _extHandle = -1;
+ _resources->unload();
for (int i = 0; i < *_vm->_scenery->_pCaptureCounter; i++)
capturePop(0);
@@ -282,9 +160,7 @@ void Game_v2::playTot(int16 skipPlay) {
} else {
_vm->_inter->initControlVars(0);
_vm->_scenery->_pCaptureCounter = oldCaptureCounter;
- _vm->_global->_inter_execPtr = _totFileData;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_totFileData + (skipPlay << 1) + 0x66);
+ _script->seek(_script->getFunctionOffset(skipPlay + 1));
_menuLevel++;
_vm->_inter->callSub(2);
@@ -299,7 +175,8 @@ void Game_v2::playTot(int16 skipPlay) {
_vm->_inter->_nestLevel = oldNestLevel;
_vm->_inter->_breakFromLevel = oldBreakFrom;
_vm->_scenery->_pCaptureCounter = oldCaptureCounter;
- _vm->_global->_inter_execPtr = savedIP;
+
+ _script->pop();
}
void Game_v2::clearCollisions() {
@@ -337,7 +214,7 @@ int16 Game_v2::addNewCollision(int16 id, uint16 left, uint16 top,
ptr->funcEnter = funcEnter;
ptr->funcLeave = funcLeave;
ptr->funcSub = funcSub;
- ptr->totFileData = 0;
+ ptr->script = 0;
return i;
}
@@ -604,7 +481,6 @@ void Game_v2::collisionsBlock(void) {
int16 array[250];
byte count;
int16 collResId;
- byte *startIP;
int16 curCmd;
int16 cmd;
int16 cmdHigh;
@@ -621,7 +497,6 @@ void Game_v2::collisionsBlock(void) {
int16 stackPos2;
int16 descIndex;
int16 timeVal;
- int16 offsetIP;
char *str;
int16 i;
int16 counter;
@@ -631,8 +506,9 @@ void Game_v2::collisionsBlock(void) {
Collision *collPtr;
Collision *collArea;
int16 timeKey;
- byte *savedIP;
byte collAreaStart;
+ uint32 startPos;
+ uint32 offsetPos;
if (_shouldPushColls)
pushCollisions(0);
@@ -645,21 +521,22 @@ void Game_v2::collisionsBlock(void) {
_shouldPushColls = 0;
collResId = -1;
- _vm->_global->_inter_execPtr++;
- count = *_vm->_global->_inter_execPtr++;
+ _script->skip(1);
+ count = _script->readByte();
- _handleMouse = _vm->_global->_inter_execPtr[0];
- deltaTime = 1000 * _vm->_global->_inter_execPtr[1];
- stackPos2 = _vm->_global->_inter_execPtr[3];
- descIndex = _vm->_global->_inter_execPtr[4];
+ _handleMouse = _script->readByte();
+ deltaTime = 1000 * _script->readByte();
+ _script->skip(1);
+ stackPos2 = _script->readByte();
+ descIndex = _script->readByte();
if ((stackPos2 != 0) || (descIndex != 0))
deltaTime /= 100;
timeVal = deltaTime;
- _vm->_global->_inter_execPtr += 6;
+ _script->skip(1);
- startIP = _vm->_global->_inter_execPtr;
+ startPos = _script->pos();
WRITE_VAR(16, 0);
var_1C = 0;
@@ -668,28 +545,27 @@ void Game_v2::collisionsBlock(void) {
for (curCmd = 0; curCmd < count; curCmd++) {
array[curCmd] = 0;
- cmd = *_vm->_global->_inter_execPtr++;
+ cmd = _script->readByte();
if ((cmd & 0x40) != 0) {
cmd -= 0x40;
- cmdHigh = *_vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr++;
+ cmdHigh = _script->readByte();
cmdHigh <<= 8;
} else
cmdHigh = 0;
if ((cmd & 0x80) != 0) {
- offsetIP = _vm->_global->_inter_execPtr - _totFileData;
- left = _vm->_parse->parseValExpr();
- top = _vm->_parse->parseValExpr();
- width = _vm->_parse->parseValExpr();
- height = _vm->_parse->parseValExpr();
+ offsetPos = _script->pos();
+ left = _script->readValExpr();
+ top = _script->readValExpr();
+ width = _script->readValExpr();
+ height = _script->readValExpr();
} else {
- offsetIP = 0;
- left = _vm->_inter->load16();
- top = _vm->_inter->load16();
- width = _vm->_inter->load16();
- height = _vm->_inter->load16();
+ offsetPos = 0;
+ left = _script->readUint16();
+ top = _script->readUint16();
+ width = _script->readUint16();
+ height = _script->readUint16();
}
if ((_vm->_draw->_renderFlags & RENDERFLAG_CAPTUREPOP) && (left != 0xFFFF)) {
@@ -712,46 +588,37 @@ void Game_v2::collisionsBlock(void) {
switch (cmd) {
case 0:
- _vm->_global->_inter_execPtr += 6;
- startIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(6);
+ startPos = _script->pos();
+ _script->skip(_script->peekUint16(2) + 2);
key = curCmd + 0xA000;
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
- cmd + cmdHigh, key, startIP - _totFileData,
- _vm->_global->_inter_execPtr - _totFileData, offsetIP);
+ cmd + cmdHigh, key, startPos,
+ _script->pos(), offsetPos);
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 1:
- key = _vm->_inter->load16();
- array[curCmd] = _vm->_inter->load16();
- flags = _vm->_inter->load16();
+ key = _script->readInt16();
+ array[curCmd] = _script->readInt16();
+ flags = _script->readInt16();
- startIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ startPos = _script->pos();
+ _script->skip(_script->peekUint16(2) + 2);
if (key == 0)
key = curCmd + 0xA000;
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
- (flags << 4) + cmd + cmdHigh, key, startIP - _totFileData,
- _vm->_global->_inter_execPtr - _totFileData, offsetIP);
-
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ (flags << 4) + cmd + cmdHigh, key, startPos,
+ _script->pos(), offsetPos);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 3:
@@ -764,23 +631,20 @@ void Game_v2::collisionsBlock(void) {
case 10:
_vm->_util->clearKeyBuf();
var_1C = 1;
- key = _vm->_parse->parseVarIndex();
- descArray[index].fontIndex = _vm->_inter->load16();
- descArray[index].backColor = *_vm->_global->_inter_execPtr++;
- descArray[index].frontColor = *_vm->_global->_inter_execPtr++;
+ key = _script->readVarIndex();
+ descArray[index].fontIndex = _script->readInt16();
+ descArray[index].backColor = _script->readByte();
+ descArray[index].frontColor = _script->readByte();
if ((cmd >= 5) && (cmd <= 8)) {
- descArray[index].ptr = _vm->_global->_inter_execPtr + 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr) + 2;
+ descArray[index].ptr = _script->getData() + _script->pos() + 2;
+ _script->skip(_script->peekUint16() + 2);
} else
descArray[index].ptr = 0;
if (left == 0xFFFF) {
if ((cmd & 1) == 0) {
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
}
break;
}
@@ -789,11 +653,9 @@ void Game_v2::collisionsBlock(void) {
addNewCollision(curCmd + 0x8000, left, top, left + width *
_vm->_draw->_fonts[descArray[index].fontIndex]-> itemWidth - 1,
top + height - 1, cmd, key, 0,
- _vm->_global->_inter_execPtr - _totFileData);
+ _script->pos());
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
} else
addNewCollision(curCmd + 0x8000, left, top, left + width *
_vm->_draw->_fonts[descArray[index].fontIndex]-> itemWidth - 1,
@@ -803,35 +665,31 @@ void Game_v2::collisionsBlock(void) {
break;
case 11:
- _vm->_global->_inter_execPtr += 6;
+ _script->skip(6);
for (i = 0; i < 150; i++) {
if ((_collisionAreas[i].id & 0xF000) == 0xE000) {
_collisionAreas[i].id &= 0xBFFF;
_collisionAreas[i].funcEnter =
- _vm->_global->_inter_execPtr - _totFileData;
+ _script->pos();
_collisionAreas[i].funcLeave =
- _vm->_global->_inter_execPtr - _totFileData;
+ _script->pos();
}
}
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 12:
- _vm->_global->_inter_execPtr += 6;
+ _script->skip(6);
for (i = 0; i < 150; i++) {
if ((_collisionAreas[i].id & 0xF000) == 0xD000) {
_collisionAreas[i].id &= 0xBFFF;
_collisionAreas[i].funcEnter =
- _vm->_global->_inter_execPtr - _totFileData;
+ _script->pos();
_collisionAreas[i].funcLeave =
- _vm->_global->_inter_execPtr - _totFileData;
+ _script->pos();
}
}
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 20:
@@ -839,34 +697,30 @@ void Game_v2::collisionsBlock(void) {
// Fall through to case 2
case 2:
- key = _vm->_inter->load16();
- array[curCmd] = _vm->_inter->load16();
- flags = _vm->_inter->load16();
+ key = _script->readInt16();
+ array[curCmd] = _script->readInt16();
+ flags = _script->readInt16();
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
(flags << 4) + cmdHigh + 2, key, 0,
- _vm->_global->_inter_execPtr - _totFileData, offsetIP);
+ _script->pos(), offsetPos);
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 21:
- key = _vm->_inter->load16();
- array[curCmd] = _vm->_inter->load16();
- flags = _vm->_inter->load16() & 3;
+ key = _script->readInt16();
+ array[curCmd] = _script->readInt16();
+ flags = _script->readInt16() & 3;
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
(flags << 4) + cmdHigh + 2, key,
- _vm->_global->_inter_execPtr - _totFileData, 0, offsetIP);
+ _script->pos(), 0, offsetPos);
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
}
@@ -1116,10 +970,8 @@ void Game_v2::collisionsBlock(void) {
if (_handleMouse == 1)
_vm->_draw->blitCursor();
- savedIP = 0;
if (!_vm->_inter->_terminate) {
- savedIP = _totFileData +
- _collisionAreas[_activeCollIndex].funcLeave;
+ _script->seek(_collisionAreas[_activeCollIndex].funcLeave);
_vm->_inter->storeMouse();
if (VAR(16) == 0) {
@@ -1128,7 +980,8 @@ void Game_v2::collisionsBlock(void) {
else
WRITE_VAR(16, _activeCollResId & 0xFFF);
}
- }
+ } else
+ _script->setFinished(true);
for (curCmd = 0; curCmd < count; curCmd++)
freeCollision(curCmd + 0x8000);
@@ -1138,8 +991,6 @@ void Game_v2::collisionsBlock(void) {
((_collisionAreas[i].id & 0xF000) == 0x9000))
_collisionAreas[i].id |= 0x4000;
}
-
- _vm->_global->_inter_execPtr = savedIP;
}
int16 Game_v2::multiEdit(int16 time, int16 index, int16 *pCurPos,
diff --git a/engines/gob/game_v6.cpp b/engines/gob/game_v6.cpp
index 9d9bd1faa3..8d40d41acc 100644
--- a/engines/gob/game_v6.cpp
+++ b/engines/gob/game_v6.cpp
@@ -31,9 +31,10 @@
#include "gob/game.h"
#include "gob/helper.h"
#include "gob/global.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/inter.h"
#include "gob/draw.h"
-#include "gob/parse.h"
namespace Gob {
@@ -48,27 +49,17 @@ void Game_v6::totSub(int8 flags, const char *newTotFile) {
if ((flags == 16) || (flags == 17))
warning("Urban Stub: Game_v6::totSub(), flags == %d", flags);
- if (_backupedCount >= 5)
+ if (_numEnvironments >= Environments::kEnvironmentCount)
return;
- _cursorHotspotXArray[_backupedCount] = _vm->_draw->_cursorHotspotXVar;
- _cursorHotspotYArray[_backupedCount] = _vm->_draw->_cursorHotspotYVar;
- _totTextDataArray[_backupedCount] = _totTextData;
- _totFileDataArray[_backupedCount] = _totFileData;
- _totResourceTableArray[_backupedCount] = _totResourceTable;
- _extTableArray[_backupedCount] = _extTable;
- _extHandleArray[_backupedCount] = _extHandle;
- _imFileDataArray[_backupedCount] = _imFileData;
- _variablesArray[_backupedCount] = _vm->_inter->_variables;
- strcpy(_curTotFileArray[_backupedCount], _curTotFile);
-
- curBackupPos = _curBackupPos;
- _backupedCount++;
- _curBackupPos = _backupedCount;
-
- _totTextData = 0;
- _totFileData = 0;
- _totResourceTable = 0;
+ _environments->set(_numEnvironments);
+
+ curBackupPos = _curEnvironment;
+ _numEnvironments++;
+ _curEnvironment = _numEnvironments;
+
+ _script = new Script(_vm);
+ _resources = new Resources(_vm);
if (flags & 0x80)
warning("Urban Stub: Game_v6::totSub(), flags & 0x80");
@@ -79,8 +70,10 @@ void Game_v6::totSub(int8 flags, const char *newTotFile) {
strncpy0(_curTotFile, newTotFile, 9);
strcat(_curTotFile, ".TOT");
- if (_vm->_inter->_terminate != 0)
+ if (_vm->_inter->_terminate != 0) {
+ clearUnusedEnvironment();
return;
+ }
pushCollisions(0);
@@ -99,22 +92,11 @@ void Game_v6::totSub(int8 flags, const char *newTotFile) {
_vm->_inter->delocateVars();
}
- _backupedCount--;
- _curBackupPos = curBackupPos;
-
- _vm->_draw->_cursorHotspotXVar = _cursorHotspotXArray[_backupedCount];
- _vm->_draw->_cursorHotspotYVar = _cursorHotspotYArray[_backupedCount];
- _totTextData = _totTextDataArray[_backupedCount];
- _totFileData = _totFileDataArray[_backupedCount];
- _totResourceTable = _totResourceTableArray[_backupedCount];
- _extTable = _extTableArray[_backupedCount];
- _extHandle = _extHandleArray[_backupedCount];
- _imFileData = _imFileDataArray[_backupedCount];
- _vm->_inter->_variables = _variablesArray[_backupedCount];
- strcpy(_curTotFile, _curTotFileArray[_backupedCount]);
- strcpy(_curExtFile, _curTotFile);
- _curExtFile[strlen(_curExtFile) - 4] = '\0';
- strcat(_curExtFile, ".EXT");
+ clearUnusedEnvironment();
+
+ _numEnvironments--;
+ _curEnvironment = curBackupPos;
+ _environments->get(_numEnvironments);
}
int16 Game_v6::addNewCollision(int16 id, uint16 left, uint16 top,
@@ -148,7 +130,7 @@ int16 Game_v6::addNewCollision(int16 id, uint16 left, uint16 top,
ptr->funcEnter = funcEnter;
ptr->funcLeave = funcLeave;
ptr->funcSub = funcSub;
- ptr->totFileData = _totFileData;
+ ptr->script = _script;
return i;
}
@@ -383,7 +365,6 @@ void Game_v6::collisionsBlock(void) {
int16 array[300];
byte count;
int16 collResId;
- byte *startIP;
int16 curCmd;
int16 cmd;
int16 cmdHigh;
@@ -397,7 +378,6 @@ void Game_v6::collisionsBlock(void) {
int16 stackPos2;
int16 descIndex;
int16 timeVal;
- int16 offsetIP;
char *str;
int16 i;
int16 counter;
@@ -406,10 +386,11 @@ void Game_v6::collisionsBlock(void) {
int16 collStackPos;
Collision *collPtr;
Collision *collArea;
- byte *savedIP;
byte collAreaStart;
int16 activeCollResId = 0;
int16 activeCollIndex = 0;
+ uint32 startPos;
+ uint32 offsetPos;
if (_shouldPushColls)
pushCollisions(0);
@@ -422,25 +403,25 @@ void Game_v6::collisionsBlock(void) {
_shouldPushColls = 0;
collResId = -1;
- _vm->_global->_inter_execPtr++;
- count = *_vm->_global->_inter_execPtr++;
+ _script->skip(1);
+ count = _script->readByte();
- _handleMouse = _vm->_global->_inter_execPtr[0];
- deltaTime = 1000 * _vm->_global->_inter_execPtr[1];
- stackPos2 = _vm->_global->_inter_execPtr[3];
- descIndex = _vm->_global->_inter_execPtr[4];
- byte var_42 = _vm->_global->_inter_execPtr[5];
+ _handleMouse = _script->peekByte(0);
+ deltaTime = 1000 * _script->peekByte(1);
+ stackPos2 = _script->peekByte(3);
+ descIndex = _script->peekByte(4);
+ byte var_42 = _script->peekByte(5);
if ((stackPos2 != 0) || (descIndex != 0)) {
deltaTime /= 100;
- if (_vm->_global->_inter_execPtr[1] == 100)
+ if (_script->peekByte(1) == 100)
deltaTime = 2;
}
timeVal = deltaTime;
- _vm->_global->_inter_execPtr += 6;
+ _script->skip(6);
- startIP = _vm->_global->_inter_execPtr;
+ startPos = _script->pos();
WRITE_VAR(16, 0);
byte var_41 = 0;
@@ -452,28 +433,27 @@ void Game_v6::collisionsBlock(void) {
for (curCmd = 0; curCmd < count; curCmd++) {
array[curCmd] = 0;
- cmd = *_vm->_global->_inter_execPtr++;
+ cmd = _script->readByte();
if ((cmd & 0x40) != 0) {
cmd -= 0x40;
- cmdHigh = *_vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr++;
+ cmdHigh = _script->readByte();
cmdHigh <<= 8;
} else
cmdHigh = 0;
if ((cmd & 0x80) != 0) {
- offsetIP = _vm->_global->_inter_execPtr - _totFileData;
- left = _vm->_parse->parseValExpr();
- top = _vm->_parse->parseValExpr();
- width = _vm->_parse->parseValExpr();
- height = _vm->_parse->parseValExpr();
+ offsetPos = _script->pos();
+ left = _script->readValExpr();
+ top = _script->readValExpr();
+ width = _script->readValExpr();
+ height = _script->readValExpr();
} else {
- offsetIP = 0;
- left = _vm->_inter->load16();
- top = _vm->_inter->load16();
- width = _vm->_inter->load16();
- height = _vm->_inter->load16();
+ offsetPos = 0;
+ left = _script->readUint16();
+ top = _script->readUint16();
+ width = _script->readUint16();
+ height = _script->readUint16();
}
if ((_vm->_draw->_renderFlags & RENDERFLAG_CAPTUREPOP) && (left != 0xFFFF)) {
@@ -496,45 +476,37 @@ void Game_v6::collisionsBlock(void) {
switch (cmd) {
case 0:
- _vm->_global->_inter_execPtr += 6;
- startIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(6);
+ startPos = _script->pos();
+ _script->skip(_script->peekUint16(2) + 2);
key = curCmd + 0xA000;
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
- cmd + cmdHigh, key, startIP - _totFileData,
- _vm->_global->_inter_execPtr - _totFileData, offsetIP);
+ cmd + cmdHigh, key, startPos,
+ _script->pos(), offsetPos);
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 1:
- key = _vm->_inter->load16();
- array[curCmd] = _vm->_inter->load16();
- flags = _vm->_inter->load16();
+ key = _script->readInt16();
+ array[curCmd] = _script->readInt16();
+ flags = _script->readInt16();
- startIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ startPos = _script->pos();
+ _script->skip(_script->peekUint16(2) + 2);
if (key == 0)
key = curCmd + 0xA000;
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
- (flags << 4) + cmd + cmdHigh, key, startIP - _totFileData,
- _vm->_global->_inter_execPtr - _totFileData, offsetIP);
+ (flags << 4) + cmd + cmdHigh, key, startPos,
+ _script->pos(), offsetPos);
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
@@ -548,23 +520,20 @@ void Game_v6::collisionsBlock(void) {
case 10:
_vm->_util->clearKeyBuf();
var_1C = 1;
- key = _vm->_parse->parseVarIndex();
- descArray[index].fontIndex = _vm->_inter->load16();
- descArray[index].backColor = *_vm->_global->_inter_execPtr++;
- descArray[index].frontColor = *_vm->_global->_inter_execPtr++;
+ key = _script->readVarIndex();
+ descArray[index].fontIndex = _script->readInt16();
+ descArray[index].backColor = _script->readByte();
+ descArray[index].frontColor = _script->readByte();
if ((cmd >= 5) && (cmd <= 8)) {
- descArray[index].ptr = _vm->_global->_inter_execPtr + 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr) + 2;
+ descArray[index].ptr = _script->getData() + _script->pos() + 2;
+ _script->skip(_script->peekUint16() + 2);
} else
descArray[index].ptr = 0;
if (left == 0xFFFF) {
if ((cmd & 1) == 0) {
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
}
break;
}
@@ -575,50 +544,44 @@ void Game_v6::collisionsBlock(void) {
funcLeave = 0;
if (!(cmd & 1))
- funcLeave = _vm->_global->_inter_execPtr - _totFileData;
+ funcLeave = _script->pos();
addNewCollision(curCmd + 0x8000, left, top, right,
top + height - 1, cmd, key, 0, funcLeave, 0);
if (!(cmd & 1)) {
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
}
index++;
break;
case 11:
- _vm->_global->_inter_execPtr += 6;
+ _script->skip(6);
for (i = 0; i < 150; i++) {
if ((_collisionAreas[i].id & 0xF000) == 0xE000) {
_collisionAreas[i].id &= 0xBFFF;
_collisionAreas[i].funcEnter =
- _vm->_global->_inter_execPtr - _totFileData;
+ _script->pos();
_collisionAreas[i].funcLeave =
- _vm->_global->_inter_execPtr - _totFileData;
+ _script->pos();
}
}
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 12:
- _vm->_global->_inter_execPtr += 6;
+ _script->skip(6);
for (i = 0; i < 150; i++) {
if ((_collisionAreas[i].id & 0xF000) == 0xD000) {
_collisionAreas[i].id &= 0xBFFF;
_collisionAreas[i].funcEnter =
- _vm->_global->_inter_execPtr - _totFileData;
+ _script->pos();
_collisionAreas[i].funcLeave =
- _vm->_global->_inter_execPtr - _totFileData;
+ _script->pos();
}
}
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 20:
@@ -626,34 +589,30 @@ void Game_v6::collisionsBlock(void) {
// Fall through to case 2
case 2:
- key = _vm->_inter->load16();
- array[curCmd] = _vm->_inter->load16();
- flags = _vm->_inter->load16();
+ key = _script->readInt16();
+ array[curCmd] = _script->readInt16();
+ flags = _script->readInt16();
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
(flags << 4) + cmdHigh + 2, key, 0,
- _vm->_global->_inter_execPtr - _totFileData, offsetIP);
+ _script->pos(), offsetPos);
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
case 21:
- key = _vm->_inter->load16();
- array[curCmd] = _vm->_inter->load16();
- flags = _vm->_inter->load16() & 3;
+ key = _script->readInt16();
+ array[curCmd] = _script->readInt16();
+ flags = _script->readInt16() & 3;
addNewCollision(curCmd + 0x8000, left, top,
left + width - 1, top + height - 1,
(flags << 4) + cmdHigh + 2, key,
- _vm->_global->_inter_execPtr - _totFileData, 0, offsetIP);
+ _script->pos(), 0, offsetPos);
- _vm->_global->_inter_execPtr += 2;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _script->skip(_script->peekUint16(2) + 2);
break;
}
@@ -915,10 +874,8 @@ void Game_v6::collisionsBlock(void) {
if (_handleMouse == 1)
_vm->_draw->blitCursor();
- savedIP = 0;
if (!_vm->_inter->_terminate && (var_41 == 0)) {
- savedIP = _totFileData +
- _collisionAreas[activeCollIndex].funcLeave;
+ _script->seek(_collisionAreas[activeCollIndex].funcLeave);
_vm->_inter->storeMouse();
if (VAR(16) == 0) {
@@ -927,7 +884,8 @@ void Game_v6::collisionsBlock(void) {
else
WRITE_VAR(16, activeCollResId & 0xFFF);
}
- }
+ } else
+ _script->setFinished(true);
for (curCmd = 0; curCmd < count; curCmd++)
freeCollision(curCmd + 0x8000);
@@ -937,8 +895,6 @@ void Game_v6::collisionsBlock(void) {
((_collisionAreas[i].id & 0xF000) == 0x9000))
_collisionAreas[i].id |= 0x4000;
}
-
- _vm->_global->_inter_execPtr = savedIP;
}
void Game_v6::setCollisions(byte arg_0) {
@@ -950,23 +906,22 @@ void Game_v6::setCollisions(byte arg_0) {
if (collArea->flags & 0x80)
continue;
- byte *totFileData = collArea->totFileData;
-
- if (!totFileData)
- totFileData = _totFileData;
+ Script *curScript = _script;
- byte *savedIP = _vm->_global->_inter_execPtr;
+ _script = collArea->script;
+ if (!_script)
+ _script = curScript;
- _vm->_global->_inter_execPtr = totFileData + collArea->funcSub;
+ _script->call(collArea->funcSub);
- int16 left = _vm->_parse->parseValExpr();
- int16 top = _vm->_parse->parseValExpr();
- int16 width = _vm->_parse->parseValExpr();
- int16 height = _vm->_parse->parseValExpr();
+ int16 left = _script->readValExpr();
+ int16 top = _script->readValExpr();
+ int16 width = _script->readValExpr();
+ int16 height = _script->readValExpr();
uint16 flags = 0;
if ((collArea->id & 0xF000) == 0xA000)
- flags = _vm->_parse->parseValExpr();
+ flags = _script->readValExpr();
if ((_vm->_draw->_renderFlags & RENDERFLAG_CAPTUREPOP) &&
(left != -1)) {
@@ -1001,16 +956,18 @@ void Game_v6::setCollisions(byte arg_0) {
if ((collArea->id & 0xF000) == 0xA000)
collArea->flags = flags;
- _vm->_global->_inter_execPtr = savedIP;
+ _script->pop();
+
+ _script = curScript;
}
}
void Game_v6::collSub(uint16 offset) {
- byte *savedIP;
int16 collStackSize;
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _totFileData + offset;
+ uint32 savedPos = _script->pos();
+
+ _script->seek(offset);
_shouldPushColls = 1;
collStackSize = _collStackSize;
@@ -1021,7 +978,8 @@ void Game_v6::collSub(uint16 offset) {
popCollisions();
_shouldPushColls = 0;
- _vm->_global->_inter_execPtr = savedIP;
+
+ _script->seek(savedPos);
if ((_vm->_util->getTimeKey() - _someTimeDly) > 500)
setCollisions(0);
diff --git a/engines/gob/global.cpp b/engines/gob/global.cpp
index 005d65815f..4165938966 100644
--- a/engines/gob/global.cpp
+++ b/engines/gob/global.cpp
@@ -37,35 +37,36 @@ Global::Global(GobEngine *vm) : _vm(vm) {
_presentVGA = UNDEF;
_presentHER = UNDEF;
- _videoMode = 0;
+ _videoMode = 0;
_fakeVideoMode = 0;
- _oldMode = 3;
+ _oldMode = 3;
_soundFlags = 0;
- _language = 0x8000;
+ _language = 0x8000;
_languageWanted = 0x8000;
+ _foundLanguage = false;
- _useMouse = UNDEF;
+ _useMouse = UNDEF;
_mousePresent = UNDEF;
- _mouseXShift = 3;
- _mouseYShift = 3;
+ _mouseXShift = 3;
+ _mouseYShift = 3;
- _mouseMinX = 0;
- _mouseMinY = 0;
+ _mouseMinX = 0;
+ _mouseMinY = 0;
_mouseMaxX = 320;
_mouseMaxY = 200;
_useJoystick = 1;
- _primaryWidth = 0;
+ _primaryWidth = 0;
_primaryHeight = 0;
_colorCount = 16;
for (int i = 0; i < 256; i++) {
- _redPalette[i] = 0;
+ _redPalette [i] = 0;
_greenPalette[i] = 0;
- _bluePalette[i] = 0;
+ _bluePalette [i] = 0;
}
_unusedPalette1[ 0] = (int16) 0x0000;
@@ -109,15 +110,12 @@ Global::Global(GobEngine *vm) : _vm(vm) {
_pPaletteDesc = 0;
- _setAllPalette = false;
+ _setAllPalette = false;
_dontSetPalette = false;
_debugFlag = 0;
_inVM = 0;
- _inter_resStr[0] = 0;
- _inter_resVal = 0;
-
_inter_execPtr = 0;
_inter_animDataSize = 10;
diff --git a/engines/gob/global.h b/engines/gob/global.h
index 9f12f4ded6..982ce113cb 100644
--- a/engines/gob/global.h
+++ b/engines/gob/global.h
@@ -33,37 +33,51 @@
namespace Gob {
-#define VIDMODE_CGA 0x05
-#define VIDMODE_EGA 0x0D
-#define VIDMODE_VGA 0x13
-#define VIDMODE_HER 7
-
-#define PROAUDIO_FLAG 0x10
-#define ADLIB_FLAG 0x08
-#define BLASTER_FLAG 0x04
-#define INTERSOUND_FLAG 0x02
-#define SPEAKER_FLAG 0x01
-#define MIDI_FLAG 0x4000
-
-#define NO 0
-#define YES 1
-#define UNDEF 2
-
-#define F1_KEY 0x3B00
-#define F2_KEY 0x3C00
-#define F3_KEY 0x3D00
-#define F4_KEY 0x3E00
-#define F5_KEY 0x3F00
-#define F6_KEY 0x4000
-#define ESCAPE 0x001B
-#define ENTER 0x000D
+#define VIDMODE_CGA 0x05
+#define VIDMODE_EGA 0x0D
+#define VIDMODE_VGA 0x13
+#define VIDMODE_HER 0x07
+
+#define MIDI_FLAG 0x4000
+#define PROAUDIO_FLAG 0x0010
+#define ADLIB_FLAG 0x0008
+#define BLASTER_FLAG 0x0004
+#define INTERSOUND_FLAG 0x0002
+#define SPEAKER_FLAG 0x0001
+
+#define NO 0
+#define YES 1
+#define UNDEF 2
+
+#define F1_KEY 0x3B00
+#define F2_KEY 0x3C00
+#define F3_KEY 0x3D00
+#define F4_KEY 0x3E00
+#define F5_KEY 0x3F00
+#define F6_KEY 0x4000
+#define ESCAPE 0x001B
+#define ENTER 0x000D
/* Video drivers */
-#define UNK_DRIVER 0
-#define VGA_DRIVER 1
-#define EGA_DRIVER 2
-#define CGA_DRIVER 3
-#define HER_DRIVER 4
+#define UNK_DRIVER 0
+#define VGA_DRIVER 1
+#define EGA_DRIVER 2
+#define CGA_DRIVER 3
+#define HER_DRIVER 4
+
+enum Language {
+ kLanguageFrench = 0,
+ kLanguageGerman = 1,
+ kLanguageBritish = 2,
+ kLanguageSpanish = 3,
+ kLanguageItalian = 4,
+ kLanguageAmerican = 5,
+ kLanguageDutch = 6,
+ kLanguageKorean = 7,
+ kLanguageHebrew = 8,
+ kLanguagePortuguese = 9,
+ kLanguageJapanese = 10
+};
class Global {
public:
@@ -82,6 +96,7 @@ public:
uint16 _language;
uint16 _languageWanted;
+ bool _foundLanguage;
char _useMouse;
int16 _mousePresent;
@@ -117,9 +132,6 @@ public:
int16 _debugFlag;
int16 _inVM;
- char _inter_resStr[200];
- int32 _inter_resVal;
-
byte *_inter_execPtr;
int16 _inter_animDataSize;
diff --git a/engines/gob/gob.cpp b/engines/gob/gob.cpp
index 1de6245297..e534464cce 100644
--- a/engines/gob/gob.cpp
+++ b/engines/gob/gob.cpp
@@ -47,7 +47,6 @@
#include "gob/map.h"
#include "gob/mult.h"
#include "gob/palanim.h"
-#include "gob/parse.h"
#include "gob/scenery.h"
#include "gob/videoplayer.h"
#include "gob/save/saveload.h"
@@ -102,12 +101,12 @@ void PauseDialog::handleKeyDown(Common::KeyState state) {
GobEngine::GobEngine(OSystem *syst) : Engine(syst) {
- _sound = 0; _mult = 0; _game = 0;
- _global = 0; _dataIO = 0; _goblin = 0;
- _vidPlayer = 0; _init = 0; _inter = 0;
- _map = 0; _palAnim = 0; _parse = 0;
- _scenery = 0; _draw = 0; _util = 0;
- _video = 0; _saveLoad = 0;
+ _sound = 0; _mult = 0; _game = 0;
+ _global = 0; _dataIO = 0; _goblin = 0;
+ _vidPlayer = 0; _init = 0; _inter = 0;
+ _map = 0; _palAnim = 0; _scenery = 0;
+ _draw = 0; _util = 0; _video = 0;
+ _saveLoad = 0;
_pauseStart = 0;
@@ -121,7 +120,7 @@ GobEngine::GobEngine(OSystem *syst) : Engine(syst) {
Common::addDebugChannel(kDebugDrawOp, "DrawOpcodes", "Script DrawOpcodes debug level");
Common::addDebugChannel(kDebugGobOp, "GoblinOpcodes", "Script GoblinOpcodes debug level");
Common::addDebugChannel(kDebugSound, "Sound", "Sound output debug level");
- Common::addDebugChannel(kDebugParser, "Parser", "Parser debug level");
+ Common::addDebugChannel(kDebugExpression, "Expression", "Expression parser debug level");
Common::addDebugChannel(kDebugGameFlow, "Gameflow", "Gameflow debug level");
Common::addDebugChannel(kDebugFileIO, "FileIO", "File Input/Output debug level");
Common::addDebugChannel(kDebugSaveLoad, "SaveLoad", "Saving/Loading debug level");
@@ -248,42 +247,42 @@ Common::Error GobEngine::run() {
switch (_language) {
case Common::FR_FRA:
case Common::RU_RUS:
- _global->_language = 0;
+ _global->_language = kLanguageFrench;
break;
case Common::DE_DEU:
- _global->_language = 1;
+ _global->_language = kLanguageGerman;
break;
case Common::EN_ANY:
case Common::EN_GRB:
- _global->_language = 2;
+ case Common::HU_HUN:
+ _global->_language = kLanguageBritish;
break;
case Common::ES_ESP:
- _global->_language = 3;
+ _global->_language = kLanguageSpanish;
break;
case Common::IT_ITA:
- _global->_language = 4;
+ _global->_language = kLanguageItalian;
break;
case Common::EN_USA:
- _global->_language = 5;
+ _global->_language = kLanguageAmerican;
break;
case Common::NL_NLD:
- _global->_language = 6;
+ _global->_language = kLanguageDutch;
break;
case Common::KO_KOR:
- _global->_language = 7;
+ _global->_language = kLanguageKorean;
break;
case Common::HB_ISR:
- _global->_language = 8;
+ _global->_language = kLanguageHebrew;
break;
case Common::PT_BRA:
- _global->_language = 9;
+ _global->_language = kLanguagePortuguese;
break;
case Common::JA_JPN:
- _global->_language = 10;
+ _global->_language = kLanguageJapanese;
break;
default:
- // Default to English
- _global->_language = 2;
+ _global->_language = kLanguageBritish;
break;
}
_global->_languageWanted = _global->_language;
@@ -332,7 +331,6 @@ bool GobEngine::initGameParts() {
_palAnim = new PalAnim(this);
_vidPlayer = new VideoPlayer(this);
_sound = new Sound(this);
- _parse = new Parse(this);
switch (_gameType) {
case kGameTypeGeisha:
@@ -465,6 +463,8 @@ bool GobEngine::initGameParts() {
break;
}
+ _inter->setupOpcodes();
+
if (is640()) {
_video->_surfWidth = _width = 640;
_video->_surfHeight = _video->_splitHeight1 = _height = 480;
@@ -495,7 +495,6 @@ void GobEngine::deinitGameParts() {
delete _inter; _inter = 0;
delete _map; _map = 0;
delete _palAnim; _palAnim = 0;
- delete _parse; _parse = 0;
delete _scenery; _scenery = 0;
delete _draw; _draw = 0;
delete _util; _util = 0;
diff --git a/engines/gob/gob.h b/engines/gob/gob.h
index 43e2270354..5d1cb3ecf2 100644
--- a/engines/gob/gob.h
+++ b/engines/gob/gob.h
@@ -52,7 +52,6 @@ class Inter;
class Map;
class Mult;
class PalAnim;
-class Parse;
class Scenery;
class Util;
class SaveLoad;
@@ -128,7 +127,7 @@ enum {
kDebugDrawOp = 1 << 1,
kDebugGobOp = 1 << 2,
kDebugSound = 1 << 3,
- kDebugParser = 1 << 4,
+ kDebugExpression = 1 << 4,
kDebugGameFlow = 1 << 5,
kDebugFileIO = 1 << 6,
kDebugSaveLoad = 1 << 7,
@@ -197,7 +196,6 @@ public:
Map *_map;
Mult *_mult;
PalAnim *_palAnim;
- Parse *_parse;
Scenery *_scenery;
Inter *_inter;
SaveLoad *_saveLoad;
diff --git a/engines/gob/init.cpp b/engines/gob/init.cpp
index 8bf9536286..f9a22f52fb 100644
--- a/engines/gob/init.cpp
+++ b/engines/gob/init.cpp
@@ -32,6 +32,7 @@
#include "gob/dataio.h"
#include "gob/draw.h"
#include "gob/game.h"
+#include "gob/script.h"
#include "gob/palanim.h"
#include "gob/inter.h"
#include "gob/video.h"
@@ -80,9 +81,6 @@ void Init::doDemo() {
}
void Init::initGame() {
- int16 handle2;
- int16 handle;
- int16 imdHandle;
byte *infBuf;
char *infPtr;
char *infEnd;
@@ -91,11 +89,8 @@ void Init::initGame() {
initVideo();
if (!_vm->isDemo()) {
- handle2 = _vm->_dataIO->openData(_vm->_startStk.c_str());
- if (handle2 >= 0) {
- _vm->_dataIO->closeData(handle2);
+ if (_vm->_dataIO->existData(_vm->_startStk.c_str()))
_vm->_dataIO->openDataFile(_vm->_startStk.c_str());
- }
}
_vm->_util->initInput();
@@ -104,8 +99,6 @@ void Init::initGame() {
_vm->_global->_mouseXShift = 1;
_vm->_global->_mouseYShift = 1;
- _vm->_game->_totTextData = 0;
- _vm->_game->_totFileData = 0;
_palDesc = new Video::PalDesc;
_vm->validateVideoMode(_vm->_global->_videoMode);
@@ -127,19 +120,13 @@ void Init::initGame() {
return;
}
- handle = _vm->_dataIO->openData("intro.inf");
+ if (!_vm->_dataIO->existData("intro.inf")) {
- if (handle < 0) {
- for (int i = 0; i < 4; i++) {
- handle2 = _vm->_dataIO->openData(_fontNames[i]);
- if (handle2 >= 0) {
- _vm->_dataIO->closeData(handle2);
+ for (int i = 0; i < 4; i++)
+ if (_vm->_dataIO->existData(_fontNames[i]))
_vm->_draw->_fonts[i] = _vm->_util->loadFont(_fontNames[i]);
- }
- }
- } else {
- _vm->_dataIO->closeData(handle);
+ } else {
infBuf = _vm->_dataIO->getData("intro.inf");
infPtr = (char *) infBuf;
@@ -153,11 +140,8 @@ void Init::initGame() {
buffer[j] = 0;
strcat(buffer, ".let");
- handle2 = _vm->_dataIO->openData(buffer);
- if (handle2 >= 0) {
- _vm->_dataIO->closeData(handle2);
+ if (_vm->_dataIO->existData(buffer))
_vm->_draw->_fonts[i] = _vm->_util->loadFont(buffer);
- }
if ((infPtr + 1) >= infEnd)
break;
@@ -167,26 +151,16 @@ void Init::initGame() {
delete[] infBuf;
}
- strcpy(buffer, _vm->_startTot.c_str());
- handle = _vm->_dataIO->openData(buffer);
+ if (_vm->_dataIO->existData(_vm->_startTot.c_str())) {
+ _vm->_inter->allocateVars(Script::getVariablesCount(_vm->_startTot.c_str(), _vm));
- if (handle >= 0) {
- DataStream *stream = _vm->_dataIO->openAsStream(handle, true);
-
- stream->seek(0x2C);
- _vm->_inter->allocateVars(stream->readUint16LE());
-
- delete stream;
-
- strcpy(_vm->_game->_curTotFile, buffer);
+ strcpy(_vm->_game->_curTotFile, _vm->_startTot.c_str());
_vm->_sound->cdTest(1, "GOB");
_vm->_sound->cdLoadLIC("gob.lic");
// Search for a Coktel logo animation or image to display
- imdHandle = _vm->_dataIO->openData("coktel.imd");
- if (imdHandle >= 0) {
- _vm->_dataIO->closeData(imdHandle);
+ if (_vm->_dataIO->existData("coktel.imd")) {
_vm->_draw->initScreen();
_vm->_draw->_cursorIndex = -1;
@@ -198,19 +172,17 @@ void Init::initGame() {
}
_vm->_draw->closeScreen();
- } else if ((imdHandle = _vm->_dataIO->openData("coktel.clt")) >= 0) {
+ } else if (_vm->_dataIO->existData("coktel.clt")) {
_vm->_draw->initScreen();
-
- stream = _vm->_dataIO->openAsStream(imdHandle, true);
_vm->_util->clearPalette();
+
+ DataStream *stream = _vm->_dataIO->getDataStream("coktel.clt");
stream->read((byte *) _vm->_draw->_vgaPalette, 768);
delete stream;
- imdHandle = _vm->_dataIO->openData("coktel.ims");
- if (imdHandle >= 0) {
+ if (_vm->_dataIO->existData("coktel.ims")) {
byte *sprBuf;
- _vm->_dataIO->closeData(imdHandle);
sprBuf = _vm->_dataIO->getData("coktel.ims");
_vm->_video->drawPackedSprite(sprBuf, 320, 200, 0, 0, 0,
*_vm->_draw->_frontSurface);
diff --git a/engines/gob/inter.cpp b/engines/gob/inter.cpp
index ce7f2ba319..8be07034c6 100644
--- a/engines/gob/inter.cpp
+++ b/engines/gob/inter.cpp
@@ -33,7 +33,8 @@
#include "gob/util.h"
#include "gob/draw.h"
#include "gob/game.h"
-#include "gob/parse.h"
+#include "gob/expression.h"
+#include "gob/script.h"
#include "gob/scenery.h"
#include "gob/sound/sound.h"
@@ -67,65 +68,93 @@ Inter::~Inter() {
delocateVars();
}
-void Inter::initControlVars(char full) {
- *_nestLevel = 0;
- *_breakFromLevel = -1;
+void Inter::setupOpcodes() {
+ setupOpcodesDraw();
+ setupOpcodesFunc();
+ setupOpcodesGob();
+}
- *_vm->_scenery->_pCaptureCounter = 0;
+void Inter::executeOpcodeDraw(byte i) {
+ debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%X] (%s)", i, i, getDescOpcodeDraw(i));
- _break = false;
- _terminate = 0;
+ if (_opcodesDraw[i].proc && _opcodesDraw[i].proc->isValid())
+ (*_opcodesDraw[i].proc)();
+ else
+ warning("unimplemented opcodeDraw: %d [0x%X]", i, i);
+}
- if (full == 1) {
- for (int i = 0; i < 8; i++)
- _animPalDir[i] = 0;
- _soundEndTimeKey = 0;
+bool Inter::executeOpcodeFunc(byte i, byte j, OpFuncParams &params) {
+ debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%X.0x%X] (%s)",
+ i, j, i, j, getDescOpcodeFunc(i, j));
+
+ if ((i > 4) || (j > 15)) {
+ warning("unimplemented opcodeFunc: %d.%d [0x%X.0x%X]", i, j, i, j);
+ return false;
}
+
+ i = i * 16 + j;
+ if (_opcodesFunc[i].proc && _opcodesFunc[i].proc->isValid())
+ return (*_opcodesFunc[i].proc)(params);
+ else
+ warning("unimplemented opcodeFunc: %d.%d [0x%X.0x%X]", i, j, i, j);
+
+ return false;
}
-int16 Inter::load16() {
- int16 tmp = (int16) READ_LE_UINT16(_vm->_global->_inter_execPtr);
- _vm->_global->_inter_execPtr += 2;
- return tmp;
+void Inter::executeOpcodeGob(int i, OpGobParams &params) {
+ debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%X] (%s)",
+ i, i, getDescOpcodeGob(i));
+
+ OpcodeEntry<OpcodeGob> *op = 0;
+
+ if (_opcodesGob.contains(i))
+ op = &_opcodesGob.getVal(i);
+
+ if (op && op->proc && op->proc->isValid()) {
+ (*op->proc)(params);
+ return;
+ }
+
+ _vm->_game->_script->skip(params.paramCount << 1);
+ warning("unimplemented opcodeGob: %d [0x%X]", i, i);
}
-char Inter::evalExpr(int16 *pRes) {
- byte token;
+const char *Inter::getDescOpcodeDraw(byte i) {
+ const char *desc = _opcodesDraw[i].desc;
- _vm->_parse->printExpr(99);
+ return ((desc) ? desc : "");
+}
- _vm->_parse->parseExpr(99, &token);
- if (!pRes)
- return token;
+const char *Inter::getDescOpcodeFunc(byte i, byte j) {
+ if ((i > 4) || (j > 15))
+ return "";
- switch (token) {
- case 20:
- *pRes = _vm->_global->_inter_resVal;
- break;
+ const char *desc = _opcodesFunc[i * 16 + j].desc;
- case 22:
- case 23:
- *pRes = 0;
- break;
+ return ((desc) ? desc : "");
+}
- case 24:
- *pRes = 1;
- break;
- }
+const char *Inter::getDescOpcodeGob(int i) {
+ if (_opcodesGob.contains(i))
+ return _opcodesGob.getVal(i).desc;
- return token;
+ return "";
}
-bool Inter::evalBoolResult() {
- byte token;
+void Inter::initControlVars(char full) {
+ *_nestLevel = 0;
+ *_breakFromLevel = -1;
+
+ *_vm->_scenery->_pCaptureCounter = 0;
- _vm->_parse->printExpr(99);
+ _break = false;
+ _terminate = 0;
- _vm->_parse->parseExpr(99, &token);
- if ((token == 24) || ((token == 20) && _vm->_global->_inter_resVal))
- return true;
- else
- return false;
+ if (full == 1) {
+ for (int i = 0; i < 8; i++)
+ _animPalDir[i] = 0;
+ _soundEndTimeKey = 0;
+ }
}
void Inter::renewTimeInVars() {
@@ -185,14 +214,14 @@ void Inter::storeKey(int16 key) {
void Inter::writeVar(uint32 offset, uint16 type, uint32 value) {
switch (type) {
- case 16:
- case 18:
+ case TYPE_VAR_INT8:
+ case TYPE_ARRAY_INT8:
WRITE_VARO_UINT8(offset, value);
break;
- case 17:
- case 24:
- case 27:
+ case TYPE_VAR_INT16:
+ case TYPE_VAR_INT32_AS_INT16:
+ case TYPE_ARRAY_INT16:
WRITE_VARO_UINT16(offset, value);
break;
@@ -209,20 +238,20 @@ void Inter::funcBlock(int16 retFlag) {
params.retFlag = retFlag;
- if (!_vm->_global->_inter_execPtr)
+ if (_vm->_game->_script->isFinished())
return;
_break = false;
- _vm->_global->_inter_execPtr++;
- params.cmdCount = *_vm->_global->_inter_execPtr++;
- _vm->_global->_inter_execPtr += 2;
+ _vm->_game->_script->skip(1);
+ params.cmdCount = _vm->_game->_script->readByte();
+ _vm->_game->_script->skip(2);
if (params.cmdCount == 0) {
- _vm->_global->_inter_execPtr = 0;
+ _vm->_game->_script->setFinished(true);
return;
}
- int startaddr = _vm->_global->_inter_execPtr - _vm->_game->_totFileData;
+ int startaddr = _vm->_game->_script->pos();
params.counter = 0;
do {
@@ -237,7 +266,7 @@ void Inter::funcBlock(int16 retFlag) {
(_vm->getPlatform() == Common::kPlatformMacintosh) ||
(_vm->getPlatform() == Common::kPlatformWindows))) {
- int addr = _vm->_global->_inter_execPtr-_vm->_game->_totFileData;
+ int addr = _vm->_game->_script->pos();
if ((startaddr == 0x18B4 && addr == 0x1A7F && // Zombie, EGA
!strncmp(_vm->_game->_curTotFile, "avt005.tot", 10)) ||
@@ -263,20 +292,19 @@ void Inter::funcBlock(int16 retFlag) {
} // End of workaround
- cmd = *_vm->_global->_inter_execPtr;
+ cmd = _vm->_game->_script->readByte();
if ((cmd >> 4) >= 12) {
cmd2 = 16 - (cmd >> 4);
cmd &= 0xF;
} else
cmd2 = 0;
- _vm->_global->_inter_execPtr++;
params.counter++;
if (cmd2 == 0)
cmd >>= 4;
- if (executeFuncOpcode(cmd2, cmd, params))
+ if (executeOpcodeFunc(cmd2, cmd, params))
return;
if (_vm->shouldQuit())
@@ -292,17 +320,17 @@ void Inter::funcBlock(int16 retFlag) {
}
} while (params.counter != params.cmdCount);
- _vm->_global->_inter_execPtr = 0;
+ _vm->_game->_script->setFinished(true);
return;
}
void Inter::callSub(int16 retFlag) {
byte block;
- while (!_vm->shouldQuit() && _vm->_global->_inter_execPtr &&
- (_vm->_global->_inter_execPtr != _vm->_game->_totFileData)) {
+ while (!_vm->shouldQuit() && !_vm->_game->_script->isFinished() &&
+ (_vm->_game->_script->pos() != 0)) {
- block = *_vm->_global->_inter_execPtr;
+ block = _vm->_game->_script->peekByte();
if (block == 1)
funcBlock(retFlag);
else if (block == 2)
@@ -311,7 +339,7 @@ void Inter::callSub(int16 retFlag) {
error("Unknown block type %d in Inter::callSub()", block);
}
- if (_vm->_global->_inter_execPtr == _vm->_game->_totFileData)
+ if (!_vm->_game->_script->isFinished() && (_vm->_game->_script->pos() == 0))
_terminate = 1;
}
diff --git a/engines/gob/inter.h b/engines/gob/inter.h
index 412c3f2673..d4ed2d3240 100644
--- a/engines/gob/inter.h
+++ b/engines/gob/inter.h
@@ -26,6 +26,9 @@
#ifndef GOB_INTER_H
#define GOB_INTER_H
+#include "common/func.h"
+#include "common/hashmap.h"
+
#include "gob/goblin.h"
#include "gob/variables.h"
@@ -34,11 +37,54 @@ namespace Gob {
// This is to help devices with small memory (PDA, smartphones, ...)
// to save abit of memory used by opcode names in the Scumm engine.
#ifndef REDUCE_MEMORY_USAGE
-# define _OPCODE(ver, x) { &ver::x, #x }
+ #define _OPCODEDRAW(ver, x) setProc(new Common::Functor0Mem<void, ver>(this, &ver::x), #x)
+ #define _OPCODEFUNC(ver, x) setProc(new Common::Functor1Mem<OpFuncParams &, bool, ver>(this, &ver::x), #x)
+ #define _OPCODEGOB(ver, x) setProc(new Common::Functor1Mem<OpGobParams &, void, ver>(this, &ver::x), #x)
#else
-# define _OPCODE(ver, x) { &ver::x, "" }
+ #define _OPCODEDRAW(ver, x) setProc(new Common::Functor0Mem<void, ver>(this, &ver::x), "")
+ #define _OPCODEFUNC(ver, x) setProc(new Common::Functor1Mem<OpFuncParams &, bool, ver>(this, &ver::x), "")
+ #define _OPCODEGOB(ver, x) setProc(new Common::Functor1Mem<OpGobParams &, void, ver>(this, &ver::x), "")
#endif
+#define CLEAROPCODEDRAW(i) _opcodesDraw[i].setProc(0, 0)
+#define CLEAROPCODEFUNC(i) _opcodesFunc[i].setProc(0, 0)
+#define CLEAROPCODEGOB(i) _opcodesGob.erase(i)
+
+typedef Common::Functor0<void> OpcodeDraw;
+typedef Common::Functor1<struct OpFuncParams &, bool> OpcodeFunc;
+typedef Common::Functor1<struct OpGobParams &, void> OpcodeGob;
+
+struct OpFuncParams {
+ byte cmdCount;
+ byte counter;
+ int16 retFlag;
+};
+struct OpGobParams {
+ int16 extraData;
+ int16 paramCount;
+ VariableReference retVarPtr;
+ Goblin::Gob_Object *objDesc;
+};
+
+template<typename T>
+struct OpcodeEntry : Common::NonCopyable {
+ T *proc;
+ const char *desc;
+
+ OpcodeEntry() : proc(0), desc(0) {}
+ ~OpcodeEntry() {
+ setProc(0, 0);
+ }
+
+ void setProc(T *p, const char *d) {
+ if (proc != p) {
+ delete proc;
+ proc = p;
+ }
+ desc = d;
+ }
+};
+
class Inter {
public:
uint8 _terminate;
@@ -51,10 +97,9 @@ public:
Variables *_variables;
+ void setupOpcodes();
+
void initControlVars(char full);
- int16 load16();
- char evalExpr(int16 *pRes);
- bool evalBoolResult();
void renewTimeInVars();
void storeMouse();
void storeKey(int16 key);
@@ -74,16 +119,9 @@ public:
virtual ~Inter();
protected:
- struct OpFuncParams {
- byte cmdCount;
- byte counter;
- int16 retFlag;
- };
- struct OpGobParams {
- int16 extraData;
- VariableReference retVarPtr;
- Goblin::Gob_Object *objDesc;
- };
+ OpcodeEntry<OpcodeDraw> _opcodesDraw[256];
+ OpcodeEntry<OpcodeFunc> _opcodesFunc[256];
+ Common::HashMap<int, OpcodeEntry<OpcodeGob> > _opcodesGob;
bool _break;
@@ -99,15 +137,19 @@ protected:
GobEngine *_vm;
- virtual void setupOpcodes() = 0;
- virtual void executeDrawOpcode(byte i) = 0;
- virtual bool executeFuncOpcode(byte i, byte j, OpFuncParams &params) = 0;
- virtual void executeGoblinOpcode(int i, OpGobParams &params) = 0;
- virtual const char *getOpcodeDrawDesc(byte i) = 0;
- virtual const char *getOpcodeFuncDesc(byte i, byte j) = 0;
- virtual const char *getOpcodeGoblinDesc(int i) = 0;
+ void executeOpcodeDraw(byte i);
+ bool executeOpcodeFunc(byte i, byte j, OpFuncParams &params);
+ void executeOpcodeGob(int i, OpGobParams &params);
+
+ const char *getDescOpcodeDraw(byte i);
+ const char *getDescOpcodeFunc(byte i, byte j);
+ const char *getDescOpcodeGob(int i);
- virtual void checkSwitchTable(byte **ppExec) = 0;
+ virtual void setupOpcodesDraw() = 0;
+ virtual void setupOpcodesFunc() = 0;
+ virtual void setupOpcodesGob() = 0;
+
+ virtual void checkSwitchTable(uint32 &offset) = 0;
void o_drawNOP() {}
bool o_funcNOP(OpFuncParams &params) { return false; }
@@ -123,35 +165,11 @@ public:
virtual void animPalette();
protected:
- typedef void (Inter_v1::*OpcodeDrawProcV1)();
- typedef bool (Inter_v1::*OpcodeFuncProcV1)(OpFuncParams &);
- typedef void (Inter_v1::*OpcodeGoblinProcV1)(OpGobParams &);
- struct OpcodeDrawEntryV1 {
- OpcodeDrawProcV1 proc;
- const char *desc;
- };
- struct OpcodeFuncEntryV1 {
- OpcodeFuncProcV1 proc;
- const char *desc;
- };
- struct OpcodeGoblinEntryV1 {
- OpcodeGoblinProcV1 proc;
- const char *desc;
- };
- const OpcodeDrawEntryV1 *_opcodesDrawV1;
- const OpcodeFuncEntryV1 *_opcodesFuncV1;
- const OpcodeGoblinEntryV1 *_opcodesGoblinV1;
- static const int _goblinFuncLookUp[][2];
-
- virtual void setupOpcodes();
- virtual void executeDrawOpcode(byte i);
- virtual bool executeFuncOpcode(byte i, byte j, OpFuncParams &params);
- virtual void executeGoblinOpcode(int i, OpGobParams &params);
- virtual const char *getOpcodeDrawDesc(byte i);
- virtual const char *getOpcodeFuncDesc(byte i, byte j);
- virtual const char *getOpcodeGoblinDesc(int i);
-
- virtual void checkSwitchTable(byte **ppExec);
+ virtual void setupOpcodesDraw();
+ virtual void setupOpcodesFunc();
+ virtual void setupOpcodesGob();
+
+ virtual void checkSwitchTable(uint32 &offset);
void o1_loadMult();
void o1_playMult();
@@ -318,35 +336,11 @@ public:
virtual void animPalette();
protected:
- typedef void (Inter_v2::*OpcodeDrawProcV2)();
- typedef bool (Inter_v2::*OpcodeFuncProcV2)(OpFuncParams &);
- typedef void (Inter_v2::*OpcodeGoblinProcV2)(OpGobParams &);
- struct OpcodeDrawEntryV2 {
- OpcodeDrawProcV2 proc;
- const char *desc;
- };
- struct OpcodeFuncEntryV2 {
- OpcodeFuncProcV2 proc;
- const char *desc;
- };
- struct OpcodeGoblinEntryV2 {
- OpcodeGoblinProcV2 proc;
- const char *desc;
- };
- const OpcodeDrawEntryV2 *_opcodesDrawV2;
- const OpcodeFuncEntryV2 *_opcodesFuncV2;
- const OpcodeGoblinEntryV2 *_opcodesGoblinV2;
- static const int _goblinFuncLookUp[][2];
-
- virtual void setupOpcodes();
- virtual void executeDrawOpcode(byte i);
- virtual bool executeFuncOpcode(byte i, byte j, OpFuncParams &params);
- virtual void executeGoblinOpcode(int i, OpGobParams &params);
- virtual const char *getOpcodeDrawDesc(byte i);
- virtual const char *getOpcodeFuncDesc(byte i, byte j);
- virtual const char *getOpcodeGoblinDesc(int i);
-
- virtual void checkSwitchTable(byte **ppExec);
+ virtual void setupOpcodesDraw();
+ virtual void setupOpcodesFunc();
+ virtual void setupOpcodesGob();
+
+ virtual void checkSwitchTable(uint32 &offset);
void o2_playMult();
void o2_freeMultKeys();
@@ -410,33 +404,9 @@ public:
virtual ~Inter_Bargon() {}
protected:
- typedef void (Inter_Bargon::*OpcodeDrawProcBargon)();
- typedef bool (Inter_Bargon::*OpcodeFuncProcBargon)(OpFuncParams &);
- typedef void (Inter_Bargon::*OpcodeGoblinProcBargon)(OpGobParams &);
- struct OpcodeDrawEntryBargon {
- OpcodeDrawProcBargon proc;
- const char *desc;
- };
- struct OpcodeFuncEntryBargon {
- OpcodeFuncProcBargon proc;
- const char *desc;
- };
- struct OpcodeGoblinEntryBargon {
- OpcodeGoblinProcBargon proc;
- const char *desc;
- };
- const OpcodeDrawEntryBargon *_opcodesDrawBargon;
- const OpcodeFuncEntryBargon *_opcodesFuncBargon;
- const OpcodeGoblinEntryBargon *_opcodesGoblinBargon;
- static const int _goblinFuncLookUp[][2];
-
- virtual void setupOpcodes();
- virtual void executeDrawOpcode(byte i);
- virtual bool executeFuncOpcode(byte i, byte j, OpFuncParams &params);
- virtual void executeGoblinOpcode(int i, OpGobParams &params);
- virtual const char *getOpcodeDrawDesc(byte i);
- virtual const char *getOpcodeFuncDesc(byte i, byte j);
- virtual const char *getOpcodeGoblinDesc(int i);
+ virtual void setupOpcodesDraw();
+ virtual void setupOpcodesFunc();
+ virtual void setupOpcodesGob();
void oBargon_intro0(OpGobParams &params);
void oBargon_intro1(OpGobParams &params);
@@ -456,33 +426,9 @@ public:
virtual ~Inter_Fascination() {}
protected:
- typedef void (Inter_Fascination::*OpcodeDrawProcFascination)();
- typedef bool (Inter_Fascination::*OpcodeFuncProcFascination)(OpFuncParams &);
- typedef void (Inter_Fascination::*OpcodeGoblinProcFascination)(OpGobParams &);
- struct OpcodeDrawEntryFascination {
- OpcodeDrawProcFascination proc;
- const char *desc;
- };
- struct OpcodeFuncEntryFascination {
- OpcodeFuncProcFascination proc;
- const char *desc;
- };
- struct OpcodeGoblinEntryFascination {
- OpcodeGoblinProcFascination proc;
- const char *desc;
- };
- const OpcodeDrawEntryFascination *_opcodesDrawFascination;
- const OpcodeFuncEntryFascination *_opcodesFuncFascination;
- const OpcodeGoblinEntryFascination *_opcodesGoblinFascination;
- static const int _goblinFuncLookUp[][2];
-
- virtual void setupOpcodes();
- virtual void executeDrawOpcode(byte i);
- virtual bool executeFuncOpcode(byte i, byte j, OpFuncParams &params);
- virtual void executeGoblinOpcode(int i, OpGobParams &params);
- virtual const char *getOpcodeDrawDesc(byte i);
- virtual const char *getOpcodeFuncDesc(byte i, byte j);
- virtual const char *getOpcodeGoblinDesc(int i);
+ virtual void setupOpcodesDraw();
+ virtual void setupOpcodesFunc();
+ virtual void setupOpcodesGob();
void oFascin_playProtracker(OpGobParams &params);
@@ -517,39 +463,12 @@ public:
virtual ~Inter_v3() {}
protected:
- typedef void (Inter_v3::*OpcodeDrawProcV3)();
- typedef bool (Inter_v3::*OpcodeFuncProcV3)(OpFuncParams &);
- typedef void (Inter_v3::*OpcodeGoblinProcV3)(OpGobParams &);
- struct OpcodeDrawEntryV3 {
- OpcodeDrawProcV3 proc;
- const char *desc;
- };
- struct OpcodeFuncEntryV3 {
- OpcodeFuncProcV3 proc;
- const char *desc;
- };
- struct OpcodeGoblinEntryV3 {
- OpcodeGoblinProcV3 proc;
- const char *desc;
- };
- const OpcodeDrawEntryV3 *_opcodesDrawV3;
- const OpcodeFuncEntryV3 *_opcodesFuncV3;
- const OpcodeGoblinEntryV3 *_opcodesGoblinV3;
- static const int _goblinFuncLookUp[][2];
-
- virtual void setupOpcodes();
- virtual void executeDrawOpcode(byte i);
- virtual bool executeFuncOpcode(byte i, byte j, OpFuncParams &params);
- virtual void executeGoblinOpcode(int i, OpGobParams &params);
- virtual const char *getOpcodeDrawDesc(byte i);
- virtual const char *getOpcodeFuncDesc(byte i, byte j);
- virtual const char *getOpcodeGoblinDesc(int i);
+ virtual void setupOpcodesDraw();
+ virtual void setupOpcodesFunc();
+ virtual void setupOpcodesGob();
bool o3_getTotTextItemPart(OpFuncParams &params);
bool o3_copySprite(OpFuncParams &params);
- bool o3_checkData(OpFuncParams &params);
- bool o3_readData(OpFuncParams &params);
- bool o3_writeData(OpFuncParams &params);
void o3_wobble(OpGobParams &params);
};
@@ -560,33 +479,9 @@ public:
virtual ~Inter_v4() {}
protected:
- typedef void (Inter_v4::*OpcodeDrawProcV4)();
- typedef bool (Inter_v4::*OpcodeFuncProcV4)(OpFuncParams &);
- typedef void (Inter_v4::*OpcodeGoblinProcV4)(OpGobParams &);
- struct OpcodeDrawEntryV4 {
- OpcodeDrawProcV4 proc;
- const char *desc;
- };
- struct OpcodeFuncEntryV4 {
- OpcodeFuncProcV4 proc;
- const char *desc;
- };
- struct OpcodeGoblinEntryV4 {
- OpcodeGoblinProcV4 proc;
- const char *desc;
- };
- const OpcodeDrawEntryV4 *_opcodesDrawV4;
- const OpcodeFuncEntryV4 *_opcodesFuncV4;
- const OpcodeGoblinEntryV4 *_opcodesGoblinV4;
- static const int _goblinFuncLookUp[][2];
-
- virtual void setupOpcodes();
- virtual void executeDrawOpcode(byte i);
- virtual bool executeFuncOpcode(byte i, byte j, OpFuncParams &params);
- virtual void executeGoblinOpcode(int i, OpGobParams &params);
- virtual const char *getOpcodeDrawDesc(byte i);
- virtual const char *getOpcodeFuncDesc(byte i, byte j);
- virtual const char *getOpcodeGoblinDesc(int i);
+ virtual void setupOpcodesDraw();
+ virtual void setupOpcodesFunc();
+ virtual void setupOpcodesGob();
void o4_initScreen();
void o4_playVmdOrMusic();
@@ -598,36 +493,12 @@ public:
virtual ~Inter_v5() {}
protected:
- typedef void (Inter_v5::*OpcodeDrawProcV5)();
- typedef bool (Inter_v5::*OpcodeFuncProcV5)(OpFuncParams &);
- typedef void (Inter_v5::*OpcodeGoblinProcV5)(OpGobParams &);
- struct OpcodeDrawEntryV5 {
- OpcodeDrawProcV5 proc;
- const char *desc;
- };
- struct OpcodeFuncEntryV5 {
- OpcodeFuncProcV5 proc;
- const char *desc;
- };
- struct OpcodeGoblinEntryV5 {
- OpcodeGoblinProcV5 proc;
- const char *desc;
- };
- const OpcodeDrawEntryV5 *_opcodesDrawV5;
- const OpcodeFuncEntryV5 *_opcodesFuncV5;
- const OpcodeGoblinEntryV5 *_opcodesGoblinV5;
- static const int _goblinFuncLookUp[][2];
-
- virtual void setupOpcodes();
- virtual void executeDrawOpcode(byte i);
- virtual bool executeFuncOpcode(byte i, byte j, OpFuncParams &params);
- virtual void executeGoblinOpcode(int i, OpGobParams &params);
- virtual const char *getOpcodeDrawDesc(byte i);
- virtual const char *getOpcodeFuncDesc(byte i, byte j);
- virtual const char *getOpcodeGoblinDesc(int i);
-
byte _gob_97_98_val;
+ virtual void setupOpcodesDraw();
+ virtual void setupOpcodesFunc();
+ virtual void setupOpcodesGob();
+
void o5_deleteFile();
void o5_initScreen();
@@ -657,35 +528,11 @@ public:
virtual ~Inter_v6() {}
protected:
- typedef void (Inter_v6::*OpcodeDrawProcV6)();
- typedef bool (Inter_v6::*OpcodeFuncProcV6)(OpFuncParams &);
- typedef void (Inter_v6::*OpcodeGoblinProcV6)(OpGobParams &);
- struct OpcodeDrawEntryV6 {
- OpcodeDrawProcV6 proc;
- const char *desc;
- };
- struct OpcodeFuncEntryV6 {
- OpcodeFuncProcV6 proc;
- const char *desc;
- };
- struct OpcodeGoblinEntryV6 {
- OpcodeGoblinProcV6 proc;
- const char *desc;
- };
- const OpcodeDrawEntryV6 *_opcodesDrawV6;
- const OpcodeFuncEntryV6 *_opcodesFuncV6;
- const OpcodeGoblinEntryV6 *_opcodesGoblinV6;
- static const int _goblinFuncLookUp[][2];
-
bool _gotFirstPalette;
- virtual void setupOpcodes();
- virtual void executeDrawOpcode(byte i);
- virtual bool executeFuncOpcode(byte i, byte j, OpFuncParams &params);
- virtual void executeGoblinOpcode(int i, OpGobParams &params);
- virtual const char *getOpcodeDrawDesc(byte i);
- virtual const char *getOpcodeFuncDesc(byte i, byte j);
- virtual const char *getOpcodeGoblinDesc(int i);
+ virtual void setupOpcodesDraw();
+ virtual void setupOpcodesFunc();
+ virtual void setupOpcodesGob();
void o6_totSub();
void o6_playVmdOrMusic();
diff --git a/engines/gob/inter_bargon.cpp b/engines/gob/inter_bargon.cpp
index 54ca32fa9e..12079600c0 100644
--- a/engines/gob/inter_bargon.cpp
+++ b/engines/gob/inter_bargon.cpp
@@ -39,680 +39,36 @@
namespace Gob {
-#define OPCODE(x) _OPCODE(Inter_Bargon, x)
-
-const int Inter_Bargon::_goblinFuncLookUp[][2] = {
- {1, 0},
- {2, 1},
- {3, 2},
- {4, 3},
- {5, 4},
- {6, 5},
- {7, 6},
- {8, 7},
- {9, 8},
- {10, 9},
- {11, 10},
- {13, 11},
- {14, 12},
- {15, 13},
- {16, 14},
- {21, 15},
- {22, 16},
- {23, 17},
- {24, 18},
- {25, 19},
- {26, 20},
- {27, 21},
- {28, 22},
- {29, 23},
- {30, 24},
- {32, 25},
- {33, 26},
- {34, 27},
- {35, 28},
- {36, 29},
- {37, 30},
- {40, 31},
- {41, 32},
- {42, 33},
- {43, 34},
- {44, 35},
- {50, 36},
- {52, 37},
- {53, 38},
- {100, 39},
- {152, 40},
- {200, 41},
- {201, 42},
- {202, 43},
- {203, 44},
- {204, 45},
- {250, 46},
- {251, 47},
- {252, 48},
- {500, 49},
- {502, 50},
- {503, 51},
- {600, 52},
- {601, 53},
- {602, 54},
- {603, 55},
- {604, 56},
- {605, 57},
- {1000, 58},
- {1001, 59},
- {1002, 60},
- {1003, 61},
- {1004, 62},
- {1005, 63},
- {1006, 64},
- {1008, 65},
- {1009, 66},
- {1010, 67},
- {1011, 68},
- {1015, 69},
- {2005, 70}
-};
+#define OPCODEVER Inter_Bargon
+#define OPCODEDRAW(i, x) _opcodesDraw[i]._OPCODEDRAW(OPCODEVER, x)
+#define OPCODEFUNC(i, x) _opcodesFunc[i]._OPCODEFUNC(OPCODEVER, x)
+#define OPCODEGOB(i, x) _opcodesGob[i]._OPCODEGOB(OPCODEVER, x)
Inter_Bargon::Inter_Bargon(GobEngine *vm) : Inter_v2(vm) {
- setupOpcodes();
-}
-
-void Inter_Bargon::setupOpcodes() {
- static const OpcodeDrawEntryBargon opcodesDraw[256] = {
- /* 00 */
- OPCODE(o1_loadMult),
- OPCODE(o2_playMult),
- OPCODE(o1_freeMultKeys),
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- OPCODE(o1_initCursor),
- /* 08 */
- OPCODE(o1_initCursorAnim),
- OPCODE(o1_clearCursorAnim),
- OPCODE(o2_setRenderFlags),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- OPCODE(o1_loadAnim),
- OPCODE(o1_freeAnim),
- OPCODE(o1_updateAnim),
- OPCODE(o2_multSub),
- /* 14 */
- OPCODE(o2_initMult),
- OPCODE(o1_freeMult),
- OPCODE(o1_animate),
- OPCODE(o2_loadMultObject),
- /* 18 */
- OPCODE(o1_getAnimLayerInfo),
- OPCODE(o1_getObjAnimSize),
- OPCODE(o1_loadStatic),
- OPCODE(o1_freeStatic),
- /* 1C */
- OPCODE(o2_renderStatic),
- OPCODE(o2_loadCurLayer),
- {0, ""},
- {0, ""},
- /* 20 */
- OPCODE(o2_playCDTrack),
- OPCODE(o2_waitCDTrackEnd),
- OPCODE(o2_stopCD),
- OPCODE(o2_readLIC),
- /* 24 */
- OPCODE(o2_freeLIC),
- OPCODE(o2_getCDTrackPos),
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o2_loadFontToSprite),
- OPCODE(o1_freeFontToSprite),
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- OPCODE(o2_totSub),
- OPCODE(o2_switchTotSub),
- OPCODE(o2_pushVars),
- OPCODE(o2_popVars),
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 48 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 4C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 50 */
- OPCODE(o2_loadMapObjects),
- OPCODE(o2_freeGoblins),
- OPCODE(o2_moveGoblin),
- OPCODE(o2_writeGoblinPos),
- /* 54 */
- OPCODE(o2_stopGoblin),
- OPCODE(o2_setGoblinState),
- OPCODE(o2_placeGoblin),
- {0, ""},
- /* 58 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 5C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 60 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 64 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 68 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 6C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 70 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 74 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 78 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 7C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 80 */
- OPCODE(o2_initScreen),
- OPCODE(o2_scroll),
- OPCODE(o2_setScrollOffset),
- OPCODE(o2_playImd),
- /* 84 */
- OPCODE(o2_getImdInfo),
- OPCODE(o2_openItk),
- OPCODE(o2_closeItk),
- OPCODE(o2_setImdFrontSurf),
- /* 88 */
- OPCODE(o2_resetImdFrontSurf),
- {0, ""},
- {0, ""},
- {0, ""},
- /* 8C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 90 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 94 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 98 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 9C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* AC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* BC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* CC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* DC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* EC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* FC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""}
- };
-
- static const OpcodeFuncEntryBargon opcodesFunc[80] = {
- /* 00 */
- OPCODE(o1_callSub),
- OPCODE(o1_callSub),
- OPCODE(o1_printTotText),
- OPCODE(o1_loadCursor),
- /* 04 */
- {0, ""},
- OPCODE(o1_switch),
- OPCODE(o1_repeatUntil),
- OPCODE(o1_whileDo),
- /* 08 */
- OPCODE(o1_if),
- OPCODE(o2_assign),
- OPCODE(o1_loadSpriteToPos),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- OPCODE(o2_printText),
- OPCODE(o1_loadTot),
- OPCODE(o1_palLoad),
- /* 14 */
- OPCODE(o1_keyFunc),
- OPCODE(o1_capturePush),
- OPCODE(o1_capturePop),
- OPCODE(o2_animPalInit),
- /* 18 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- OPCODE(o1_drawOperations),
- OPCODE(o1_setcmdCount),
- /* 20 */
- OPCODE(o1_return),
- OPCODE(o1_renewTimeInVars),
- OPCODE(o1_speakerOn),
- OPCODE(o1_speakerOff),
- /* 24 */
- OPCODE(o1_putPixel),
- OPCODE(o2_goblinFunc),
- OPCODE(o1_createSprite),
- OPCODE(o1_freeSprite),
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o1_returnTo),
- OPCODE(o1_loadSpriteContent),
- OPCODE(o1_copySprite),
- OPCODE(o1_fillRect),
- /* 34 */
- OPCODE(o1_drawLine),
- OPCODE(o1_strToLong),
- OPCODE(o1_invalidate),
- OPCODE(o1_setBackDelta),
- /* 38 */
- OPCODE(o1_playSound),
- OPCODE(o2_stopSound),
- OPCODE(o2_loadSound),
- OPCODE(o1_freeSoundSlot),
- /* 3C */
- OPCODE(o1_waitEndPlay),
- OPCODE(o1_playComposition),
- OPCODE(o2_getFreeMem),
- OPCODE(o2_checkData),
- /* 40 */
- {0, ""},
- OPCODE(o1_prepareStr),
- OPCODE(o1_insertStr),
- OPCODE(o1_cutStr),
- /* 44 */
- OPCODE(o1_strstr),
- OPCODE(o1_istrlen),
- OPCODE(o1_setMousePos),
- OPCODE(o1_setFrameRate),
- /* 48 */
- OPCODE(o1_animatePalette),
- OPCODE(o1_animateCursor),
- OPCODE(o1_blitCursor),
- OPCODE(o1_loadFont),
- /* 4C */
- OPCODE(o1_freeFont),
- OPCODE(o2_readData),
- OPCODE(o2_writeData),
- OPCODE(o1_manageDataFile),
- };
-
- static const OpcodeGoblinEntryBargon opcodesGoblin[71] = {
- /* 00 */
- OPCODE(oBargon_intro0),
- OPCODE(oBargon_intro1),
- OPCODE(oBargon_intro2),
- OPCODE(oBargon_intro3),
- /* 04 */
- OPCODE(oBargon_intro4),
- OPCODE(oBargon_intro5),
- OPCODE(oBargon_intro6),
- OPCODE(oBargon_intro7),
- /* 08 */
- OPCODE(oBargon_intro8),
- OPCODE(oBargon_intro9),
- OPCODE(o_gobNOP),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 14 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 18 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 20 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 24 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- };
-
- _opcodesDrawBargon = opcodesDraw;
- _opcodesFuncBargon = opcodesFunc;
- _opcodesGoblinBargon = opcodesGoblin;
-}
-
-void Inter_Bargon::executeDrawOpcode(byte i) {
- debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%X] (%s)",
- i, i, getOpcodeDrawDesc(i));
-
- OpcodeDrawProcBargon op = _opcodesDrawBargon[i].proc;
-
- if (op == 0)
- warning("unimplemented opcodeDraw: %d", i);
- else
- (this->*op) ();
-}
-
-bool Inter_Bargon::executeFuncOpcode(byte i, byte j, OpFuncParams &params) {
- debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%X.0x%X] (%s)",
- i, j, i, j, getOpcodeFuncDesc(i, j));
-
- if ((i > 4) || (j > 15)) {
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- return false;
- }
-
- OpcodeFuncProcBargon op = _opcodesFuncBargon[i*16 + j].proc;
-
- if (op == 0)
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- else
- return (this->*op) (params);
-
- return false;
}
-void Inter_Bargon::executeGoblinOpcode(int i, OpGobParams &params) {
- debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%X] (%s)",
- i, i, getOpcodeGoblinDesc(i));
-
- OpcodeGoblinProcBargon op = 0;
-
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i) {
- op = _opcodesGoblinBargon[_goblinFuncLookUp[j][1]].proc;
- break;
- }
-
- if (op == 0) {
- int16 val;
-
- _vm->_global->_inter_execPtr -= 2;
- val = load16();
- _vm->_global->_inter_execPtr += val << 1;
- warning("unimplemented opcodeGob: %d", i);
- } else
- (this->*op) (params);
+void Inter_Bargon::setupOpcodesDraw() {
+ Inter_v2::setupOpcodesDraw();
}
-const char *Inter_Bargon::getOpcodeDrawDesc(byte i) {
- return _opcodesDrawBargon[i].desc;
+void Inter_Bargon::setupOpcodesFunc() {
+ Inter_v2::setupOpcodesFunc();
}
-const char *Inter_Bargon::getOpcodeFuncDesc(byte i, byte j) {
- if ((i > 4) || (j > 15))
- return "";
+void Inter_Bargon::setupOpcodesGob() {
+ OPCODEGOB( 1, oBargon_intro0);
+ OPCODEGOB( 2, oBargon_intro1);
+ OPCODEGOB( 3, oBargon_intro2);
+ OPCODEGOB( 4, oBargon_intro3);
- return _opcodesFuncBargon[i*16 + j].desc;
-}
+ OPCODEGOB( 5, oBargon_intro4);
+ OPCODEGOB( 6, oBargon_intro5);
+ OPCODEGOB( 7, oBargon_intro6);
+ OPCODEGOB( 8, oBargon_intro7);
-const char *Inter_Bargon::getOpcodeGoblinDesc(int i) {
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i)
- return _opcodesGoblinBargon[_goblinFuncLookUp[j][1]].desc;
- return "";
+ OPCODEGOB( 9, oBargon_intro8);
+ OPCODEGOB(10, oBargon_intro9);
+ OPCODEGOB(11, o_gobNOP);
}
void Inter_Bargon::oBargon_intro0(OpGobParams &params) {
diff --git a/engines/gob/inter_fascin.cpp b/engines/gob/inter_fascin.cpp
index bd0b0a94c6..3c4713f9eb 100644
--- a/engines/gob/inter_fascin.cpp
+++ b/engines/gob/inter_fascin.cpp
@@ -31,8 +31,8 @@
#include "gob/util.h"
#include "gob/dataio.h"
#include "gob/draw.h"
-#include "gob/parse.h"
#include "gob/game.h"
+#include "gob/script.h"
#include "gob/palanim.h"
#include "gob/video.h"
#include "gob/videoplayer.h"
@@ -40,494 +40,73 @@
namespace Gob {
-#define OPCODE(x) _OPCODE(Inter_Fascination, x)
-
-const int Inter_Fascination::_goblinFuncLookUp[][2] = {
- {1, 0},
- {2, 1},
- {3, 2},
- {4, 3},
- {5, 4},
- {6, 5},
- {7, 6},
- {8, 7},
- {9, 8},
- {10, 9},
- {11, 10},
- {12, 11},
- {1000, 12},
- {1001, 13},
- {1002, 14}
-};
+#define OPCODEVER Inter_Fascination
+#define OPCODEDRAW(i, x) _opcodesDraw[i]._OPCODEDRAW(OPCODEVER, x)
+#define OPCODEFUNC(i, x) _opcodesFunc[i]._OPCODEFUNC(OPCODEVER, x)
+#define OPCODEGOB(i, x) _opcodesGob[i]._OPCODEGOB(OPCODEVER, x)
Inter_Fascination::Inter_Fascination(GobEngine *vm) : Inter_v2(vm) {
- setupOpcodes();
}
-void Inter_Fascination::setupOpcodes() {
- static const OpcodeDrawEntryFascination opcodesDraw[256] = {
- /* 00 */
- OPCODE(o1_loadMult),
- OPCODE(o2_playMult),
- OPCODE(o1_freeMultKeys),
- OPCODE(oFascin_cdUnknown3),
- /* 04 */
- OPCODE(oFascin_cdUnknown4),
- OPCODE(oFascin_cdUnknown5),
- OPCODE(oFascin_cdUnknown6),
- OPCODE(o1_initCursor),
- /* 08 */
- OPCODE(o1_initCursorAnim),
- OPCODE(o1_clearCursorAnim),
- OPCODE(oFascin_setRenderFlags),
- OPCODE(oFascin_cdUnknown11),
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- OPCODE(o1_loadAnim),
- OPCODE(o1_freeAnim),
- OPCODE(o1_updateAnim),
- OPCODE(o2_multSub),
- /* 14 */
- OPCODE(o2_initMult),
- OPCODE(o1_freeMult),
- OPCODE(o1_animate),
- OPCODE(o2_loadMultObject),
- /* 18 */
- OPCODE(o1_getAnimLayerInfo),
- OPCODE(o1_getObjAnimSize),
- OPCODE(o1_loadStatic),
- OPCODE(o1_freeStatic),
- /* 1C */
- OPCODE(o2_renderStatic),
- OPCODE(o2_loadCurLayer),
- {0, ""},
- {0, ""},
- /* 20 */
- OPCODE(o2_playCDTrack),
- OPCODE(o2_waitCDTrackEnd),
- OPCODE(o2_stopCD),
- OPCODE(o2_readLIC),
- /* 24 */
- OPCODE(o2_freeLIC),
- OPCODE(o2_getCDTrackPos),
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o2_loadFontToSprite),
- OPCODE(o1_freeFontToSprite),
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- OPCODE(o2_totSub),
- OPCODE(o2_switchTotSub),
- OPCODE(o2_pushVars),
- OPCODE(o2_popVars),
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 48 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 4C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 50 */
- {0, ""},//OPCODE(o2_loadMapObjects),
- {0, ""},//OPCODE(o2_freeGoblins),
- {0, ""},//OPCODE(o2_moveGoblin),
- {0, ""},//OPCODE(o2_writeGoblinPos),
- /* 54 */
- {0, ""},//OPCODE(o2_stopGoblin),
- {0, ""},//OPCODE(o2_setGoblinState),
- {0, ""},//OPCODE(o2_placeGoblin),
- {0, ""},
- /* 58 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 5C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 60 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 64 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 68 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 6C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 70 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 74 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 78 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 7C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 80 */
- {0, ""},//OPCODE(o2_initScreen),
- {0, ""},//OPCODE(o2_scroll),
- {0, ""},//OPCODE(o2_setScrollOffset),
- {0, ""},//OPCODE(o2_playImd),
- /* 84 */
- {0, ""},//OPCODE(o2_getImdInfo),
- {0, ""},//OPCODE(o2_openItk),
- {0, ""},//OPCODE(o2_closeItk),
- {0, ""},//OPCODE(o2_setImdFrontSurf),
- /* 88 */
- {0, ""},//OPCODE(o2_resetImdFrontSurf),
- {0, ""},
- {0, ""},
- {0, ""},
- /* 8C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 90 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 94 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 98 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 9C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* AC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* BC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* CC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* DC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* EC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* FC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""}
- };
-
- static const OpcodeFuncEntryFascination opcodesFunc[80] = {
- /* 00 */
- OPCODE(o1_callSub),
- OPCODE(o1_callSub),
- OPCODE(o1_printTotText),
- OPCODE(o1_loadCursor),
- /* 04 */
- {0, ""},
- OPCODE(o1_switch),
- OPCODE(o1_repeatUntil),
- OPCODE(o1_whileDo),
- /* 08 */
- OPCODE(o1_if),
- OPCODE(o1_assign),
- OPCODE(o1_loadSpriteToPos),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- OPCODE(o2_printText),
- OPCODE(o1_loadTot),
- OPCODE(o1_palLoad),
- /* 14 */
- OPCODE(o1_keyFunc),
- OPCODE(o1_capturePush),
- OPCODE(o1_capturePop),
- OPCODE(o1_animPalInit),
- /* 18 */
- OPCODE(o2_addCollision),
- OPCODE(o2_freeCollision),
- {0, ""},
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- OPCODE(o1_drawOperations),
- OPCODE(o1_setcmdCount),
- /* 20 */
- OPCODE(o1_return),
- OPCODE(o1_renewTimeInVars),
- OPCODE(o1_speakerOn),
- OPCODE(o1_speakerOff),
- /* 24 */
- OPCODE(o1_putPixel),
- OPCODE(o2_goblinFunc),
- OPCODE(o1_createSprite),
- OPCODE(o1_freeSprite),
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o1_returnTo),
- OPCODE(o1_loadSpriteContent),
- OPCODE(o1_copySprite),
- OPCODE(o1_fillRect),
- /* 34 */
- OPCODE(o1_drawLine),
- OPCODE(o1_strToLong),
- OPCODE(o1_invalidate),
- OPCODE(o1_setBackDelta),
- /* 38 */
- OPCODE(o1_playSound),
- OPCODE(o2_stopSound),
- OPCODE(o2_loadSound),
- OPCODE(o1_freeSoundSlot),
- /* 3C */
- OPCODE(o1_waitEndPlay),
- OPCODE(o1_playComposition),
- OPCODE(o2_getFreeMem),
- OPCODE(o2_checkData),
- /* 40 */
- {0, ""},
- OPCODE(o1_prepareStr),
- OPCODE(o1_insertStr),
- OPCODE(o1_cutStr),
- /* 44 */
- OPCODE(o1_strstr),
- OPCODE(o1_istrlen),
- OPCODE(o1_setMousePos),
- OPCODE(o1_setFrameRate),
- /* 48 */
- OPCODE(o1_animatePalette),
- OPCODE(o1_animateCursor),
- OPCODE(o1_blitCursor),
- OPCODE(o1_loadFont),
- /* 4C */
- OPCODE(o1_freeFont),
- OPCODE(o2_readData),
- OPCODE(o2_writeData),
- OPCODE(o1_manageDataFile),
- };
-
- static const OpcodeGoblinEntryFascination opcodesGoblin[15] = {
- /* 00 */
- OPCODE(oFascin_geUnknown0),
- OPCODE(oFascin_geUnknown1),
- OPCODE(oFascin_geUnknown2),
- OPCODE(oFascin_geUnknown3),
- /* 04 */
- OPCODE(oFascin_geUnknown4),
- OPCODE(oFascin_geUnknown5),
- OPCODE(oFascin_geUnknown6),
- OPCODE(oFascin_geUnknown7),
- /* 08 */
- OPCODE(oFascin_geUnknown8),
- OPCODE(oFascin_geUnknown9),
- OPCODE(oFascin_geUnknown10),
- OPCODE(oFascin_geUnknown11),
- /* 0C */
- OPCODE(oFascin_geUnknown1000),
- OPCODE(oFascin_geUnknown1001), //protrackerPlay doesn't play correctly "mod.extasy"
- OPCODE(oFascin_geUnknown1002), //to be replaced by o2_stopProtracker when protrackerPlay is fixed
- };
-
- _opcodesDrawFascination = opcodesDraw;
- _opcodesFuncFascination = opcodesFunc;
- _opcodesGoblinFascination = opcodesGoblin;
+void Inter_Fascination::setupOpcodesDraw() {
+ Inter_v2::setupOpcodesDraw();
+
+ OPCODEDRAW(0x03, oFascin_cdUnknown3);
+
+ OPCODEDRAW(0x04, oFascin_cdUnknown4);
+ OPCODEDRAW(0x05, oFascin_cdUnknown5);
+ OPCODEDRAW(0x06, oFascin_cdUnknown6);
+
+ OPCODEDRAW(0x0A, oFascin_setRenderFlags);
+ OPCODEDRAW(0x0B, oFascin_cdUnknown11);
+
+ CLEAROPCODEDRAW(0x50);
+ CLEAROPCODEDRAW(0x51);
+ CLEAROPCODEDRAW(0x52);
+ CLEAROPCODEDRAW(0x53);
+
+ CLEAROPCODEDRAW(0x54);
+ CLEAROPCODEDRAW(0x55);
+ CLEAROPCODEDRAW(0x56);
+
+ CLEAROPCODEDRAW(0x80);
+ CLEAROPCODEDRAW(0x81);
+ CLEAROPCODEDRAW(0x82);
+ CLEAROPCODEDRAW(0x83);
+
+ CLEAROPCODEDRAW(0x84);
+ CLEAROPCODEDRAW(0x85);
+ CLEAROPCODEDRAW(0x86);
+ CLEAROPCODEDRAW(0x87);
+
+ CLEAROPCODEDRAW(0x88);
}
-void Inter_Fascination::executeDrawOpcode(byte i) {
- debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%X] (%s)",
- i, i, getOpcodeDrawDesc(i));
+void Inter_Fascination::setupOpcodesFunc() {
+ Inter_v2::setupOpcodesFunc();
- OpcodeDrawProcFascination op = _opcodesDrawFascination[i].proc;
+ OPCODEFUNC(0x09, o1_assign);
+}
+
+void Inter_Fascination::setupOpcodesGob() {
+ OPCODEGOB( 1, oFascin_geUnknown0);
+ OPCODEGOB( 2, oFascin_geUnknown1);
+ OPCODEGOB( 3, oFascin_geUnknown2);
+ OPCODEGOB( 4, oFascin_geUnknown3);
+
+ OPCODEGOB( 5, oFascin_geUnknown4);
+ OPCODEGOB( 6, oFascin_geUnknown5);
+ OPCODEGOB( 7, oFascin_geUnknown6);
+ OPCODEGOB( 8, oFascin_geUnknown7);
+
+ OPCODEGOB( 9, oFascin_geUnknown8);
+ OPCODEGOB( 10, oFascin_geUnknown9);
+ OPCODEGOB( 11, oFascin_geUnknown10);
+ OPCODEGOB( 12, oFascin_geUnknown11);
- if (op == 0)
- warning("Not yet implemented Fascination opcodeDraw: %d", i);
- else
- (this->*op) ();
+ OPCODEGOB(1000, oFascin_geUnknown1000);
+ OPCODEGOB(1001, oFascin_geUnknown1001); //protrackerPlay doesn't play correctly "mod.extasy"
+ OPCODEGOB(1002, oFascin_geUnknown1002); //to be replaced by o2_stopProtracker when protrackerPlay is fixed
}
void Inter_Fascination::oFascin_geUnknown0(OpGobParams &params) {
@@ -552,70 +131,58 @@ void Inter_Fascination::oFascin_geUnknown1(OpGobParams &params) {
}
void Inter_Fascination::oFascin_geUnknown2(OpGobParams &params) {
- warning("Fascination Unknown GE Function 2");
- warning("funcLoadInstruments with parameter : 'extasy.tbr'. (Guess)");
- warning("funcLoadMusic with parameter : 'extasy.mdy'. (Guess)");
+ _vm->_sound->adlibLoadTBR("extasy.tbr");
+ _vm->_sound->adlibLoadMDY("extasy.mdy");
}
void Inter_Fascination::oFascin_geUnknown3(OpGobParams &params) {
- warning("Fascination Unknown GE Function 3");
- warning("Verify if 'Guess music' is loaded. If yes, call funcPlayMusic. (Guess)");
+ _vm->_sound->adlibPlay();
}
void Inter_Fascination::oFascin_geUnknown4(OpGobParams &params) {
- warning("Fascination Unknown GE Function 4");
- warning("Verify if 'Guess music' is loaded. If yes, call funcStopMusic. (Guess)");
+ _vm->_sound->adlibStop();
}
void Inter_Fascination::oFascin_geUnknown5(OpGobParams &params) {
- warning("Fascination Unknown GE Function 5");
- warning("Verify if 'instruments' are loaded, If so, call mem_free");
- warning("Verify if 'Guess music' is loaded. If yes, call _cleanupMdy");
- warning("Then set _ptrTbr and _ptrMdy to 0");
+ _vm->_sound->adlibUnload();
}
void Inter_Fascination::oFascin_geUnknown6(OpGobParams &params) {
- warning("Fascination Unknown GE Function 6");
- warning("funcLoadInstruments with parameter : 'music1.tbr'. (Guess)");
- warning("funcLoadMusic with parameter : 'music1.mdy'. (Guess)");
+ _vm->_sound->adlibLoadTBR("music1.tbr");
+ _vm->_sound->adlibLoadMDY("music1.mdy");
}
void Inter_Fascination::oFascin_geUnknown7(OpGobParams &params) {
- warning("Fascination Unknown GE Function 7");
- warning("funcLoadInstruments with parameter : 'music2.tbr'. (Guess)");
- warning("funcLoadMusic with parameter : 'music2.mdy'. (Guess)");
+ _vm->_sound->adlibLoadTBR("music2.tbr");
+ _vm->_sound->adlibLoadMDY("music2.mdy");
}
void Inter_Fascination::oFascin_geUnknown8(OpGobParams &params) {
- warning("Fascination Unknown GE Function 8");
- warning("funcLoadInstruments with parameter : 'music3.tbr'. (Guess)");
- warning("funcLoadMusic with parameter : 'music3.mdy'. (Guess)");
+ _vm->_sound->adlibLoadTBR("music3.tbr");
+ _vm->_sound->adlibLoadMDY("music3.mdy");
}
void Inter_Fascination::oFascin_geUnknown9(OpGobParams &params) {
- warning("Fascination Unknown GE Function 9");
- warning("funcLoadInstruments with parameter : 'batt1.tbr'. (Guess)");
- warning("funcLoadMusic with parameter : 'batt1.mdy'. (Guess)");
+ _vm->_sound->adlibLoadTBR("batt1.tbr");
+ _vm->_sound->adlibLoadMDY("batt1.mdy");
}
void Inter_Fascination::oFascin_geUnknown10(OpGobParams &params) {
- warning("Fascination Unknown GE Function 10");
- warning("funcLoadInstruments with parameter : 'batt2.tbr'. (Guess)");
- warning("funcLoadMusic with parameter : 'batt2.mdy'. (Guess)");
+ _vm->_sound->adlibLoadTBR("batt2.tbr");
+ _vm->_sound->adlibLoadMDY("batt2.mdy");
}
void Inter_Fascination::oFascin_geUnknown11(OpGobParams &params) {
- warning("Fascination Unknown GE Function 11");
- warning("funcLoadInstruments with parameter : 'batt3.tbr'. (Guess)");
- warning("funcLoadMusic with parameter : 'batt3.mdy'. (Guess)");
+ _vm->_sound->adlibLoadTBR("batt3.tbr");
+ _vm->_sound->adlibLoadMDY("batt3.mdy");
}
void Inter_Fascination::oFascin_geUnknown1000(OpGobParams &params) {
- warning("Fascination Unknown GE Function 1000 - Load music ?");
+ warning("Fascination Unknown GE Function 1000 - Load MOD music");
}
void Inter_Fascination::oFascin_geUnknown1001(OpGobParams &params) {
- warning("Fascination oFascin_playProtracker - MOD not compatible, ToBeFixed");
+ warning("Fascination oFascin_playProtracker - MOD not compatible (sample > 32768), To Be Fixed");
}
void Inter_Fascination::oFascin_geUnknown1002(OpGobParams &params) {
@@ -638,15 +205,15 @@ void Inter_Fascination::oFascin_cdUnknown3() {
warning("Fascination oFascin_cdUnknown3 - Variables initialisations");
- resVar = (uint16) load16();
- resVar2 = (uint16) load16();
- retVal1 = _vm->_parse->parseVarIndex();
- retVal2 = _vm->_parse->parseVarIndex();
- retVal3 = _vm->_parse->parseVarIndex();
- retVal4 = _vm->_parse->parseVarIndex();
- retVal5 = _vm->_parse->parseVarIndex();
- retVal6 = _vm->_parse->parseVarIndex();
- retVal7 = _vm->_parse->parseVarIndex();
+ resVar = _vm->_game->_script->readUint16();
+ resVar2 = _vm->_game->_script->readUint16();
+ retVal1 = _vm->_game->_script->readVarIndex();
+ retVal2 = _vm->_game->_script->readVarIndex();
+ retVal3 = _vm->_game->_script->readVarIndex();
+ retVal4 = _vm->_game->_script->readVarIndex();
+ retVal5 = _vm->_game->_script->readVarIndex();
+ retVal6 = _vm->_game->_script->readVarIndex();
+ retVal7 = _vm->_game->_script->readVarIndex();
warning ("Width? :%d Height? :%d",resVar, resVar2);
warning ("Fetched variables 1:%d 2:%d 3:%d 4:%d 5:%d 6:%d 7:%d", retVal1, retVal2, retVal3, retVal4, retVal5, retVal6, retVal7);
}
@@ -654,98 +221,37 @@ void Inter_Fascination::oFascin_cdUnknown3() {
void Inter_Fascination::oFascin_cdUnknown4() {
int16 expr;
warning("Fascination oFascin_cdUnknown4");
- evalExpr(&expr);
- warning ("evalExpr: %d, the rest is not yet implemented",expr);
+ _vm->_game->_script->evalExpr(&expr);
+ warning ("_vm->_game->_script->evalExpr: %d, the rest is not yet implemented",expr);
}
void Inter_Fascination::oFascin_cdUnknown5() {
int16 retVal1,expr;
warning("Fascination oFascin_cdUnknown5");
- evalExpr(&expr);
- retVal1 = _vm->_parse->parseVarIndex();
- warning ("evalExpr: %d Variable index %d, the rest is not yet implemented",expr, retVal1);
+ _vm->_game->_script->evalExpr(&expr);
+ retVal1 = _vm->_game->_script->readVarIndex();
+ warning ("_vm->_game->_script->evalExpr: %d Variable index %d, the rest is not yet implemented",expr, retVal1);
}
void Inter_Fascination::oFascin_cdUnknown6() {
int16 retVal1,expr;
warning("Fascination oFascin_cdUnknown6");
- evalExpr(&expr);
- retVal1 = _vm->_parse->parseVarIndex();
- warning ("evalExpr: %d Variable index %d, the rest is not yet implemented",expr, retVal1);
+ _vm->_game->_script->evalExpr(&expr);
+ retVal1 = _vm->_game->_script->readVarIndex();
+ warning ("_vm->_game->_script->evalExpr: %d Variable index %d, the rest is not yet implemented",expr, retVal1);
}
void Inter_Fascination::oFascin_setRenderFlags() {
int16 expr;
// warning("Fascination oFascin_cdUnknown10 (set render flags)");
- evalExpr(&expr);
+ _vm->_game->_script->evalExpr(&expr);
warning("_draw_renderFlags <- %d",expr);
_vm->_draw->_renderFlags = expr;
}
void Inter_Fascination::oFascin_cdUnknown11() {
// warning("Fascination oFascin_cdUnknown11 (set variable)");
- evalExpr(0);
-}
-
-bool Inter_Fascination::executeFuncOpcode(byte i, byte j, OpFuncParams &params) {
- debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%X.0x%X] (%s)",
- i, j, i, j, getOpcodeFuncDesc(i, j));
-
- if ((i > 4) || (j > 16)) {
- warning("Invalid opcodeFunc: %d.%d", i, j);
- return false;
- }
-
- OpcodeFuncProcFascination op = _opcodesFuncFascination[i*16 + j].proc;
-
- if (op == 0)
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- else
- return (this->*op) (params);
-
- return false;
-}
-
-void Inter_Fascination::executeGoblinOpcode(int i, OpGobParams &params) {
- debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%X] (%s)",
- i, i, getOpcodeGoblinDesc(i));
-
- OpcodeGoblinProcFascination op = 0;
-
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i) {
- op = _opcodesGoblinFascination[_goblinFuncLookUp[j][1]].proc;
- break;
- }
-
- if (op == 0) {
- int16 val;
-
- _vm->_global->_inter_execPtr -= 2;
- val = load16();
- _vm->_global->_inter_execPtr += val << 1;
- warning("unimplemented opcodeGob: %d", i);
- } else
- (this->*op) (params);
-}
-
-const char *Inter_Fascination::getOpcodeDrawDesc(byte i) {
- return _opcodesDrawFascination[i].desc;
-}
-
-const char *Inter_Fascination::getOpcodeFuncDesc(byte i, byte j) {
- if ((i > 4) || (j > 15))
- return "";
-
- return _opcodesFuncFascination[i*16 + j].desc;
-}
-
-const char *Inter_Fascination::getOpcodeGoblinDesc(int i) {
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i)
- return _opcodesGoblinFascination[_goblinFuncLookUp[j][1]].desc;
- warning("Error in getOpcodeGoblinDesc %d",i);
- return "";
+ _vm->_game->_script->evalExpr(0);
}
void Inter_Fascination::oFascin_playProtracker(OpGobParams &params) {
diff --git a/engines/gob/inter_v1.cpp b/engines/gob/inter_v1.cpp
index ace5a7a3be..d5d5fcad9a 100644
--- a/engines/gob/inter_v1.cpp
+++ b/engines/gob/inter_v1.cpp
@@ -34,692 +34,214 @@
#include "gob/dataio.h"
#include "gob/draw.h"
#include "gob/game.h"
+#include "gob/expression.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/goblin.h"
#include "gob/inter.h"
#include "gob/map.h"
#include "gob/mult.h"
#include "gob/palanim.h"
-#include "gob/parse.h"
#include "gob/scenery.h"
#include "gob/video.h"
#include "gob/sound/sound.h"
namespace Gob {
-#define OPCODE(x) _OPCODE(Inter_v1, x)
-
-const int Inter_v1::_goblinFuncLookUp[][2] = {
- {1, 0},
- {2, 1},
- {3, 2},
- {4, 3},
- {5, 4},
- {6, 5},
- {7, 6},
- {8, 7},
- {9, 8},
- {10, 9},
- {12, 10},
- {13, 11},
- {14, 12},
- {15, 13},
- {16, 14},
- {21, 15},
- {22, 16},
- {23, 17},
- {24, 18},
- {25, 19},
- {26, 20},
- {27, 21},
- {28, 22},
- {29, 23},
- {30, 24},
- {32, 25},
- {33, 26},
- {34, 27},
- {35, 28},
- {36, 29},
- {37, 30},
- {40, 31},
- {41, 32},
- {42, 33},
- {43, 34},
- {44, 35},
- {50, 36},
- {52, 37},
- {53, 38},
- {150, 39},
- {152, 40},
- {200, 41},
- {201, 42},
- {202, 43},
- {203, 44},
- {204, 45},
- {250, 46},
- {251, 47},
- {252, 48},
- {500, 49},
- {502, 50},
- {503, 51},
- {600, 52},
- {601, 53},
- {602, 54},
- {603, 55},
- {604, 56},
- {605, 57},
- {1000, 58},
- {1001, 59},
- {1002, 60},
- {1003, 61},
- {1004, 62},
- {1005, 63},
- {1006, 64},
- {1008, 65},
- {1009, 66},
- {1010, 67},
- {1011, 68},
- {1015, 69},
- {2005, 70}
-};
+#define OPCODEVER Inter_v1
+#define OPCODEDRAW(i, x) _opcodesDraw[i]._OPCODEDRAW(OPCODEVER, x)
+#define OPCODEFUNC(i, x) _opcodesFunc[i]._OPCODEFUNC(OPCODEVER, x)
+#define OPCODEGOB(i, x) _opcodesGob[i]._OPCODEGOB(OPCODEVER, x)
Inter_v1::Inter_v1(GobEngine *vm) : Inter(vm) {
- setupOpcodes();
-}
-
-void Inter_v1::setupOpcodes() {
- static const OpcodeDrawEntryV1 opcodesDraw[256] = {
- /* 00 */
- OPCODE(o1_loadMult),
- OPCODE(o1_playMult),
- OPCODE(o1_freeMultKeys),
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- OPCODE(o1_initCursor),
- /* 08 */
- OPCODE(o1_initCursorAnim),
- OPCODE(o1_clearCursorAnim),
- OPCODE(o1_setRenderFlags),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- OPCODE(o1_loadAnim),
- OPCODE(o1_freeAnim),
- OPCODE(o1_updateAnim),
- {0, ""},
- /* 14 */
- OPCODE(o1_initMult),
- OPCODE(o1_freeMult),
- OPCODE(o1_animate),
- OPCODE(o1_loadMultObject),
- /* 18 */
- OPCODE(o1_getAnimLayerInfo),
- OPCODE(o1_getObjAnimSize),
- OPCODE(o1_loadStatic),
- OPCODE(o1_freeStatic),
- /* 1C */
- OPCODE(o1_renderStatic),
- OPCODE(o1_loadCurLayer),
- {0, ""},
- {0, ""},
- /* 20 */
- OPCODE(o1_playCDTrack),
- OPCODE(o1_getCDTrackPos),
- OPCODE(o1_stopCD),
- {0, ""},
- /* 24 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o1_loadFontToSprite),
- OPCODE(o1_freeFontToSprite),
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 48 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 4C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 50 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 54 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 58 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 5C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 60 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 64 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 68 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 6C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 70 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 74 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 78 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 7C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 80 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 84 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 88 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 8C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 90 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 94 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 98 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 9C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* AC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* BC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* CC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* DC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* EC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* FC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""}
- };
-
- static const OpcodeFuncEntryV1 opcodesFunc[80] = {
- /* 00 */
- OPCODE(o1_callSub),
- OPCODE(o1_callSub),
- OPCODE(o1_printTotText),
- OPCODE(o1_loadCursor),
- /* 04 */
- {0, ""},
- OPCODE(o1_switch),
- OPCODE(o1_repeatUntil),
- OPCODE(o1_whileDo),
- /* 08 */
- OPCODE(o1_if),
- OPCODE(o1_assign),
- OPCODE(o1_loadSpriteToPos),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- OPCODE(o1_printText),
- OPCODE(o1_loadTot),
- OPCODE(o1_palLoad),
- /* 14 */
- OPCODE(o1_keyFunc),
- OPCODE(o1_capturePush),
- OPCODE(o1_capturePop),
- OPCODE(o1_animPalInit),
- /* 18 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- OPCODE(o1_drawOperations),
- OPCODE(o1_setcmdCount),
- /* 20 */
- OPCODE(o1_return),
- OPCODE(o1_renewTimeInVars),
- OPCODE(o1_speakerOn),
- OPCODE(o1_speakerOff),
- /* 24 */
- OPCODE(o1_putPixel),
- OPCODE(o1_goblinFunc),
- OPCODE(o1_createSprite),
- OPCODE(o1_freeSprite),
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o1_returnTo),
- OPCODE(o1_loadSpriteContent),
- OPCODE(o1_copySprite),
- OPCODE(o1_fillRect),
- /* 34 */
- OPCODE(o1_drawLine),
- OPCODE(o1_strToLong),
- OPCODE(o1_invalidate),
- OPCODE(o1_setBackDelta),
- /* 38 */
- OPCODE(o1_playSound),
- OPCODE(o1_stopSound),
- OPCODE(o1_loadSound),
- OPCODE(o1_freeSoundSlot),
- /* 3C */
- OPCODE(o1_waitEndPlay),
- OPCODE(o1_playComposition),
- OPCODE(o1_getFreeMem),
- OPCODE(o1_checkData),
- /* 40 */
- {0, ""},
- OPCODE(o1_prepareStr),
- OPCODE(o1_insertStr),
- OPCODE(o1_cutStr),
- /* 44 */
- OPCODE(o1_strstr),
- OPCODE(o1_istrlen),
- OPCODE(o1_setMousePos),
- OPCODE(o1_setFrameRate),
- /* 48 */
- OPCODE(o1_animatePalette),
- OPCODE(o1_animateCursor),
- OPCODE(o1_blitCursor),
- OPCODE(o1_loadFont),
- /* 4C */
- OPCODE(o1_freeFont),
- OPCODE(o1_readData),
- OPCODE(o1_writeData),
- OPCODE(o1_manageDataFile),
- };
-
- static const OpcodeGoblinEntryV1 opcodesGoblin[71] = {
- /* 00 */
- OPCODE(o1_setState),
- OPCODE(o1_setCurFrame),
- OPCODE(o1_setNextState),
- OPCODE(o1_setMultState),
- /* 04 */
- OPCODE(o1_setOrder),
- OPCODE(o1_setActionStartState),
- OPCODE(o1_setCurLookDir),
- OPCODE(o1_setType),
- /* 08 */
- OPCODE(o1_setNoTick),
- OPCODE(o1_setPickable),
- OPCODE(o1_setXPos),
- OPCODE(o1_setYPos),
- /* 0C */
- OPCODE(o1_setDoAnim),
- OPCODE(o1_setRelaxTime),
- OPCODE(o1_setMaxTick),
- OPCODE(o1_getState),
- /* 10 */
- OPCODE(o1_getCurFrame),
- OPCODE(o1_getNextState),
- OPCODE(o1_getMultState),
- OPCODE(o1_getOrder),
- /* 14 */
- OPCODE(o1_getActionStartState),
- OPCODE(o1_getCurLookDir),
- OPCODE(o1_getType),
- OPCODE(o1_getNoTick),
- /* 18 */
- OPCODE(o1_getPickable),
- OPCODE(o1_getObjMaxFrame),
- OPCODE(o1_getXPos),
- OPCODE(o1_getYPos),
- /* 1C */
- OPCODE(o1_getDoAnim),
- OPCODE(o1_getRelaxTime),
- OPCODE(o1_getMaxTick),
- OPCODE(o1_manipulateMap),
- /* 20 */
- OPCODE(o1_getItem),
- OPCODE(o1_manipulateMapIndirect),
- OPCODE(o1_getItemIndirect),
- OPCODE(o1_setPassMap),
- /* 24 */
- OPCODE(o1_setGoblinPosH),
- OPCODE(o1_getGoblinPosXH),
- OPCODE(o1_getGoblinPosYH),
- OPCODE(o1_setGoblinMultState),
- /* 28 */
- OPCODE(o1_setGoblinUnk14),
- OPCODE(o1_setItemIdInPocket),
- OPCODE(o1_setItemIndInPocket),
- OPCODE(o1_getItemIdInPocket),
- /* 2C */
- OPCODE(o1_getItemIndInPocket),
- OPCODE(o1_setItemPos),
- OPCODE(o1_setGoblinPos),
- OPCODE(o1_setGoblinState),
- /* 30 */
- OPCODE(o1_setGoblinStateRedraw),
- OPCODE(o1_decRelaxTime),
- OPCODE(o1_getGoblinPosX),
- OPCODE(o1_getGoblinPosY),
- /* 34 */
- OPCODE(o1_clearPathExistence),
- OPCODE(o1_setGoblinVisible),
- OPCODE(o1_setGoblinInvisible),
- OPCODE(o1_getObjectIntersect),
- /* 38 */
- OPCODE(o1_getGoblinIntersect),
- OPCODE(o1_setItemPos),
- OPCODE(o1_loadObjects),
- OPCODE(o1_freeObjects),
- /* 3C */
- OPCODE(o1_animateObjects),
- OPCODE(o1_drawObjects),
- OPCODE(o1_loadMap),
- OPCODE(o1_moveGoblin),
- /* 40 */
- OPCODE(o1_switchGoblin),
- OPCODE(o1_loadGoblin),
- OPCODE(o1_writeTreatItem),
- OPCODE(o1_moveGoblin0),
- /* 44 */
- OPCODE(o1_setGoblinTarget),
- OPCODE(o1_setGoblinObjectsPos),
- OPCODE(o1_initGoblin)
- };
-
- _opcodesDrawV1 = opcodesDraw;
- _opcodesFuncV1 = opcodesFunc;
- _opcodesGoblinV1 = opcodesGoblin;
-}
-
-void Inter_v1::executeDrawOpcode(byte i) {
- debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%X] (%s)",
- i, i, getOpcodeDrawDesc(i));
-
- OpcodeDrawProcV1 op = _opcodesDrawV1[i].proc;
-
- if (op == 0)
- warning("unimplemented opcodeDraw: %d", i);
- else
- (this->*op) ();
-}
-
-bool Inter_v1::executeFuncOpcode(byte i, byte j, OpFuncParams &params) {
- debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%X.0x%X] (%s)",
- i, j, i, j, getOpcodeFuncDesc(i, j));
-
- if ((i > 4) || (j > 15)) {
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- return false;
- }
-
- OpcodeFuncProcV1 op = _opcodesFuncV1[i*16 + j].proc;
-
- if (op == 0)
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- else
- return (this->*op) (params);
- return false;
}
-void Inter_v1::executeGoblinOpcode(int i, OpGobParams &params) {
- debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%X] (%s)",
- i, i, getOpcodeGoblinDesc(i));
+void Inter_v1::setupOpcodesDraw() {
+ OPCODEDRAW(0x00, o1_loadMult);
+ OPCODEDRAW(0x01, o1_playMult);
+ OPCODEDRAW(0x02, o1_freeMultKeys);
- OpcodeGoblinProcV1 op = 0;
+ OPCODEDRAW(0x07, o1_initCursor);
+
+ OPCODEDRAW(0x08, o1_initCursorAnim);
+ OPCODEDRAW(0x09, o1_clearCursorAnim);
+ OPCODEDRAW(0x0A, o1_setRenderFlags);
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i) {
- op = _opcodesGoblinV1[_goblinFuncLookUp[j][1]].proc;
- break;
- }
-
- if (op == 0) {
- warning("unimplemented opcodeGoblin: %d", i);
- _vm->_global->_inter_execPtr -= 2;
- int16 cmd = load16();
- _vm->_global->_inter_execPtr += cmd * 2;
- } else
- (this->*op) (params);
-}
-
-const char *Inter_v1::getOpcodeDrawDesc(byte i) {
- return _opcodesDrawV1[i].desc;
-}
-
-const char *Inter_v1::getOpcodeFuncDesc(byte i, byte j) {
- if ((i > 4) || (j > 15))
- return "";
-
- return _opcodesFuncV1[i*16 + j].desc;
-}
-
-const char *Inter_v1::getOpcodeGoblinDesc(int i) {
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i)
- return _opcodesGoblinV1[_goblinFuncLookUp[j][1]].desc;
- return "";
-}
-
-void Inter_v1::checkSwitchTable(byte **ppExec) {
+ OPCODEDRAW(0x10, o1_loadAnim);
+ OPCODEDRAW(0x11, o1_freeAnim);
+ OPCODEDRAW(0x12, o1_updateAnim);
+
+ OPCODEDRAW(0x14, o1_initMult);
+ OPCODEDRAW(0x15, o1_freeMult);
+ OPCODEDRAW(0x16, o1_animate);
+ OPCODEDRAW(0x17, o1_loadMultObject);
+
+ OPCODEDRAW(0x18, o1_getAnimLayerInfo);
+ OPCODEDRAW(0x19, o1_getObjAnimSize);
+ OPCODEDRAW(0x1A, o1_loadStatic);
+ OPCODEDRAW(0x1B, o1_freeStatic);
+
+ OPCODEDRAW(0x1C, o1_renderStatic);
+ OPCODEDRAW(0x1D, o1_loadCurLayer);
+
+ OPCODEDRAW(0x20, o1_playCDTrack);
+ OPCODEDRAW(0x21, o1_getCDTrackPos);
+ OPCODEDRAW(0x22, o1_stopCD);
+
+ OPCODEDRAW(0x30, o1_loadFontToSprite);
+ OPCODEDRAW(0x31, o1_freeFontToSprite);
+}
+
+void Inter_v1::setupOpcodesFunc() {
+ OPCODEFUNC(0x00, o1_callSub);
+ OPCODEFUNC(0x01, o1_callSub);
+ OPCODEFUNC(0x02, o1_printTotText);
+ OPCODEFUNC(0x03, o1_loadCursor);
+
+ OPCODEFUNC(0x05, o1_switch);
+ OPCODEFUNC(0x06, o1_repeatUntil);
+ OPCODEFUNC(0x07, o1_whileDo);
+
+ OPCODEFUNC(0x08, o1_if);
+ OPCODEFUNC(0x09, o1_assign);
+ OPCODEFUNC(0x0A, o1_loadSpriteToPos);
+ OPCODEFUNC(0x11, o1_printText);
+ OPCODEFUNC(0x12, o1_loadTot);
+ OPCODEFUNC(0x13, o1_palLoad);
+
+ OPCODEFUNC(0x14, o1_keyFunc);
+ OPCODEFUNC(0x15, o1_capturePush);
+ OPCODEFUNC(0x16, o1_capturePop);
+ OPCODEFUNC(0x17, o1_animPalInit);
+
+ OPCODEFUNC(0x1E, o1_drawOperations);
+ OPCODEFUNC(0x1F, o1_setcmdCount);
+
+ OPCODEFUNC(0x20, o1_return);
+ OPCODEFUNC(0x21, o1_renewTimeInVars);
+ OPCODEFUNC(0x22, o1_speakerOn);
+ OPCODEFUNC(0x23, o1_speakerOff);
+
+ OPCODEFUNC(0x24, o1_putPixel);
+ OPCODEFUNC(0x25, o1_goblinFunc);
+ OPCODEFUNC(0x26, o1_createSprite);
+ OPCODEFUNC(0x27, o1_freeSprite);
+
+ OPCODEFUNC(0x30, o1_returnTo);
+ OPCODEFUNC(0x31, o1_loadSpriteContent);
+ OPCODEFUNC(0x32, o1_copySprite);
+ OPCODEFUNC(0x33, o1_fillRect);
+
+ OPCODEFUNC(0x34, o1_drawLine);
+ OPCODEFUNC(0x35, o1_strToLong);
+ OPCODEFUNC(0x36, o1_invalidate);
+ OPCODEFUNC(0x37, o1_setBackDelta);
+
+ OPCODEFUNC(0x38, o1_playSound);
+ OPCODEFUNC(0x39, o1_stopSound);
+ OPCODEFUNC(0x3A, o1_loadSound);
+ OPCODEFUNC(0x3B, o1_freeSoundSlot);
+
+ OPCODEFUNC(0x3C, o1_waitEndPlay);
+ OPCODEFUNC(0x3D, o1_playComposition);
+ OPCODEFUNC(0x3E, o1_getFreeMem);
+ OPCODEFUNC(0x3F, o1_checkData);
+
+ OPCODEFUNC(0x41, o1_prepareStr);
+ OPCODEFUNC(0x42, o1_insertStr);
+ OPCODEFUNC(0x43, o1_cutStr);
+
+ OPCODEFUNC(0x44, o1_strstr);
+ OPCODEFUNC(0x45, o1_istrlen);
+ OPCODEFUNC(0x46, o1_setMousePos);
+ OPCODEFUNC(0x47, o1_setFrameRate);
+
+ OPCODEFUNC(0x48, o1_animatePalette);
+ OPCODEFUNC(0x49, o1_animateCursor);
+ OPCODEFUNC(0x4A, o1_blitCursor);
+ OPCODEFUNC(0x4B, o1_loadFont);
+
+ OPCODEFUNC(0x4C, o1_freeFont);
+ OPCODEFUNC(0x4D, o1_readData);
+ OPCODEFUNC(0x4E, o1_writeData);
+ OPCODEFUNC(0x4F, o1_manageDataFile);
+}
+
+void Inter_v1::setupOpcodesGob() {
+ OPCODEGOB( 1, o1_setState);
+ OPCODEGOB( 2, o1_setCurFrame);
+ OPCODEGOB( 3, o1_setNextState);
+ OPCODEGOB( 4, o1_setMultState);
+ OPCODEGOB( 5, o1_setOrder);
+ OPCODEGOB( 6, o1_setActionStartState);
+ OPCODEGOB( 7, o1_setCurLookDir);
+ OPCODEGOB( 8, o1_setType);
+ OPCODEGOB( 9, o1_setNoTick);
+ OPCODEGOB( 10, o1_setPickable);
+ OPCODEGOB( 12, o1_setXPos);
+ OPCODEGOB( 13, o1_setYPos);
+ OPCODEGOB( 14, o1_setDoAnim);
+ OPCODEGOB( 15, o1_setRelaxTime);
+ OPCODEGOB( 16, o1_setMaxTick);
+ OPCODEGOB( 21, o1_getState);
+ OPCODEGOB( 22, o1_getCurFrame);
+ OPCODEGOB( 23, o1_getNextState);
+ OPCODEGOB( 24, o1_getMultState);
+ OPCODEGOB( 25, o1_getOrder);
+ OPCODEGOB( 26, o1_getActionStartState);
+ OPCODEGOB( 27, o1_getCurLookDir);
+ OPCODEGOB( 28, o1_getType);
+ OPCODEGOB( 29, o1_getNoTick);
+ OPCODEGOB( 30, o1_getPickable);
+ OPCODEGOB( 32, o1_getObjMaxFrame);
+ OPCODEGOB( 33, o1_getXPos);
+ OPCODEGOB( 34, o1_getYPos);
+ OPCODEGOB( 35, o1_getDoAnim);
+ OPCODEGOB( 36, o1_getRelaxTime);
+ OPCODEGOB( 37, o1_getMaxTick);
+ OPCODEGOB( 40, o1_manipulateMap);
+ OPCODEGOB( 41, o1_getItem);
+ OPCODEGOB( 42, o1_manipulateMapIndirect);
+ OPCODEGOB( 43, o1_getItemIndirect);
+ OPCODEGOB( 44, o1_setPassMap);
+ OPCODEGOB( 50, o1_setGoblinPosH);
+ OPCODEGOB( 52, o1_getGoblinPosXH);
+ OPCODEGOB( 53, o1_getGoblinPosYH);
+ OPCODEGOB( 150, o1_setGoblinMultState);
+ OPCODEGOB( 152, o1_setGoblinUnk14);
+ OPCODEGOB( 200, o1_setItemIdInPocket);
+ OPCODEGOB( 201, o1_setItemIndInPocket);
+ OPCODEGOB( 202, o1_getItemIdInPocket);
+ OPCODEGOB( 203, o1_getItemIndInPocket);
+ OPCODEGOB( 204, o1_setItemPos);
+ OPCODEGOB( 250, o1_setGoblinPos);
+ OPCODEGOB( 251, o1_setGoblinState);
+ OPCODEGOB( 252, o1_setGoblinStateRedraw);
+ OPCODEGOB( 500, o1_decRelaxTime);
+ OPCODEGOB( 502, o1_getGoblinPosX);
+ OPCODEGOB( 503, o1_getGoblinPosY);
+ OPCODEGOB( 600, o1_clearPathExistence);
+ OPCODEGOB( 601, o1_setGoblinVisible);
+ OPCODEGOB( 602, o1_setGoblinInvisible);
+ OPCODEGOB( 603, o1_getObjectIntersect);
+ OPCODEGOB( 604, o1_getGoblinIntersect);
+ OPCODEGOB( 605, o1_setItemPos);
+ OPCODEGOB(1000, o1_loadObjects);
+ OPCODEGOB(1001, o1_freeObjects);
+ OPCODEGOB(1002, o1_animateObjects);
+ OPCODEGOB(1003, o1_drawObjects);
+ OPCODEGOB(1004, o1_loadMap);
+ OPCODEGOB(1005, o1_moveGoblin);
+ OPCODEGOB(1006, o1_switchGoblin);
+ OPCODEGOB(1008, o1_loadGoblin);
+ OPCODEGOB(1009, o1_writeTreatItem);
+ OPCODEGOB(1010, o1_moveGoblin0);
+ OPCODEGOB(1011, o1_setGoblinTarget);
+ OPCODEGOB(1015, o1_setGoblinObjectsPos);
+ OPCODEGOB(2005, o1_initGoblin);
+}
+
+void Inter_v1::checkSwitchTable(uint32 &offset) {
int16 len;
int32 value;
bool found;
@@ -727,56 +249,54 @@ void Inter_v1::checkSwitchTable(byte **ppExec) {
found = false;
notFound = true;
- *ppExec = 0;
- value = VAR_OFFSET(_vm->_parse->parseVarIndex());
+ offset = 0;
+ value = VAR_OFFSET(_vm->_game->_script->readVarIndex());
- len = (int8) *_vm->_global->_inter_execPtr++;
+ len = _vm->_game->_script->readInt8();
while (len != -5) {
for (int i = 0; i < len; i++) {
- evalExpr(0);
+ _vm->_game->_script->evalExpr(0);
if (_terminate)
return;
- if (_vm->_global->_inter_resVal == value) {
+ if (_vm->_game->_script->getResultInt() == value) {
found = true;
notFound = false;
}
}
if (found)
- *ppExec = _vm->_global->_inter_execPtr;
+ offset = _vm->_game->_script->pos();
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ _vm->_game->_script->skip(_vm->_game->_script->peekUint16(2) + 2);
found = false;
- len = (int8) *_vm->_global->_inter_execPtr++;
+ len = _vm->_game->_script->readInt8();
}
- if ((*_vm->_global->_inter_execPtr >> 4) != 4)
+ if ((_vm->_game->_script->peekByte() >> 4) != 4)
return;
- _vm->_global->_inter_execPtr++;
+ _vm->_game->_script->skip(1);
if (notFound)
- *ppExec = _vm->_global->_inter_execPtr;
+ offset = _vm->_game->_script->pos();
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ _vm->_game->_script->skip(_vm->_game->_script->peekUint16(2) + 2);
}
void Inter_v1::o1_loadMult() {
- _vm->_mult->loadMult(load16());
+ _vm->_mult->loadMult(_vm->_game->_script->readInt16());
}
void Inter_v1::o1_playMult() {
int16 checkEscape;
- checkEscape = load16();
+ checkEscape = _vm->_game->_script->readInt16();
_vm->_mult->playMult(VAR(57), -1, checkEscape, 0);
}
void Inter_v1::o1_freeMultKeys() {
- load16();
+ _vm->_game->_script->readInt16();
_vm->_mult->freeMultKeys();
}
@@ -785,20 +305,20 @@ void Inter_v1::o1_initCursor() {
int16 height;
int16 count;
- _vm->_draw->_cursorHotspotXVar = _vm->_parse->parseVarIndex() / 4;
- _vm->_draw->_cursorHotspotYVar = _vm->_parse->parseVarIndex() / 4;
+ _vm->_draw->_cursorHotspotXVar = _vm->_game->_script->readVarIndex() / 4;
+ _vm->_draw->_cursorHotspotYVar = _vm->_game->_script->readVarIndex() / 4;
- width = load16();
+ width = _vm->_game->_script->readInt16();
if (width < 16)
width = 16;
- height = load16();
+ height = _vm->_game->_script->readInt16();
if (height < 16)
height = 16;
_vm->_draw->adjustCoords(0, &width, &height);
- count = load16();
+ count = _vm->_game->_script->readInt16();
if (count < 2)
count = 2;
@@ -846,24 +366,24 @@ void Inter_v1::o1_initCursorAnim() {
int16 ind;
_vm->_draw->_showCursor = 3;
- ind = _vm->_parse->parseValExpr();
- _vm->_draw->_cursorAnimLow[ind] = load16();
- _vm->_draw->_cursorAnimHigh[ind] = load16();
- _vm->_draw->_cursorAnimDelays[ind] = load16();
+ ind = _vm->_game->_script->readValExpr();
+ _vm->_draw->_cursorAnimLow[ind] = _vm->_game->_script->readInt16();
+ _vm->_draw->_cursorAnimHigh[ind] = _vm->_game->_script->readInt16();
+ _vm->_draw->_cursorAnimDelays[ind] = _vm->_game->_script->readInt16();
}
void Inter_v1::o1_clearCursorAnim() {
int16 ind;
_vm->_draw->_showCursor = 0;
- ind = _vm->_parse->parseValExpr();
+ ind = _vm->_game->_script->readValExpr();
_vm->_draw->_cursorAnimLow[ind] = -1;
_vm->_draw->_cursorAnimHigh[ind] = 0;
_vm->_draw->_cursorAnimDelays[ind] = 0;
}
void Inter_v1::o1_setRenderFlags() {
- _vm->_draw->_renderFlags = _vm->_parse->parseValExpr();
+ _vm->_draw->_renderFlags = _vm->_game->_script->readValExpr();
}
void Inter_v1::o1_loadAnim() {
@@ -882,12 +402,12 @@ void Inter_v1::o1_updateAnim() {
int16 layer;
int16 animation;
- evalExpr(&deltaX);
- evalExpr(&deltaY);
- evalExpr(&animation);
- evalExpr(&layer);
- evalExpr(&frame);
- flags = load16();
+ _vm->_game->_script->evalExpr(&deltaX);
+ _vm->_game->_script->evalExpr(&deltaY);
+ _vm->_game->_script->evalExpr(&animation);
+ _vm->_game->_script->evalExpr(&layer);
+ _vm->_game->_script->evalExpr(&frame);
+ flags = _vm->_game->_script->readInt16();
_vm->_scenery->updateAnim(layer, frame, animation, flags,
deltaX, deltaY, 1);
}
@@ -904,14 +424,14 @@ void Inter_v1::o1_initMult() {
oldAnimHeight = _vm->_mult->_animHeight;
oldObjCount = _vm->_mult->_objCount;
- _vm->_mult->_animLeft = load16();
- _vm->_mult->_animTop = load16();
- _vm->_mult->_animWidth = load16();
- _vm->_mult->_animHeight = load16();
- _vm->_mult->_objCount = load16();
- posXVar = _vm->_parse->parseVarIndex();
- posYVar = _vm->_parse->parseVarIndex();
- animDataVar = _vm->_parse->parseVarIndex();
+ _vm->_mult->_animLeft = _vm->_game->_script->readInt16();
+ _vm->_mult->_animTop = _vm->_game->_script->readInt16();
+ _vm->_mult->_animWidth = _vm->_game->_script->readInt16();
+ _vm->_mult->_animHeight = _vm->_game->_script->readInt16();
+ _vm->_mult->_objCount = _vm->_game->_script->readInt16();
+ posXVar = _vm->_game->_script->readVarIndex();
+ posYVar = _vm->_game->_script->readVarIndex();
+ animDataVar = _vm->_game->_script->readVarIndex();
if (_vm->_mult->_objects && (oldObjCount != _vm->_mult->_objCount)) {
@@ -944,8 +464,8 @@ void Inter_v1::o1_initMult() {
uint32 offPosY = i * 4 + (posYVar / 4) * 4;
uint32 offAnim = animDataVar + i * 4 * _vm->_global->_inter_animDataSize;
- _vm->_mult->_objects[i].pPosX = new VariableReference(*_vm->_inter->_variables, offPosX);
- _vm->_mult->_objects[i].pPosY = new VariableReference(*_vm->_inter->_variables, offPosY);
+ _vm->_mult->_objects[i].pPosX = new VariableReference(*_variables, offPosX);
+ _vm->_mult->_objects[i].pPosY = new VariableReference(*_variables, offPosY);
_vm->_mult->_objects[i].pAnimData =
(Mult::Mult_AnimData *) _variables->getAddressOff8(offAnim);
@@ -998,21 +518,21 @@ void Inter_v1::o1_loadMultObject() {
int16 objIndex;
byte *multData;
- evalExpr(&objIndex);
- evalExpr(&val);
+ _vm->_game->_script->evalExpr(&objIndex);
+ _vm->_game->_script->evalExpr(&val);
*_vm->_mult->_objects[objIndex].pPosX = val;
- evalExpr(&val);
+ _vm->_game->_script->evalExpr(&val);
*_vm->_mult->_objects[objIndex].pPosY = val;
debugC(4, kDebugGameFlow, "Loading mult object %d", objIndex);
multData = (byte *) _vm->_mult->_objects[objIndex].pAnimData;
for (int i = 0; i < 11; i++) {
- if (READ_LE_UINT16(_vm->_global->_inter_execPtr) != 99) {
- evalExpr(&val);
+ if (_vm->_game->_script->peekUint16() != 99) {
+ _vm->_game->_script->evalExpr(&val);
multData[i] = val;
} else
- _vm->_global->_inter_execPtr++;
+ _vm->_game->_script->skip(1);
}
}
@@ -1023,13 +543,13 @@ void Inter_v1::o1_getAnimLayerInfo() {
int16 varUnk0;
int16 varFrames;
- evalExpr(&anim);
- evalExpr(&layer);
+ _vm->_game->_script->evalExpr(&anim);
+ _vm->_game->_script->evalExpr(&layer);
- varDX = _vm->_parse->parseVarIndex();
- varDY = _vm->_parse->parseVarIndex();
- varUnk0 = _vm->_parse->parseVarIndex();
- varFrames = _vm->_parse->parseVarIndex();
+ varDX = _vm->_game->_script->readVarIndex();
+ varDY = _vm->_game->_script->readVarIndex();
+ varUnk0 = _vm->_game->_script->readVarIndex();
+ varFrames = _vm->_game->_script->readVarIndex();
_vm->_scenery->writeAnimLayerInfo(anim, layer,
varDX, varDY, varUnk0, varFrames);
@@ -1038,7 +558,7 @@ void Inter_v1::o1_getAnimLayerInfo() {
void Inter_v1::o1_getObjAnimSize() {
int16 objIndex;
- evalExpr(&objIndex);
+ _vm->_game->_script->evalExpr(&objIndex);
Mult::Mult_AnimData &animData = *(_vm->_mult->_objects[objIndex].pAnimData);
if (animData.isStatic == 0)
@@ -1048,10 +568,10 @@ void Inter_v1::o1_getObjAnimSize() {
_vm->_scenery->_toRedrawLeft = MAX(_vm->_scenery->_toRedrawLeft, (int16) 0);
_vm->_scenery->_toRedrawTop = MAX(_vm->_scenery->_toRedrawTop, (int16) 0);
- WRITE_VAR_OFFSET(_vm->_parse->parseVarIndex(), _vm->_scenery->_toRedrawLeft);
- WRITE_VAR_OFFSET(_vm->_parse->parseVarIndex(), _vm->_scenery->_toRedrawTop);
- WRITE_VAR_OFFSET(_vm->_parse->parseVarIndex(), _vm->_scenery->_toRedrawRight);
- WRITE_VAR_OFFSET(_vm->_parse->parseVarIndex(), _vm->_scenery->_toRedrawBottom);
+ WRITE_VAR_OFFSET(_vm->_game->_script->readVarIndex(), _vm->_scenery->_toRedrawLeft);
+ WRITE_VAR_OFFSET(_vm->_game->_script->readVarIndex(), _vm->_scenery->_toRedrawTop);
+ WRITE_VAR_OFFSET(_vm->_game->_script->readVarIndex(), _vm->_scenery->_toRedrawRight);
+ WRITE_VAR_OFFSET(_vm->_game->_script->readVarIndex(), _vm->_scenery->_toRedrawBottom);
}
void Inter_v1::o1_loadStatic() {
@@ -1066,20 +586,20 @@ void Inter_v1::o1_renderStatic() {
int16 layer;
int16 index;
- _vm->_inter->evalExpr(&index);
- _vm->_inter->evalExpr(&layer);
+ _vm->_game->_script->evalExpr(&index);
+ _vm->_game->_script->evalExpr(&layer);
_vm->_scenery->renderStatic(index, layer);
}
void Inter_v1::o1_loadCurLayer() {
- evalExpr(&_vm->_scenery->_curStatic);
- evalExpr(&_vm->_scenery->_curStaticLayer);
+ _vm->_game->_script->evalExpr(&_vm->_scenery->_curStatic);
+ _vm->_game->_script->evalExpr(&_vm->_scenery->_curStaticLayer);
}
void Inter_v1::o1_playCDTrack() {
- evalExpr(0);
+ _vm->_game->_script->evalExpr(0);
_vm->_sound->adlibPlayBgMusic(); // Mac version
- _vm->_sound->cdPlay(_vm->_global->_inter_resStr); // PC CD version
+ _vm->_sound->cdPlay(_vm->_game->_script->getResultStr()); // PC CD version
}
void Inter_v1::o1_getCDTrackPos() {
@@ -1103,15 +623,15 @@ void Inter_v1::o1_stopCD() {
}
void Inter_v1::o1_loadFontToSprite() {
- int16 i = load16();
- _vm->_draw->_fontToSprite[i].sprite = load16();
- _vm->_draw->_fontToSprite[i].base = load16();
- _vm->_draw->_fontToSprite[i].width = load16();
- _vm->_draw->_fontToSprite[i].height = load16();
+ int16 i = _vm->_game->_script->readInt16();
+ _vm->_draw->_fontToSprite[i].sprite = _vm->_game->_script->readInt16();
+ _vm->_draw->_fontToSprite[i].base = _vm->_game->_script->readInt16();
+ _vm->_draw->_fontToSprite[i].width = _vm->_game->_script->readInt16();
+ _vm->_draw->_fontToSprite[i].height = _vm->_game->_script->readInt16();
}
void Inter_v1::o1_freeFontToSprite() {
- int16 i = load16();
+ int16 i = _vm->_game->_script->readInt16();
_vm->_draw->_fontToSprite[i].sprite = -1;
_vm->_draw->_fontToSprite[i].base = -1;
_vm->_draw->_fontToSprite[i].width = -1;
@@ -1119,11 +639,7 @@ void Inter_v1::o1_freeFontToSprite() {
}
bool Inter_v1::o1_callSub(OpFuncParams &params) {
- byte *storedIP;
- uint16 offset;
-
- offset = load16();
- storedIP = _vm->_global->_inter_execPtr;
+ uint16 offset = _vm->_game->_script->readUint16();
debugC(5, kDebugGameFlow, "tot = \"%s\", offset = %d",
_vm->_game->_curTotFile, offset);
@@ -1147,79 +663,89 @@ bool Inter_v1::o1_callSub(OpFuncParams &params) {
return false;
}
- _vm->_global->_inter_execPtr = _vm->_game->_totFileData + offset;
+ _vm->_game->_script->call(offset);
- if ((params.counter == params.cmdCount) && (params.retFlag == 2))
+ if ((params.counter == params.cmdCount) && (params.retFlag == 2)) {
+ _vm->_game->_script->pop(false);
return true;
+ }
callSub(2);
- _vm->_global->_inter_execPtr = storedIP;
+
+ _vm->_game->_script->pop();
return false;
}
bool Inter_v1::o1_printTotText(OpFuncParams &params) {
- _vm->_draw->printTotText(load16());
+ _vm->_draw->printTotText(_vm->_game->_script->readInt16());
return false;
}
bool Inter_v1::o1_loadCursor(OpFuncParams &params) {
- int16 width, height;
- byte *dataBuf;
- int16 id;
- int8 index;
-
- id = load16();
- index = (int8) *_vm->_global->_inter_execPtr++;
+ int16 id = _vm->_game->_script->readInt16();
+ int8 index = _vm->_game->_script->readInt8();
if ((index * _vm->_draw->_cursorWidth) >= _vm->_draw->_cursorSprites->getWidth())
return false;
- dataBuf = _vm->_game->loadTotResource(id, 0, &width, &height);
+ Resource *resource = _vm->_game->_resources->getResource(id);
+ if (!resource)
+ return false;
_vm->_video->fillRect(*_vm->_draw->_cursorSprites,
index * _vm->_draw->_cursorWidth, 0,
index * _vm->_draw->_cursorWidth + _vm->_draw->_cursorWidth - 1,
_vm->_draw->_cursorHeight - 1, 0);
- _vm->_video->drawPackedSprite(dataBuf, width, height,
+ _vm->_video->drawPackedSprite(resource->getData(),
+ resource->getWidth(), resource->getHeight(),
index * _vm->_draw->_cursorWidth, 0, 0, *_vm->_draw->_cursorSprites);
_vm->_draw->_cursorAnimLow[index] = 0;
+ delete resource;
return false;
}
bool Inter_v1::o1_switch(OpFuncParams &params) {
- byte *callAddr;
+ uint32 offset;
+
+ checkSwitchTable(offset);
- checkSwitchTable(&callAddr);
- byte *storedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = callAddr;
+ _vm->_game->_script->call(offset);
- if ((params.counter == params.cmdCount) && (params.retFlag == 2))
+ if (offset == 0)
+ _vm->_game->_script->setFinished(true);
+
+ if ((params.counter == params.cmdCount) && (params.retFlag == 2)) {
+ _vm->_game->_script->pop(false);
return true;
+ }
funcBlock(0);
- _vm->_global->_inter_execPtr = storedIP;
+
+ _vm->_game->_script->pop();
return false;
}
bool Inter_v1::o1_repeatUntil(OpFuncParams &params) {
- byte *blockPtr;
int16 size;
bool flag;
_nestLevel[0]++;
- blockPtr = _vm->_global->_inter_execPtr;
+
+ uint32 blockPos = _vm->_game->_script->pos();
do {
- _vm->_global->_inter_execPtr = blockPtr;
- size = READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ _vm->_game->_script->seek(blockPos);
+ size = _vm->_game->_script->peekUint16(2) + 2;
funcBlock(1);
- _vm->_global->_inter_execPtr = blockPtr + size + 1;
- flag = evalBoolResult();
+
+ _vm->_game->_script->seek(blockPos + size + 1);
+
+ flag = _vm->_game->_script->evalBoolResult();
} while (!flag && !_break && !_terminate && !_vm->shouldQuit());
_nestLevel[0]--;
@@ -1232,32 +758,31 @@ bool Inter_v1::o1_repeatUntil(OpFuncParams &params) {
}
bool Inter_v1::o1_whileDo(OpFuncParams &params) {
- byte *blockPtr;
- byte *savedIP;
bool flag;
int16 size;
_nestLevel[0]++;
do {
- savedIP = _vm->_global->_inter_execPtr;
- flag = evalBoolResult();
+ uint32 startPos = _vm->_game->_script->pos();
+
+ flag = _vm->_game->_script->evalBoolResult();
if (_terminate)
return false;
- blockPtr = _vm->_global->_inter_execPtr;
+ uint32 blockPos = _vm->_game->_script->pos();
- size = READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ size = _vm->_game->_script->peekUint16(2) + 2;
if (flag) {
funcBlock(1);
- _vm->_global->_inter_execPtr = savedIP;
+ _vm->_game->_script->seek(startPos);
} else
- _vm->_global->_inter_execPtr += size;
+ _vm->_game->_script->skip(size);
if (_break || _terminate || _vm->shouldQuit()) {
- _vm->_global->_inter_execPtr = blockPtr;
- _vm->_global->_inter_execPtr += size;
+ _vm->_game->_script->seek(blockPos);
+ _vm->_game->_script->skip(size);
break;
}
} while (flag);
@@ -1273,76 +798,65 @@ bool Inter_v1::o1_whileDo(OpFuncParams &params) {
bool Inter_v1::o1_if(OpFuncParams &params) {
byte cmd;
bool boolRes;
- byte *storedIP;
- boolRes = evalBoolResult();
+ boolRes = _vm->_game->_script->evalBoolResult();
if (boolRes) {
if ((params.counter == params.cmdCount) && (params.retFlag == 2))
return true;
- storedIP = _vm->_global->_inter_execPtr;
+ _vm->_game->_script->push();
funcBlock(0);
- _vm->_global->_inter_execPtr = storedIP;
+ _vm->_game->_script->pop();
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ _vm->_game->_script->skip(_vm->_game->_script->peekUint16(2) + 2);
- debugC(5, kDebugGameFlow, "cmd = %d",
- (int16) *_vm->_global->_inter_execPtr);
+ debugC(5, kDebugGameFlow, "cmd = %d", (int16) _vm->_game->_script->peekByte());
- cmd = *_vm->_global->_inter_execPtr >> 4;
- _vm->_global->_inter_execPtr++;
+ cmd = _vm->_game->_script->readByte() >> 4;
if (cmd != 12)
return false;
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ _vm->_game->_script->skip(_vm->_game->_script->peekUint16(2) + 2);
} else {
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ _vm->_game->_script->skip(_vm->_game->_script->peekUint16(2) + 2);
- debugC(5, kDebugGameFlow, "cmd = %d",
- (int16) *_vm->_global->_inter_execPtr);
+ debugC(5, kDebugGameFlow, "cmd = %d", (int16) _vm->_game->_script->peekByte());
- cmd = *_vm->_global->_inter_execPtr >> 4;
- _vm->_global->_inter_execPtr++;
+ cmd = _vm->_game->_script->readByte() >> 4;
if (cmd != 12)
return false;
if ((params.counter == params.cmdCount) && (params.retFlag == 2))
return true;
- storedIP = _vm->_global->_inter_execPtr;
+ _vm->_game->_script->push();
funcBlock(0);
- _vm->_global->_inter_execPtr = storedIP;
+ _vm->_game->_script->pop();
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ _vm->_game->_script->skip(_vm->_game->_script->peekUint16(2) + 2);
}
return false;
}
bool Inter_v1::o1_assign(OpFuncParams &params) {
- byte *savedPos;
- int16 token;
+ byte destType = _vm->_game->_script->peekByte();
+ int16 dest = _vm->_game->_script->readVarIndex();
+
int16 result;
- int16 varOff;
+ int16 srcType = _vm->_game->_script->evalExpr(&result);
- savedPos = _vm->_global->_inter_execPtr;
- varOff = _vm->_parse->parseVarIndex();
- token = evalExpr(&result);
- switch (savedPos[0]) {
- case 23:
- case 26:
- WRITE_VAR_OFFSET(varOff, _vm->_global->_inter_resVal);
+ switch (destType) {
+ case TYPE_VAR_INT32:
+ case TYPE_ARRAY_INT32:
+ WRITE_VAR_OFFSET(dest, _vm->_game->_script->getResultInt());
break;
- case 25:
- case 28:
- if (token == 20)
- WRITE_VARO_UINT8(varOff, result);
+ case TYPE_VAR_STR:
+ case TYPE_ARRAY_STR:
+ if (srcType == TYPE_IMM_INT16)
+ WRITE_VARO_UINT8(dest, result);
else
- WRITE_VARO_STR(varOff, _vm->_global->_inter_resStr);
+ WRITE_VARO_STR(dest, _vm->_game->_script->getResultStr());
break;
}
@@ -1350,17 +864,17 @@ bool Inter_v1::o1_assign(OpFuncParams &params) {
}
bool Inter_v1::o1_loadSpriteToPos(OpFuncParams &params) {
- _vm->_draw->_spriteLeft = load16();
+ _vm->_draw->_spriteLeft = _vm->_game->_script->readInt16();
- _vm->_draw->_destSpriteX = _vm->_parse->parseValExpr();
- _vm->_draw->_destSpriteY = _vm->_parse->parseValExpr();
+ _vm->_draw->_destSpriteX = _vm->_game->_script->readValExpr();
+ _vm->_draw->_destSpriteY = _vm->_game->_script->readValExpr();
- _vm->_draw->_transparency = *_vm->_global->_inter_execPtr & 1;
- _vm->_draw->_destSurface = ((int16) (*_vm->_global->_inter_execPtr >> 1)) - 1;
+ _vm->_draw->_transparency = _vm->_game->_script->peekByte() & 1;
+ _vm->_draw->_destSurface = ((int16) (_vm->_game->_script->peekByte() >> 1)) - 1;
if (_vm->_draw->_destSurface < 0)
_vm->_draw->_destSurface = 101;
- _vm->_global->_inter_execPtr += 2;
+ _vm->_game->_script->skip(2);
_vm->_draw->spriteOperation(DRAW_LOADSPRITE);
@@ -1371,12 +885,12 @@ bool Inter_v1::o1_printText(OpFuncParams &params) {
char buf[60];
int i;
- _vm->_draw->_destSpriteX = _vm->_parse->parseValExpr();
- _vm->_draw->_destSpriteY = _vm->_parse->parseValExpr();
+ _vm->_draw->_destSpriteX = _vm->_game->_script->readValExpr();
+ _vm->_draw->_destSpriteY = _vm->_game->_script->readValExpr();
- _vm->_draw->_backColor = _vm->_parse->parseValExpr();
- _vm->_draw->_frontColor = _vm->_parse->parseValExpr();
- _vm->_draw->_fontIndex = _vm->_parse->parseValExpr();
+ _vm->_draw->_backColor = _vm->_game->_script->readValExpr();
+ _vm->_draw->_frontColor = _vm->_game->_script->readValExpr();
+ _vm->_draw->_fontIndex = _vm->_game->_script->readValExpr();
_vm->_draw->_destSurface = 21;
_vm->_draw->_textToPrint = buf;
_vm->_draw->_transparency = 0;
@@ -1387,35 +901,35 @@ bool Inter_v1::o1_printText(OpFuncParams &params) {
}
do {
- for (i = 0; (((char) *_vm->_global->_inter_execPtr) != '.') &&
- (*_vm->_global->_inter_execPtr != 200);
- i++, _vm->_global->_inter_execPtr++) {
- buf[i] = (char) *_vm->_global->_inter_execPtr;
+ for (i = 0; ((_vm->_game->_script->peekChar()) != '.') &&
+ (_vm->_game->_script->peekByte() != 200);
+ i++, _vm->_game->_script->skip(1)) {
+ buf[i] = _vm->_game->_script->peekChar();
}
- if (*_vm->_global->_inter_execPtr != 200) {
- _vm->_global->_inter_execPtr++;
- switch (*_vm->_global->_inter_execPtr) {
- case 23:
- case 26:
+ if (_vm->_game->_script->peekByte() != 200) {
+ _vm->_game->_script->skip(1);
+ switch (_vm->_game->_script->peekByte()) {
+ case TYPE_VAR_INT32:
+ case TYPE_ARRAY_INT32:
sprintf(buf + i, "%d",
- VAR_OFFSET(_vm->_parse->parseVarIndex()));
+ VAR_OFFSET(_vm->_game->_script->readVarIndex()));
break;
- case 25:
- case 28:
+ case TYPE_VAR_STR:
+ case TYPE_ARRAY_STR:
sprintf(buf + i, "%s",
- GET_VARO_STR(_vm->_parse->parseVarIndex()));
+ GET_VARO_STR(_vm->_game->_script->readVarIndex()));
break;
}
- _vm->_global->_inter_execPtr++;
+ _vm->_game->_script->skip(1);
} else
buf[i] = 0;
_vm->_draw->spriteOperation(DRAW_PRINTTEXT);
- } while (*_vm->_global->_inter_execPtr != 200);
+ } while (_vm->_game->_script->peekByte() != 200);
- _vm->_global->_inter_execPtr++;
+ _vm->_game->_script->skip(1);
return false;
}
@@ -1424,16 +938,14 @@ bool Inter_v1::o1_loadTot(OpFuncParams &params) {
char buf[20];
int8 size;
- if ((*_vm->_global->_inter_execPtr & 0x80) != 0) {
- _vm->_global->_inter_execPtr++;
- evalExpr(0);
- strncpy0(buf, _vm->_global->_inter_resStr, 15);
+ if ((_vm->_game->_script->peekByte() & 0x80) != 0) {
+ _vm->_game->_script->skip(1);
+ _vm->_game->_script->evalExpr(0);
+ strncpy0(buf, _vm->_game->_script->getResultStr(), 15);
} else {
- size = (int8) *_vm->_global->_inter_execPtr++;
- for (int i = 0; i < size; i++)
- buf[i] = *_vm->_global->_inter_execPtr++;
-
- buf[size] = 0;
+ size = _vm->_game->_script->readInt8();
+ memcpy(buf, _vm->_game->_script->readString(size), size);
+ buf[size] = '\0';
}
// if (_vm->getGameType() == kGameTypeGeisha)
@@ -1450,15 +962,15 @@ bool Inter_v1::o1_loadTot(OpFuncParams &params) {
bool Inter_v1::o1_palLoad(OpFuncParams &params) {
int index1, index2;
- byte *palPtr;
byte cmd;
+ Resource *resource;
- cmd = *_vm->_global->_inter_execPtr++;
+ cmd = _vm->_game->_script->readByte();
switch (cmd & 0x7F) {
case 48:
if ((_vm->_global->_fakeVideoMode < 0x32) ||
(_vm->_global->_fakeVideoMode > 0x63)) {
- _vm->_global->_inter_execPtr += 48;
+ _vm->_game->_script->skip(48);
return false;
}
break;
@@ -1466,35 +978,35 @@ bool Inter_v1::o1_palLoad(OpFuncParams &params) {
case 49:
if ((_vm->_global->_fakeVideoMode != 5) &&
(_vm->_global->_fakeVideoMode != 7)) {
- _vm->_global->_inter_execPtr += 18;
+ _vm->_game->_script->skip(18);
return false;
}
break;
case 50:
if (_vm->_global->_colorCount == 256) {
- _vm->_global->_inter_execPtr += 16;
+ _vm->_game->_script->skip(16);
return false;
}
break;
case 51:
if (_vm->_global->_fakeVideoMode < 0x64) {
- _vm->_global->_inter_execPtr += 2;
+ _vm->_game->_script->skip(2);
return false;
}
break;
case 52:
if (_vm->_global->_colorCount == 256) {
- _vm->_global->_inter_execPtr += 48;
+ _vm->_game->_script->skip(48);
return false;
}
break;
case 53:
if (_vm->_global->_colorCount != 256) {
- _vm->_global->_inter_execPtr += 2;
+ _vm->_game->_script->skip(2);
return false;
}
break;
@@ -1507,14 +1019,14 @@ bool Inter_v1::o1_palLoad(OpFuncParams &params) {
case 61:
if (_vm->_global->_fakeVideoMode < 0x13) {
- _vm->_global->_inter_execPtr += 4;
+ _vm->_game->_script->skip(4);
return false;
}
break;
}
if ((cmd & 0x7F) == 0x30) {
- _vm->_global->_inter_execPtr += 48;
+ _vm->_game->_script->skip(48);
return false;
}
@@ -1525,7 +1037,7 @@ bool Inter_v1::o1_palLoad(OpFuncParams &params) {
bool allZero = true;
for (int i = 2; i < 18; i++) {
- if (_vm->_global->_inter_execPtr[i] != 0) {
+ if (_vm->_game->_script->peekByte(i) != 0) {
allZero = false;
break;
}
@@ -1533,28 +1045,30 @@ bool Inter_v1::o1_palLoad(OpFuncParams &params) {
if (!allZero) {
_vm->_video->clearSurf(*_vm->_draw->_frontSurface);
_vm->_draw->_noInvalidated57 = true;
- _vm->_global->_inter_execPtr += 18;
+ _vm->_game->_script->skip(48);
return false;
}
_vm->_draw->_noInvalidated57 = false;
- for (int i = 0; i < 18; i++, _vm->_global->_inter_execPtr++) {
+ for (int i = 0; i < 18; i++) {
if (i < 2) {
if (!_vm->_draw->_applyPal)
continue;
- _vm->_draw->_unusedPalette1[i] = *_vm->_global->_inter_execPtr;
+ _vm->_draw->_unusedPalette1[i] = _vm->_game->_script->peekByte();
continue;
}
- index1 = *_vm->_global->_inter_execPtr >> 4;
- index2 = (*_vm->_global->_inter_execPtr & 0xF);
+ index1 = _vm->_game->_script->peekByte() >> 4;
+ index2 = _vm->_game->_script->peekByte() & 0xF;
_vm->_draw->_unusedPalette1[i] =
((_vm->_draw->_palLoadData1[index1] +
_vm->_draw->_palLoadData2[index2]) << 8) +
(_vm->_draw->_palLoadData2[index1] +
_vm->_draw->_palLoadData1[index2]);
+
+ _vm->_game->_script->skip(1);
}
_vm->_global->_pPaletteDesc->unused1 = _vm->_draw->_unusedPalette1;
@@ -1564,21 +1078,25 @@ bool Inter_v1::o1_palLoad(OpFuncParams &params) {
switch (cmd) {
case 50:
- for (int i = 0; i < 16; i++, _vm->_global->_inter_execPtr++)
- _vm->_draw->_unusedPalette2[i] = *_vm->_global->_inter_execPtr;
+ for (int i = 0; i < 16; i++)
+ _vm->_draw->_unusedPalette2[i] = _vm->_game->_script->readByte();
break;
case 52:
- for (int i = 0; i < 16; i++, _vm->_global->_inter_execPtr += 3) {
- _vm->_draw->_vgaPalette[i].red = _vm->_global->_inter_execPtr[0];
- _vm->_draw->_vgaPalette[i].green = _vm->_global->_inter_execPtr[1];
- _vm->_draw->_vgaPalette[i].blue = _vm->_global->_inter_execPtr[2];
+ for (int i = 0; i < 16; i++) {
+ _vm->_draw->_vgaPalette[i].red = _vm->_game->_script->readByte();
+ _vm->_draw->_vgaPalette[i].green = _vm->_game->_script->readByte();
+ _vm->_draw->_vgaPalette[i].blue = _vm->_game->_script->readByte();
}
break;
case 53:
- palPtr = _vm->_game->loadTotResource(_vm->_inter->load16());
- memcpy((char *) _vm->_draw->_vgaPalette, palPtr, 768);
+ resource = _vm->_game->_resources->getResource(_vm->_game->_script->readInt16());
+ if (!resource)
+ break;
+
+ memcpy((char *) _vm->_draw->_vgaPalette, resource->getData(), MIN(768, resource->getSize()));
+ delete resource;
break;
case 54:
@@ -1586,11 +1104,15 @@ bool Inter_v1::o1_palLoad(OpFuncParams &params) {
break;
case 61:
- index1 = *_vm->_global->_inter_execPtr++;
- index2 = (*_vm->_global->_inter_execPtr++ - index1 + 1) * 3;
- palPtr = _vm->_game->loadTotResource(_vm->_inter->load16());
+ index1 = _vm->_game->_script->readByte();
+ index2 = (_vm->_game->_script->readByte() - index1 + 1) * 3;
+ resource = _vm->_game->_resources->getResource(_vm->_game->_script->readInt16());
+ if (!resource)
+ break;
+
memcpy((char *) _vm->_draw->_vgaPalette + index1 * 3,
- palPtr + index1 * 3, index2);
+ resource->getData() + index1 * 3, index2);
+ delete resource;
if (_vm->_draw->_applyPal) {
_vm->_draw->_applyPal = false;
@@ -1628,7 +1150,7 @@ bool Inter_v1::o1_keyFunc(OpFuncParams &params) {
int16 key;
uint32 now;
- cmd = load16();
+ cmd = _vm->_game->_script->readInt16();
animPalette();
_vm->_draw->blitInvalidated();
@@ -1643,7 +1165,7 @@ bool Inter_v1::o1_keyFunc(OpFuncParams &params) {
// to become 5000. We deliberately slow down busy-waiting, so we shorten
// the counting, too.
if ((_vm->getGameType() == kGameTypeWeen) && (VAR(59) < 4000) &&
- ((_vm->_global->_inter_execPtr - _vm->_game->_totFileData) == 729) &&
+ (_vm->_game->_script->pos() == 729) &&
!scumm_stricmp(_vm->_game->_curTotFile, "intro5.tot"))
WRITE_VAR(59, 4000);
@@ -1689,10 +1211,10 @@ bool Inter_v1::o1_capturePush(OpFuncParams &params) {
int16 left, top;
int16 width, height;
- left = _vm->_parse->parseValExpr();
- top = _vm->_parse->parseValExpr();
- width = _vm->_parse->parseValExpr();
- height = _vm->_parse->parseValExpr();
+ left = _vm->_game->_script->readValExpr();
+ top = _vm->_game->_script->readValExpr();
+ width = _vm->_game->_script->readValExpr();
+ height = _vm->_game->_script->readValExpr();
if ((width < 0) || (height < 0))
return false;
@@ -1711,24 +1233,24 @@ bool Inter_v1::o1_capturePop(OpFuncParams &params) {
}
bool Inter_v1::o1_animPalInit(OpFuncParams &params) {
- _animPalDir[0] = load16();
- _animPalLowIndex[0] = _vm->_parse->parseValExpr();
- _animPalHighIndex[0] = _vm->_parse->parseValExpr();
+ _animPalDir[0] = _vm->_game->_script->readInt16();
+ _animPalLowIndex[0] = _vm->_game->_script->readValExpr();
+ _animPalHighIndex[0] = _vm->_game->_script->readValExpr();
return false;
}
bool Inter_v1::o1_drawOperations(OpFuncParams &params) {
byte cmd;
- cmd = *_vm->_global->_inter_execPtr++;
+ cmd = _vm->_game->_script->readByte();
- executeDrawOpcode(cmd);
+ executeOpcodeDraw(cmd);
return false;
}
bool Inter_v1::o1_setcmdCount(OpFuncParams &params) {
- params.cmdCount = *_vm->_global->_inter_execPtr++;
+ params.cmdCount = _vm->_game->_script->readByte();
params.counter = 0;
return false;
}
@@ -1737,7 +1259,7 @@ bool Inter_v1::o1_return(OpFuncParams &params) {
if (params.retFlag != 2)
_break = true;
- _vm->_global->_inter_execPtr = 0;
+ _vm->_game->_script->setFinished(true);
return true;
}
@@ -1747,7 +1269,7 @@ bool Inter_v1::o1_renewTimeInVars(OpFuncParams &params) {
}
bool Inter_v1::o1_speakerOn(OpFuncParams &params) {
- _vm->_sound->speakerOn(_vm->_parse->parseValExpr(), -1);
+ _vm->_sound->speakerOn(_vm->_game->_script->readValExpr(), -1);
return false;
}
@@ -1757,11 +1279,11 @@ bool Inter_v1::o1_speakerOff(OpFuncParams &params) {
}
bool Inter_v1::o1_putPixel(OpFuncParams &params) {
- _vm->_draw->_destSurface = load16();
+ _vm->_draw->_destSurface = _vm->_game->_script->readInt16();
- _vm->_draw->_destSpriteX = _vm->_parse->parseValExpr();
- _vm->_draw->_destSpriteY = _vm->_parse->parseValExpr();
- _vm->_draw->_frontColor = _vm->_parse->parseValExpr();
+ _vm->_draw->_destSpriteX = _vm->_game->_script->readValExpr();
+ _vm->_draw->_destSpriteY = _vm->_game->_script->readValExpr();
+ _vm->_draw->_frontColor = _vm->_game->_script->readValExpr();
_vm->_draw->spriteOperation(DRAW_PUTPIXEL);
return false;
}
@@ -1773,33 +1295,33 @@ bool Inter_v1::o1_goblinFunc(OpFuncParams &params) {
gobParams.extraData = 0;
gobParams.objDesc = 0;
- gobParams.retVarPtr.set(*_vm->_inter->_variables, 236);
+ gobParams.retVarPtr.set(*_variables, 236);
- cmd = load16();
- _vm->_global->_inter_execPtr += 2;
+ cmd = _vm->_game->_script->readInt16();
+ _vm->_game->_script->skip(2);
if ((cmd > 0) && (cmd < 17)) {
objDescSet = true;
- gobParams.extraData = load16();
+ gobParams.extraData = _vm->_game->_script->readInt16();
gobParams.objDesc = _vm->_goblin->_objects[gobParams.extraData];
- gobParams.extraData = load16();
+ gobParams.extraData = _vm->_game->_script->readInt16();
}
if ((cmd > 90) && (cmd < 107)) {
objDescSet = true;
- gobParams.extraData = load16();
+ gobParams.extraData = _vm->_game->_script->readInt16();
gobParams.objDesc = _vm->_goblin->_goblins[gobParams.extraData];
- gobParams.extraData = load16();
+ gobParams.extraData = _vm->_game->_script->readInt16();
cmd -= 90;
}
if ((cmd > 110) && (cmd < 128)) {
objDescSet = true;
- gobParams.extraData = load16();
+ gobParams.extraData = _vm->_game->_script->readInt16();
gobParams.objDesc = _vm->_goblin->_goblins[gobParams.extraData];
cmd -= 90;
} else if ((cmd > 20) && (cmd < 38)) {
objDescSet = true;
- gobParams.extraData = load16();
+ gobParams.extraData = _vm->_game->_script->readInt16();
gobParams.objDesc = _vm->_goblin->_objects[gobParams.extraData];
}
@@ -1815,7 +1337,7 @@ bool Inter_v1::o1_goblinFunc(OpFuncParams &params) {
if ((cmd < 40) && objDescSet && !gobParams.objDesc)
return false;
- executeGoblinOpcode(cmd, gobParams);
+ executeOpcodeGob(cmd, gobParams);
return false;
}
@@ -1825,31 +1347,31 @@ bool Inter_v1::o1_createSprite(OpFuncParams &params) {
int16 width, height;
int16 flag;
- if (_vm->_global->_inter_execPtr[1] == 0) {
- index = load16();
- width = load16();
- height = load16();
+ if (_vm->_game->_script->peekByte(1) == 0) {
+ index = _vm->_game->_script->readInt16();
+ width = _vm->_game->_script->readInt16();
+ height = _vm->_game->_script->readInt16();
} else {
- index = _vm->_parse->parseValExpr();
- width = _vm->_parse->parseValExpr();
- height = _vm->_parse->parseValExpr();
+ index = _vm->_game->_script->readValExpr();
+ width = _vm->_game->_script->readValExpr();
+ height = _vm->_game->_script->readValExpr();
}
- flag = load16();
+ flag = _vm->_game->_script->readInt16();
_vm->_draw->initSpriteSurf(index, width, height, flag ? 2 : 0);
return false;
}
bool Inter_v1::o1_freeSprite(OpFuncParams &params) {
- _vm->_draw->freeSprite(load16());
+ _vm->_draw->freeSprite(_vm->_game->_script->readInt16());
return false;
}
bool Inter_v1::o1_returnTo(OpFuncParams &params) {
if (params.retFlag == 1) {
_break = true;
- _vm->_global->_inter_execPtr = 0;
+ _vm->_game->_script->setFinished(true);
return true;
}
@@ -1858,14 +1380,14 @@ bool Inter_v1::o1_returnTo(OpFuncParams &params) {
*_breakFromLevel = *_nestLevel;
_break = true;
- _vm->_global->_inter_execPtr = 0;
+ _vm->_game->_script->setFinished(true);
return true;
}
bool Inter_v1::o1_loadSpriteContent(OpFuncParams &params) {
- _vm->_draw->_spriteLeft = load16();
- _vm->_draw->_destSurface = load16();
- _vm->_draw->_transparency = load16();
+ _vm->_draw->_spriteLeft = _vm->_game->_script->readInt16();
+ _vm->_draw->_destSurface = _vm->_game->_script->readInt16();
+ _vm->_draw->_transparency = _vm->_game->_script->readInt16();
_vm->_draw->_destSpriteX = 0;
_vm->_draw->_destSpriteY = 0;
@@ -1874,25 +1396,25 @@ bool Inter_v1::o1_loadSpriteContent(OpFuncParams &params) {
}
bool Inter_v1::o1_copySprite(OpFuncParams &params) {
- if (_vm->_global->_inter_execPtr[1] == 0)
- _vm->_draw->_sourceSurface = load16();
+ if (_vm->_game->_script->peekByte(1) == 0)
+ _vm->_draw->_sourceSurface = _vm->_game->_script->readInt16();
else
- _vm->_draw->_sourceSurface = _vm->_parse->parseValExpr();
+ _vm->_draw->_sourceSurface = _vm->_game->_script->readValExpr();
- if (_vm->_global->_inter_execPtr[1] == 0)
- _vm->_draw->_destSurface = load16();
+ if (_vm->_game->_script->peekByte(1) == 0)
+ _vm->_draw->_destSurface = _vm->_game->_script->readInt16();
else
- _vm->_draw->_destSurface = _vm->_parse->parseValExpr();
+ _vm->_draw->_destSurface = _vm->_game->_script->readValExpr();
- _vm->_draw->_spriteLeft = _vm->_parse->parseValExpr();
- _vm->_draw->_spriteTop = _vm->_parse->parseValExpr();
- _vm->_draw->_spriteRight = _vm->_parse->parseValExpr();
- _vm->_draw->_spriteBottom = _vm->_parse->parseValExpr();
+ _vm->_draw->_spriteLeft = _vm->_game->_script->readValExpr();
+ _vm->_draw->_spriteTop = _vm->_game->_script->readValExpr();
+ _vm->_draw->_spriteRight = _vm->_game->_script->readValExpr();
+ _vm->_draw->_spriteBottom = _vm->_game->_script->readValExpr();
- _vm->_draw->_destSpriteX = _vm->_parse->parseValExpr();
- _vm->_draw->_destSpriteY = _vm->_parse->parseValExpr();
+ _vm->_draw->_destSpriteX = _vm->_game->_script->readValExpr();
+ _vm->_draw->_destSpriteY = _vm->_game->_script->readValExpr();
- _vm->_draw->_transparency = load16();
+ _vm->_draw->_transparency = _vm->_game->_script->readInt16();
_vm->_draw->spriteOperation(DRAW_BLITSURF);
return false;
@@ -1901,14 +1423,14 @@ bool Inter_v1::o1_copySprite(OpFuncParams &params) {
bool Inter_v1::o1_fillRect(OpFuncParams &params) {
int16 destSurf;
- _vm->_draw->_destSurface = destSurf = load16();
+ _vm->_draw->_destSurface = destSurf = _vm->_game->_script->readInt16();
- _vm->_draw->_destSpriteX = _vm->_parse->parseValExpr();
- _vm->_draw->_destSpriteY = _vm->_parse->parseValExpr();
- _vm->_draw->_spriteRight = _vm->_parse->parseValExpr();
- _vm->_draw->_spriteBottom = _vm->_parse->parseValExpr();
+ _vm->_draw->_destSpriteX = _vm->_game->_script->readValExpr();
+ _vm->_draw->_destSpriteY = _vm->_game->_script->readValExpr();
+ _vm->_draw->_spriteRight = _vm->_game->_script->readValExpr();
+ _vm->_draw->_spriteBottom = _vm->_game->_script->readValExpr();
- _vm->_draw->_backColor = _vm->_parse->parseValExpr();
+ _vm->_draw->_backColor = _vm->_game->_script->readValExpr();
if (!_vm->_draw->_spritesArray[(destSurf >= 100) ? (destSurf - 80) : destSurf])
return false;
@@ -1927,14 +1449,14 @@ bool Inter_v1::o1_fillRect(OpFuncParams &params) {
}
bool Inter_v1::o1_drawLine(OpFuncParams &params) {
- _vm->_draw->_destSurface = load16();
+ _vm->_draw->_destSurface = _vm->_game->_script->readInt16();
- _vm->_draw->_destSpriteX = _vm->_parse->parseValExpr();
- _vm->_draw->_destSpriteY = _vm->_parse->parseValExpr();
- _vm->_draw->_spriteRight = _vm->_parse->parseValExpr();
- _vm->_draw->_spriteBottom = _vm->_parse->parseValExpr();
+ _vm->_draw->_destSpriteX = _vm->_game->_script->readValExpr();
+ _vm->_draw->_destSpriteY = _vm->_game->_script->readValExpr();
+ _vm->_draw->_spriteRight = _vm->_game->_script->readValExpr();
+ _vm->_draw->_spriteBottom = _vm->_game->_script->readValExpr();
- _vm->_draw->_frontColor = _vm->_parse->parseValExpr();
+ _vm->_draw->_frontColor = _vm->_game->_script->readValExpr();
_vm->_draw->spriteOperation(DRAW_DRAWLINE);
return false;
}
@@ -1945,28 +1467,28 @@ bool Inter_v1::o1_strToLong(OpFuncParams &params) {
int16 destVar;
int32 res;
- strVar = _vm->_parse->parseVarIndex();
+ strVar = _vm->_game->_script->readVarIndex();
strncpy0(str, GET_VARO_STR(strVar), 19);
res = atoi(str);
- destVar = _vm->_parse->parseVarIndex();
+ destVar = _vm->_game->_script->readVarIndex();
WRITE_VAR_OFFSET(destVar, res);
return false;
}
bool Inter_v1::o1_invalidate(OpFuncParams &params) {
- _vm->_draw->_destSurface = load16();
- _vm->_draw->_destSpriteX = _vm->_parse->parseValExpr();
- _vm->_draw->_destSpriteY = _vm->_parse->parseValExpr();
- _vm->_draw->_spriteRight = _vm->_parse->parseValExpr();
- _vm->_draw->_frontColor = _vm->_parse->parseValExpr();
+ _vm->_draw->_destSurface = _vm->_game->_script->readInt16();
+ _vm->_draw->_destSpriteX = _vm->_game->_script->readValExpr();
+ _vm->_draw->_destSpriteY = _vm->_game->_script->readValExpr();
+ _vm->_draw->_spriteRight = _vm->_game->_script->readValExpr();
+ _vm->_draw->_frontColor = _vm->_game->_script->readValExpr();
_vm->_draw->spriteOperation(DRAW_INVALIDATE);
return false;
}
bool Inter_v1::o1_setBackDelta(OpFuncParams &params) {
- _vm->_draw->_backDeltaX = _vm->_parse->parseValExpr();
- _vm->_draw->_backDeltaY = _vm->_parse->parseValExpr();
+ _vm->_draw->_backDeltaX = _vm->_game->_script->readValExpr();
+ _vm->_draw->_backDeltaY = _vm->_game->_script->readValExpr();
return false;
}
@@ -1977,9 +1499,9 @@ bool Inter_v1::o1_playSound(OpFuncParams &params) {
int16 index;
int16 endRep;
- index = _vm->_parse->parseValExpr();
- repCount = _vm->_parse->parseValExpr();
- frequency = _vm->_parse->parseValExpr();
+ index = _vm->_game->_script->readValExpr();
+ repCount = _vm->_game->_script->readValExpr();
+ frequency = _vm->_game->_script->readValExpr();
SoundDesc *sample = _vm->_sound->sampleGetBySlot(index);
@@ -2002,7 +1524,7 @@ bool Inter_v1::o1_playSound(OpFuncParams &params) {
}
if (sample->getType() == SOUND_ADL) {
- _vm->_sound->adlibLoad(sample->getData(), sample->size(), index);
+ _vm->_sound->adlibLoadADL(sample->getData(), sample->size(), index);
_vm->_sound->adlibSetRepeating(repCount - 1);
_vm->_sound->adlibPlay();
} else {
@@ -2015,7 +1537,7 @@ bool Inter_v1::o1_playSound(OpFuncParams &params) {
bool Inter_v1::o1_stopSound(OpFuncParams &params) {
_vm->_sound->adlibStop();
- _vm->_sound->blasterStop(_vm->_parse->parseValExpr());
+ _vm->_sound->blasterStop(_vm->_game->_script->readValExpr());
_soundEndTimeKey = 0;
return false;
@@ -2041,8 +1563,8 @@ bool Inter_v1::o1_playComposition(OpFuncParams &params) {
int16 dataVar;
int16 freqVal;
- dataVar = _vm->_parse->parseVarIndex();
- freqVal = _vm->_parse->parseValExpr();
+ dataVar = _vm->_game->_script->readVarIndex();
+ freqVal = _vm->_game->_script->readValExpr();
for (int i = 0; i < 50; i++)
composition[i] = (int16) VAR_OFFSET(dataVar + i * 4);
@@ -2054,8 +1576,8 @@ bool Inter_v1::o1_getFreeMem(OpFuncParams &params) {
int16 freeVar;
int16 maxFreeVar;
- freeVar = _vm->_parse->parseVarIndex();
- maxFreeVar = _vm->_parse->parseVarIndex();
+ freeVar = _vm->_game->_script->readVarIndex();
+ maxFreeVar = _vm->_game->_script->readVarIndex();
// HACK
WRITE_VAR_OFFSET(freeVar, 1000000);
@@ -2067,22 +1589,22 @@ bool Inter_v1::o1_checkData(OpFuncParams &params) {
int16 handle;
int16 varOff;
- evalExpr(0);
- varOff = _vm->_parse->parseVarIndex();
- handle = _vm->_dataIO->openData(_vm->_global->_inter_resStr);
+ _vm->_game->_script->evalExpr(0);
+ varOff = _vm->_game->_script->readVarIndex();
+ handle = _vm->_dataIO->openData(_vm->_game->_script->getResultStr());
WRITE_VAR_OFFSET(varOff, handle);
if (handle >= 0)
_vm->_dataIO->closeData(handle);
else
- warning("File \"%s\" not found", _vm->_global->_inter_resStr);
+ warning("File \"%s\" not found", _vm->_game->_script->getResultStr());
return false;
}
bool Inter_v1::o1_prepareStr(OpFuncParams &params) {
int16 strVar;
- strVar = _vm->_parse->parseVarIndex();
+ strVar = _vm->_game->_script->readVarIndex();
_vm->_util->prepareStr(GET_VARO_FSTR(strVar));
return false;
}
@@ -2091,12 +1613,12 @@ bool Inter_v1::o1_insertStr(OpFuncParams &params) {
int16 pos;
int16 strVar;
- strVar = _vm->_parse->parseVarIndex();
- evalExpr(0);
- pos = _vm->_parse->parseValExpr();
+ strVar = _vm->_game->_script->readVarIndex();
+ _vm->_game->_script->evalExpr(0);
+ pos = _vm->_game->_script->readValExpr();
char *str = GET_VARO_FSTR(strVar);
- _vm->_util->insertStr(_vm->_global->_inter_resStr, str, pos);
+ _vm->_util->insertStr(_vm->_game->_script->getResultStr(), str, pos);
return false;
}
@@ -2105,9 +1627,9 @@ bool Inter_v1::o1_cutStr(OpFuncParams &params) {
int16 pos;
int16 size;
- strVar = _vm->_parse->parseVarIndex();
- pos = _vm->_parse->parseValExpr();
- size = _vm->_parse->parseValExpr();
+ strVar = _vm->_game->_script->readVarIndex();
+ pos = _vm->_game->_script->readValExpr();
+ size = _vm->_game->_script->readValExpr();
_vm->_util->cutFromStr(GET_VARO_STR(strVar), pos, size);
return false;
}
@@ -2117,11 +1639,11 @@ bool Inter_v1::o1_strstr(OpFuncParams &params) {
int16 resVar;
int16 pos;
- strVar = _vm->_parse->parseVarIndex();
- evalExpr(0);
- resVar = _vm->_parse->parseVarIndex();
+ strVar = _vm->_game->_script->readVarIndex();
+ _vm->_game->_script->evalExpr(0);
+ resVar = _vm->_game->_script->readVarIndex();
- char *res = strstr(GET_VARO_STR(strVar), _vm->_global->_inter_resStr);
+ char *res = strstr(GET_VARO_STR(strVar), _vm->_game->_script->getResultStr());
pos = res ? (res - (GET_VARO_STR(strVar))) : -1;
WRITE_VAR_OFFSET(resVar, pos);
return false;
@@ -2131,17 +1653,17 @@ bool Inter_v1::o1_istrlen(OpFuncParams &params) {
int16 len;
int16 strVar;
- strVar = _vm->_parse->parseVarIndex();
+ strVar = _vm->_game->_script->readVarIndex();
len = strlen(GET_VARO_STR(strVar));
- strVar = _vm->_parse->parseVarIndex();
+ strVar = _vm->_game->_script->readVarIndex();
WRITE_VAR_OFFSET(strVar, len);
return false;
}
bool Inter_v1::o1_setMousePos(OpFuncParams &params) {
- _vm->_global->_inter_mouseX = _vm->_parse->parseValExpr();
- _vm->_global->_inter_mouseY = _vm->_parse->parseValExpr();
+ _vm->_global->_inter_mouseX = _vm->_game->_script->readValExpr();
+ _vm->_global->_inter_mouseY = _vm->_game->_script->readValExpr();
_vm->_global->_inter_mouseX -= _vm->_video->_scrollOffsetX;
_vm->_global->_inter_mouseY -= _vm->_video->_scrollOffsetY;
if (_vm->_global->_useMouse != 0)
@@ -2151,7 +1673,7 @@ bool Inter_v1::o1_setMousePos(OpFuncParams &params) {
}
bool Inter_v1::o1_setFrameRate(OpFuncParams &params) {
- _vm->_util->setFrameRate(_vm->_parse->parseValExpr());
+ _vm->_util->setFrameRate(_vm->_game->_script->readValExpr());
return false;
}
@@ -2177,27 +1699,23 @@ bool Inter_v1::o1_blitCursor(OpFuncParams &params) {
bool Inter_v1::o1_loadFont(OpFuncParams &params) {
int16 index;
- evalExpr(0);
- index = load16();
+ _vm->_game->_script->evalExpr(0);
+ index = _vm->_game->_script->readInt16();
delete _vm->_draw->_fonts[index];
_vm->_draw->animateCursor(4);
- if (_vm->_game->_extHandle >= 0)
- _vm->_dataIO->closeData(_vm->_game->_extHandle);
_vm->_draw->_fonts[index] =
- _vm->_util->loadFont(_vm->_global->_inter_resStr);
+ _vm->_util->loadFont(_vm->_game->_script->getResultStr());
- if (_vm->_game->_extHandle >= 0)
- _vm->_game->_extHandle = _vm->_dataIO->openData(_vm->_game->_curExtFile);
return false;
}
bool Inter_v1::o1_freeFont(OpFuncParams &params) {
int16 index;
- index = load16();
+ index = _vm->_game->_script->readInt16();
delete _vm->_draw->_fonts[index];
_vm->_draw->_fonts[index] = 0;
return false;
@@ -2210,17 +1728,14 @@ bool Inter_v1::o1_readData(OpFuncParams &params) {
int16 offset;
int16 handle;
- evalExpr(0);
- dataVar = _vm->_parse->parseVarIndex();
- size = _vm->_parse->parseValExpr();
- offset = _vm->_parse->parseValExpr();
+ _vm->_game->_script->evalExpr(0);
+ dataVar = _vm->_game->_script->readVarIndex();
+ size = _vm->_game->_script->readValExpr();
+ offset = _vm->_game->_script->readValExpr();
retSize = 0;
- if (_vm->_game->_extHandle >= 0)
- _vm->_dataIO->closeData(_vm->_game->_extHandle);
-
WRITE_VAR(1, 1);
- handle = _vm->_dataIO->openData(_vm->_global->_inter_resStr);
+ handle = _vm->_dataIO->openData(_vm->_game->_script->getResultStr());
if (handle >= 0) {
DataStream *stream = _vm->_dataIO->openAsStream(handle, true);
@@ -2241,8 +1756,6 @@ bool Inter_v1::o1_readData(OpFuncParams &params) {
delete stream;
}
- if (_vm->_game->_extHandle >= 0)
- _vm->_game->_extHandle = _vm->_dataIO->openData(_vm->_game->_curExtFile);
return false;
}
@@ -2255,22 +1768,22 @@ bool Inter_v1::o1_writeData(OpFuncParams &params) {
// (Gobliiins 1 doesn't use save file), so we just warn should it be
// called regardless.
- evalExpr(0);
- dataVar = _vm->_parse->parseVarIndex();
- size = _vm->_parse->parseValExpr();
- offset = _vm->_parse->parseValExpr();
+ _vm->_game->_script->evalExpr(0);
+ dataVar = _vm->_game->_script->readVarIndex();
+ size = _vm->_game->_script->readValExpr();
+ offset = _vm->_game->_script->readValExpr();
- warning("Attempted to write to file \"%s\"", _vm->_global->_inter_resStr);
+ warning("Attempted to write to file \"%s\"", _vm->_game->_script->getResultStr());
WRITE_VAR(1, 0);
return false;
}
bool Inter_v1::o1_manageDataFile(OpFuncParams &params) {
- evalExpr(0);
+ _vm->_game->_script->evalExpr(0);
- if (_vm->_global->_inter_resStr[0] != 0)
- _vm->_dataIO->openDataFile(_vm->_global->_inter_resStr);
+ if (_vm->_game->_script->getResultStr()[0] != 0)
+ _vm->_dataIO->openDataFile(_vm->_game->_script->getResultStr());
else
_vm->_dataIO->closeDataFile();
return false;
@@ -2434,16 +1947,16 @@ void Inter_v1::o1_getMaxTick(OpGobParams &params) {
}
void Inter_v1::o1_manipulateMap(OpGobParams &params) {
- int16 xPos = load16();
- int16 yPos = load16();
- int16 item = load16();
+ int16 xPos = _vm->_game->_script->readInt16();
+ int16 yPos = _vm->_game->_script->readInt16();
+ int16 item = _vm->_game->_script->readInt16();
manipulateMap(xPos, yPos, item);
}
void Inter_v1::o1_getItem(OpGobParams &params) {
- int16 xPos = load16();
- int16 yPos = load16();
+ int16 xPos = _vm->_game->_script->readInt16();
+ int16 yPos = _vm->_game->_script->readInt16();
if ((_vm->_map->getItem(xPos, yPos) & 0xFF00) != 0)
params.retVarPtr = (uint32) ((_vm->_map->getItem(xPos, yPos) & 0xFF00) >> 8);
@@ -2452,9 +1965,9 @@ void Inter_v1::o1_getItem(OpGobParams &params) {
}
void Inter_v1::o1_manipulateMapIndirect(OpGobParams &params) {
- int16 xPos = load16();
- int16 yPos = load16();
- int16 item = load16();
+ int16 xPos = _vm->_game->_script->readInt16();
+ int16 yPos = _vm->_game->_script->readInt16();
+ int16 item = _vm->_game->_script->readInt16();
xPos = VAR(xPos);
yPos = VAR(yPos);
@@ -2464,8 +1977,8 @@ void Inter_v1::o1_manipulateMapIndirect(OpGobParams &params) {
}
void Inter_v1::o1_getItemIndirect(OpGobParams &params) {
- int16 xPos = load16();
- int16 yPos = load16();
+ int16 xPos = _vm->_game->_script->readInt16();
+ int16 yPos = _vm->_game->_script->readInt16();
xPos = VAR(xPos);
yPos = VAR(yPos);
@@ -2477,17 +1990,17 @@ void Inter_v1::o1_getItemIndirect(OpGobParams &params) {
}
void Inter_v1::o1_setPassMap(OpGobParams &params) {
- int16 xPos = load16();
- int16 yPos = load16();
- int16 val = load16();
+ int16 xPos = _vm->_game->_script->readInt16();
+ int16 yPos = _vm->_game->_script->readInt16();
+ int16 val = _vm->_game->_script->readInt16();
_vm->_map->setPass(xPos, yPos, val);
}
void Inter_v1::o1_setGoblinPosH(OpGobParams &params) {
int16 layer;
- int16 item = load16();
- int16 xPos = load16();
- int16 yPos = load16();
+ int16 item = _vm->_game->_script->readInt16();
+ int16 xPos = _vm->_game->_script->readInt16();
+ int16 yPos = _vm->_game->_script->readInt16();
_vm->_goblin->_gobPositions[item].x = xPos * 2;
_vm->_goblin->_gobPositions[item].y = yPos * 2;
@@ -2522,20 +2035,20 @@ void Inter_v1::o1_setGoblinPosH(OpGobParams &params) {
}
void Inter_v1::o1_getGoblinPosXH(OpGobParams &params) {
- int16 item = load16();
+ int16 item = _vm->_game->_script->readInt16();
params.retVarPtr = (uint32) (_vm->_goblin->_gobPositions[item].x >> 1);
}
void Inter_v1::o1_getGoblinPosYH(OpGobParams &params) {
- int16 item = load16();
+ int16 item = _vm->_game->_script->readInt16();
params.retVarPtr = (uint32) (_vm->_goblin->_gobPositions[item].y >> 1);
}
void Inter_v1::o1_setGoblinMultState(OpGobParams &params) {
int16 layer;
- int16 item = load16();
- int16 xPos = load16();
- int16 yPos = load16();
+ int16 item = _vm->_game->_script->readInt16();
+ int16 xPos = _vm->_game->_script->readInt16();
+ int16 yPos = _vm->_game->_script->readInt16();
params.objDesc = _vm->_goblin->_goblins[item];
if (yPos == 0) {
@@ -2594,18 +2107,18 @@ void Inter_v1::o1_setGoblinMultState(OpGobParams &params) {
}
void Inter_v1::o1_setGoblinUnk14(OpGobParams &params) {
- int16 item = load16();
- int16 val = load16();
+ int16 item = _vm->_game->_script->readInt16();
+ int16 val = _vm->_game->_script->readInt16();
params.objDesc = _vm->_goblin->_objects[item];
params.objDesc->unk14 = val;
}
void Inter_v1::o1_setItemIdInPocket(OpGobParams &params) {
- _vm->_goblin->_itemIdInPocket = load16();
+ _vm->_goblin->_itemIdInPocket = _vm->_game->_script->readInt16();
}
void Inter_v1::o1_setItemIndInPocket(OpGobParams &params) {
- _vm->_goblin->_itemIndInPocket = load16();
+ _vm->_goblin->_itemIndInPocket = _vm->_game->_script->readInt16();
}
void Inter_v1::o1_getItemIdInPocket(OpGobParams &params) {
@@ -2618,9 +2131,9 @@ void Inter_v1::o1_getItemIndInPocket(OpGobParams &params) {
void Inter_v1::o1_setGoblinPos(OpGobParams &params) {
int16 layer;
- int16 item = load16();
- int16 xPos = load16();
- int16 yPos = load16();
+ int16 item = _vm->_game->_script->readInt16();
+ int16 xPos = _vm->_game->_script->readInt16();
+ int16 yPos = _vm->_game->_script->readInt16();
_vm->_goblin->_gobPositions[item].x = xPos;
_vm->_goblin->_gobPositions[item].y = yPos;
@@ -2655,8 +2168,8 @@ void Inter_v1::o1_setGoblinPos(OpGobParams &params) {
void Inter_v1::o1_setGoblinState(OpGobParams &params) {
int16 layer;
- int16 item = load16();
- int16 state = load16();
+ int16 item = _vm->_game->_script->readInt16();
+ int16 state = _vm->_game->_script->readInt16();
params.objDesc = _vm->_goblin->_goblins[item];
params.objDesc->nextState = state;
@@ -2680,8 +2193,8 @@ void Inter_v1::o1_setGoblinState(OpGobParams &params) {
void Inter_v1::o1_setGoblinStateRedraw(OpGobParams &params) {
int16 layer;
- int16 item = load16();
- int16 state = load16();
+ int16 item = _vm->_game->_script->readInt16();
+ int16 state = _vm->_game->_script->readInt16();
params.objDesc = _vm->_goblin->_objects[item];
params.objDesc->nextState = state;
@@ -2708,7 +2221,7 @@ void Inter_v1::o1_setGoblinStateRedraw(OpGobParams &params) {
}
void Inter_v1::o1_decRelaxTime(OpGobParams &params) {
- params.extraData = load16();
+ params.extraData = _vm->_game->_script->readInt16();
params.objDesc = _vm->_goblin->_objects[params.extraData];
params.objDesc->relaxTime--;
@@ -2722,12 +2235,12 @@ void Inter_v1::o1_decRelaxTime(OpGobParams &params) {
}
void Inter_v1::o1_getGoblinPosX(OpGobParams &params) {
- int16 item = load16();
+ int16 item = _vm->_game->_script->readInt16();
params.retVarPtr = (uint32) _vm->_goblin->_gobPositions[item].x;
}
void Inter_v1::o1_getGoblinPosY(OpGobParams &params) {
- int16 item = load16();
+ int16 item = _vm->_game->_script->readInt16();
params.retVarPtr = (uint32) _vm->_goblin->_gobPositions[item].y;
}
@@ -2736,18 +2249,18 @@ void Inter_v1::o1_clearPathExistence(OpGobParams &params) {
}
void Inter_v1::o1_setGoblinVisible(OpGobParams &params) {
- params.extraData = load16();
+ params.extraData = _vm->_game->_script->readInt16();
_vm->_goblin->_goblins[params.extraData]->visible = 1;
}
void Inter_v1::o1_setGoblinInvisible(OpGobParams &params) {
- params.extraData = load16();
+ params.extraData = _vm->_game->_script->readInt16();
_vm->_goblin->_goblins[params.extraData]->visible = 0;
}
void Inter_v1::o1_getObjectIntersect(OpGobParams &params) {
- params.extraData = load16();
- int16 item = load16();
+ params.extraData = _vm->_game->_script->readInt16();
+ int16 item = _vm->_game->_script->readInt16();
params.objDesc = _vm->_goblin->_objects[params.extraData];
if (_vm->_goblin->objIntersected(params.objDesc,
@@ -2758,8 +2271,8 @@ void Inter_v1::o1_getObjectIntersect(OpGobParams &params) {
}
void Inter_v1::o1_getGoblinIntersect(OpGobParams &params) {
- params.extraData = load16();
- int16 item = load16();
+ params.extraData = _vm->_game->_script->readInt16();
+ int16 item = _vm->_game->_script->readInt16();
params.objDesc = _vm->_goblin->_goblins[params.extraData];
if (_vm->_goblin->objIntersected(params.objDesc,
@@ -2770,10 +2283,10 @@ void Inter_v1::o1_getGoblinIntersect(OpGobParams &params) {
}
void Inter_v1::o1_setItemPos(OpGobParams &params) {
- int16 item = load16();
- int16 xPos = load16();
- int16 yPos = load16();
- int16 val = load16();
+ int16 item = _vm->_game->_script->readInt16();
+ int16 xPos = _vm->_game->_script->readInt16();
+ int16 yPos = _vm->_game->_script->readInt16();
+ int16 val = _vm->_game->_script->readInt16();
_vm->_map->_itemPoses[item].x = xPos;
_vm->_map->_itemPoses[item].y = yPos;
@@ -2781,12 +2294,9 @@ void Inter_v1::o1_setItemPos(OpGobParams &params) {
}
void Inter_v1::o1_loadObjects(OpGobParams &params) {
- params.extraData = load16();
- if (_vm->_game->_extHandle >= 0)
- _vm->_dataIO->closeData(_vm->_game->_extHandle);
+ params.extraData = _vm->_game->_script->readInt16();
_vm->_goblin->loadObjects((char *) VAR_ADDRESS(params.extraData));
- _vm->_game->_extHandle = _vm->_dataIO->openData(_vm->_game->_curExtFile);
}
void Inter_v1::o1_freeObjects(OpGobParams &params) {
@@ -2811,8 +2321,8 @@ void Inter_v1::o1_loadMap(OpGobParams &params) {
void Inter_v1::o1_moveGoblin(OpGobParams &params) {
int16 item;
- params.extraData = load16();
- int16 xPos = load16();
+ params.extraData = _vm->_game->_script->readInt16();
+ int16 xPos = _vm->_game->_script->readInt16();
if ((uint16) VAR(xPos) == 0) {
item =
@@ -2837,9 +2347,9 @@ void Inter_v1::o1_loadGoblin(OpGobParams &params) {
}
void Inter_v1::o1_writeTreatItem(OpGobParams &params) {
- params.extraData = load16();
- int16 cmd = load16();
- int16 xPos = load16();
+ params.extraData = _vm->_game->_script->readInt16();
+ int16 cmd = _vm->_game->_script->readInt16();
+ int16 xPos = _vm->_game->_script->readInt16();
if ((uint16) VAR(xPos) == 0) {
WRITE_VAR(cmd, _vm->_goblin->treatItem((uint16) VAR(params.extraData)));
@@ -2855,7 +2365,7 @@ void Inter_v1::o1_moveGoblin0(OpGobParams &params) {
}
void Inter_v1::o1_setGoblinTarget(OpGobParams &params) {
- params.extraData = load16();
+ params.extraData = _vm->_game->_script->readInt16();
if (VAR(params.extraData) != 0)
_vm->_goblin->_goesAtTarget = 1;
else
@@ -2863,11 +2373,11 @@ void Inter_v1::o1_setGoblinTarget(OpGobParams &params) {
}
void Inter_v1::o1_setGoblinObjectsPos(OpGobParams &params) {
- params.extraData = load16();
+ params.extraData = _vm->_game->_script->readInt16();
params.extraData = VAR(params.extraData);
_vm->_goblin->_objects[10]->xPos = params.extraData;
- params.extraData = load16();
+ params.extraData = _vm->_game->_script->readInt16();
params.extraData = VAR(params.extraData);
_vm->_goblin->_objects[10]->yPos = params.extraData;
}
@@ -2961,38 +2471,24 @@ void Inter_v1::o1_initGoblin(OpGobParams &params) {
}
int16 Inter_v1::loadSound(int16 slot) {
- byte *dataPtr;
- int16 id;
- uint32 dataSize;
- SoundSource source;
-
if (slot == -1)
- slot = _vm->_parse->parseValExpr();
+ slot = _vm->_game->_script->readValExpr();
- id = load16();
- if (id == -1) {
- _vm->_global->_inter_execPtr += 9;
+ uint16 id = _vm->_game->_script->readUint16();
+ if (id == 0xFFFF) {
+ _vm->_game->_script->skip(9);
return 0;
}
- if (id >= 30000) {
- source = SOUND_EXT;
-
- dataPtr = (byte *) _vm->_game->loadExtData(id, 0, 0, &dataSize);
- } else {
- int16 totSize;
-
- source = SOUND_TOT;
+ Resource *resource = _vm->_game->_resources->getResource(id);
+ if (!resource)
+ return 0;
- dataPtr = (byte *) _vm->_game->loadTotResource(id, &totSize);
- dataSize = (uint32) ((int32) totSize);
- }
+ SoundDesc *sample = _vm->_sound->sampleGetBySlot(slot);
+ if (!sample)
+ return 0;
- if (dataPtr) {
- SoundDesc *sample = _vm->_sound->sampleGetBySlot(slot);
- if (sample)
- sample->load(SOUND_SND, source, dataPtr, dataSize);
- }
+ sample->load(SOUND_SND, resource);
return 0;
}
diff --git a/engines/gob/inter_v2.cpp b/engines/gob/inter_v2.cpp
index 3107fcf9bc..82822330b1 100644
--- a/engines/gob/inter_v2.cpp
+++ b/engines/gob/inter_v2.cpp
@@ -36,10 +36,12 @@
#include "gob/dataio.h"
#include "gob/draw.h"
#include "gob/game.h"
+#include "gob/expression.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/goblin.h"
#include "gob/map.h"
#include "gob/mult.h"
-#include "gob/parse.h"
#include "gob/scenery.h"
#include "gob/video.h"
#include "gob/save/saveload.h"
@@ -48,673 +50,126 @@
namespace Gob {
-#define OPCODE(x) _OPCODE(Inter_v2, x)
-
-const int Inter_v2::_goblinFuncLookUp[][2] = {
- {0, 0},
- {1, 1},
- {2, 2},
- {4, 3},
- {5, 4},
- {6, 5},
- {7, 6},
- {8, 7},
- {9, 8},
- {10, 9},
- {12, 10},
- {13, 11},
- {14, 12},
- {15, 13},
- {16, 14},
- {21, 15},
- {22, 16},
- {23, 17},
- {24, 18},
- {25, 19},
- {26, 20},
- {27, 21},
- {28, 22},
- {29, 23},
- {30, 24},
- {32, 25},
- {33, 26},
- {34, 27},
- {35, 28},
- {36, 29},
- {37, 30},
- {40, 31},
- {41, 32},
- {42, 33},
- {43, 34},
- {44, 35},
- {50, 36},
- {52, 37},
- {53, 38},
- {100, 39},
- {500, 40},
- {501, 41}
-};
+#define OPCODEVER Inter_v2
+#define OPCODEDRAW(i, x) _opcodesDraw[i]._OPCODEDRAW(OPCODEVER, x)
+#define OPCODEFUNC(i, x) _opcodesFunc[i]._OPCODEFUNC(OPCODEVER, x)
+#define OPCODEGOB(i, x) _opcodesGob[i]._OPCODEGOB(OPCODEVER, x)
Inter_v2::Inter_v2(GobEngine *vm) : Inter_v1(vm) {
- setupOpcodes();
}
-void Inter_v2::setupOpcodes() {
- static const OpcodeDrawEntryV2 opcodesDraw[256] = {
- /* 00 */
- OPCODE(o1_loadMult),
- OPCODE(o2_playMult),
- OPCODE(o2_freeMultKeys),
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- OPCODE(o1_initCursor),
- /* 08 */
- OPCODE(o1_initCursorAnim),
- OPCODE(o1_clearCursorAnim),
- OPCODE(o2_setRenderFlags),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- OPCODE(o1_loadAnim),
- OPCODE(o1_freeAnim),
- OPCODE(o1_updateAnim),
- OPCODE(o2_multSub),
- /* 14 */
- OPCODE(o2_initMult),
- OPCODE(o1_freeMult),
- OPCODE(o1_animate),
- OPCODE(o2_loadMultObject),
- /* 18 */
- OPCODE(o1_getAnimLayerInfo),
- OPCODE(o1_getObjAnimSize),
- OPCODE(o1_loadStatic),
- OPCODE(o1_freeStatic),
- /* 1C */
- OPCODE(o2_renderStatic),
- OPCODE(o2_loadCurLayer),
- {0, ""},
- {0, ""},
- /* 20 */
- OPCODE(o2_playCDTrack),
- OPCODE(o2_waitCDTrackEnd),
- OPCODE(o2_stopCD),
- OPCODE(o2_readLIC),
- /* 24 */
- OPCODE(o2_freeLIC),
- OPCODE(o2_getCDTrackPos),
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o2_loadFontToSprite),
- OPCODE(o1_freeFontToSprite),
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- OPCODE(o2_totSub),
- OPCODE(o2_switchTotSub),
- OPCODE(o2_pushVars),
- OPCODE(o2_popVars),
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 48 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 4C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 50 */
- OPCODE(o2_loadMapObjects),
- OPCODE(o2_freeGoblins),
- OPCODE(o2_moveGoblin),
- OPCODE(o2_writeGoblinPos),
- /* 54 */
- OPCODE(o2_stopGoblin),
- OPCODE(o2_setGoblinState),
- OPCODE(o2_placeGoblin),
- {0, ""},
- /* 58 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 5C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 60 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 64 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 68 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 6C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 70 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 74 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 78 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 7C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 80 */
- OPCODE(o2_initScreen),
- OPCODE(o2_scroll),
- OPCODE(o2_setScrollOffset),
- OPCODE(o2_playImd),
- /* 84 */
- OPCODE(o2_getImdInfo),
- OPCODE(o2_openItk),
- OPCODE(o2_closeItk),
- OPCODE(o2_setImdFrontSurf),
- /* 88 */
- OPCODE(o2_resetImdFrontSurf),
- {0, ""},
- {0, ""},
- {0, ""},
- /* 8C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 90 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 94 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 98 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 9C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* AC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* BC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* CC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* DC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* EC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* FC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""}
- };
-
- static const OpcodeFuncEntryV2 opcodesFunc[80] = {
- /* 00 */
- OPCODE(o1_callSub),
- OPCODE(o1_callSub),
- OPCODE(o1_printTotText),
- OPCODE(o1_loadCursor),
- /* 04 */
- {0, ""},
- OPCODE(o1_switch),
- OPCODE(o1_repeatUntil),
- OPCODE(o1_whileDo),
- /* 08 */
- OPCODE(o1_if),
- OPCODE(o2_assign),
- OPCODE(o1_loadSpriteToPos),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- OPCODE(o2_printText),
- OPCODE(o1_loadTot),
- OPCODE(o1_palLoad),
- /* 14 */
- OPCODE(o1_keyFunc),
- OPCODE(o1_capturePush),
- OPCODE(o1_capturePop),
- OPCODE(o2_animPalInit),
- /* 18 */
- OPCODE(o2_addCollision),
- OPCODE(o2_freeCollision),
- {0, ""},
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- OPCODE(o1_drawOperations),
- OPCODE(o1_setcmdCount),
- /* 20 */
- OPCODE(o1_return),
- OPCODE(o1_renewTimeInVars),
- OPCODE(o1_speakerOn),
- OPCODE(o1_speakerOff),
- /* 24 */
- OPCODE(o1_putPixel),
- OPCODE(o2_goblinFunc),
- OPCODE(o1_createSprite),
- OPCODE(o1_freeSprite),
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o1_returnTo),
- OPCODE(o1_loadSpriteContent),
- OPCODE(o1_copySprite),
- OPCODE(o1_fillRect),
- /* 34 */
- OPCODE(o1_drawLine),
- OPCODE(o1_strToLong),
- OPCODE(o1_invalidate),
- OPCODE(o1_setBackDelta),
- /* 38 */
- OPCODE(o1_playSound),
- OPCODE(o2_stopSound),
- OPCODE(o2_loadSound),
- OPCODE(o1_freeSoundSlot),
- /* 3C */
- OPCODE(o1_waitEndPlay),
- OPCODE(o1_playComposition),
- OPCODE(o2_getFreeMem),
- OPCODE(o2_checkData),
- /* 40 */
- {0, ""},
- OPCODE(o1_prepareStr),
- OPCODE(o1_insertStr),
- OPCODE(o1_cutStr),
- /* 44 */
- OPCODE(o1_strstr),
- OPCODE(o1_istrlen),
- OPCODE(o1_setMousePos),
- OPCODE(o1_setFrameRate),
- /* 48 */
- OPCODE(o1_animatePalette),
- OPCODE(o1_animateCursor),
- OPCODE(o1_blitCursor),
- OPCODE(o1_loadFont),
- /* 4C */
- OPCODE(o1_freeFont),
- OPCODE(o2_readData),
- OPCODE(o2_writeData),
- OPCODE(o1_manageDataFile),
- };
-
- static const OpcodeGoblinEntryV2 opcodesGoblin[71] = {
- /* 00 */
- OPCODE(o2_loadInfogramesIns),
- OPCODE(o2_startInfogrames),
- OPCODE(o2_stopInfogrames),
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 08 */
- {0, ""},
- OPCODE(o2_playInfogrames),
- {0, ""},
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 14 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 18 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 20 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 24 */
- {0, ""},
- {0, ""},
- {0, ""},
- OPCODE(o2_handleGoblins),
- /* 28 */
- OPCODE(o2_playProtracker),
- OPCODE(o2_stopProtracker),
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- };
-
- _opcodesDrawV2 = opcodesDraw;
- _opcodesFuncV2 = opcodesFunc;
- _opcodesGoblinV2 = opcodesGoblin;
-}
+void Inter_v2::setupOpcodesDraw() {
+ Inter_v1::setupOpcodesDraw();
-void Inter_v2::executeDrawOpcode(byte i) {
- debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%X] (%s)",
- i, i, getOpcodeDrawDesc(i));
+ OPCODEDRAW(0x01, o2_playMult);
+ OPCODEDRAW(0x02, o2_freeMultKeys);
- OpcodeDrawProcV2 op = _opcodesDrawV2[i].proc;
+ OPCODEDRAW(0x0A, o2_setRenderFlags);
- if (op == 0)
- warning("unimplemented opcodeDraw: %d", i);
- else
- (this->*op) ();
-}
+ OPCODEDRAW(0x13, o2_multSub);
-bool Inter_v2::executeFuncOpcode(byte i, byte j, OpFuncParams &params) {
- debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%X.0x%X] (%s)",
- i, j, i, j, getOpcodeFuncDesc(i, j));
+ OPCODEDRAW(0x14, o2_initMult);
- if ((i > 4) || (j > 15)) {
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- return false;
- }
+ OPCODEDRAW(0x17, o2_loadMultObject);
- OpcodeFuncProcV2 op = _opcodesFuncV2[i*16 + j].proc;
+ OPCODEDRAW(0x1C, o2_renderStatic);
+ OPCODEDRAW(0x1D, o2_loadCurLayer);
- if (op == 0)
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- else
- return (this->*op) (params);
+ OPCODEDRAW(0x20, o2_playCDTrack);
+ OPCODEDRAW(0x21, o2_waitCDTrackEnd);
+ OPCODEDRAW(0x22, o2_stopCD);
+ OPCODEDRAW(0x23, o2_readLIC);
- return false;
-}
+ OPCODEDRAW(0x24, o2_freeLIC);
+ OPCODEDRAW(0x25, o2_getCDTrackPos);
-void Inter_v2::executeGoblinOpcode(int i, OpGobParams &params) {
- debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%X] (%s)",
- i, i, getOpcodeGoblinDesc(i));
+ OPCODEDRAW(0x30, o2_loadFontToSprite);
- OpcodeGoblinProcV2 op = 0;
+ OPCODEDRAW(0x40, o2_totSub);
+ OPCODEDRAW(0x41, o2_switchTotSub);
+ OPCODEDRAW(0x42, o2_pushVars);
+ OPCODEDRAW(0x43, o2_popVars);
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i) {
- op = _opcodesGoblinV2[_goblinFuncLookUp[j][1]].proc;
- break;
- }
+ OPCODEDRAW(0x50, o2_loadMapObjects);
+ OPCODEDRAW(0x51, o2_freeGoblins);
+ OPCODEDRAW(0x52, o2_moveGoblin);
+ OPCODEDRAW(0x53, o2_writeGoblinPos);
- if (op == 0) {
- int16 val;
+ OPCODEDRAW(0x54, o2_stopGoblin);
+ OPCODEDRAW(0x55, o2_setGoblinState);
+ OPCODEDRAW(0x56, o2_placeGoblin);
- _vm->_global->_inter_execPtr -= 2;
- val = load16();
- _vm->_global->_inter_execPtr += val << 1;
- } else
- (this->*op) (params);
-}
+ OPCODEDRAW(0x80, o2_initScreen);
+ OPCODEDRAW(0x81, o2_scroll);
+ OPCODEDRAW(0x82, o2_setScrollOffset);
+ OPCODEDRAW(0x83, o2_playImd);
+
+ OPCODEDRAW(0x84, o2_getImdInfo);
+ OPCODEDRAW(0x85, o2_openItk);
+ OPCODEDRAW(0x86, o2_closeItk);
+ OPCODEDRAW(0x87, o2_setImdFrontSurf);
-const char *Inter_v2::getOpcodeDrawDesc(byte i) {
- return _opcodesDrawV2[i].desc;
+ OPCODEDRAW(0x88, o2_resetImdFrontSurf);
}
-const char *Inter_v2::getOpcodeFuncDesc(byte i, byte j) {
- if ((i > 4) || (j > 15))
- return "";
+void Inter_v2::setupOpcodesFunc() {
+ Inter_v1::setupOpcodesFunc();
+
+ OPCODEFUNC(0x09, o2_assign);
+
+ OPCODEFUNC(0x11, o2_printText);
+
+ OPCODEFUNC(0x17, o2_animPalInit);
- return _opcodesFuncV2[i*16 + j].desc;
+ OPCODEFUNC(0x18, o2_addCollision);
+ OPCODEFUNC(0x19, o2_freeCollision);
+
+ OPCODEFUNC(0x25, o2_goblinFunc);
+
+ OPCODEFUNC(0x39, o2_stopSound);
+ OPCODEFUNC(0x3A, o2_loadSound);
+
+ OPCODEFUNC(0x3E, o2_getFreeMem);
+ OPCODEFUNC(0x3F, o2_checkData);
+
+ OPCODEFUNC(0x4D, o2_readData);
+ OPCODEFUNC(0x4E, o2_writeData);
}
-const char *Inter_v2::getOpcodeGoblinDesc(int i) {
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i)
- return _opcodesGoblinV2[_goblinFuncLookUp[j][1]].desc;
- return "";
+void Inter_v2::setupOpcodesGob() {
+ OPCODEGOB( 0, o2_loadInfogramesIns);
+ OPCODEGOB( 1, o2_startInfogrames);
+ OPCODEGOB( 2, o2_stopInfogrames);
+
+ OPCODEGOB( 10, o2_playInfogrames);
+
+ OPCODEGOB(100, o2_handleGoblins);
+
+ OPCODEGOB(500, o2_playProtracker);
+ OPCODEGOB(501, o2_stopProtracker);
}
-void Inter_v2::checkSwitchTable(byte **ppExec) {
- byte cmd;
+void Inter_v2::checkSwitchTable(uint32 &offset) {
+ byte type;
int16 len;
int32 value;
bool found;
found = false;
- *ppExec = 0;
+ offset = 0;
- cmd = *_vm->_global->_inter_execPtr;
+ type = _vm->_game->_script->peekByte();
- value = _vm->_parse->parseVarIndex();
+ value = _vm->_game->_script->readVarIndex();
- switch (cmd) {
- case 16:
- case 18:
+ switch (type) {
+ case TYPE_VAR_INT8:
+ case TYPE_ARRAY_INT8:
value = (int8) READ_VARO_UINT8(value);
break;
- case 23:
- case 26:
+ case TYPE_VAR_INT32:
+ case TYPE_ARRAY_INT32:
value = READ_VARO_UINT32(value);
break;
@@ -726,78 +181,74 @@ void Inter_v2::checkSwitchTable(byte **ppExec) {
if (_terminate)
return;
- len = (int8) *_vm->_global->_inter_execPtr++;
+ len = _vm->_game->_script->readInt8();
while (len != -5) {
for (int i = 0; i < len; i++) {
- cmd = *_vm->_global->_inter_execPtr;
+ type = _vm->_game->_script->peekByte();
- switch (cmd) {
- case 19:
- _vm->_global->_inter_execPtr++;
+ switch (type) {
+ case TYPE_IMM_INT32:
+ _vm->_game->_script->skip(1);
if (!found &&
- (value ==
- (int32) (READ_LE_UINT32(_vm->_global->_inter_execPtr))))
+ (value == _vm->_game->_script->peekInt32()))
found = true;
- _vm->_global->_inter_execPtr += 5;
+ _vm->_game->_script->skip(5);
break;
- case 20:
- _vm->_global->_inter_execPtr++;
+ case TYPE_IMM_INT16:
+ _vm->_game->_script->skip(1);
if (!found &&
- (value ==
- (int16) (READ_LE_UINT16(_vm->_global->_inter_execPtr))))
+ (value == _vm->_game->_script->peekInt16()))
found = true;
- _vm->_global->_inter_execPtr += 3;
+ _vm->_game->_script->skip(3);
break;
- case 21:
- _vm->_global->_inter_execPtr++;
- if (!found && (value == (int8) *_vm->_global->_inter_execPtr))
+ case TYPE_IMM_INT8:
+ _vm->_game->_script->skip(1);
+ if (!found && (value == _vm->_game->_script->peekInt8()))
found = true;
- _vm->_global->_inter_execPtr += 2;
+ _vm->_game->_script->skip(2);
break;
default:
if (!found) {
- evalExpr(0);
- if (value == _vm->_global->_inter_resVal)
+ _vm->_game->_script->evalExpr(0);
+ if (value == _vm->_game->_script->getResultInt())
found = true;
} else
- _vm->_parse->skipExpr(99);
+ _vm->_game->_script->skipExpr(99);
break;
}
}
- if (found && !*ppExec)
- *ppExec = _vm->_global->_inter_execPtr;
+ if (found && (offset == 0))
+ offset = _vm->_game->_script->pos();
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
- len = (int8) *_vm->_global->_inter_execPtr++;
+ _vm->_game->_script->skip(_vm->_game->_script->peekUint16(2) + 2);
+ len = _vm->_game->_script->readInt8();
}
- if ((*_vm->_global->_inter_execPtr >> 4) != 4)
+ if ((_vm->_game->_script->peekByte() >> 4) != 4)
return;
- _vm->_global->_inter_execPtr++;
- if (!*ppExec)
- *ppExec = _vm->_global->_inter_execPtr;
+ _vm->_game->_script->skip(1);
+ if (offset == 0)
+ offset = _vm->_game->_script->pos();
- _vm->_global->_inter_execPtr +=
- READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ _vm->_game->_script->skip(_vm->_game->_script->peekUint16(2) + 2);
}
void Inter_v2::o2_playMult() {
int16 checkEscape;
- checkEscape = load16();
+ checkEscape = _vm->_game->_script->readInt16();
_vm->_mult->setMultData(checkEscape >> 1);
_vm->_mult->playMult(VAR(57), -1, checkEscape & 0x1, 0);
}
void Inter_v2::o2_freeMultKeys() {
- uint16 index = load16();
+ uint16 index = _vm->_game->_script->readUint16();
if (!_vm->_mult->hasMultData(index))
return;
@@ -810,7 +261,7 @@ void Inter_v2::o2_freeMultKeys() {
void Inter_v2::o2_setRenderFlags() {
int16 expr;
- expr = _vm->_parse->parseValExpr();
+ expr = _vm->_game->_script->readValExpr();
if (expr & 0x8000) {
_vm->_draw->_renderFlags |= expr & 0x3FFF;
@@ -823,7 +274,7 @@ void Inter_v2::o2_setRenderFlags() {
}
void Inter_v2::o2_multSub() {
- _vm->_mult->multSub(_vm->_parse->parseValExpr());
+ _vm->_mult->multSub(_vm->_game->_script->readValExpr());
}
void Inter_v2::o2_initMult() {
@@ -838,14 +289,14 @@ void Inter_v2::o2_initMult() {
oldAnimHeight = _vm->_mult->_animHeight;
oldObjCount = _vm->_mult->_objCount;
- _vm->_mult->_animLeft = load16();
- _vm->_mult->_animTop = load16();
- _vm->_mult->_animWidth = load16();
- _vm->_mult->_animHeight = load16();
- _vm->_mult->_objCount = load16();
- posXVar = _vm->_parse->parseVarIndex();
- posYVar = _vm->_parse->parseVarIndex();
- animDataVar = _vm->_parse->parseVarIndex();
+ _vm->_mult->_animLeft = _vm->_game->_script->readInt16();
+ _vm->_mult->_animTop = _vm->_game->_script->readInt16();
+ _vm->_mult->_animWidth = _vm->_game->_script->readInt16();
+ _vm->_mult->_animHeight = _vm->_game->_script->readInt16();
+ _vm->_mult->_objCount = _vm->_game->_script->readInt16();
+ posXVar = _vm->_game->_script->readVarIndex();
+ posYVar = _vm->_game->_script->readVarIndex();
+ animDataVar = _vm->_game->_script->readVarIndex();
if (_vm->_mult->_objects && (oldObjCount != _vm->_mult->_objCount)) {
warning("Initializing new objects without having "
@@ -947,20 +398,20 @@ void Inter_v2::o2_loadMultObject() {
int16 layer;
byte *multData;
- objIndex = _vm->_parse->parseValExpr();
- val = _vm->_parse->parseValExpr();
+ objIndex = _vm->_game->_script->readValExpr();
+ val = _vm->_game->_script->readValExpr();
*_vm->_mult->_objects[objIndex].pPosX = val;
- val = _vm->_parse->parseValExpr();
+ val = _vm->_game->_script->readValExpr();
*_vm->_mult->_objects[objIndex].pPosY = val;
debugC(4, kDebugGameFlow, "Loading mult object %d", objIndex);
multData = (byte *) _vm->_mult->_objects[objIndex].pAnimData;
for (int i = 0; i < 11; i++) {
- if (*_vm->_global->_inter_execPtr != 99)
- multData[i] = _vm->_parse->parseValExpr();
+ if (_vm->_game->_script->peekByte() != 99)
+ multData[i] = _vm->_game->_script->readValExpr();
else
- _vm->_global->_inter_execPtr++;
+ _vm->_game->_script->skip(1);
}
Mult::Mult_Object &obj = _vm->_mult->_objects[objIndex];
@@ -1043,22 +494,22 @@ void Inter_v2::o2_renderStatic() {
int16 layer;
int16 index;
- index = _vm->_parse->parseValExpr();
- layer = _vm->_parse->parseValExpr();
+ index = _vm->_game->_script->readValExpr();
+ layer = _vm->_game->_script->readValExpr();
_vm->_scenery->renderStatic(index, layer);
}
void Inter_v2::o2_loadCurLayer() {
- _vm->_scenery->_curStatic = _vm->_parse->parseValExpr();
- _vm->_scenery->_curStaticLayer = _vm->_parse->parseValExpr();
+ _vm->_scenery->_curStatic = _vm->_game->_script->readValExpr();
+ _vm->_scenery->_curStaticLayer = _vm->_game->_script->readValExpr();
}
void Inter_v2::o2_playCDTrack() {
if (!(_vm->_draw->_renderFlags & RENDERFLAG_NOBLITINVALIDATED))
_vm->_draw->blitInvalidated();
- evalExpr(0);
- _vm->_sound->cdPlay(_vm->_global->_inter_resStr);
+ _vm->_game->_script->evalExpr(0);
+ _vm->_sound->cdPlay(_vm->_game->_script->getResultStr());
}
void Inter_v2::o2_waitCDTrackEnd() {
@@ -1075,8 +526,8 @@ void Inter_v2::o2_stopCD() {
void Inter_v2::o2_readLIC() {
char path[40];
- evalExpr(0);
- strncpy0(path, _vm->_global->_inter_resStr, 35);
+ _vm->_game->_script->evalExpr(0);
+ strncpy0(path, _vm->_game->_script->getResultStr(), 35);
strcat(path, ".LIC");
_vm->_sound->cdLoadLIC(path);
@@ -1092,24 +543,24 @@ void Inter_v2::o2_getCDTrackPos() {
_vm->_util->longDelay(1);
- varPos = _vm->_parse->parseVarIndex();
- varName = _vm->_parse->parseVarIndex();
+ varPos = _vm->_game->_script->readVarIndex();
+ varName = _vm->_game->_script->readVarIndex();
WRITE_VAR_OFFSET(varPos, _vm->_sound->cdGetTrackPos(GET_VARO_STR(varName)));
WRITE_VARO_STR(varName, _vm->_sound->cdGetCurrentTrack());
}
void Inter_v2::o2_loadFontToSprite() {
- int16 i = load16();
-
- _vm->_draw->_fontToSprite[i].sprite = *_vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += 2;
- _vm->_draw->_fontToSprite[i].base = *_vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += 2;
- _vm->_draw->_fontToSprite[i].width = *_vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += 2;
- _vm->_draw->_fontToSprite[i].height = *_vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += 2;
+ int16 i = _vm->_game->_script->readInt16();
+
+ _vm->_draw->_fontToSprite[i].sprite = _vm->_game->_script->readByte();
+ _vm->_game->_script->skip(1);
+ _vm->_draw->_fontToSprite[i].base = _vm->_game->_script->readByte();
+ _vm->_game->_script->skip(1);
+ _vm->_draw->_fontToSprite[i].width = _vm->_game->_script->readByte();
+ _vm->_game->_script->skip(1);
+ _vm->_draw->_fontToSprite[i].height = _vm->_game->_script->readByte();
+ _vm->_game->_script->skip(1);
}
void Inter_v2::o2_totSub() {
@@ -1118,16 +569,16 @@ void Inter_v2::o2_totSub() {
int flags;
int i;
- length = *_vm->_global->_inter_execPtr++;
+ length = _vm->_game->_script->readByte();
if ((length & 0x7F) > 13)
error("Length in o2_totSub is greater than 13 (%d)", length);
if (length & 0x80) {
- evalExpr(0);
- strcpy(totFile, _vm->_global->_inter_resStr);
+ _vm->_game->_script->evalExpr(0);
+ strcpy(totFile, _vm->_game->_script->getResultStr());
} else {
for (i = 0; i < length; i++)
- totFile[i] = (char) *_vm->_global->_inter_execPtr++;
+ totFile[i] = _vm->_game->_script->readChar();
totFile[i] = 0;
}
@@ -1135,7 +586,7 @@ void Inter_v2::o2_totSub() {
if (!scumm_stricmp(totFile, "edit"))
_vm->_util->forceMouseUp();
- flags = *_vm->_global->_inter_execPtr++;
+ flags = _vm->_game->_script->readByte();
_vm->_game->totSub(flags, totFile);
}
@@ -1143,8 +594,8 @@ void Inter_v2::o2_switchTotSub() {
int16 index;
int16 skipPlay;
- index = load16();
- skipPlay = load16();
+ index = _vm->_game->_script->readInt16();
+ skipPlay = _vm->_game->_script->readInt16();
_vm->_game->switchTotSub(index, skipPlay);
}
@@ -1153,13 +604,13 @@ void Inter_v2::o2_pushVars() {
byte count;
int16 varOff;
- count = *_vm->_global->_inter_execPtr++;
+ count = _vm->_game->_script->readByte();
for (int i = 0; i < count; i++, _varStackPos++) {
- if ((*_vm->_global->_inter_execPtr == 25) ||
- (*_vm->_global->_inter_execPtr == 28)) {
+ if ((_vm->_game->_script->peekByte() == 25) ||
+ (_vm->_game->_script->peekByte() == 28)) {
- varOff = _vm->_parse->parseVarIndex();
- _vm->_global->_inter_execPtr++;
+ varOff = _vm->_game->_script->readVarIndex();
+ _vm->_game->_script->skip(1);
_variables->copyTo(varOff, _varStack + _varStackPos, _vm->_global->_inter_animDataSize * 4);
@@ -1167,10 +618,12 @@ void Inter_v2::o2_pushVars() {
_varStack[_varStackPos] = _vm->_global->_inter_animDataSize * 4;
} else {
- if (evalExpr(&varOff) != 20)
- _vm->_global->_inter_resVal = 0;
+ int32 n = _vm->_game->_script->getResultInt();
+
+ if (_vm->_game->_script->evalExpr(&varOff) != 20)
+ n = 0;
- memcpy(_varStack + _varStackPos, &_vm->_global->_inter_resVal, 4);
+ memcpy(_varStack + _varStackPos, &n, 4);
_varStackPos += 4;
_varStack[_varStackPos] = 4;
}
@@ -1182,9 +635,9 @@ void Inter_v2::o2_popVars() {
int16 varOff;
int16 size;
- count = *_vm->_global->_inter_execPtr++;
+ count = _vm->_game->_script->readByte();
for (int i = 0; i < count; i++) {
- varOff = _vm->_parse->parseVarIndex();
+ varOff = _vm->_game->_script->readVarIndex();
size = _varStack[--_varStackPos];
_varStackPos -= size;
@@ -1204,9 +657,9 @@ void Inter_v2::o2_moveGoblin() {
int16 destX, destY;
int16 index;
- destX = _vm->_parse->parseValExpr();
- destY = _vm->_parse->parseValExpr();
- index = _vm->_parse->parseValExpr();
+ destX = _vm->_game->_script->readValExpr();
+ destY = _vm->_game->_script->readValExpr();
+ index = _vm->_game->_script->readValExpr();
_vm->_goblin->move(destX, destY, index);
}
@@ -1214,15 +667,15 @@ void Inter_v2::o2_writeGoblinPos() {
int16 varX, varY;
int16 index;
- varX = _vm->_parse->parseVarIndex();
- varY = _vm->_parse->parseVarIndex();
- index = _vm->_parse->parseValExpr();
+ varX = _vm->_game->_script->readVarIndex();
+ varY = _vm->_game->_script->readVarIndex();
+ index = _vm->_game->_script->readValExpr();
WRITE_VAR_OFFSET(varX, _vm->_mult->_objects[index].goblinX);
WRITE_VAR_OFFSET(varY, _vm->_mult->_objects[index].goblinY);
}
void Inter_v2::o2_stopGoblin() {
- int16 index = _vm->_parse->parseValExpr();
+ int16 index = _vm->_game->_script->readValExpr();
_vm->_mult->_objects[index].pAnimData->pathExistence = 4;
}
@@ -1236,9 +689,9 @@ void Inter_v2::o2_setGoblinState() {
int16 deltaX, deltaY;
int16 deltaWidth, deltaHeight;
- index = _vm->_parse->parseValExpr();
- state = _vm->_parse->parseValExpr();
- type = _vm->_parse->parseValExpr();
+ index = _vm->_game->_script->readValExpr();
+ state = _vm->_game->_script->readValExpr();
+ type = _vm->_game->_script->readValExpr();
Mult::Mult_Object &obj = _vm->_mult->_objects[index];
Mult::Mult_AnimData &objAnim = *(obj.pAnimData);
@@ -1334,10 +787,10 @@ void Inter_v2::o2_placeGoblin() {
int16 x, y;
int16 state;
- index = _vm->_parse->parseValExpr();
- x = _vm->_parse->parseValExpr();
- y = _vm->_parse->parseValExpr();
- state = _vm->_parse->parseValExpr();
+ index = _vm->_game->_script->readValExpr();
+ x = _vm->_game->_script->readValExpr();
+ y = _vm->_game->_script->readValExpr();
+ state = _vm->_game->_script->readValExpr();
_vm->_goblin->placeObject(0, 0, index, x, y, state);
}
@@ -1347,13 +800,13 @@ void Inter_v2::o2_initScreen() {
int16 videoMode;
int16 width, height;
- offY = load16();
+ offY = _vm->_game->_script->readInt16();
videoMode = offY & 0xFF;
offY = (offY >> 8) & 0xFF;
- width = _vm->_parse->parseValExpr();
- height = _vm->_parse->parseValExpr();
+ width = _vm->_game->_script->readValExpr();
+ height = _vm->_game->_script->readValExpr();
_vm->_video->clearScreen();
@@ -1441,16 +894,16 @@ void Inter_v2::o2_scroll() {
int16 curX;
int16 curY;
- startX = CLIP((int) _vm->_parse->parseValExpr(), 0,
+ startX = CLIP((int) _vm->_game->_script->readValExpr(), 0,
_vm->_video->_surfWidth - _vm->_width);
- startY = CLIP((int) _vm->_parse->parseValExpr(), 0,
+ startY = CLIP((int) _vm->_game->_script->readValExpr(), 0,
_vm->_video->_surfHeight - _vm->_height);
- endX = CLIP((int) _vm->_parse->parseValExpr(), 0,
+ endX = CLIP((int) _vm->_game->_script->readValExpr(), 0,
_vm->_video->_surfWidth - _vm->_width);
- endY = CLIP((int) _vm->_parse->parseValExpr(), 0,
+ endY = CLIP((int) _vm->_game->_script->readValExpr(), 0,
_vm->_video->_surfHeight - _vm->_height);
- stepX = _vm->_parse->parseValExpr();
- stepY = _vm->_parse->parseValExpr();
+ stepX = _vm->_game->_script->readValExpr();
+ stepY = _vm->_game->_script->readValExpr();
curX = startX;
curY = startY;
@@ -1470,8 +923,8 @@ void Inter_v2::o2_scroll() {
void Inter_v2::o2_setScrollOffset() {
int16 offsetX, offsetY;
- offsetX = _vm->_parse->parseValExpr();
- offsetY = _vm->_parse->parseValExpr();
+ offsetX = _vm->_game->_script->readValExpr();
+ offsetY = _vm->_game->_script->readValExpr();
if (offsetX == -1) {
WRITE_VAR(2, _vm->_draw->_scrollOffsetX);
@@ -1506,22 +959,22 @@ void Inter_v2::o2_playImd() {
uint16 palCmd;
bool close;
- evalExpr(0);
- _vm->_global->_inter_resStr[8] = 0;
- strncpy0(imd, _vm->_global->_inter_resStr, 127);
-
- x = _vm->_parse->parseValExpr();
- y = _vm->_parse->parseValExpr();
- startFrame = _vm->_parse->parseValExpr();
- lastFrame = _vm->_parse->parseValExpr();
- breakKey = _vm->_parse->parseValExpr();
- flags = _vm->_parse->parseValExpr();
- palStart = _vm->_parse->parseValExpr();
- palEnd = _vm->_parse->parseValExpr();
+ _vm->_game->_script->evalExpr(0);
+ _vm->_game->_script->getResultStr()[8] = 0;
+ strncpy0(imd, _vm->_game->_script->getResultStr(), 127);
+
+ x = _vm->_game->_script->readValExpr();
+ y = _vm->_game->_script->readValExpr();
+ startFrame = _vm->_game->_script->readValExpr();
+ lastFrame = _vm->_game->_script->readValExpr();
+ breakKey = _vm->_game->_script->readValExpr();
+ flags = _vm->_game->_script->readValExpr();
+ palStart = _vm->_game->_script->readValExpr();
+ palEnd = _vm->_game->_script->readValExpr();
palCmd = 1 << (flags & 0x3F);
debugC(1, kDebugVideo, "Playing video \"%s\" @ %d+%d, frames %d - %d, "
- "paletteCmd %d (%d - %d), flags %X", _vm->_global->_inter_resStr, x, y,
+ "paletteCmd %d (%d - %d), flags %X", _vm->_game->_script->getResultStr(), x, y,
startFrame, lastFrame, palCmd, palStart, palEnd, flags);
if ((imd[0] != 0) && !_vm->_vidPlayer->primaryOpen(imd, x, y, flags)) {
@@ -1550,28 +1003,28 @@ void Inter_v2::o2_getImdInfo() {
int16 varFrames;
int16 varWidth, varHeight;
- evalExpr(0);
- varX = _vm->_parse->parseVarIndex();
- varY = _vm->_parse->parseVarIndex();
- varFrames = _vm->_parse->parseVarIndex();
- varWidth = _vm->_parse->parseVarIndex();
- varHeight = _vm->_parse->parseVarIndex();
+ _vm->_game->_script->evalExpr(0);
+ varX = _vm->_game->_script->readVarIndex();
+ varY = _vm->_game->_script->readVarIndex();
+ varFrames = _vm->_game->_script->readVarIndex();
+ varWidth = _vm->_game->_script->readVarIndex();
+ varHeight = _vm->_game->_script->readVarIndex();
// WORKAROUND: The nut rolling animation in the administration center
// in Woodruff is called "noixroul", but the scripts think it's "noixroule".
if ((_vm->getGameType() == kGameTypeWoodruff) &&
- (!scumm_stricmp(_vm->_global->_inter_resStr, "noixroule")))
- strcpy(_vm->_global->_inter_resStr, "noixroul");
+ (!scumm_stricmp(_vm->_game->_script->getResultStr(), "noixroule")))
+ strcpy(_vm->_game->_script->getResultStr(), "noixroul");
- _vm->_vidPlayer->writeVideoInfo(_vm->_global->_inter_resStr, varX, varY,
+ _vm->_vidPlayer->writeVideoInfo(_vm->_game->_script->getResultStr(), varX, varY,
varFrames, varWidth, varHeight);
}
void Inter_v2::o2_openItk() {
char fileName[32];
- evalExpr(0);
- strncpy0(fileName, _vm->_global->_inter_resStr, 27);
+ _vm->_game->_script->evalExpr(0);
+ strncpy0(fileName, _vm->_game->_script->getResultStr(), 27);
if (!strchr(fileName, '.'))
strcat(fileName, ".ITK");
@@ -1589,49 +1042,46 @@ void Inter_v2::o2_resetImdFrontSurf() {
}
bool Inter_v2::o2_assign(OpFuncParams &params) {
- byte *savedPos;
- int16 varOff;
- int16 token;
- int16 result;
- byte loopCount;
-
- savedPos = _vm->_global->_inter_execPtr;
- varOff = _vm->_parse->parseVarIndex();
+ byte destType = _vm->_game->_script->peekByte();
+ int16 dest = _vm->_game->_script->readVarIndex();
- if (*_vm->_global->_inter_execPtr == 99) {
- _vm->_global->_inter_execPtr++;
- loopCount = *_vm->_global->_inter_execPtr++;
+ byte loopCount;
+ if (_vm->_game->_script->peekByte() == 99) {
+ _vm->_game->_script->skip(1);
+ loopCount = _vm->_game->_script->readByte();
} else
loopCount = 1;
for (int i = 0; i < loopCount; i++) {
- token = evalExpr(&result);
- switch (savedPos[0]) {
- case 16:
- case 18:
- WRITE_VARO_UINT8(varOff + i, _vm->_global->_inter_resVal);
+ int16 result;
+ int16 srcType = _vm->_game->_script->evalExpr(&result);
+
+ switch (destType) {
+ case TYPE_VAR_INT8:
+ case TYPE_ARRAY_INT8:
+ WRITE_VARO_UINT8(dest + i, _vm->_game->_script->getResultInt());
break;
- case 17:
- case 27:
- WRITE_VARO_UINT16(varOff + i * 2, _vm->_global->_inter_resVal);
+ case TYPE_VAR_INT16:
+ case TYPE_ARRAY_INT16:
+ WRITE_VARO_UINT16(dest + i * 2, _vm->_game->_script->getResultInt());
break;
- case 23:
- case 26:
- WRITE_VAR_OFFSET(varOff + i * 4, _vm->_global->_inter_resVal);
+ case TYPE_VAR_INT32:
+ case TYPE_ARRAY_INT32:
+ WRITE_VAR_OFFSET(dest + i * 4, _vm->_game->_script->getResultInt());
break;
- case 24:
- WRITE_VARO_UINT16(varOff + i * 4, _vm->_global->_inter_resVal);
+ case TYPE_VAR_INT32_AS_INT16:
+ WRITE_VARO_UINT16(dest + i * 4, _vm->_game->_script->getResultInt());
break;
- case 25:
- case 28:
- if (token == 20)
- WRITE_VARO_UINT8(varOff, result);
+ case TYPE_VAR_STR:
+ case TYPE_ARRAY_STR:
+ if (srcType == TYPE_IMM_INT16)
+ WRITE_VARO_UINT8(dest, result);
else
- WRITE_VARO_STR(varOff, _vm->_global->_inter_resStr);
+ WRITE_VARO_STR(dest, _vm->_game->_script->getResultStr());
break;
}
}
@@ -1643,12 +1093,12 @@ bool Inter_v2::o2_printText(OpFuncParams &params) {
char buf[60];
int i;
- _vm->_draw->_destSpriteX = _vm->_parse->parseValExpr();
- _vm->_draw->_destSpriteY = _vm->_parse->parseValExpr();
+ _vm->_draw->_destSpriteX = _vm->_game->_script->readValExpr();
+ _vm->_draw->_destSpriteY = _vm->_game->_script->readValExpr();
- _vm->_draw->_backColor = _vm->_parse->parseValExpr();
- _vm->_draw->_frontColor = _vm->_parse->parseValExpr();
- _vm->_draw->_fontIndex = _vm->_parse->parseValExpr();
+ _vm->_draw->_backColor = _vm->_game->_script->readValExpr();
+ _vm->_draw->_frontColor = _vm->_game->_script->readValExpr();
+ _vm->_draw->_fontIndex = _vm->_game->_script->readValExpr();
_vm->_draw->_destSurface = 21;
_vm->_draw->_textToPrint = buf;
_vm->_draw->_transparency = 0;
@@ -1659,48 +1109,47 @@ bool Inter_v2::o2_printText(OpFuncParams &params) {
}
do {
- for (i = 0; (((char) *_vm->_global->_inter_execPtr) != '.') &&
- (*_vm->_global->_inter_execPtr != 200);
- i++, _vm->_global->_inter_execPtr++) {
- buf[i] = (char) *_vm->_global->_inter_execPtr;
+ for (i = 0; (_vm->_game->_script->peekChar() != '.') &&
+ (_vm->_game->_script->peekByte() != 200); i++) {
+ buf[i] = _vm->_game->_script->readChar();
}
- if (*_vm->_global->_inter_execPtr != 200) {
- _vm->_global->_inter_execPtr++;
- switch (*_vm->_global->_inter_execPtr) {
- case 16:
- case 18:
+ if (_vm->_game->_script->peekByte() != 200) {
+ _vm->_game->_script->skip(1);
+ switch (_vm->_game->_script->peekByte()) {
+ case TYPE_VAR_INT8:
+ case TYPE_ARRAY_INT8:
sprintf(buf + i, "%d",
- (int8) READ_VARO_UINT8(_vm->_parse->parseVarIndex()));
+ (int8) READ_VARO_UINT8(_vm->_game->_script->readVarIndex()));
break;
- case 17:
- case 24:
- case 27:
+ case TYPE_VAR_INT16:
+ case TYPE_VAR_INT32_AS_INT16:
+ case TYPE_ARRAY_INT16:
sprintf(buf + i, "%d",
- (int16) READ_VARO_UINT16(_vm->_parse->parseVarIndex()));
+ (int16) READ_VARO_UINT16(_vm->_game->_script->readVarIndex()));
break;
- case 23:
- case 26:
+ case TYPE_VAR_INT32:
+ case TYPE_ARRAY_INT32:
sprintf(buf + i, "%d",
- VAR_OFFSET(_vm->_parse->parseVarIndex()));
+ VAR_OFFSET(_vm->_game->_script->readVarIndex()));
break;
- case 25:
- case 28:
+ case TYPE_VAR_STR:
+ case TYPE_ARRAY_STR:
sprintf(buf + i, "%s",
- GET_VARO_STR(_vm->_parse->parseVarIndex()));
+ GET_VARO_STR(_vm->_game->_script->readVarIndex()));
break;
}
- _vm->_global->_inter_execPtr++;
+ _vm->_game->_script->skip(1);
} else
buf[i] = 0;
_vm->_draw->spriteOperation(DRAW_PRINTTEXT);
- } while (*_vm->_global->_inter_execPtr != 200);
+ } while (_vm->_game->_script->peekByte() != 200);
- _vm->_global->_inter_execPtr++;
+ _vm->_game->_script->skip(1);
return false;
}
@@ -1708,20 +1157,20 @@ bool Inter_v2::o2_printText(OpFuncParams &params) {
bool Inter_v2::o2_animPalInit(OpFuncParams &params) {
int16 index;
- index = load16();
+ index = _vm->_game->_script->readInt16();
if (index > 0) {
index--;
- _animPalLowIndex[index] = _vm->_parse->parseValExpr();
- _animPalHighIndex[index] = _vm->_parse->parseValExpr();
+ _animPalLowIndex[index] = _vm->_game->_script->readValExpr();
+ _animPalHighIndex[index] = _vm->_game->_script->readValExpr();
_animPalDir[index] = 1;
} else if (index == 0) {
memset(_animPalDir, 0, 8 * sizeof(int16));
- _vm->_parse->parseValExpr();
- _vm->_parse->parseValExpr();
+ _vm->_game->_script->readValExpr();
+ _vm->_game->_script->readValExpr();
} else {
index = -index - 1;
- _animPalLowIndex[index] = _vm->_parse->parseValExpr();
- _animPalHighIndex[index] = _vm->_parse->parseValExpr();
+ _animPalLowIndex[index] = _vm->_game->_script->readValExpr();
+ _animPalHighIndex[index] = _vm->_game->_script->readValExpr();
_animPalDir[index] = -1;
}
return false;
@@ -1734,14 +1183,14 @@ bool Inter_v2::o2_addCollision(OpFuncParams &params) {
int16 key;
int16 funcSub;
- id = _vm->_parse->parseValExpr();
- funcSub = _vm->_global->_inter_execPtr - _vm->_game->_totFileData;
- left = _vm->_parse->parseValExpr();
- top = _vm->_parse->parseValExpr();
- width = _vm->_parse->parseValExpr();
- height = _vm->_parse->parseValExpr();
- flags = _vm->_parse->parseValExpr();
- key = load16();
+ id = _vm->_game->_script->readValExpr();
+ funcSub = _vm->_game->_script->pos();
+ left = _vm->_game->_script->readValExpr();
+ top = _vm->_game->_script->readValExpr();
+ width = _vm->_game->_script->readValExpr();
+ height = _vm->_game->_script->readValExpr();
+ flags = _vm->_game->_script->readValExpr();
+ key = _vm->_game->_script->readInt16();
if (key == 0)
key = ABS(id) + 41960;
@@ -1775,7 +1224,7 @@ bool Inter_v2::o2_addCollision(OpFuncParams &params) {
bool Inter_v2::o2_freeCollision(OpFuncParams &params) {
int16 id;
- id = _vm->_parse->parseValExpr();
+ id = _vm->_game->_script->readValExpr();
if (id == -2) {
for (int i = 0; i < 150; i++) {
if ((_vm->_game->_collisionAreas[i].id & 0xF000) == 0xD000)
@@ -1797,9 +1246,9 @@ bool Inter_v2::o2_goblinFunc(OpFuncParams &params) {
// It's not yet implemented, so we fudge our way through
// and pretend we've won.
if (_vm->getGameType() == kGameTypeInca2) {
- _vm->_global->_inter_execPtr += 4;
- uint16 resVar = (uint16) load16();
- _vm->_global->_inter_execPtr += 4;
+ _vm->_game->_script->skip(4);
+ uint16 resVar = _vm->_game->_script->readUint16();
+ _vm->_game->_script->skip(4);
WRITE_VAR(resVar, 1);
return false;
@@ -1808,18 +1257,20 @@ bool Inter_v2::o2_goblinFunc(OpFuncParams &params) {
OpGobParams gobParams;
int16 cmd;
- cmd = load16();
- _vm->_global->_inter_execPtr += 2;
+ cmd = _vm->_game->_script->readInt16();
+
+ gobParams.paramCount = _vm->_game->_script->readInt16();
+ gobParams.extraData = cmd;
if (cmd != 101)
- executeGoblinOpcode(cmd, gobParams);
+ executeOpcodeGob(cmd, gobParams);
return false;
}
bool Inter_v2::o2_stopSound(OpFuncParams &params) {
int16 expr;
- expr = _vm->_parse->parseValExpr();
+ expr = _vm->_game->_script->readValExpr();
if (expr < 0) {
_vm->_sound->adlibStop();
@@ -1839,13 +1290,13 @@ bool Inter_v2::o2_getFreeMem(OpFuncParams &params) {
int16 freeVar;
int16 maxFreeVar;
- freeVar = _vm->_parse->parseVarIndex();
- maxFreeVar = _vm->_parse->parseVarIndex();
+ freeVar = _vm->_game->_script->readVarIndex();
+ maxFreeVar = _vm->_game->_script->readVarIndex();
// HACK
WRITE_VAR_OFFSET(freeVar, 1000000);
WRITE_VAR_OFFSET(maxFreeVar, 1000000);
- WRITE_VAR(16, READ_LE_UINT32(_vm->_game->_totFileData + 0x2C) * 4);
+ WRITE_VAR(16, _vm->_game->_script->getVariablesCount() * 4);
return false;
}
@@ -1855,23 +1306,22 @@ bool Inter_v2::o2_checkData(OpFuncParams &params) {
int32 size;
SaveLoad::SaveMode mode;
- evalExpr(0);
- varOff = _vm->_parse->parseVarIndex();
+ _vm->_game->_script->evalExpr(0);
+ varOff = _vm->_game->_script->readVarIndex();
size = -1;
handle = 1;
- mode = _vm->_saveLoad->getSaveMode(_vm->_global->_inter_resStr);
+ mode = _vm->_saveLoad->getSaveMode(_vm->_game->_script->getResultStr());
if (mode == SaveLoad::kSaveModeNone) {
- handle = _vm->_dataIO->openData(_vm->_global->_inter_resStr);
- if (handle >= 0) {
- _vm->_dataIO->closeData(handle);
- size = _vm->_dataIO->getDataSize(_vm->_global->_inter_resStr);
- } else
- warning("File \"%s\" not found", _vm->_global->_inter_resStr);
+ if (_vm->_dataIO->existData(_vm->_game->_script->getResultStr()))
+ size = _vm->_dataIO->getDataSize(_vm->_game->_script->getResultStr());
+ else
+ warning("File \"%s\" not found", _vm->_game->_script->getResultStr());
+
} else if (mode == SaveLoad::kSaveModeSave)
- size = _vm->_saveLoad->getSize(_vm->_global->_inter_resStr);
+ size = _vm->_saveLoad->getSize(_vm->_game->_script->getResultStr());
else if (mode == SaveLoad::kSaveModeExists)
size = 23;
@@ -1879,7 +1329,7 @@ bool Inter_v2::o2_checkData(OpFuncParams &params) {
handle = -1;
debugC(2, kDebugFileIO, "Requested size of file \"%s\": %d",
- _vm->_global->_inter_resStr, size);
+ _vm->_game->_script->getResultStr(), size);
WRITE_VAR_OFFSET(varOff, handle);
WRITE_VAR(16, (uint32) size);
@@ -1896,20 +1346,20 @@ bool Inter_v2::o2_readData(OpFuncParams &params) {
byte *buf;
SaveLoad::SaveMode mode;
- evalExpr(0);
- dataVar = _vm->_parse->parseVarIndex();
- size = _vm->_parse->parseValExpr();
- evalExpr(0);
- offset = _vm->_global->_inter_resVal;
+ _vm->_game->_script->evalExpr(0);
+ dataVar = _vm->_game->_script->readVarIndex();
+ size = _vm->_game->_script->readValExpr();
+ _vm->_game->_script->evalExpr(0);
+ offset = _vm->_game->_script->getResultInt();
retSize = 0;
debugC(2, kDebugFileIO, "Read from file \"%s\" (%d, %d bytes at %d)",
- _vm->_global->_inter_resStr, dataVar, size, offset);
+ _vm->_game->_script->getResultStr(), dataVar, size, offset);
- mode = _vm->_saveLoad->getSaveMode(_vm->_global->_inter_resStr);
+ mode = _vm->_saveLoad->getSaveMode(_vm->_game->_script->getResultStr());
if (mode == SaveLoad::kSaveModeSave) {
WRITE_VAR(1, 1);
- if (_vm->_saveLoad->load(_vm->_global->_inter_resStr, dataVar, size, offset))
+ if (_vm->_saveLoad->load(_vm->_game->_script->getResultStr(), dataVar, size, offset))
WRITE_VAR(1, 0);
return false;
} else if (mode == SaveLoad::kSaveModeIgnore)
@@ -1917,22 +1367,22 @@ bool Inter_v2::o2_readData(OpFuncParams &params) {
if (size < 0) {
warning("Attempted to read a raw sprite from file \"%s\"",
- _vm->_global->_inter_resStr);
+ _vm->_game->_script->getResultStr());
return false ;
} else if (size == 0) {
dataVar = 0;
- size = READ_LE_UINT32(_vm->_game->_totFileData + 0x2C) * 4;
+ size = _vm->_game->_script->getVariablesCount() * 4;
}
buf = _variables->getAddressOff8(dataVar);
- if (_vm->_global->_inter_resStr[0] == 0) {
+ if (_vm->_game->_script->getResultStr()[0] == 0) {
WRITE_VAR(1, size);
return false;
}
WRITE_VAR(1, 1);
- handle = _vm->_dataIO->openData(_vm->_global->_inter_resStr);
+ handle = _vm->_dataIO->openData(_vm->_game->_script->getResultStr());
if (handle < 0)
return false;
@@ -1967,23 +1417,23 @@ bool Inter_v2::o2_writeData(OpFuncParams &params) {
int16 dataVar;
SaveLoad::SaveMode mode;
- evalExpr(0);
- dataVar = _vm->_parse->parseVarIndex();
- size = _vm->_parse->parseValExpr();
- evalExpr(0);
- offset = _vm->_global->_inter_resVal;
+ _vm->_game->_script->evalExpr(0);
+ dataVar = _vm->_game->_script->readVarIndex();
+ size = _vm->_game->_script->readValExpr();
+ _vm->_game->_script->evalExpr(0);
+ offset = _vm->_game->_script->getResultInt();
debugC(2, kDebugFileIO, "Write to file \"%s\" (%d, %d bytes at %d)",
- _vm->_global->_inter_resStr, dataVar, size, offset);
+ _vm->_game->_script->getResultStr(), dataVar, size, offset);
WRITE_VAR(1, 1);
- mode = _vm->_saveLoad->getSaveMode(_vm->_global->_inter_resStr);
+ mode = _vm->_saveLoad->getSaveMode(_vm->_game->_script->getResultStr());
if (mode == SaveLoad::kSaveModeSave) {
- if (_vm->_saveLoad->save(_vm->_global->_inter_resStr, dataVar, size, offset))
+ if (_vm->_saveLoad->save(_vm->_game->_script->getResultStr(), dataVar, size, offset))
WRITE_VAR(1, 0);
} else if (mode == SaveLoad::kSaveModeNone)
- warning("Attempted to write to file \"%s\"", _vm->_global->_inter_resStr);
+ warning("Attempted to write to file \"%s\"", _vm->_game->_script->getResultStr());
return false;
}
@@ -1992,7 +1442,7 @@ void Inter_v2::o2_loadInfogramesIns(OpGobParams &params) {
int16 varName;
char fileName[20];
- varName = load16();
+ varName = _vm->_game->_script->readInt16();
strncpy0(fileName, GET_VAR_STR(varName), 15);
strcat(fileName, ".INS");
@@ -2004,7 +1454,7 @@ void Inter_v2::o2_playInfogrames(OpGobParams &params) {
int16 varName;
char fileName[20];
- varName = load16();
+ varName = _vm->_game->_script->readInt16();
strncpy0(fileName, GET_VAR_STR(varName), 15);
strcat(fileName, ".DUM");
@@ -2014,13 +1464,13 @@ void Inter_v2::o2_playInfogrames(OpGobParams &params) {
}
void Inter_v2::o2_startInfogrames(OpGobParams &params) {
- load16();
+ _vm->_game->_script->readInt16();
_vm->_sound->infogramesPlay();
}
void Inter_v2::o2_stopInfogrames(OpGobParams &params) {
- load16();
+ _vm->_game->_script->readInt16();
_vm->_sound->infogramesStop();
}
@@ -2034,12 +1484,12 @@ void Inter_v2::o2_stopProtracker(OpGobParams &params) {
}
void Inter_v2::o2_handleGoblins(OpGobParams &params) {
- _vm->_goblin->_gob1NoTurn = VAR(load16()) != 0;
- _vm->_goblin->_gob2NoTurn = VAR(load16()) != 0;
- _vm->_goblin->_gob1RelaxTimeVar = load16();
- _vm->_goblin->_gob2RelaxTimeVar = load16();
- _vm->_goblin->_gob1Busy = VAR(load16()) != 0;
- _vm->_goblin->_gob2Busy = VAR(load16()) != 0;
+ _vm->_goblin->_gob1NoTurn = VAR(_vm->_game->_script->readInt16()) != 0;
+ _vm->_goblin->_gob2NoTurn = VAR(_vm->_game->_script->readInt16()) != 0;
+ _vm->_goblin->_gob1RelaxTimeVar = _vm->_game->_script->readInt16();
+ _vm->_goblin->_gob2RelaxTimeVar = _vm->_game->_script->readInt16();
+ _vm->_goblin->_gob1Busy = VAR(_vm->_game->_script->readInt16()) != 0;
+ _vm->_goblin->_gob2Busy = VAR(_vm->_game->_script->readInt16()) != 0;
_vm->_goblin->handleGoblins();
}
@@ -2050,21 +1500,20 @@ int16 Inter_v2::loadSound(int16 search) {
uint16 slotIdMask;
uint32 dataSize;
SoundType type;
- SoundSource source;
type = SOUND_SND;
slotIdMask = 0;
dataSize = 0;
if (!search) {
- slot = _vm->_parse->parseValExpr();
+ slot = _vm->_game->_script->readValExpr();
if (slot < 0) {
type = SOUND_ADL;
slot = -slot;
}
- id = load16();
+ id = _vm->_game->_script->readInt16();
} else {
- id = load16();
+ id = _vm->_game->_script->readInt16();
for (slot = 0; slot < Sound::kSoundsCount; slot++)
if (_vm->_sound->sampleGetBySlot(slot)->isId(id)) {
@@ -2093,37 +1542,37 @@ int16 Inter_v2::loadSound(int16 search) {
if (id == -1) {
char sndfile[14];
- source = SOUND_FILE;
-
- strncpy0(sndfile, (const char *) _vm->_global->_inter_execPtr, 9);
- _vm->_global->_inter_execPtr += 9;
+ strncpy0(sndfile, _vm->_game->_script->readString(9), 9);
if (type == SOUND_ADL)
strcat(sndfile, ".ADL");
else
strcat(sndfile, ".SND");
- dataPtr = (byte *) _vm->_dataIO->getData(sndfile);
- if (dataPtr)
- dataSize = _vm->_dataIO->getDataSize(sndfile);
- } else if (id >= 30000) {
- source = SOUND_EXT;
-
- dataPtr = (byte *) _vm->_game->loadExtData(id, 0, 0, &dataSize);
- } else {
- int16 totSize;
+ dataPtr = _vm->_dataIO->getData(sndfile);
+ dataSize = _vm->_dataIO->getDataSize(sndfile);
+ if (!dataPtr)
+ return 0;
- source = SOUND_TOT;
+ if (!sample->load(type, dataPtr, dataSize)) {
+ delete[] dataPtr;
+ return 0;
+ }
- dataPtr = (byte *) _vm->_game->loadTotResource(id, &totSize);
- dataSize = (uint32) ((int32) totSize);
+ sample->_id = id;
+ return slot | slotIdMask;
}
- if (dataPtr) {
- sample->load(type, source, dataPtr, dataSize);
- sample->_id = id;
+ Resource *resource = _vm->_game->_resources->getResource(id);
+ if (!resource)
+ return 0;
+
+ if (!sample->load(type, resource)) {
+ delete resource;
+ return 0;
}
+ sample->_id = id;
return slot | slotIdMask;
}
diff --git a/engines/gob/inter_v3.cpp b/engines/gob/inter_v3.cpp
index 6819b369b8..17ce7feafa 100644
--- a/engines/gob/inter_v3.cpp
+++ b/engines/gob/inter_v3.cpp
@@ -32,683 +32,38 @@
#include "gob/dataio.h"
#include "gob/draw.h"
#include "gob/game.h"
-#include "gob/parse.h"
+#include "gob/script.h"
+#include "gob/resources.h"
namespace Gob {
-#define OPCODE(x) _OPCODE(Inter_v3, x)
-
-const int Inter_v3::_goblinFuncLookUp[][2] = {
- {0, 0},
- {1, 1},
- {2, 2},
- {4, 3},
- {5, 4},
- {6, 5},
- {7, 6},
- {8, 7},
- {9, 8},
- {10, 9},
- {12, 10},
- {13, 11},
- {14, 12},
- {15, 13},
- {16, 14},
- {21, 15},
- {22, 16},
- {23, 17},
- {24, 18},
- {25, 19},
- {26, 20},
- {27, 21},
- {28, 22},
- {29, 23},
- {30, 24},
- {32, 25},
- {33, 26},
- {34, 27},
- {35, 28},
- {36, 29},
- {37, 30},
- {40, 31},
- {41, 32},
- {42, 33},
- {43, 34},
- {44, 35},
- {50, 36},
- {52, 37},
- {53, 38},
- {100, 39},
- {152, 40},
- {200, 41},
- {201, 42},
- {202, 43},
- {203, 44},
- {204, 45},
- {250, 46},
- {251, 47},
- {252, 48},
- {500, 49},
- {502, 50},
- {503, 51},
- {600, 52},
- {601, 53},
- {602, 54},
- {603, 55},
- {604, 56},
- {605, 57},
- {1000, 58},
- {1001, 59},
- {1002, 60},
- {1003, 61},
- {1004, 62},
- {1005, 63},
- {1006, 64},
- {1008, 65},
- {1009, 66},
- {1010, 67},
- {1011, 68},
- {1015, 69},
- {2005, 70}
-};
+#define OPCODEVER Inter_v3
+#define OPCODEDRAW(i, x) _opcodesDraw[i]._OPCODEDRAW(OPCODEVER, x)
+#define OPCODEFUNC(i, x) _opcodesFunc[i]._OPCODEFUNC(OPCODEVER, x)
+#define OPCODEGOB(i, x) _opcodesGob[i]._OPCODEGOB(OPCODEVER, x)
Inter_v3::Inter_v3(GobEngine *vm) : Inter_v2(vm) {
- setupOpcodes();
}
-void Inter_v3::setupOpcodes() {
- static const OpcodeDrawEntryV3 opcodesDraw[256] = {
- /* 00 */
- OPCODE(o1_loadMult),
- OPCODE(o2_playMult),
- OPCODE(o2_freeMultKeys),
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- OPCODE(o1_initCursor),
- /* 08 */
- OPCODE(o1_initCursorAnim),
- OPCODE(o1_clearCursorAnim),
- OPCODE(o2_setRenderFlags),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- OPCODE(o1_loadAnim),
- OPCODE(o1_freeAnim),
- OPCODE(o1_updateAnim),
- OPCODE(o2_multSub),
- /* 14 */
- OPCODE(o2_initMult),
- OPCODE(o1_freeMult),
- OPCODE(o1_animate),
- OPCODE(o2_loadMultObject),
- /* 18 */
- OPCODE(o1_getAnimLayerInfo),
- OPCODE(o1_getObjAnimSize),
- OPCODE(o1_loadStatic),
- OPCODE(o1_freeStatic),
- /* 1C */
- OPCODE(o2_renderStatic),
- OPCODE(o2_loadCurLayer),
- {0, ""},
- {0, ""},
- /* 20 */
- OPCODE(o2_playCDTrack),
- OPCODE(o2_waitCDTrackEnd),
- OPCODE(o2_stopCD),
- OPCODE(o2_readLIC),
- /* 24 */
- OPCODE(o2_freeLIC),
- OPCODE(o2_getCDTrackPos),
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o2_loadFontToSprite),
- OPCODE(o1_freeFontToSprite),
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- OPCODE(o2_totSub),
- OPCODE(o2_switchTotSub),
- OPCODE(o2_pushVars),
- OPCODE(o2_popVars),
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 48 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 4C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 50 */
- OPCODE(o2_loadMapObjects),
- OPCODE(o2_freeGoblins),
- OPCODE(o2_moveGoblin),
- OPCODE(o2_writeGoblinPos),
- /* 54 */
- OPCODE(o2_stopGoblin),
- OPCODE(o2_setGoblinState),
- OPCODE(o2_placeGoblin),
- {0, ""},
- /* 58 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 5C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 60 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 64 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 68 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 6C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 70 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 74 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 78 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 7C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 80 */
- OPCODE(o2_initScreen),
- OPCODE(o2_scroll),
- OPCODE(o2_setScrollOffset),
- OPCODE(o2_playImd),
- /* 84 */
- OPCODE(o2_getImdInfo),
- OPCODE(o2_openItk),
- OPCODE(o2_closeItk),
- OPCODE(o2_setImdFrontSurf),
- /* 88 */
- OPCODE(o2_resetImdFrontSurf),
- {0, ""},
- {0, ""},
- {0, ""},
- /* 8C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 90 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 94 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 98 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 9C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* AC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* BC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* CC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* DC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* EC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* FC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""}
- };
-
- static const OpcodeFuncEntryV3 opcodesFunc[80] = {
- /* 00 */
- OPCODE(o1_callSub),
- OPCODE(o1_callSub),
- OPCODE(o1_printTotText),
- OPCODE(o1_loadCursor),
- /* 04 */
- {0, ""},
- OPCODE(o1_switch),
- OPCODE(o1_repeatUntil),
- OPCODE(o1_whileDo),
- /* 08 */
- OPCODE(o1_if),
- OPCODE(o2_assign),
- OPCODE(o1_loadSpriteToPos),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- OPCODE(o2_printText),
- OPCODE(o1_loadTot),
- OPCODE(o1_palLoad),
- /* 14 */
- OPCODE(o1_keyFunc),
- OPCODE(o1_capturePush),
- OPCODE(o1_capturePop),
- OPCODE(o2_animPalInit),
- /* 18 */
- OPCODE(o2_addCollision),
- OPCODE(o2_freeCollision),
- OPCODE(o3_getTotTextItemPart),
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- OPCODE(o1_drawOperations),
- OPCODE(o1_setcmdCount),
- /* 20 */
- OPCODE(o1_return),
- OPCODE(o1_renewTimeInVars),
- OPCODE(o1_speakerOn),
- OPCODE(o1_speakerOff),
- /* 24 */
- OPCODE(o1_putPixel),
- OPCODE(o2_goblinFunc),
- OPCODE(o1_createSprite),
- OPCODE(o1_freeSprite),
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o1_returnTo),
- OPCODE(o1_loadSpriteContent),
- OPCODE(o3_copySprite),
- OPCODE(o1_fillRect),
- /* 34 */
- OPCODE(o1_drawLine),
- OPCODE(o1_strToLong),
- OPCODE(o1_invalidate),
- OPCODE(o1_setBackDelta),
- /* 38 */
- OPCODE(o1_playSound),
- OPCODE(o2_stopSound),
- OPCODE(o2_loadSound),
- OPCODE(o1_freeSoundSlot),
- /* 3C */
- OPCODE(o1_waitEndPlay),
- OPCODE(o1_playComposition),
- OPCODE(o2_getFreeMem),
- OPCODE(o2_checkData),
- /* 40 */
- {0, ""},
- OPCODE(o1_prepareStr),
- OPCODE(o1_insertStr),
- OPCODE(o1_cutStr),
- /* 44 */
- OPCODE(o1_strstr),
- OPCODE(o1_istrlen),
- OPCODE(o1_setMousePos),
- OPCODE(o1_setFrameRate),
- /* 48 */
- OPCODE(o1_animatePalette),
- OPCODE(o1_animateCursor),
- OPCODE(o1_blitCursor),
- OPCODE(o1_loadFont),
- /* 4C */
- OPCODE(o1_freeFont),
- OPCODE(o2_readData),
- OPCODE(o2_writeData),
- OPCODE(o1_manageDataFile),
- };
-
- static const OpcodeGoblinEntryV3 opcodesGoblin[71] = {
- /* 00 */
- OPCODE(o2_loadInfogramesIns),
- OPCODE(o2_startInfogrames),
- OPCODE(o2_stopInfogrames),
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 08 */
- {0, ""},
- OPCODE(o2_playInfogrames),
- {0, ""},
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 14 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 18 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 20 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 24 */
- {0, ""},
- {0, ""},
- {0, ""},
- OPCODE(o3_wobble),
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- };
-
- _opcodesDrawV3 = opcodesDraw;
- _opcodesFuncV3 = opcodesFunc;
- _opcodesGoblinV3 = opcodesGoblin;
+void Inter_v3::setupOpcodesDraw() {
+ Inter_v2::setupOpcodesDraw();
}
-void Inter_v3::executeDrawOpcode(byte i) {
- debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%X] (%s)",
- i, i, getOpcodeDrawDesc(i));
+void Inter_v3::setupOpcodesFunc() {
+ Inter_v2::setupOpcodesFunc();
- OpcodeDrawProcV3 op = _opcodesDrawV3[i].proc;
-
- if (op == 0)
- warning("unimplemented opcodeDraw: %d", i);
- else
- (this->*op) ();
-}
-
-bool Inter_v3::executeFuncOpcode(byte i, byte j, OpFuncParams &params) {
- debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%X.0x%X] (%s)",
- i, j, i, j, getOpcodeFuncDesc(i, j));
-
- if ((i > 4) || (j > 15)) {
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- return false;
- }
-
- OpcodeFuncProcV3 op = _opcodesFuncV3[i*16 + j].proc;
-
- if (op == 0)
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- else
- return (this->*op) (params);
-
- return false;
-}
-
-void Inter_v3::executeGoblinOpcode(int i, OpGobParams &params) {
- debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%X] (%s)",
- i, i, getOpcodeGoblinDesc(i));
-
- OpcodeGoblinProcV3 op = 0;
-
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i) {
- op = _opcodesGoblinV3[_goblinFuncLookUp[j][1]].proc;
- break;
- }
-
- if (op == 0) {
- int16 val;
-
- _vm->_global->_inter_execPtr -= 2;
- val = load16();
- _vm->_global->_inter_execPtr += val << 1;
- } else
- (this->*op) (params);
+ OPCODEFUNC(0x1A, o3_getTotTextItemPart);
+ OPCODEFUNC(0x32, o3_copySprite);
}
-const char *Inter_v3::getOpcodeDrawDesc(byte i) {
- return _opcodesDrawV3[i].desc;
-}
+void Inter_v3::setupOpcodesGob() {
+ OPCODEGOB( 0, o2_loadInfogramesIns);
+ OPCODEGOB( 1, o2_startInfogrames);
+ OPCODEGOB( 2, o2_stopInfogrames);
-const char *Inter_v3::getOpcodeFuncDesc(byte i, byte j) {
- if ((i > 4) || (j > 15))
- return "";
+ OPCODEGOB( 10, o2_playInfogrames);
- return _opcodesFuncV3[i*16 + j].desc;
-}
-
-const char *Inter_v3::getOpcodeGoblinDesc(int i) {
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i)
- return _opcodesGoblinV3[_goblinFuncLookUp[j][1]].desc;
- return "";
+ OPCODEGOB(100, o3_wobble);
}
bool Inter_v3::o3_getTotTextItemPart(OpFuncParams &params) {
@@ -720,18 +75,18 @@ bool Inter_v3::o3_getTotTextItemPart(OpFuncParams &params) {
uint32 stringStartVar, stringVar;
bool end;
- totTextItem = load16();
- stringStartVar = _vm->_parse->parseVarIndex();
- part = _vm->_parse->parseValExpr();
+ totTextItem = _vm->_game->_script->readInt16();
+ stringStartVar = _vm->_game->_script->readVarIndex();
+ part = _vm->_game->_script->readValExpr();
stringVar = stringStartVar;
WRITE_VARO_UINT8(stringVar, 0);
- if (!_vm->_game->_totTextData)
+ TextItem *textItem = _vm->_game->_resources->getTextItem(totTextItem);
+ if (!textItem)
return false;
- totData = _vm->_game->_totTextData->dataPtr +
- _vm->_game->_totTextData->items[totTextItem].offset;
+ totData = textItem->getData();
// Skip background rectangles
while (((int16) READ_LE_UINT16(totData)) != -1)
@@ -782,6 +137,7 @@ bool Inter_v3::o3_getTotTextItemPart(OpFuncParams &params) {
if ((n != 0) || (*totData == 1) ||
(*totData == 6) || (*totData == 7)) {
WRITE_VARO_UINT8(stringVar, 0);
+ delete textItem;
return false;
}
@@ -813,8 +169,9 @@ bool Inter_v3::o3_getTotTextItemPart(OpFuncParams &params) {
WRITE_VARO_UINT16(stringVar, offX);
WRITE_VARO_UINT16(stringVar + 2, offY);
WRITE_VARO_UINT16(stringVar + 4,
- totData - _vm->_game->_totTextData->dataPtr);
+ totData - _vm->_game->_resources->getTexts());
WRITE_VARO_UINT8(stringVar + 6, 0);
+ delete textItem;
return false;
}
@@ -860,8 +217,10 @@ bool Inter_v3::o3_getTotTextItemPart(OpFuncParams &params) {
if (((*totData != 2) && (*totData != 5)) ||
(ABS(offY - READ_LE_UINT16(totData + 3)) > 1)) {
- if (curPart == part)
+ if (curPart == part) {
+ delete textItem;
return false;
+ }
stringVar = stringStartVar;
WRITE_VARO_UINT8(stringVar, 0);
@@ -881,6 +240,7 @@ bool Inter_v3::o3_getTotTextItemPart(OpFuncParams &params) {
}
}
+ delete textItem;
return false;
}
diff --git a/engines/gob/inter_v4.cpp b/engines/gob/inter_v4.cpp
index 6ab55d70af..48378a5987 100644
--- a/engines/gob/inter_v4.cpp
+++ b/engines/gob/inter_v4.cpp
@@ -32,689 +32,32 @@
#include "gob/global.h"
#include "gob/draw.h"
#include "gob/game.h"
-#include "gob/parse.h"
+#include "gob/script.h"
#include "gob/videoplayer.h"
#include "gob/sound/sound.h"
namespace Gob {
-#define OPCODE(x) _OPCODE(Inter_v4, x)
-
-const int Inter_v4::_goblinFuncLookUp[][2] = {
- {0, 0},
- {1, 1},
- {2, 2},
- {4, 3},
- {5, 4},
- {6, 5},
- {7, 6},
- {8, 7},
- {9, 8},
- {10, 9},
- {12, 10},
- {13, 11},
- {14, 12},
- {15, 13},
- {16, 14},
- {21, 15},
- {22, 16},
- {23, 17},
- {24, 18},
- {25, 19},
- {26, 20},
- {27, 21},
- {28, 22},
- {29, 23},
- {30, 24},
- {32, 25},
- {33, 26},
- {34, 27},
- {35, 28},
- {36, 29},
- {37, 30},
- {40, 31},
- {41, 32},
- {42, 33},
- {43, 34},
- {44, 35},
- {50, 36},
- {52, 37},
- {53, 38},
- {100, 39},
- {152, 40},
- {200, 41},
- {201, 42},
- {202, 43},
- {203, 44},
- {204, 45},
- {250, 46},
- {251, 47},
- {252, 48},
- {500, 49},
- {502, 50},
- {503, 51},
- {600, 52},
- {601, 53},
- {602, 54},
- {603, 55},
- {604, 56},
- {605, 57},
- {1000, 58},
- {1001, 59},
- {1002, 60},
- {1003, 61},
- {1004, 62},
- {1005, 63},
- {1006, 64},
- {1008, 65},
- {1009, 66},
- {1010, 67},
- {1011, 68},
- {1015, 69},
- {2005, 70}
-};
+#define OPCODEVER Inter_v4
+#define OPCODEDRAW(i, x) _opcodesDraw[i]._OPCODEDRAW(OPCODEVER, x)
+#define OPCODEFUNC(i, x) _opcodesFunc[i]._OPCODEFUNC(OPCODEVER, x)
+#define OPCODEGOB(i, x) _opcodesGob[i]._OPCODEGOB(OPCODEVER, x)
Inter_v4::Inter_v4(GobEngine *vm) : Inter_v3(vm) {
- setupOpcodes();
}
-void Inter_v4::setupOpcodes() {
- static const OpcodeDrawEntryV4 opcodesDraw[256] = {
- /* 00 */
- OPCODE(o1_loadMult),
- OPCODE(o2_playMult),
- OPCODE(o2_freeMultKeys),
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- OPCODE(o1_initCursor),
- /* 08 */
- OPCODE(o1_initCursorAnim),
- OPCODE(o1_clearCursorAnim),
- OPCODE(o2_setRenderFlags),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- OPCODE(o1_loadAnim),
- OPCODE(o1_freeAnim),
- OPCODE(o1_updateAnim),
- OPCODE(o2_multSub),
- /* 14 */
- OPCODE(o2_initMult),
- OPCODE(o1_freeMult),
- OPCODE(o1_animate),
- OPCODE(o2_loadMultObject),
- /* 18 */
- OPCODE(o1_getAnimLayerInfo),
- OPCODE(o1_getObjAnimSize),
- OPCODE(o1_loadStatic),
- OPCODE(o1_freeStatic),
- /* 1C */
- OPCODE(o2_renderStatic),
- OPCODE(o2_loadCurLayer),
- {0, ""},
- {0, ""},
- /* 20 */
- OPCODE(o2_playCDTrack),
- OPCODE(o2_waitCDTrackEnd),
- OPCODE(o2_stopCD),
- OPCODE(o2_readLIC),
- /* 24 */
- OPCODE(o2_freeLIC),
- OPCODE(o2_getCDTrackPos),
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o2_loadFontToSprite),
- OPCODE(o1_freeFontToSprite),
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- OPCODE(o2_totSub),
- OPCODE(o2_switchTotSub),
- OPCODE(o2_pushVars),
- OPCODE(o2_popVars),
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 48 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 4C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 50 */
- OPCODE(o2_loadMapObjects),
- OPCODE(o2_freeGoblins),
- OPCODE(o2_moveGoblin),
- OPCODE(o2_writeGoblinPos),
- /* 54 */
- OPCODE(o2_stopGoblin),
- OPCODE(o2_setGoblinState),
- OPCODE(o2_placeGoblin),
- {0, ""},
- /* 58 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 5C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 60 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 64 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 68 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 6C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 70 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 74 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 78 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 7C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 80 */
- OPCODE(o4_initScreen),
- OPCODE(o2_scroll),
- OPCODE(o2_setScrollOffset),
- OPCODE(o4_playVmdOrMusic),
- /* 84 */
- OPCODE(o2_getImdInfo),
- OPCODE(o2_openItk),
- OPCODE(o2_closeItk),
- OPCODE(o2_setImdFrontSurf),
- /* 88 */
- OPCODE(o2_resetImdFrontSurf),
- {0, ""},
- {0, ""},
- {0, ""},
- /* 8C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 90 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 94 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 98 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 9C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* AC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* BC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* CC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* DC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* EC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* FC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""}
- };
-
- static const OpcodeFuncEntryV4 opcodesFunc[80] = {
- /* 00 */
- OPCODE(o1_callSub),
- OPCODE(o1_callSub),
- OPCODE(o1_printTotText),
- OPCODE(o1_loadCursor),
- /* 04 */
- {0, ""},
- OPCODE(o1_switch),
- OPCODE(o1_repeatUntil),
- OPCODE(o1_whileDo),
- /* 08 */
- OPCODE(o1_if),
- OPCODE(o2_assign),
- OPCODE(o1_loadSpriteToPos),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- OPCODE(o2_printText),
- OPCODE(o1_loadTot),
- OPCODE(o1_palLoad),
- /* 14 */
- OPCODE(o1_keyFunc),
- OPCODE(o1_capturePush),
- OPCODE(o1_capturePop),
- OPCODE(o2_animPalInit),
- /* 18 */
- OPCODE(o2_addCollision),
- OPCODE(o2_freeCollision),
- OPCODE(o3_getTotTextItemPart),
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- OPCODE(o1_drawOperations),
- OPCODE(o1_setcmdCount),
- /* 20 */
- OPCODE(o1_return),
- OPCODE(o1_renewTimeInVars),
- OPCODE(o1_speakerOn),
- OPCODE(o1_speakerOff),
- /* 24 */
- OPCODE(o1_putPixel),
- OPCODE(o2_goblinFunc),
- OPCODE(o1_createSprite),
- OPCODE(o1_freeSprite),
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o1_returnTo),
- OPCODE(o1_loadSpriteContent),
- OPCODE(o1_copySprite),
- OPCODE(o1_fillRect),
- /* 34 */
- OPCODE(o1_drawLine),
- OPCODE(o1_strToLong),
- OPCODE(o1_invalidate),
- OPCODE(o1_setBackDelta),
- /* 38 */
- OPCODE(o1_playSound),
- OPCODE(o2_stopSound),
- OPCODE(o2_loadSound),
- OPCODE(o1_freeSoundSlot),
- /* 3C */
- OPCODE(o1_waitEndPlay),
- OPCODE(o1_playComposition),
- OPCODE(o2_getFreeMem),
- OPCODE(o2_checkData),
- /* 40 */
- {0, ""},
- OPCODE(o1_prepareStr),
- OPCODE(o1_insertStr),
- OPCODE(o1_cutStr),
- /* 44 */
- OPCODE(o1_strstr),
- OPCODE(o1_istrlen),
- OPCODE(o1_setMousePos),
- OPCODE(o1_setFrameRate),
- /* 48 */
- OPCODE(o1_animatePalette),
- OPCODE(o1_animateCursor),
- OPCODE(o1_blitCursor),
- OPCODE(o1_loadFont),
- /* 4C */
- OPCODE(o1_freeFont),
- OPCODE(o2_readData),
- OPCODE(o2_writeData),
- OPCODE(o1_manageDataFile),
- };
-
- static const OpcodeGoblinEntryV4 opcodesGoblin[71] = {
- /* 00 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 08 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 14 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 18 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 20 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 24 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- };
-
- _opcodesDrawV4 = opcodesDraw;
- _opcodesFuncV4 = opcodesFunc;
- _opcodesGoblinV4 = opcodesGoblin;
-}
-
-void Inter_v4::executeDrawOpcode(byte i) {
- debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%X] (%s)",
- i, i, getOpcodeDrawDesc(i));
-
- OpcodeDrawProcV4 op = _opcodesDrawV4[i].proc;
-
- if (op == 0)
- warning("unimplemented opcodeDraw: %d", i);
- else
- (this->*op) ();
-}
-
-bool Inter_v4::executeFuncOpcode(byte i, byte j, OpFuncParams &params) {
- debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%X.0x%X] (%s) - %s, %d, %d",
- i, j, i, j, getOpcodeFuncDesc(i, j), _vm->_game->_curTotFile,
- (uint) (_vm->_global->_inter_execPtr - _vm->_game->_totFileData),
- (uint) (_vm->_global->_inter_execPtr - _vm->_game->_totFileData - params.counter - 4));
-
- if ((i > 4) || (j > 15)) {
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- return false;
- }
-
- OpcodeFuncProcV4 op = _opcodesFuncV4[i*16 + j].proc;
-
- if (op == 0)
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- else
- return (this->*op) (params);
+void Inter_v4::setupOpcodesDraw() {
+ Inter_v3::setupOpcodesDraw();
- return false;
+ OPCODEDRAW(0x80, o4_initScreen);
+ OPCODEDRAW(0x83, o4_playVmdOrMusic);
}
-void Inter_v4::executeGoblinOpcode(int i, OpGobParams &params) {
- debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%X] (%s)",
- i, i, getOpcodeGoblinDesc(i));
-
- OpcodeGoblinProcV4 op = 0;
-
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i) {
- op = _opcodesGoblinV4[_goblinFuncLookUp[j][1]].proc;
- break;
- }
-
- if (op == 0) {
- warning("unimplemented opcodeGoblin: %d", i);
-
- int16 val;
-
- _vm->_global->_inter_execPtr -= 2;
- val = load16();
- _vm->_global->_inter_execPtr += val << 1;
- } else
- (this->*op) (params);
-}
-
-const char *Inter_v4::getOpcodeDrawDesc(byte i) {
- return _opcodesDrawV4[i].desc;
-}
-
-const char *Inter_v4::getOpcodeFuncDesc(byte i, byte j) {
- if ((i > 4) || (j > 15))
- return "";
-
- return _opcodesFuncV4[i*16 + j].desc;
+void Inter_v4::setupOpcodesFunc() {
+ Inter_v3::setupOpcodesFunc();
}
-const char *Inter_v4::getOpcodeGoblinDesc(int i) {
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i)
- return _opcodesGoblinV4[_goblinFuncLookUp[j][1]].desc;
- return "";
+void Inter_v4::setupOpcodesGob() {
}
void Inter_v4::o4_initScreen() {
@@ -722,13 +65,13 @@ void Inter_v4::o4_initScreen() {
int16 videoMode;
int16 width, height;
- offY = load16();
+ offY = _vm->_game->_script->readInt16();
videoMode = offY & 0xFF;
offY = (offY >> 8) & 0xFF;
- width = _vm->_parse->parseValExpr();
- height = _vm->_parse->parseValExpr();
+ width = _vm->_game->_script->readValExpr();
+ height = _vm->_game->_script->readValExpr();
_vm->_video->clearScreen();
@@ -809,8 +152,8 @@ void Inter_v4::o4_playVmdOrMusic() {
uint16 palCmd;
bool close;
- evalExpr(0);
- strncpy0(fileName, _vm->_global->_inter_resStr, 127);
+ _vm->_game->_script->evalExpr(0);
+ strncpy0(fileName, _vm->_game->_script->getResultStr(), 127);
// WORKAROUND: The nut rolling animation in the administration center
// in Woodruff is called "noixroul", but the scripts think it's "noixroule".
@@ -818,14 +161,14 @@ void Inter_v4::o4_playVmdOrMusic() {
(!scumm_stricmp(fileName, "noixroule")))
strcpy(fileName, "noixroul");
- x = _vm->_parse->parseValExpr();
- y = _vm->_parse->parseValExpr();
- startFrame = _vm->_parse->parseValExpr();
- lastFrame = _vm->_parse->parseValExpr();
- breakKey = _vm->_parse->parseValExpr();
- flags = _vm->_parse->parseValExpr();
- palStart = _vm->_parse->parseValExpr();
- palEnd = _vm->_parse->parseValExpr();
+ x = _vm->_game->_script->readValExpr();
+ y = _vm->_game->_script->readValExpr();
+ startFrame = _vm->_game->_script->readValExpr();
+ lastFrame = _vm->_game->_script->readValExpr();
+ breakKey = _vm->_game->_script->readValExpr();
+ flags = _vm->_game->_script->readValExpr();
+ palStart = _vm->_game->_script->readValExpr();
+ palEnd = _vm->_game->_script->readValExpr();
palCmd = 1 << (flags & 0x3F);
debugC(1, kDebugVideo, "Playing video \"%s\" @ %d+%d, frames %d - %d, "
diff --git a/engines/gob/inter_v5.cpp b/engines/gob/inter_v5.cpp
index cb5b28cb67..1c20851c8d 100644
--- a/engines/gob/inter_v5.cpp
+++ b/engines/gob/inter_v5.cpp
@@ -30,652 +30,73 @@
#include "gob/inter.h"
#include "gob/global.h"
#include "gob/game.h"
-#include "gob/parse.h"
+#include "gob/script.h"
#include "gob/draw.h"
namespace Gob {
-#define OPCODE(x) _OPCODE(Inter_v5, x)
-
-const int Inter_v5::_goblinFuncLookUp[][2] = {
- {0, 0},
- {1, 0},
- {3, 0},
- {2, 0},
- {33, 0},
- {80, 1},
- {81, 2},
- {82, 3},
- {83, 4},
- {84, 5},
- {85, 6},
- {86, 7},
- {87, 0},
- {88, 0},
- {89, 0},
- {90, 0},
- {91, 0},
- {92, 8},
- {93, 0},
- {94, 0},
- {95, 9},
- {96, 10},
- {97, 11},
- {98, 12},
- {99, 0},
- {100, 13},
- {200, 14}
-};
+#define OPCODEVER Inter_v5
+#define OPCODEDRAW(i, x) _opcodesDraw[i]._OPCODEDRAW(OPCODEVER, x)
+#define OPCODEFUNC(i, x) _opcodesFunc[i]._OPCODEFUNC(OPCODEVER, x)
+#define OPCODEGOB(i, x) _opcodesGob[i]._OPCODEGOB(OPCODEVER, x)
Inter_v5::Inter_v5(GobEngine *vm) : Inter_v4(vm) {
- setupOpcodes();
}
-void Inter_v5::setupOpcodes() {
- static const OpcodeDrawEntryV5 opcodesDraw[256] = {
- /* 00 */
- OPCODE(o1_loadMult),
- OPCODE(o2_playMult),
- OPCODE(o2_freeMultKeys),
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- OPCODE(o1_initCursor),
- /* 08 */
- OPCODE(o1_initCursorAnim),
- OPCODE(o1_clearCursorAnim),
- OPCODE(o2_setRenderFlags),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- OPCODE(o1_loadAnim),
- OPCODE(o1_freeAnim),
- OPCODE(o1_updateAnim),
- OPCODE(o2_multSub),
- /* 14 */
- OPCODE(o2_initMult),
- OPCODE(o1_freeMult),
- OPCODE(o1_animate),
- OPCODE(o2_loadMultObject),
- /* 18 */
- OPCODE(o1_getAnimLayerInfo),
- OPCODE(o1_getObjAnimSize),
- OPCODE(o1_loadStatic),
- OPCODE(o1_freeStatic),
- /* 1C */
- OPCODE(o2_renderStatic),
- OPCODE(o2_loadCurLayer),
- {0, ""},
- {0, ""},
- /* 20 */
- OPCODE(o2_playCDTrack),
- OPCODE(o2_waitCDTrackEnd),
- OPCODE(o2_stopCD),
- OPCODE(o2_readLIC),
- /* 24 */
- OPCODE(o2_freeLIC),
- OPCODE(o2_getCDTrackPos),
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o2_loadFontToSprite),
- OPCODE(o1_freeFontToSprite),
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- OPCODE(o2_totSub),
- OPCODE(o2_switchTotSub),
- OPCODE(o2_pushVars),
- OPCODE(o2_popVars),
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 48 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 4C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 50 */
- OPCODE(o2_loadMapObjects),
- OPCODE(o2_freeGoblins),
- OPCODE(o2_moveGoblin),
- OPCODE(o2_writeGoblinPos),
- /* 54 */
- OPCODE(o2_stopGoblin),
- OPCODE(o2_setGoblinState),
- OPCODE(o2_placeGoblin),
- {0, ""},
- /* 58 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 5C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 60 */
- {0, ""},
- OPCODE(o5_deleteFile),
- {0, ""},
- {0, ""},
- /* 64 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 68 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 6C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 70 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 74 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 78 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 7C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 80 */
- OPCODE(o5_initScreen),
- OPCODE(o2_scroll),
- OPCODE(o2_setScrollOffset),
- OPCODE(o4_playVmdOrMusic),
- /* 84 */
- OPCODE(o2_getImdInfo),
- OPCODE(o2_openItk),
- OPCODE(o2_closeItk),
- OPCODE(o2_setImdFrontSurf),
- /* 88 */
- OPCODE(o2_resetImdFrontSurf),
- {0, ""},
- {0, ""},
- {0, ""},
- /* 8C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 90 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 94 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 98 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 9C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* AC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* BC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* CC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* DC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* EC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* FC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""}
- };
-
- static const OpcodeFuncEntryV5 opcodesFunc[80] = {
- /* 00 */
- OPCODE(o1_callSub),
- OPCODE(o1_callSub),
- OPCODE(o1_printTotText),
- OPCODE(o1_loadCursor),
- /* 04 */
- {0, ""},
- OPCODE(o1_switch),
- OPCODE(o1_repeatUntil),
- OPCODE(o1_whileDo),
- /* 08 */
- OPCODE(o1_if),
- OPCODE(o2_assign),
- OPCODE(o1_loadSpriteToPos),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- OPCODE(o2_printText),
- OPCODE(o1_loadTot),
- OPCODE(o1_palLoad),
- /* 14 */
- OPCODE(o1_keyFunc),
- OPCODE(o1_capturePush),
- OPCODE(o1_capturePop),
- OPCODE(o2_animPalInit),
- /* 18 */
- OPCODE(o2_addCollision),
- OPCODE(o2_freeCollision),
- OPCODE(o3_getTotTextItemPart),
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- OPCODE(o1_drawOperations),
- OPCODE(o1_setcmdCount),
- /* 20 */
- OPCODE(o1_return),
- OPCODE(o1_renewTimeInVars),
- OPCODE(o1_speakerOn),
- OPCODE(o1_speakerOff),
- /* 24 */
- OPCODE(o1_putPixel),
- OPCODE(o2_goblinFunc),
- OPCODE(o1_createSprite),
- OPCODE(o1_freeSprite),
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o1_returnTo),
- OPCODE(o1_loadSpriteContent),
- OPCODE(o1_copySprite),
- OPCODE(o1_fillRect),
- /* 34 */
- OPCODE(o1_drawLine),
- OPCODE(o1_strToLong),
- OPCODE(o1_invalidate),
- OPCODE(o1_setBackDelta),
- /* 38 */
- OPCODE(o1_playSound),
- OPCODE(o2_stopSound),
- OPCODE(o2_loadSound),
- OPCODE(o1_freeSoundSlot),
- /* 3C */
- OPCODE(o1_waitEndPlay),
- OPCODE(o1_playComposition),
- OPCODE(o2_getFreeMem),
- OPCODE(o2_checkData),
- /* 40 */
- {0, ""},
- OPCODE(o1_prepareStr),
- OPCODE(o1_insertStr),
- OPCODE(o1_cutStr),
- /* 44 */
- OPCODE(o1_strstr),
- OPCODE(o5_istrlen),
- OPCODE(o1_setMousePos),
- OPCODE(o1_setFrameRate),
- /* 48 */
- OPCODE(o1_animatePalette),
- OPCODE(o1_animateCursor),
- OPCODE(o1_blitCursor),
- OPCODE(o1_loadFont),
- /* 4C */
- OPCODE(o1_freeFont),
- OPCODE(o2_readData),
- OPCODE(o2_writeData),
- OPCODE(o1_manageDataFile),
- };
-
- static const OpcodeGoblinEntryV5 opcodesGoblin[71] = {
- /* 00 */
- OPCODE(o5_spaceShooter),
- OPCODE(o5_getSystemCDSpeed),
- OPCODE(o5_getSystemRAM),
- OPCODE(o5_getSystemCPUSpeed),
- /* 04 */
- OPCODE(o5_getSystemDrawSpeed),
- OPCODE(o5_totalSystemSpecs),
- OPCODE(o5_saveSystemSpecs),
- OPCODE(o5_loadSystemSpecs),
- /* 08 */
- OPCODE(o5_gob92),
- OPCODE(o5_gob95),
- OPCODE(o5_gob96),
- OPCODE(o5_gob97),
- /* 0C */
- OPCODE(o5_gob98),
- OPCODE(o5_gob100),
- OPCODE(o5_gob200),
- {0, ""},
- /* 10 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 14 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 18 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 20 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 24 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- };
-
- _opcodesDrawV5 = opcodesDraw;
- _opcodesFuncV5 = opcodesFunc;
- _opcodesGoblinV5 = opcodesGoblin;
-}
-
-void Inter_v5::executeDrawOpcode(byte i) {
- debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%X] (%s)",
- i, i, getOpcodeDrawDesc(i));
-
- OpcodeDrawProcV5 op = _opcodesDrawV5[i].proc;
+void Inter_v5::setupOpcodesDraw() {
+ Inter_v4::setupOpcodesDraw();
- if (op == 0)
- warning("unimplemented opcodeDraw: %d", i);
- else
- (this->*op) ();
+ OPCODEDRAW(0x61, o5_deleteFile);
+ OPCODEDRAW(0x80, o5_initScreen);
}
-bool Inter_v5::executeFuncOpcode(byte i, byte j, OpFuncParams &params) {
- debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%X.0x%X] (%s) - %s, %d, %d",
- i, j, i, j, getOpcodeFuncDesc(i, j), _vm->_game->_curTotFile,
- (uint) (_vm->_global->_inter_execPtr - _vm->_game->_totFileData),
- (uint) (_vm->_global->_inter_execPtr - _vm->_game->_totFileData - params.counter - 4));
-
- if ((i > 4) || (j > 15)) {
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- return false;
- }
+void Inter_v5::setupOpcodesFunc() {
+ Inter_v4::setupOpcodesFunc();
- OpcodeFuncProcV5 op = _opcodesFuncV5[i*16 + j].proc;
-
- if (op == 0)
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- else
- return (this->*op) (params);
-
- return false;
-}
-
-void Inter_v5::executeGoblinOpcode(int i, OpGobParams &params) {
- debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%X] (%s)",
- i, i, getOpcodeGoblinDesc(i));
-
- OpcodeGoblinProcV5 op = 0;
-
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i) {
- op = _opcodesGoblinV5[_goblinFuncLookUp[j][1]].proc;
- break;
- }
-
- _vm->_global->_inter_execPtr -= 2;
-
- if (op == 0) {
- warning("unimplemented opcodeGoblin: %d", i);
-
- int16 paramCount = load16();
- _vm->_global->_inter_execPtr += paramCount * 2;
- } else {
- params.extraData = i;
-
- (this->*op) (params);
- }
+ OPCODEFUNC(0x45, o5_istrlen);
}
-const char *Inter_v5::getOpcodeDrawDesc(byte i) {
- return _opcodesDrawV5[i].desc;
-}
-
-const char *Inter_v5::getOpcodeFuncDesc(byte i, byte j) {
- if ((i > 4) || (j > 15))
- return "";
-
- return _opcodesFuncV5[i*16 + j].desc;
-}
-
-const char *Inter_v5::getOpcodeGoblinDesc(int i) {
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i)
- return _opcodesGoblinV5[_goblinFuncLookUp[j][1]].desc;
- return "";
+void Inter_v5::setupOpcodesGob() {
+ OPCODEGOB( 0, o5_spaceShooter);
+ OPCODEGOB( 1, o5_spaceShooter);
+ OPCODEGOB( 2, o5_spaceShooter);
+ OPCODEGOB( 3, o5_spaceShooter);
+
+ OPCODEGOB( 33, o5_spaceShooter);
+
+ OPCODEGOB( 80, o5_getSystemCDSpeed);
+ OPCODEGOB( 81, o5_getSystemRAM);
+ OPCODEGOB( 82, o5_getSystemCPUSpeed);
+ OPCODEGOB( 83, o5_getSystemDrawSpeed);
+ OPCODEGOB( 84, o5_totalSystemSpecs);
+
+ OPCODEGOB( 85, o5_saveSystemSpecs);
+ OPCODEGOB( 86, o5_loadSystemSpecs);
+
+ OPCODEGOB( 87, o5_spaceShooter);
+ OPCODEGOB( 88, o5_spaceShooter);
+ OPCODEGOB( 89, o5_spaceShooter);
+ OPCODEGOB( 90, o5_spaceShooter);
+
+ OPCODEGOB( 91, o5_spaceShooter);
+ OPCODEGOB( 92, o5_gob92);
+ OPCODEGOB( 93, o5_spaceShooter);
+ OPCODEGOB( 94, o5_spaceShooter);
+
+ OPCODEGOB( 95, o5_gob95);
+ OPCODEGOB( 96, o5_gob96);
+ OPCODEGOB( 97, o5_gob97);
+ OPCODEGOB( 98, o5_gob98);
+
+ OPCODEGOB( 99, o5_spaceShooter);
+ OPCODEGOB(100, o5_gob100);
+ OPCODEGOB(200, o5_gob200);
}
void Inter_v5::o5_deleteFile() {
- evalExpr(0);
+ _vm->_game->_script->evalExpr(0);
- warning("Dynasty Stub: deleteFile \"%s\"", _vm->_global->_inter_resStr);
+ warning("Dynasty Stub: deleteFile \"%s\"", _vm->_game->_script->getResultStr());
}
void Inter_v5::o5_initScreen() {
@@ -683,13 +104,13 @@ void Inter_v5::o5_initScreen() {
int16 videoMode;
int16 width, height;
- offY = load16();
+ offY = _vm->_game->_script->readInt16();
videoMode = offY & 0xFF;
offY = (offY >> 8) & 0xFF;
- width = _vm->_parse->parseValExpr();
- height = _vm->_parse->parseValExpr();
+ width = _vm->_game->_script->readValExpr();
+ height = _vm->_game->_script->readValExpr();
warning("initScreen: %d, %d, %d, %d", width, height, offY, videoMode);
@@ -784,18 +205,18 @@ bool Inter_v5::o5_istrlen(OpFuncParams &params) {
int16 len;
uint16 type;
- if (*_vm->_global->_inter_execPtr == 0x80) {
- _vm->_global->_inter_execPtr++;
+ if (_vm->_game->_script->peekByte() == 0x80) {
+ _vm->_game->_script->skip(1);
- strVar1 = _vm->_parse->parseVarIndex();
- strVar2 = _vm->_parse->parseVarIndex(0, &type);
+ strVar1 = _vm->_game->_script->readVarIndex();
+ strVar2 = _vm->_game->_script->readVarIndex(0, &type);
len = _vm->_draw->stringLength(GET_VARO_STR(strVar1), READ_VARO_UINT16(strVar2));
} else {
- strVar1 = _vm->_parse->parseVarIndex();
- strVar2 = _vm->_parse->parseVarIndex(0, &type);
+ strVar1 = _vm->_game->_script->readVarIndex();
+ strVar2 = _vm->_game->_script->readVarIndex(0, &type);
if (_vm->_global->_language == 10) {
// Extra handling for Japanese strings
@@ -814,40 +235,36 @@ bool Inter_v5::o5_istrlen(OpFuncParams &params) {
}
void Inter_v5::o5_spaceShooter(OpGobParams &params) {
- int16 paramCount = load16();
-
warning("Dynasty Stub: Space shooter: %d, %d, %s",
- params.extraData, paramCount, _vm->_game->_curTotFile);
+ params.extraData, params.paramCount, _vm->_game->_curTotFile);
- if (paramCount < 4) {
+ if (params.paramCount < 4) {
warning("Space shooter variable counter < 4");
- _vm->_global->_inter_execPtr += paramCount * 2;
+ _vm->_game->_script->skip(params.paramCount * 2);
return;
}
- uint32 var1 = load16() * 4;
- uint32 var2 = load16() * 4;
+ uint32 var1 = _vm->_game->_script->readInt16() * 4;
+ uint32 var2 = _vm->_game->_script->readInt16() * 4;
- load16();
- load16();
+ _vm->_game->_script->readInt16();
+ _vm->_game->_script->readInt16();
if (params.extraData != 0) {
WRITE_VARO_UINT32(var1, 2);
WRITE_VARO_UINT32(var2, 0);
} else {
- if (paramCount < 5) {
+ if (params.paramCount < 5) {
warning("Space shooter variable counter < 5");
return;
}
- _vm->_global->_inter_execPtr += (paramCount - 4) * 2;
+ _vm->_game->_script->skip((params.paramCount - 4) * 2);
}
}
void Inter_v5::o5_getSystemCDSpeed(OpGobParams &params) {
- _vm->_global->_inter_execPtr += 2;
-
- WRITE_VAR_UINT32(load16(), 100); // Fudging 100%
+ WRITE_VAR_UINT32(_vm->_game->_script->readInt16(), 100); // Fudging 100%
Video::FontDesc *font;
if ((font = _vm->_util->loadFont("SPEED.LET"))) {
@@ -859,9 +276,7 @@ void Inter_v5::o5_getSystemCDSpeed(OpGobParams &params) {
}
void Inter_v5::o5_getSystemRAM(OpGobParams &params) {
- _vm->_global->_inter_execPtr += 2;
-
- WRITE_VAR_UINT32(load16(), 100); // Fudging 100%
+ WRITE_VAR_UINT32(_vm->_game->_script->readInt16(), 100); // Fudging 100%
Video::FontDesc *font;
if ((font = _vm->_util->loadFont("SPEED.LET"))) {
@@ -873,9 +288,7 @@ void Inter_v5::o5_getSystemRAM(OpGobParams &params) {
}
void Inter_v5::o5_getSystemCPUSpeed(OpGobParams &params) {
- _vm->_global->_inter_execPtr += 2;
-
- WRITE_VAR_UINT32(load16(), 100); // Fudging 100%
+ WRITE_VAR_UINT32(_vm->_game->_script->readInt16(), 100); // Fudging 100%
Video::FontDesc *font;
if ((font = _vm->_util->loadFont("SPEED.LET"))) {
@@ -887,9 +300,7 @@ void Inter_v5::o5_getSystemCPUSpeed(OpGobParams &params) {
}
void Inter_v5::o5_getSystemDrawSpeed(OpGobParams &params) {
- _vm->_global->_inter_execPtr += 2;
-
- WRITE_VAR_UINT32(load16(), 100); // Fudging 100%
+ WRITE_VAR_UINT32(_vm->_game->_script->readInt16(), 100); // Fudging 100%
Video::FontDesc *font;
if ((font = _vm->_util->loadFont("SPEED.LET"))) {
@@ -901,9 +312,7 @@ void Inter_v5::o5_getSystemDrawSpeed(OpGobParams &params) {
}
void Inter_v5::o5_totalSystemSpecs(OpGobParams &params) {
- _vm->_global->_inter_execPtr += 2;
-
- WRITE_VAR_UINT32(load16(), 100); // Fudging 100%
+ WRITE_VAR_UINT32(_vm->_game->_script->readInt16(), 100); // Fudging 100%
Video::FontDesc *font;
if ((font = _vm->_util->loadFont("SPEED.LET"))) {
@@ -917,8 +326,6 @@ void Inter_v5::o5_totalSystemSpecs(OpGobParams &params) {
void Inter_v5::o5_saveSystemSpecs(OpGobParams &params) {
warning("Dynasty Stub: Saving system specifications");
- _vm->_global->_inter_execPtr += 2;
-
/*
FILE *f = fopen("SAVE\\SPEED.INF", w);
fwrite(&_cdSpeed, sizeof(_cdSpeed), 1, f);
@@ -933,8 +340,6 @@ void Inter_v5::o5_saveSystemSpecs(OpGobParams &params) {
void Inter_v5::o5_loadSystemSpecs(OpGobParams &params) {
warning("Dynasty Stub: Loading system specifications");
- _vm->_global->_inter_execPtr += 2;
-
/*
FILE *f = fopen("SAVE\\SPEED.INF", r);
fread(&_cdSpeed, sizeof(_cdSpeed), 1, f);
@@ -971,32 +376,26 @@ void Inter_v5::o5_loadSystemSpecs(OpGobParams &params) {
void Inter_v5::o5_gob92(OpGobParams &params) {
warning("Dynasty Stub: GobFunc 92");
- _vm->_global->_inter_execPtr += 2;
-
- WRITE_VAR_UINT32(load16(), 0 /* (uint32) ((int32) ((int8) _gob92_1)) */);
+ WRITE_VAR_UINT32(_vm->_game->_script->readInt16(), 0 /* (uint32) ((int32) ((int8) _gob92_1)) */);
}
void Inter_v5::o5_gob95(OpGobParams &params) {
warning("Dynasty Stub: GobFunc 95");
- _vm->_global->_inter_execPtr += 2;
-
- WRITE_VAR_UINT32(load16(), 0 /* (uint32) ((int32) ((int16) speedThrottle4)) */);
- WRITE_VAR_UINT32(load16(), 0 /* (uint32) ((int32) ((int8) speedThrottle3)) */);
- WRITE_VAR_UINT32(load16(), 0 /* (uint32) ((int32) ((int8) speedThrottle2)) */);
- WRITE_VAR_UINT32(load16(), 0 /* (uint32) ((int32) ((int16) speedThrottle1)) */);
+ WRITE_VAR_UINT32(_vm->_game->_script->readInt16(), 0 /* (uint32) ((int32) ((int16) speedThrottle4)) */);
+ WRITE_VAR_UINT32(_vm->_game->_script->readInt16(), 0 /* (uint32) ((int32) ((int8) speedThrottle3)) */);
+ WRITE_VAR_UINT32(_vm->_game->_script->readInt16(), 0 /* (uint32) ((int32) ((int8) speedThrottle2)) */);
+ WRITE_VAR_UINT32(_vm->_game->_script->readInt16(), 0 /* (uint32) ((int32) ((int16) speedThrottle1)) */);
}
void Inter_v5::o5_gob96(OpGobParams &params) {
int16 speedThrottle4, speedThrottle1;
byte speedThrottle3, speedThrottle2;
- _vm->_global->_inter_execPtr += 2;
-
- speedThrottle4 = READ_VAR_UINT16(load16());
- speedThrottle3 = READ_VAR_UINT8(load16());
- speedThrottle2 = READ_VAR_UINT8(load16());
- speedThrottle1 = READ_VAR_UINT16(load16());
+ speedThrottle4 = READ_VAR_UINT16(_vm->_game->_script->readInt16());
+ speedThrottle3 = READ_VAR_UINT8(_vm->_game->_script->readInt16());
+ speedThrottle2 = READ_VAR_UINT8(_vm->_game->_script->readInt16());
+ speedThrottle1 = READ_VAR_UINT16(_vm->_game->_script->readInt16());
warning("Dynasty Stub: GobFunc 96: %d, %d, %d, %d",
speedThrottle4, speedThrottle3, speedThrottle2, speedThrottle1);
@@ -1006,23 +405,17 @@ void Inter_v5::o5_gob96(OpGobParams &params) {
void Inter_v5::o5_gob97(OpGobParams &params) {
_gob_97_98_val = 1;
-
- _vm->_global->_inter_execPtr += 2;
}
void Inter_v5::o5_gob98(OpGobParams &params) {
_gob_97_98_val = 0;
-
- _vm->_global->_inter_execPtr += 2;
}
void Inter_v5::o5_gob100(OpGobParams &params) {
- _vm->_global->_inter_execPtr += 2;
-
- uint16 var1 = READ_VAR_UINT16(load16());
- uint16 var2 = READ_VAR_UINT16(load16());
- uint16 var3 = READ_VAR_UINT16(load16());
- uint16 var4 = READ_VAR_UINT16(load16());
+ uint16 var1 = READ_VAR_UINT16(_vm->_game->_script->readInt16());
+ uint16 var2 = READ_VAR_UINT16(_vm->_game->_script->readInt16());
+ uint16 var3 = READ_VAR_UINT16(_vm->_game->_script->readInt16());
+ uint16 var4 = READ_VAR_UINT16(_vm->_game->_script->readInt16());
warning("Dynasty Stub: GobFunc 100: %d, %d, %d, %d", var1, var2, var3, var4);
@@ -1031,11 +424,9 @@ void Inter_v5::o5_gob100(OpGobParams &params) {
}
void Inter_v5::o5_gob200(OpGobParams &params) {
- _vm->_global->_inter_execPtr += 2;
-
- uint16 var1 = load16(); // index into the spritesArray
- uint16 var2 = load16();
- uint16 var3 = load16();
+ uint16 var1 = _vm->_game->_script->readUint16(); // index into the spritesArray
+ uint16 var2 = _vm->_game->_script->readUint16();
+ uint16 var3 = _vm->_game->_script->readUint16();
warning("Dynasty Stub: GobFunc 200: %d, %d, %d", var1, var2, var3);
}
diff --git a/engines/gob/inter_v6.cpp b/engines/gob/inter_v6.cpp
index f40314f87e..506de821d4 100644
--- a/engines/gob/inter_v6.cpp
+++ b/engines/gob/inter_v6.cpp
@@ -32,626 +32,43 @@
#include "gob/helper.h"
#include "gob/global.h"
#include "gob/game.h"
-#include "gob/parse.h"
+#include "gob/expression.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/draw.h"
#include "gob/sound/sound.h"
#include "gob/videoplayer.h"
namespace Gob {
-#define OPCODE(x) _OPCODE(Inter_v6, x)
-
-const int Inter_v6::_goblinFuncLookUp[][2] = {
- {0, 0},
-};
+#define OPCODEVER Inter_v6
+#define OPCODEDRAW(i, x) _opcodesDraw[i]._OPCODEDRAW(OPCODEVER, x)
+#define OPCODEFUNC(i, x) _opcodesFunc[i]._OPCODEFUNC(OPCODEVER, x)
+#define OPCODEGOB(i, x) _opcodesGob[i]._OPCODEGOB(OPCODEVER, x)
Inter_v6::Inter_v6(GobEngine *vm) : Inter_v5(vm) {
_gotFirstPalette = false;
-
- setupOpcodes();
-}
-
-void Inter_v6::setupOpcodes() {
- static const OpcodeDrawEntryV6 opcodesDraw[256] = {
- /* 00 */
- OPCODE(o1_loadMult),
- OPCODE(o2_playMult),
- OPCODE(o2_freeMultKeys),
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- OPCODE(o1_initCursor),
- /* 08 */
- OPCODE(o1_initCursorAnim),
- OPCODE(o1_clearCursorAnim),
- OPCODE(o2_setRenderFlags),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- OPCODE(o1_loadAnim),
- OPCODE(o1_freeAnim),
- OPCODE(o1_updateAnim),
- OPCODE(o2_multSub),
- /* 14 */
- OPCODE(o2_initMult),
- OPCODE(o1_freeMult),
- OPCODE(o1_animate),
- OPCODE(o2_loadMultObject),
- /* 18 */
- OPCODE(o1_getAnimLayerInfo),
- OPCODE(o1_getObjAnimSize),
- OPCODE(o1_loadStatic),
- OPCODE(o1_freeStatic),
- /* 1C */
- OPCODE(o2_renderStatic),
- OPCODE(o2_loadCurLayer),
- {0, ""},
- {0, ""},
- /* 20 */
- OPCODE(o2_playCDTrack),
- OPCODE(o2_waitCDTrackEnd),
- OPCODE(o2_stopCD),
- OPCODE(o2_readLIC),
- /* 24 */
- OPCODE(o2_freeLIC),
- OPCODE(o2_getCDTrackPos),
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o2_loadFontToSprite),
- OPCODE(o1_freeFontToSprite),
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- OPCODE(o6_totSub),
- OPCODE(o2_switchTotSub),
- OPCODE(o2_pushVars),
- OPCODE(o2_popVars),
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 48 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 4C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 50 */
- OPCODE(o2_loadMapObjects),
- OPCODE(o2_freeGoblins),
- OPCODE(o2_moveGoblin),
- OPCODE(o2_writeGoblinPos),
- /* 54 */
- OPCODE(o2_stopGoblin),
- OPCODE(o2_setGoblinState),
- OPCODE(o2_placeGoblin),
- {0, ""},
- /* 58 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 5C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 60 */
- {0, ""},
- OPCODE(o5_deleteFile),
- {0, ""},
- {0, ""},
- /* 64 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 68 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 6C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 70 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 74 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 78 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 7C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 80 */
- OPCODE(o5_initScreen),
- OPCODE(o2_scroll),
- OPCODE(o2_setScrollOffset),
- OPCODE(o6_playVmdOrMusic),
- /* 84 */
- OPCODE(o2_getImdInfo),
- OPCODE(o6_openItk),
- OPCODE(o2_closeItk),
- OPCODE(o2_setImdFrontSurf),
- /* 88 */
- OPCODE(o2_resetImdFrontSurf),
- {0, ""},
- {0, ""},
- {0, ""},
- /* 8C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 90 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 94 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 98 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 9C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* A8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* AC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* B8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* BC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* C8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* CC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* D8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* DC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* E8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* EC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F0 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F4 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* F8 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* FC */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""}
- };
-
- static const OpcodeFuncEntryV6 opcodesFunc[80] = {
- /* 00 */
- OPCODE(o1_callSub),
- OPCODE(o1_callSub),
- OPCODE(o1_printTotText),
- OPCODE(o6_loadCursor),
- /* 04 */
- {0, ""},
- OPCODE(o1_switch),
- OPCODE(o1_repeatUntil),
- OPCODE(o1_whileDo),
- /* 08 */
- OPCODE(o1_if),
- OPCODE(o6_assign),
- OPCODE(o1_loadSpriteToPos),
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- OPCODE(o2_printText),
- OPCODE(o1_loadTot),
- OPCODE(o6_palLoad),
- /* 14 */
- OPCODE(o1_keyFunc),
- OPCODE(o1_capturePush),
- OPCODE(o1_capturePop),
- OPCODE(o2_animPalInit),
- /* 18 */
- OPCODE(o2_addCollision),
- OPCODE(o6_freeCollision),
- OPCODE(o3_getTotTextItemPart),
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- OPCODE(o1_drawOperations),
- OPCODE(o1_setcmdCount),
- /* 20 */
- OPCODE(o1_return),
- OPCODE(o1_renewTimeInVars),
- OPCODE(o1_speakerOn),
- OPCODE(o1_speakerOff),
- /* 24 */
- OPCODE(o1_putPixel),
- OPCODE(o2_goblinFunc),
- OPCODE(o1_createSprite),
- OPCODE(o1_freeSprite),
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- OPCODE(o1_returnTo),
- OPCODE(o1_loadSpriteContent),
- OPCODE(o1_copySprite),
- OPCODE(o6_fillRect),
- /* 34 */
- OPCODE(o1_drawLine),
- OPCODE(o1_strToLong),
- OPCODE(o1_invalidate),
- OPCODE(o1_setBackDelta),
- /* 38 */
- OPCODE(o1_playSound),
- OPCODE(o2_stopSound),
- OPCODE(o2_loadSound),
- OPCODE(o1_freeSoundSlot),
- /* 3C */
- OPCODE(o1_waitEndPlay),
- OPCODE(o1_playComposition),
- OPCODE(o2_getFreeMem),
- OPCODE(o2_checkData),
- /* 40 */
- {0, ""},
- OPCODE(o1_prepareStr),
- OPCODE(o1_insertStr),
- OPCODE(o1_cutStr),
- /* 44 */
- OPCODE(o1_strstr),
- OPCODE(o5_istrlen),
- OPCODE(o1_setMousePos),
- OPCODE(o1_setFrameRate),
- /* 48 */
- OPCODE(o1_animatePalette),
- OPCODE(o1_animateCursor),
- OPCODE(o1_blitCursor),
- OPCODE(o1_loadFont),
- /* 4C */
- OPCODE(o1_freeFont),
- OPCODE(o2_readData),
- OPCODE(o2_writeData),
- OPCODE(o1_manageDataFile),
- };
-
- static const OpcodeGoblinEntryV6 opcodesGoblin[71] = {
- /* 00 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 04 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 08 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 0C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 10 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 14 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 18 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 1C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 20 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 24 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 28 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 2C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 30 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 34 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 38 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 3C */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 40 */
- {0, ""},
- {0, ""},
- {0, ""},
- {0, ""},
- /* 44 */
- {0, ""},
- {0, ""},
- {0, ""},
- };
-
- _opcodesDrawV6 = opcodesDraw;
- _opcodesFuncV6 = opcodesFunc;
- _opcodesGoblinV6 = opcodesGoblin;
-}
-
-void Inter_v6::executeDrawOpcode(byte i) {
- debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%X] (%s)",
- i, i, getOpcodeDrawDesc(i));
-
- OpcodeDrawProcV6 op = _opcodesDrawV6[i].proc;
-
- if (op == 0)
- warning("unimplemented opcodeDraw: %d", i);
- else
- (this->*op) ();
-}
-
-bool Inter_v6::executeFuncOpcode(byte i, byte j, OpFuncParams &params) {
- _vm->_video->_palLUT->buildNext();
-
- debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%X.0x%X] (%s) - %s, %d, %d",
- i, j, i, j, getOpcodeFuncDesc(i, j), _vm->_game->_curTotFile,
- (uint) (_vm->_global->_inter_execPtr - _vm->_game->_totFileData),
- (uint) (_vm->_global->_inter_execPtr - _vm->_game->_totFileData - params.counter - 4));
-
- if ((i > 4) || (j > 15)) {
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- return false;
- }
-
- OpcodeFuncProcV6 op = _opcodesFuncV6[i*16 + j].proc;
-
- if (op == 0)
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- else
- return (this->*op) (params);
-
- return false;
}
-void Inter_v6::executeGoblinOpcode(int i, OpGobParams &params) {
- debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%X] (%s)",
- i, i, getOpcodeGoblinDesc(i));
-
- OpcodeGoblinProcV6 op = 0;
-
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i) {
- op = _opcodesGoblinV6[_goblinFuncLookUp[j][1]].proc;
- break;
- }
-
- _vm->_global->_inter_execPtr -= 2;
-
- if (op == 0) {
- warning("unimplemented opcodeGoblin: %d", i);
-
- int16 paramCount = load16();
- _vm->_global->_inter_execPtr += paramCount * 2;
- } else {
- params.extraData = i;
+void Inter_v6::setupOpcodesDraw() {
+ Inter_v5::setupOpcodesDraw();
- (this->*op) (params);
- }
-}
-
-const char *Inter_v6::getOpcodeDrawDesc(byte i) {
- return _opcodesDrawV6[i].desc;
+ OPCODEDRAW(0x40, o6_totSub);
+ OPCODEDRAW(0x83, o6_playVmdOrMusic);
+ OPCODEDRAW(0x85, o6_openItk);
}
-const char *Inter_v6::getOpcodeFuncDesc(byte i, byte j) {
- if ((i > 4) || (j > 15))
- return "";
+void Inter_v6::setupOpcodesFunc() {
+ Inter_v5::setupOpcodesFunc();
- return _opcodesFuncV6[i*16 + j].desc;
+ OPCODEFUNC(0x03, o6_loadCursor);
+ OPCODEFUNC(0x09, o6_assign);
+ OPCODEFUNC(0x13, o6_palLoad);
+ OPCODEFUNC(0x19, o6_freeCollision);
+ OPCODEFUNC(0x33, o6_fillRect);
}
-const char *Inter_v6::getOpcodeGoblinDesc(int i) {
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i)
- return _opcodesGoblinV6[_goblinFuncLookUp[j][1]].desc;
- return "";
+void Inter_v6::setupOpcodesGob() {
}
void Inter_v6::o6_totSub() {
@@ -660,20 +77,20 @@ void Inter_v6::o6_totSub() {
int flags;
int i;
- length = *_vm->_global->_inter_execPtr++;
+ length = _vm->_game->_script->readByte();
if ((length & 0x7F) > 13)
error("Length in o2_totSub is greater than 13 (%d)", length);
if (length & 0x80) {
- evalExpr(0);
- strcpy(totFile, _vm->_global->_inter_resStr);
+ _vm->_game->_script->evalExpr(0);
+ strcpy(totFile, _vm->_game->_script->getResultStr());
} else {
for (i = 0; i < length; i++)
- totFile[i] = (char) *_vm->_global->_inter_execPtr++;
+ totFile[i] = _vm->_game->_script->readChar();
totFile[i] = 0;
}
- flags = *_vm->_global->_inter_execPtr++;
+ flags = _vm->_game->_script->readByte();
if (flags & 0x40)
warning("Urban Stub: o6_totSub(), flags & 0x40");
@@ -693,17 +110,17 @@ void Inter_v6::o6_playVmdOrMusic() {
uint16 palCmd;
bool close;
- evalExpr(0);
- strncpy0(fileName, _vm->_global->_inter_resStr, 127);
-
- x = _vm->_parse->parseValExpr();
- y = _vm->_parse->parseValExpr();
- startFrame = _vm->_parse->parseValExpr();
- lastFrame = _vm->_parse->parseValExpr();
- breakKey = _vm->_parse->parseValExpr();
- flags = _vm->_parse->parseValExpr();
- palStart = _vm->_parse->parseValExpr();
- palEnd = _vm->_parse->parseValExpr();
+ _vm->_game->_script->evalExpr(0);
+ strncpy0(fileName, _vm->_game->_script->getResultStr(), 127);
+
+ x = _vm->_game->_script->readValExpr();
+ y = _vm->_game->_script->readValExpr();
+ startFrame = _vm->_game->_script->readValExpr();
+ lastFrame = _vm->_game->_script->readValExpr();
+ breakKey = _vm->_game->_script->readValExpr();
+ flags = _vm->_game->_script->readValExpr();
+ palStart = _vm->_game->_script->readValExpr();
+ palEnd = _vm->_game->_script->readValExpr();
palCmd = 1 << (flags & 0x3F);
debugC(1, kDebugVideo, "Playing video \"%s\" @ %d+%d, frames %d - %d, "
@@ -759,8 +176,8 @@ void Inter_v6::o6_playVmdOrMusic() {
void Inter_v6::o6_openItk() {
char fileName[32];
- evalExpr(0);
- strncpy0(fileName, _vm->_global->_inter_resStr, 27);
+ _vm->_game->_script->evalExpr(0);
+ strncpy0(fileName, _vm->_game->_script->getResultStr(), 27);
if (!strchr(fileName, '.'))
strcat(fileName, ".ITK");
@@ -778,21 +195,21 @@ void Inter_v6::o6_openItk() {
}
bool Inter_v6::o6_loadCursor(OpFuncParams &params) {
- int16 id = load16();
+ int16 id = _vm->_game->_script->readInt16();
if ((id == -1) || (id == -2)) {
char file[10];
if (id == -1) {
for (int i = 0; i < 9; i++)
- file[i] = *_vm->_global->_inter_execPtr++;
+ file[i] = _vm->_game->_script->readChar();
} else
- strncpy(file, GET_VAR_STR(load16()), 10);
+ strncpy(file, GET_VAR_STR(_vm->_game->_script->readInt16()), 10);
file[9] = '\0';
- uint16 start = load16();
- int8 index = (int8) *_vm->_global->_inter_execPtr++;
+ uint16 start = _vm->_game->_script->readUint16();
+ int8 index = _vm->_game->_script->readInt8();
int vmdSlot = _vm->_vidPlayer->slotOpen(file);
@@ -820,101 +237,102 @@ bool Inter_v6::o6_loadCursor(OpFuncParams &params) {
return false;
}
- int8 index = (int8) *_vm->_global->_inter_execPtr++;
+ int8 index = _vm->_game->_script->readInt8();
if ((index * _vm->_draw->_cursorWidth) >= _vm->_draw->_cursorSprites->getWidth())
return false;
- int16 width, height;
- byte *dataBuf = _vm->_game->loadTotResource(id, 0, &width, &height);
+ Resource *resource = _vm->_game->_resources->getResource((uint16) id);
+ if (!resource)
+ return false;
_vm->_video->fillRect(*_vm->_draw->_cursorSprites,
index * _vm->_draw->_cursorWidth, 0,
index * _vm->_draw->_cursorWidth + _vm->_draw->_cursorWidth - 1,
_vm->_draw->_cursorHeight - 1, 0);
- _vm->_video->drawPackedSprite(dataBuf, width, height,
+ _vm->_video->drawPackedSprite(resource->getData(),
+ resource->getWidth(), resource->getHeight(),
index * _vm->_draw->_cursorWidth, 0, 0, *_vm->_draw->_cursorSprites);
_vm->_draw->_cursorAnimLow[index] = 0;
+ delete resource;
return false;
}
bool Inter_v6::o6_assign(OpFuncParams &params) {
- byte *savedPos;
- int16 varOff;
- int16 token;
- int16 result;
- byte loopCount;
- uint16 var_6, var_A;
+ uint16 size, destType;
+ int16 dest = _vm->_game->_script->readVarIndex(&size, &destType);
- varOff = _vm->_parse->parseVarIndex(&var_6, &var_A);
+ if (size != 0) {
+ int16 src;
- if (var_6 != 0) {
- int16 var_4;
+ _vm->_game->_script->push();
- savedPos = _vm->_global->_inter_execPtr;
+ src = _vm->_game->_script->readVarIndex(&size, 0);
- var_4 = _vm->_parse->parseVarIndex(&var_6, 0);
+ memcpy(_vm->_inter->_variables->getAddressOff8(dest),
+ _vm->_inter->_variables->getAddressOff8(src), size * 4);
- memcpy(_vm->_inter->_variables->getAddressOff8(varOff),
- _vm->_inter->_variables->getAddressOff8(var_4), var_6 * 4);
+ _vm->_game->_script->pop();
- _vm->_global->_inter_execPtr = savedPos;
- evalExpr(&var_4);
+ _vm->_game->_script->evalExpr(&src);
return false;
}
- if (*_vm->_global->_inter_execPtr == 98) {
- _vm->_global->_inter_execPtr++;
- loopCount = *_vm->_global->_inter_execPtr++;
+ byte loopCount;
+ if (_vm->_game->_script->peekByte() == 98) {
+ _vm->_game->_script->skip(1);
+ loopCount = _vm->_game->_script->readByte();
for (int i = 0; i < loopCount; i++) {
- uint8 c = *_vm->_global->_inter_execPtr++;
- uint16 n = load16();
+ uint8 c = _vm->_game->_script->readByte();
+ uint16 n = _vm->_game->_script->readUint16();
- memset(_vm->_inter->_variables->getAddressOff8(varOff), c, n);
+ memset(_vm->_inter->_variables->getAddressOff8(dest), c, n);
- varOff += n;
+ dest += n;
}
return false;
- } else if (*_vm->_global->_inter_execPtr == 99) {
- _vm->_global->_inter_execPtr++;
- loopCount = *_vm->_global->_inter_execPtr++;
+ } else if (_vm->_game->_script->peekByte() == 99) {
+ _vm->_game->_script->skip(1);
+ loopCount = _vm->_game->_script->readByte();
} else
loopCount = 1;
for (int i = 0; i < loopCount; i++) {
- token = evalExpr(&result);
- switch (var_A) {
- case 16:
- case 18:
- WRITE_VARO_UINT8(varOff + i, _vm->_global->_inter_resVal);
+ int16 result;
+ int16 srcType = _vm->_game->_script->evalExpr(&result);
+
+ switch (destType) {
+ case TYPE_VAR_INT8:
+ case TYPE_ARRAY_INT8:
+ WRITE_VARO_UINT8(dest + i, _vm->_game->_script->getResultInt());
break;
- case 17:
- case 27:
- WRITE_VARO_UINT16(varOff + i * 2, _vm->_global->_inter_resVal);
+ case TYPE_VAR_INT16:
+ case TYPE_ARRAY_INT16:
+ WRITE_VARO_UINT16(dest + i * 2, _vm->_game->_script->getResultInt());
break;
- case 23:
- case 26:
- WRITE_VAR_OFFSET(varOff + i * 4, _vm->_global->_inter_resVal);
+ case TYPE_VAR_INT32:
+ case TYPE_ARRAY_INT32:
+ WRITE_VAR_OFFSET(dest + i * 4, _vm->_game->_script->getResultInt());
break;
- case 24:
- WRITE_VARO_UINT16(varOff + i * 4, _vm->_global->_inter_resVal);
+ case TYPE_VAR_INT32_AS_INT16:
+ WRITE_VARO_UINT16(dest + i * 4, _vm->_game->_script->getResultInt());
break;
- case 25:
- case 28:
- if (token == 20)
- WRITE_VARO_UINT8(varOff, result);
+ case TYPE_VAR_STR:
+ case TYPE_ARRAY_STR:
+ if (srcType == TYPE_IMM_INT16)
+ WRITE_VARO_UINT8(dest, result);
else
- WRITE_VARO_STR(varOff, _vm->_global->_inter_resStr);
+ WRITE_VARO_STR(dest, _vm->_game->_script->getResultStr());
break;
}
}
@@ -936,7 +354,7 @@ bool Inter_v6::o6_palLoad(OpFuncParams &params) {
bool Inter_v6::o6_freeCollision(OpFuncParams &params) {
int16 id;
- id = _vm->_parse->parseValExpr();
+ id = _vm->_game->_script->readValExpr();
switch (id + 5) {
case 0:
@@ -972,17 +390,17 @@ bool Inter_v6::o6_freeCollision(OpFuncParams &params) {
bool Inter_v6::o6_fillRect(OpFuncParams &params) {
int16 destSurf;
- _vm->_draw->_destSurface = destSurf = load16();
+ _vm->_draw->_destSurface = destSurf = _vm->_game->_script->readInt16();
- _vm->_draw->_destSpriteX = _vm->_parse->parseValExpr();
- _vm->_draw->_destSpriteY = _vm->_parse->parseValExpr();
- _vm->_draw->_spriteRight = _vm->_parse->parseValExpr();
- _vm->_draw->_spriteBottom = _vm->_parse->parseValExpr();
+ _vm->_draw->_destSpriteX = _vm->_game->_script->readValExpr();
+ _vm->_draw->_destSpriteY = _vm->_game->_script->readValExpr();
+ _vm->_draw->_spriteRight = _vm->_game->_script->readValExpr();
+ _vm->_draw->_spriteBottom = _vm->_game->_script->readValExpr();
- evalExpr(0);
+ _vm->_game->_script->evalExpr(0);
- _vm->_draw->_backColor = _vm->_global->_inter_resVal & 0xFFFF;
- uint16 extraVar = _vm->_global->_inter_resVal >> 16;
+ _vm->_draw->_backColor = _vm->_game->_script->getResultInt() & 0xFFFF;
+ uint16 extraVar = _vm->_game->_script->getResultInt() >> 16;
if (extraVar != 0)
warning("Urban Stub: o6_fillRect(), extraVar = %d", extraVar);
@@ -1019,11 +437,8 @@ void Inter_v6::probe16bitMusic(char *fileName) {
fileName[len - 1] = 'V';
- int16 handle;
- if ((handle = _vm->_dataIO->openData(fileName)) >= 0) {
- _vm->_dataIO->closeData(handle);
+ if (_vm->_dataIO->existData(fileName))
return;
- }
fileName[len - 1] = '8';
}
diff --git a/engines/gob/map_v1.cpp b/engines/gob/map_v1.cpp
index 2c94b3fb24..dacc72d6c7 100644
--- a/engines/gob/map_v1.cpp
+++ b/engines/gob/map_v1.cpp
@@ -64,7 +64,6 @@ void Map_v1::init(void) {
void Map_v1::loadMapObjects(const char *avjFile) {
char avoName[128];
byte *dataBuf;
- int16 handle;
int16 tmp;
int32 flag;
int16 gobDataCount;
@@ -75,15 +74,14 @@ void Map_v1::loadMapObjects(const char *avjFile) {
strcpy(avoName, _sourceFile);
strcat(avoName, ".avo");
- handle = _vm->_dataIO->openData(avoName);
- if (handle >= 0) {
+ if (_vm->_dataIO->existData(avoName)) {
_loadFromAvo = true;
- _vm->_dataIO->closeData(handle);
dataBuf = _vm->_dataIO->getData(avoName);
} else {
_loadFromAvo = false;
dataBuf = _vm->_dataIO->getData(avjFile);
}
+
Common::MemoryReadStream mapData(dataBuf, 4294967295U);
init();
@@ -146,7 +144,6 @@ void Map_v1::loadMapObjects(const char *avjFile) {
void Map_v1::loadSounds(Common::SeekableReadStream &data) {
int16 count;
- int16 handle;
char buf[19];
char sndNames[20][14];
@@ -162,11 +159,9 @@ void Map_v1::loadSounds(Common::SeekableReadStream &data) {
_vm->_sound->sampleLoad(&_vm->_goblin->_soundData[14], SOUND_SND, "diamant1.snd");
for (int i = 0; i < count; i++) {
- handle = _vm->_dataIO->openData(sndNames[i]);
- if (handle < 0)
+ if (!_vm->_dataIO->existData(sndNames[i]))
continue;
- _vm->_dataIO->closeData(handle);
_vm->_sound->sampleLoad(&_vm->_goblin->_soundData[i], SOUND_SND, sndNames[i]);
}
}
diff --git a/engines/gob/map_v2.cpp b/engines/gob/map_v2.cpp
index db4f2075e1..6ceda7ab44 100644
--- a/engines/gob/map_v2.cpp
+++ b/engines/gob/map_v2.cpp
@@ -31,7 +31,8 @@
#include "gob/goblin.h"
#include "gob/inter.h"
#include "gob/game.h"
-#include "gob/parse.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/mult.h"
namespace Gob {
@@ -51,22 +52,24 @@ void Map_v2::loadMapObjects(const char *avjFile) {
int16 mapWidth, mapHeight;
int16 tmp;
byte *variables;
- byte *extData;
uint32 tmpPos;
uint32 passPos;
- var = _vm->_parse->parseVarIndex();
+ var = _vm->_game->_script->readVarIndex();
variables = _vm->_inter->_variables->getAddressOff8(var);
- id = _vm->_inter->load16();
+ id = _vm->_game->_script->readInt16();
if (id == -1) {
_passMap = (int8 *) _vm->_inter->_variables->getAddressOff8(var);
return;
}
- extData = _vm->_game->loadExtData(id, 0, 0);
- Common::MemoryReadStream mapData(extData, 4294967295U);
+ Resource *resource = _vm->_game->_resources->getResource(id);
+ if (!resource)
+ return;
+
+ Common::SeekableReadStream &mapData = *resource->stream();
if (mapData.readByte() == 3) {
_screenWidth = 640;
@@ -88,7 +91,7 @@ void Map_v2::loadMapObjects(const char *avjFile) {
passPos = mapData.pos();
mapData.skip(_mapWidth * _mapHeight);
- if (*extData == 1)
+ if (resource->getData()[0] == 1)
wayPointsCount = _wayPointsCount = 40;
else
wayPointsCount = _wayPointsCount == 0 ? 1 : _wayPointsCount;
@@ -130,11 +133,11 @@ void Map_v2::loadMapObjects(const char *avjFile) {
for (int i = 0; i < _vm->_goblin->_gobsCount; i++)
loadGoblinStates(mapData, i);
- _vm->_goblin->_soundSlotsCount = _vm->_inter->load16();
+ _vm->_goblin->_soundSlotsCount = _vm->_game->_script->readInt16();
for (int i = 0; i < _vm->_goblin->_soundSlotsCount; i++)
_vm->_goblin->_soundSlots[i] = _vm->_inter->loadSound(1);
- delete[] extData;
+ delete resource;
}
void Map_v2::loadGoblinStates(Common::SeekableReadStream &data, int index) {
diff --git a/engines/gob/map_v4.cpp b/engines/gob/map_v4.cpp
index 858e7972bc..1db3d6a3f8 100644
--- a/engines/gob/map_v4.cpp
+++ b/engines/gob/map_v4.cpp
@@ -31,7 +31,8 @@
#include "gob/goblin.h"
#include "gob/inter.h"
#include "gob/game.h"
-#include "gob/parse.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/mult.h"
namespace Gob {
@@ -49,14 +50,13 @@ void Map_v4::loadMapObjects(const char *avjFile) {
int16 mapWidth, mapHeight;
int16 tmp;
byte *variables;
- byte *extData;
uint32 tmpPos;
uint32 passPos;
- var = _vm->_parse->parseVarIndex();
+ var = _vm->_game->_script->readVarIndex();
variables = _vm->_inter->_variables->getAddressOff8(var);
- id = _vm->_inter->load16();
+ id = _vm->_game->_script->readInt16();
if (((uint16) id) >= 65520) {
warning("Woodruff Stub: loadMapObjects ID >= 65520");
@@ -66,8 +66,11 @@ void Map_v4::loadMapObjects(const char *avjFile) {
return;
}
- extData = _vm->_game->loadExtData(id, 0, 0);
- Common::MemoryReadStream mapData(extData, 4294967295U);
+ Resource *resource = _vm->_game->_resources->getResource(id);
+ if (!resource)
+ return;
+
+ Common::SeekableReadStream &mapData = *resource->stream();
_widthByte = mapData.readByte();
if (_widthByte == 4) {
@@ -99,7 +102,7 @@ void Map_v4::loadMapObjects(const char *avjFile) {
passPos = mapData.pos();
mapData.skip(_mapWidth * _mapHeight);
- if (*extData == 1)
+ if (resource->getData()[0] == 1)
wayPointsCount = _wayPointsCount = 40;
else
wayPointsCount = _wayPointsCount == 0 ? 1 : _wayPointsCount;
@@ -146,11 +149,11 @@ void Map_v4::loadMapObjects(const char *avjFile) {
for (int i = 0; i < _vm->_goblin->_gobsCount; i++)
loadGoblinStates(mapData, i);
- _vm->_goblin->_soundSlotsCount = _vm->_inter->load16();
+ _vm->_goblin->_soundSlotsCount = _vm->_game->_script->readInt16();
for (int i = 0; i < _vm->_goblin->_soundSlotsCount; i++)
_vm->_goblin->_soundSlots[i] = _vm->_inter->loadSound(1);
- delete[] extData;
+ delete resource;
}
} // End of namespace Gob
diff --git a/engines/gob/module.mk b/engines/gob/module.mk
index 22a5cd37b9..695976da61 100644
--- a/engines/gob/module.mk
+++ b/engines/gob/module.mk
@@ -9,6 +9,7 @@ MODULE_OBJS := \
draw_bargon.o \
draw_fascin.o \
driver_vga.o \
+ expression.o \
game.o \
game_v1.o \
game_v2.o \
@@ -43,10 +44,12 @@ MODULE_OBJS := \
mult_v1.o \
mult_v2.o \
palanim.o \
- parse.o \
+ resources.o \
scenery.o \
scenery_v1.o \
scenery_v2.o \
+ script.o \
+ totfile.o \
util.o \
variables.o \
video.o \
diff --git a/engines/gob/mult.cpp b/engines/gob/mult.cpp
index 1670c26ea5..5aec5ff76e 100644
--- a/engines/gob/mult.cpp
+++ b/engines/gob/mult.cpp
@@ -31,6 +31,7 @@
#include "gob/util.h"
#include "gob/draw.h"
#include "gob/game.h"
+#include "gob/script.h"
#include "gob/palanim.h"
#include "gob/scenery.h"
#include "gob/video.h"
@@ -251,8 +252,6 @@ void Mult::playMult(int16 startFrame, int16 endFrame, char checkEscape,
}
void Mult::drawText(bool &stop, bool &stopNoClear) {
- byte *savedIP;
-
int16 cmd;
for (_index = 0; _index < _multData->textKeysCount; _index++) {
if (_multData->textKeys[_index].frame != _frame)
@@ -265,9 +264,10 @@ void Mult::drawText(bool &stop, bool &stopNoClear) {
stopNoClear = true;
_multData->frameStart = 0;
} else if (cmd == 3) {
+ warning("Mult::drawText, cmd == 3");
stop = false;
- savedIP = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr = _multData->textKeys[_index].script;
+// uint32 startPos = _vm->_game->_script->pos();
+// _vm->_global->_inter_execPtr = _multData->textKeys[_index].script;
}
}
}
diff --git a/engines/gob/mult_v1.cpp b/engines/gob/mult_v1.cpp
index e2c16674c9..1bb162c789 100644
--- a/engines/gob/mult_v1.cpp
+++ b/engines/gob/mult_v1.cpp
@@ -1,4 +1,4 @@
-/* ScummVM - Graphic Adventure Engine
+/* ScummVM - Graphic Adventure Engine
*
* ScummVM is the legal property of its developers, whose names
* are too numerous to list here. Please refer to the COPYRIGHT
@@ -32,6 +32,8 @@
#include "gob/util.h"
#include "gob/draw.h"
#include "gob/game.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/inter.h"
#include "gob/scenery.h"
@@ -41,9 +43,6 @@ Mult_v1::Mult_v1(GobEngine *vm) : Mult(vm) {
}
void Mult_v1::loadMult(int16 resId) {
- uint32 dataSize;
- byte *extData;
-
debugC(4, kDebugGameFlow, "Loading mult");
_multData = new Mult_Data;
@@ -52,8 +51,11 @@ void Mult_v1::loadMult(int16 resId) {
_multData->sndSlotsCount = 0;
_multData->frameStart = 0;
- extData = (byte *) _vm->_game->loadExtData(resId, 0, 0, &dataSize);
- Common::MemoryReadStream data(extData, dataSize);
+ Resource *resource = _vm->_game->_resources->getResource(resId);
+ if (!resource)
+ return;
+
+ Common::SeekableReadStream &data = *resource->stream();
_multData->staticCount = data.readSByte() + 1;
_multData->animCount = data.readSByte() + 1;
@@ -157,15 +159,14 @@ void Mult_v1::loadMult(int16 resId) {
switch (_multData->sndKeys[i].cmd) {
case 1:
case 4:
- _multData->sndKeys[i].resId =
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _multData->sndKeys[i].resId = _vm->_game->_script->peekUint16();
for (j = 0; j < i; j++) {
if (_multData->sndKeys[i].resId ==
_multData->sndKeys[j].resId) {
_multData->sndKeys[i].soundIndex =
_multData->sndKeys[j].soundIndex;
- _vm->_global->_inter_execPtr += 2;
+ _vm->_game->_script->skip(2);
break;
}
}
@@ -178,16 +179,16 @@ void Mult_v1::loadMult(int16 resId) {
break;
case 3:
- _vm->_global->_inter_execPtr += 6;
+ _vm->_game->_script->skip(6);
break;
case 5:
- _vm->_global->_inter_execPtr += _multData->sndKeys[i].freq * 2;
+ _vm->_game->_script->skip(_multData->sndKeys[i].freq * 2);
break;
}
}
- delete[] extData;
+ delete resource;
}
void Mult_v1::freeMultKeys() {
diff --git a/engines/gob/mult_v2.cpp b/engines/gob/mult_v2.cpp
index d9b5be0847..135c50c92c 100644
--- a/engines/gob/mult_v2.cpp
+++ b/engines/gob/mult_v2.cpp
@@ -32,9 +32,10 @@
#include "gob/util.h"
#include "gob/draw.h"
#include "gob/game.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/goblin.h"
#include "gob/inter.h"
-#include "gob/parse.h"
#include "gob/scenery.h"
#include "gob/video.h"
#include "gob/videoplayer.h"
@@ -60,11 +61,9 @@ void Mult_v2::loadMult(int16 resId) {
int8 index;
uint8 staticCount;
uint8 animCount;
- uint32 dataSize;
- byte *extData;
bool hasImds;
- index = (resId & 0x8000) ? *_vm->_global->_inter_execPtr++ : 0;
+ index = (resId & 0x8000) ? _vm->_game->_script->readByte() : 0;
resId &= 0x7FFF;
debugC(4, kDebugGameFlow, "Loading mult %d", index);
@@ -80,8 +79,11 @@ void Mult_v2::loadMult(int16 resId) {
_multData->sndSlotsCount = 0;
_multData->frameStart = 0;
- extData = (byte *) _vm->_game->loadExtData(resId, 0, 0, &dataSize);
- Common::MemoryReadStream data(extData, dataSize);
+ Resource *resource = _vm->_game->_resources->getResource(resId);
+ if (!resource)
+ return;
+
+ Common::SeekableReadStream &data = *resource->stream();
_multData->staticCount = staticCount = data.readSByte();
_multData->animCount = animCount = data.readSByte();
@@ -206,14 +208,13 @@ void Mult_v2::loadMult(int16 resId) {
switch (_multData->sndKeys[i].cmd) {
case 1:
case 4:
- _multData->sndKeys[i].resId =
- READ_LE_UINT16(_vm->_global->_inter_execPtr);
+ _multData->sndKeys[i].resId = _vm->_game->_script->peekUint16();
for (j = 0; j < i; j++) {
if (_multData->sndKeys[j].resId ==
_multData->sndKeys[i].resId) {
_multData->sndKeys[i].soundIndex =
_multData->sndKeys[j].soundIndex;
- _vm->_global->_inter_execPtr += 2;
+ _vm->_game->_script->skip(2);
break;
}
}
@@ -226,7 +227,7 @@ void Mult_v2::loadMult(int16 resId) {
}
break;
case 3:
- _vm->_global->_inter_execPtr += 4;
+ _vm->_game->_script->skip(4);
break;
case -1:
@@ -244,17 +245,17 @@ void Mult_v2::loadMult(int16 resId) {
if (hasImds)
loadImds(data);
- delete[] extData;
+ delete resource;
}
void Mult_v2::loadImds(Common::SeekableReadStream &data) {
int16 size;
- size = _vm->_inter->load16();
- _multData->execPtr = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += size * 2;
+ size = _vm->_game->_script->readInt16();
+ _multData->execPtr = _vm->_game->_script->getData() + _vm->_game->_script->pos();
+ _vm->_game->_script->skip(size * 2);
- if (_vm->_game->_totFileData[0x29] < 51)
+ if (_vm->_game->_script->getVersionMinor() < 3)
return;
size = data.readSint16LE();
@@ -263,13 +264,27 @@ void Mult_v2::loadImds(Common::SeekableReadStream &data) {
data.read(_multData->somepointer10, size * 20);
}
- size = _vm->_inter->load16();
+ size = _vm->_game->_script->readInt16();
if (size <= 0)
return;
_multData->imdFiles = new char[size * 14];
- memcpy(_multData->imdFiles, _vm->_global->_inter_execPtr, size * 14);
- _vm->_global->_inter_execPtr += size * 14;
+ memcpy(_multData->imdFiles,
+ _vm->_game->_script->getData() + _vm->_game->_script->pos(), size * 14);
+
+ // WORKAROUND: The Windows version of Lost in Time has VMD not IMD files,
+ // but they are still referenced as IMD.
+ if ((_vm->getGameType() == kGameTypeLostInTime) &&
+ (_vm->getPlatform() == Common::kPlatformWindows)) {
+
+ for (int i = 0; i < size; i++) {
+ char *dot = strrchr(_multData->imdFiles + (i * 14), '.');
+ if (dot)
+ *dot = '\0';
+ }
+ }
+
+ _vm->_game->_script->skip(size * 14);
data.seek(2, SEEK_CUR);
for (int i = 0; i < 4; i++) {
_multData->imdKeysCount[i] = data.readSint16LE();
@@ -382,14 +397,16 @@ void Mult_v2::multSub(uint16 multIndex) {
if (multIndex > 7)
error("Multindex out of range");
+ _vm->_util->notifyNewAnim();
+
debugC(4, kDebugGameFlow, "Sub mult %d", multIndex);
_multData = _multDatas[multIndex];
if (!_multData) {
- _vm->_parse->parseValExpr();
- _vm->_parse->parseValExpr();
- _vm->_parse->parseValExpr();
- _vm->_parse->parseValExpr();
+ _vm->_game->_script->readValExpr();
+ _vm->_game->_script->readValExpr();
+ _vm->_game->_script->readValExpr();
+ _vm->_game->_script->readValExpr();
return;
}
@@ -412,9 +429,9 @@ void Mult_v2::multSub(uint16 multIndex) {
_multData->animObjs[index][0] = flags;
for (int i = 1; i < 4; i++)
- _multData->animObjs[index][i] = _vm->_parse->parseValExpr();
+ _multData->animObjs[index][i] = _vm->_game->_script->readValExpr();
- expr = _vm->_parse->parseValExpr();
+ expr = _vm->_game->_script->readValExpr();
_multData->animKeysFrames[index] = expr;
_multData->animKeysStartFrames[index] = expr;
@@ -856,7 +873,7 @@ void Mult_v2::animate() {
animObj.newBottom =
MAX(animObj.lastBottom, _vm->_scenery->_toRedrawBottom);
- if ((_vm->_game->_totFileData[0x29] > 50) &&
+ if ((_vm->_game->_script->getVersionMinor() > 2) &&
(animObj.newLeft == animObj.lastLeft) &&
(animObj.newTop == animObj.lastTop) &&
(animObj.newRight == animObj.lastRight) &&
diff --git a/engines/gob/parse.cpp b/engines/gob/parse.cpp
deleted file mode 100644
index 0fa46097a3..0000000000
--- a/engines/gob/parse.cpp
+++ /dev/null
@@ -1,1499 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
-
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
-
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- * $URL$
- * $Id$
- *
- */
-
-#include "common/endian.h"
-
-#include "gob/gob.h"
-#include "gob/parse.h"
-#include "gob/global.h"
-#include "gob/game.h"
-#include "gob/inter.h"
-
-namespace Gob {
-
-Parse::Parse(GobEngine *vm) : _vm(vm) {
-}
-
-int32 Parse::encodePtr(byte *ptr, int type) {
- int32 offset = 0;
-
- switch (type) {
- case kExecPtr:
- offset = ptr - _vm->_game->_totFileData;
- break;
- case kInterVar:
- offset = ptr - ((byte *) _vm->_inter->_variables->getAddressOff8(0));
- break;
- case kResStr:
- offset = ptr - ((byte *) _vm->_global->_inter_resStr);
- break;
- default:
- error("Parse::encodePtr(): Unknown pointer type");
- }
- assert((offset & 0xF0000000) == 0);
- return (type << 28) | offset;
-}
-
-byte *Parse::decodePtr(int32 n) {
- byte *ptr;
-
- switch (n >> 28) {
- case kExecPtr:
- ptr = _vm->_game->_totFileData;
- break;
- case kInterVar:
- ptr = (byte *) _vm->_inter->_variables->getAddressOff8(0);
- break;
- case kResStr:
- ptr = (byte *) _vm->_global->_inter_resStr;
- break;
- default:
- error("Parse::decodePtr(): Unknown pointer type");
- }
- return ptr + (n & 0x0FFFFFFF);
-}
-
-void Parse::skipExpr(char stopToken) {
- int16 dimCount;
- byte operation;
- int16 num;
- int16 dim;
-
- num = 0;
- while (true) {
- operation = *_vm->_global->_inter_execPtr++;
-
- if ((operation >= 14) && (operation <= OP_FUNC)) {
- switch (operation) {
- case 14:
- _vm->_global->_inter_execPtr += 4;
- if (*_vm->_global->_inter_execPtr == 97)
- _vm->_global->_inter_execPtr++;
- break;
-
- case OP_LOAD_VAR_INT16:
- case OP_LOAD_VAR_INT8:
- case OP_LOAD_IMM_INT16:
- case 23:
- case 24:
- _vm->_global->_inter_execPtr += 2;
- break;
-
- case OP_LOAD_IMM_INT32:
- _vm->_global->_inter_execPtr += 4;
- break;
-
- case OP_LOAD_IMM_INT8:
- _vm->_global->_inter_execPtr += 1;
- break;
-
- case OP_LOAD_IMM_STR:
- _vm->_global->_inter_execPtr +=
- strlen((char *) _vm->_global->_inter_execPtr) + 1;
- break;
-
- case OP_LOAD_VAR_STR:
- _vm->_global->_inter_execPtr += 2;
- if (*_vm->_global->_inter_execPtr == 13) {
- _vm->_global->_inter_execPtr++;
- skipExpr(OP_END_MARKER);
- }
- break;
-
- case 15:
- _vm->_global->_inter_execPtr += 2;
-
- case OP_ARRAY_UINT8:
- case OP_ARRAY_UINT32:
- case OP_ARRAY_UINT16:
- case OP_ARRAY_STR:
- dimCount = _vm->_global->_inter_execPtr[2];
- // skip header and dimensions
- _vm->_global->_inter_execPtr += 3 + dimCount;
- // skip indices
- for (dim = 0; dim < dimCount; dim++)
- skipExpr(OP_END_MARKER);
-
- if ((operation == OP_ARRAY_STR) && (*_vm->_global->_inter_execPtr == 13)) {
- _vm->_global->_inter_execPtr++;
- skipExpr(OP_END_MARKER);
- }
- break;
-
- case OP_FUNC:
- _vm->_global->_inter_execPtr++;
- skipExpr(OP_END_EXPR);
- }
- continue;
- } // if ((operation >= OP_ARRAY_UINT8) && (operation <= OP_FUNC))
-
- if (operation == OP_BEGIN_EXPR) {
- num++;
- continue;
- }
-
- if ((operation == OP_NOT) || ((operation >= OP_NEG) && (operation <= 8)))
- continue;
-
- if ((operation >= OP_OR) && (operation <= OP_NEQ))
- continue;
-
- if (operation == OP_END_EXPR)
- num--;
-
- if (operation != stopToken)
- continue;
-
- if ((stopToken != OP_END_EXPR) || (num < 0))
- return;
- }
-}
-
-void Parse::printExpr(char stopToken) {
- // Expression printing disabled by default
- return;
-
- byte *savedPos = _vm->_global->_inter_execPtr;
- printExpr_internal(stopToken);
-
- // restore IP to start of expression
- _vm->_global->_inter_execPtr = savedPos;
-}
-
-void Parse::printExpr_internal(char stopToken) {
- int16 dimCount;
- byte operation;
- int16 num;
- int16 dim;
- byte *arrDesc;
- byte func;
-
- num = 0;
- while (true) {
- operation = *_vm->_global->_inter_execPtr++;
-
- if ((operation >= OP_ARRAY_UINT8) && (operation <= OP_FUNC)) {
- // operands
-
- switch (operation) {
- case OP_LOAD_VAR_INT16: // int16 variable load
- debugN(5, "var16_%d", _vm->_inter->load16());
- break;
-
- case OP_LOAD_VAR_INT8: // int8 variable load:
- debugN(5, "var8_%d", _vm->_inter->load16());
- break;
-
- case OP_LOAD_IMM_INT32: // int32/uint32 immediate
- debugN(5, "%d", READ_LE_UINT32(_vm->_global->_inter_execPtr));
- _vm->_global->_inter_execPtr += 4;
- break;
-
- case OP_LOAD_IMM_INT16: // int16 immediate
- debugN(5, "%d", _vm->_inter->load16());
- break;
-
- case OP_LOAD_IMM_INT8: // int8 immediate
- debugN(5, "%d", (int8) *_vm->_global->_inter_execPtr++);
- break;
-
- case OP_LOAD_IMM_STR: // string immediate
- debugN(5, "\42%s\42", _vm->_global->_inter_execPtr);
- _vm->_global->_inter_execPtr +=
- strlen((char *) _vm->_global->_inter_execPtr) + 1;
- break;
-
- case 23: // uint32 variable load
- case 24: // uint32 variable load as uint16
- debugN(5, "var_%d", _vm->_inter->load16());
- break;
-
- case OP_LOAD_VAR_STR: // string variable load
- debugN(5, "(&var_%d)", _vm->_inter->load16());
- if (*_vm->_global->_inter_execPtr == 13) {
- _vm->_global->_inter_execPtr++;
- debugN(5, "{");
- printExpr_internal(OP_END_MARKER); // this also prints the closing }
- }
- break;
-
- case OP_ARRAY_UINT8: // uint8 array access
- case OP_ARRAY_UINT32: // uint32 array access
- case OP_ARRAY_UINT16: // uint16 array access
- case OP_ARRAY_STR: // string array access
- debugN(5, "\n");
- if (operation == OP_ARRAY_STR)
- debugN(5, "(&");
-
- debugN(5, "var_%d[", _vm->_inter->load16());
- dimCount = *_vm->_global->_inter_execPtr++;
- arrDesc = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += dimCount;
- for (dim = 0; dim < dimCount; dim++) {
- printExpr_internal(OP_END_MARKER);
- debugN(5, " of %d", (int16) arrDesc[dim]);
- if (dim != dimCount - 1)
- debugN(5, ",");
- }
- debugN(5, "]");
- if (operation == OP_ARRAY_STR)
- debugN(5, ")");
-
- if ((operation == OP_ARRAY_STR) && (*_vm->_global->_inter_execPtr == 13)) {
- _vm->_global->_inter_execPtr++;
- debugN(5, "{");
- printExpr_internal(OP_END_MARKER); // this also prints the closing }
- }
- break;
-
- case OP_FUNC: // function
- func = *_vm->_global->_inter_execPtr++;
- if (func == FUNC_SQR)
- debugN(5, "sqr(");
- else if (func == FUNC_RAND)
- debugN(5, "rand(");
- else if (func == FUNC_ABS)
- debugN(5, "abs(");
- else if ((func == FUNC_SQRT1) || (func == FUNC_SQRT2) || (func == FUNC_SQRT3))
- debugN(5, "sqrt(");
- else
- debugN(5, "id(");
- printExpr_internal(OP_END_EXPR);
- break;
- }
- continue;
- } // if ((operation >= OP_ARRAY_UINT8) && (operation <= OP_FUNC))
-
- // operators
- switch (operation) {
- case OP_BEGIN_EXPR:
- debugN(5, "(");
- break;
-
- case OP_NOT:
- debugN(5, "!");
- break;
-
- case OP_END_EXPR:
- debugN(5, ")");
- break;
-
- case OP_NEG:
- debugN(5, "-");
- break;
-
- case OP_ADD:
- debugN(5, "+");
- break;
-
- case OP_SUB:
- debugN(5, "-");
- break;
-
- case OP_BITOR:
- debugN(5, "|");
- break;
-
- case OP_MUL:
- debugN(5, "*");
- break;
-
- case OP_DIV:
- debugN(5, "/");
- break;
-
- case OP_MOD:
- debugN(5, "%%");
- break;
-
- case OP_BITAND:
- debugN(5, "&");
- break;
-
- case OP_OR:
- debugN(5, "||");
- break;
-
- case 31:
- debugN(5, "&&");
- break;
-
- case OP_LESS:
- debugN(5, "<");
- break;
-
- case OP_LEQ:
- debugN(5, "<=");
- break;
-
- case OP_GREATER:
- debugN(5, ">");
- break;
-
- case OP_GEQ:
- debugN(5, ">=");
- break;
-
- case OP_EQ:
- debugN(5, "==");
- break;
-
- case OP_NEQ:
- debugN(5, "!=");
- break;
-
- case 99:
- debugN(5, "\n");
- break;
-
- case OP_END_MARKER:
- debugN(5, "}");
- if (stopToken != OP_END_MARKER) {
- debugN(5, "Closing paren without opening?");
- }
- break;
-
- default:
- debugN(5, "<%d>", (int16) operation);
- error("Parse::printExpr(): invalid operator in expression");
- break;
- }
-
- if (operation == OP_BEGIN_EXPR) {
- num++;
- continue;
- }
-
- if ((operation == OP_NOT) || ((operation >= OP_NEG) && (operation <= 8)))
- continue;
-
- if ((operation >= OP_OR) && (operation <= OP_NEQ))
- continue;
-
- if (operation == OP_END_EXPR)
- num--;
-
- if (operation == stopToken) {
- if ((stopToken != OP_END_EXPR) || (num < 0)) {
- return;
- }
- }
- }
-}
-
-
-void Parse::printVarIndex() {
- byte *arrDesc;
- int16 dim;
- int16 dimCount;
- int16 operation;
- int16 temp;
-
- byte *pos = _vm->_global->_inter_execPtr;
-
- operation = *_vm->_global->_inter_execPtr++;
- switch (operation) {
- case 23:
- case OP_LOAD_VAR_STR:
- temp = _vm->_inter->load16() * 4;
- debugN(5, "&var_%d", temp);
- if ((operation == OP_LOAD_VAR_STR) && (*_vm->_global->_inter_execPtr == 13)) {
- _vm->_global->_inter_execPtr++;
- debugN(5, "+");
- printExpr(OP_END_MARKER);
- }
- break;
-
- case OP_ARRAY_UINT32:
- case OP_ARRAY_STR:
- debugN(5, "&var_%d[", _vm->_inter->load16());
- dimCount = *_vm->_global->_inter_execPtr++;
- arrDesc = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += dimCount;
- for (dim = 0; dim < dimCount; dim++) {
- printExpr(OP_END_MARKER);
- debugN(5, " of %d", (int16) arrDesc[dim]);
- if (dim != dimCount - 1)
- debugN(5, ",");
- }
- debugN(5, "]");
-
- if ((operation == OP_ARRAY_STR) && (*_vm->_global->_inter_execPtr == 13)) {
- _vm->_global->_inter_execPtr++;
- debugN(5, "+");
- printExpr(OP_END_MARKER);
- }
- break;
-
- default:
- debugN(5, "var_0");
- break;
- }
- debugN(5, "\n");
- _vm->_global->_inter_execPtr = pos;
- return;
-}
-
-int16 Parse::getOffset(int16 arg_0, byte arg_2, uint32 arg_3, uint16 arg_7, uint16 arg_9) {
- if (arg_0 < 0)
- return 0;
-
- if (arg_2 > arg_0)
- return arg_0;
-
- return arg_2 - 1;
-}
-
-int Parse::cmpHelper(byte *operPtr, int32 *valPtr) {
- byte var_C = operPtr[-3];
- int cmpTemp = 0;
- if (var_C == OP_LOAD_IMM_INT16) {
- cmpTemp = (int)valPtr[-3] - (int)valPtr[-1];
- } else if (var_C == OP_LOAD_IMM_STR) {
- if ((char *)decodePtr(valPtr[-3]) != _vm->_global->_inter_resStr) {
- strcpy(_vm->_global->_inter_resStr, (char *)decodePtr(valPtr[-3]));
- valPtr[-3] = encodePtr((byte *) _vm->_global->_inter_resStr, kResStr);
- }
- cmpTemp = strcmp(_vm->_global->_inter_resStr, (char *)decodePtr(valPtr[-1]));
- }
-
- return cmpTemp;
-}
-
-int16 Parse::parseVarIndex(uint16 *arg_0, uint16 *arg_4) {
- int16 temp2;
- byte *arrDesc;
- int16 dim;
- int16 dimCount;
- int16 operation;
- int16 temp;
- int16 offset;
- int16 val;
- uint32 varPos = 0;
-
- operation = *_vm->_global->_inter_execPtr++;
-
- while ((operation == 14) || (operation == 15)) {
- if (operation == 14) {
- uint16 n = _vm->_inter->load16();
- varPos += n * 4;
-
- if (arg_0)
- *arg_0 = READ_LE_UINT16(_vm->_global->_inter_execPtr);
- if (arg_4)
- *arg_4 = 14;
-
- _vm->_global->_inter_execPtr += 2;
-
- debugC(2, kDebugParser, "parseVarIndex: Prefix %d (%d)", varPos, operation);
-
- if (*_vm->_global->_inter_execPtr != 97)
- return varPos;
-
- _vm->_global->_inter_execPtr++;
-
- } else if (operation == 15) {
- uint16 n = _vm->_inter->load16();
- varPos += n * 4;
-
- uint16 var_0C = _vm->_inter->load16();
- if (arg_0)
- *arg_0 = var_0C;
- if (arg_4)
- *arg_4 = 15;
-
- uint8 var_A = *_vm->_global->_inter_execPtr++;
-
- byte *var_12 = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += var_A;
-
- uint16 var_6 = 0;
-
- for (int i = 0; i < var_A; i++) {
- temp2 = parseValExpr(OP_END_MARKER);
-
- int16 ax = getOffset(temp2, var_12[i], varPos, 0, 0);
-
- var_6 = var_6 * var_12[i] + ax;
- }
-
- varPos += var_6 * var_0C * 4;
-
- debugC(2, kDebugParser, "parseVarIndex: Prefix %d (%d)", varPos, operation);
-
- if (*_vm->_global->_inter_execPtr != 97)
- return varPos;
-
- _vm->_global->_inter_execPtr++;
- }
-
- operation = *_vm->_global->_inter_execPtr++;
- }
-
- if (arg_0)
- *arg_0 = 0;
- if (arg_4)
- *arg_4 = operation;
-
- debugC(5, kDebugParser, "var parse = %d", operation);
- switch (operation) {
- case OP_ARRAY_UINT8:
- case OP_ARRAY_UINT32:
- case OP_ARRAY_UINT16:
- case OP_ARRAY_STR:
- temp = _vm->_inter->load16();
- dimCount = *_vm->_global->_inter_execPtr++;
- arrDesc = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += dimCount;
- offset = 0;
- for (dim = 0; dim < dimCount; dim++) {
- temp2 = parseValExpr(OP_END_MARKER);
- offset = arrDesc[dim] * offset + temp2;
- }
- if (operation == OP_ARRAY_UINT8)
- return varPos + temp + offset;
- if (operation == OP_ARRAY_UINT32)
- return varPos + (temp + offset) * 4;
- if (operation == OP_ARRAY_UINT16)
- return varPos + (temp + offset) * 2;
- temp *= 4;
- offset *= 4;
- if (*_vm->_global->_inter_execPtr == 13) {
- _vm->_global->_inter_execPtr++;
- temp += parseValExpr(OP_END_MARKER);
- }
- return varPos + offset * _vm->_global->_inter_animDataSize + temp;
-
- case OP_LOAD_VAR_INT16:
- return varPos + _vm->_inter->load16() * 2;
-
- case OP_LOAD_VAR_INT8:
- return varPos + _vm->_inter->load16();
-
- case 23:
- case 24:
- case OP_LOAD_VAR_STR:
- temp = _vm->_inter->load16() * 4;
- debugC(5, kDebugParser, "oper = %d",
- (int16) *_vm->_global->_inter_execPtr);
- if ((operation == OP_LOAD_VAR_STR) && (*_vm->_global->_inter_execPtr == 13)) {
- _vm->_global->_inter_execPtr++;
- val = parseValExpr(OP_END_MARKER);
- temp += val;
- debugC(5, kDebugParser, "parse subscript = %d", val);
- }
- return varPos + temp;
-
- default:
- return 0;
- }
-}
-
-int16 Parse::parseValExpr(byte stopToken) {
- int16 values[20];
- byte operStack[20];
- int16 *valPtr;
- byte *operPtr;
- byte *arrDesc;
- byte operation;
- int16 temp2;
- int16 dim;
- int16 dimCount;
- int16 temp;
- int16 offset;
- int16 stkPos;
- int16 brackPos;
- static int16 flag = 0;
- int16 oldflag;
- uint32 varPos = 0;
-
- memset(values, 0, 20 * sizeof(int16));
-
- oldflag = flag;
- if (flag == 0) {
- flag = 1;
- printExpr(stopToken);
- }
-
- stkPos = -1;
- operPtr = operStack - 1;
- valPtr = values - 1;
-
- while (1) {
- operation = *_vm->_global->_inter_execPtr++;
-
- while ((operation == 14) || (operation == 15)) {
- if (operation == 14) {
- uint16 n = _vm->_inter->load16();
- varPos += n * 4;
-
- _vm->_global->_inter_execPtr += 3;
- } else if (operation == 15) {
- uint16 n = _vm->_inter->load16();
- varPos += n * 4;
-
- uint16 var_0C = _vm->_inter->load16();
- uint8 var_A = *_vm->_global->_inter_execPtr++;
-
- byte *var_12 = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += var_A;
-
- uint16 var_6 = 0;
-
- for (int i = 0; i < var_A; i++) {
- temp2 = parseValExpr(OP_END_MARKER);
-
- int16 ax = getOffset(temp2, var_12[i], varPos, 0, 0);
-
- var_6 = var_6 * var_12[i] + ax;
- }
-
- varPos += var_6 * var_0C * 4;
-
- _vm->_global->_inter_execPtr++;
- }
-
- debugC(2, kDebugParser, "parseValExpr: Prefix %d (%d)", varPos, operation);
-
- operation = *_vm->_global->_inter_execPtr++;
- }
-
- stkPos++;
- operPtr++;
- valPtr++;
-
- if ((operation >= OP_ARRAY_UINT8) && (operation <= OP_FUNC)) {
- *operPtr = OP_LOAD_IMM_INT16;
- switch (operation) {
- case OP_ARRAY_UINT8:
- case OP_ARRAY_UINT32:
- case OP_ARRAY_UINT16:
- case OP_ARRAY_STR:
- temp = _vm->_inter->load16();
- dimCount = *_vm->_global->_inter_execPtr++;
- arrDesc = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += dimCount;
- offset = 0;
- for (dim = 0; dim < dimCount; dim++) {
- temp2 = parseValExpr(OP_END_MARKER);
- offset = arrDesc[dim] * offset + temp2;
- }
- if (operation == OP_ARRAY_UINT8)
- *valPtr = (int8) READ_VARO_UINT8(varPos + temp + offset);
- else if (operation == OP_ARRAY_UINT32)
- *valPtr = (uint16) READ_VARO_UINT32(varPos + temp * 4 + offset * 4);
- else if (operation == OP_ARRAY_UINT16)
- *valPtr = READ_VARO_UINT16(varPos + temp * 2 + offset * 2);
- else if (operation == OP_ARRAY_STR) {
- _vm->_global->_inter_execPtr++;
- temp2 = parseValExpr(OP_END_MARKER);
- *valPtr = READ_VARO_UINT8(varPos + temp * 4 +
- offset * 4 * _vm->_global->_inter_animDataSize + temp2);
- }
- break;
-
- case OP_LOAD_VAR_INT16:
- *valPtr = READ_VARO_UINT16(varPos + _vm->_inter->load16() * 2);
- break;
-
- case OP_LOAD_VAR_INT8:
- *valPtr = (int8) READ_VARO_UINT8(varPos + _vm->_inter->load16());
- break;
-
- case OP_LOAD_IMM_INT32:
- *valPtr = (uint16) READ_LE_UINT32(varPos + _vm->_global->_inter_execPtr);
- _vm->_global->_inter_execPtr += 4;
- break;
-
- case OP_LOAD_IMM_INT16:
- *valPtr = _vm->_inter->load16();
- break;
-
- case OP_LOAD_IMM_INT8:
- *valPtr = (int8) *_vm->_global->_inter_execPtr++;
- break;
-
- case 23:
- *valPtr = (uint16) READ_VARO_UINT32(varPos + _vm->_inter->load16() * 4);
- break;
-
- case 24:
- *valPtr = READ_VARO_UINT16(varPos + _vm->_inter->load16() * 4);
- break;
-
- case OP_LOAD_VAR_STR:
- temp = _vm->_inter->load16() * 4;
- _vm->_global->_inter_execPtr++;
- temp += parseValExpr(OP_END_MARKER);
- *valPtr = READ_VARO_UINT8(varPos + temp);
- break;
-
- case OP_FUNC:
- operation = *_vm->_global->_inter_execPtr++;
- parseExpr(OP_END_EXPR, 0);
-
- if (operation == FUNC_SQR) {
- _vm->_global->_inter_resVal =
- _vm->_global->_inter_resVal * _vm->_global->_inter_resVal;
- } else if (operation == FUNC_ABS) {
- if (_vm->_global->_inter_resVal < 0)
- _vm->_global->_inter_resVal = -_vm->_global->_inter_resVal;
- } else if (operation == FUNC_RAND) {
- _vm->_global->_inter_resVal =
- _vm->_util->getRandom(_vm->_global->_inter_resVal);
- }
- *valPtr = _vm->_global->_inter_resVal;
- break;
-
- } // switch
- if ((stkPos > 0) && (operPtr[-1] == OP_NEG)) {
- stkPos--;
- operPtr--;
- valPtr--;
- operPtr[0] = OP_LOAD_IMM_INT16;
- valPtr[0] = -valPtr[1];
- }
-
- if ((stkPos > 0) && (operPtr[-1] >= OP_MUL) && (operPtr[-1] <= OP_BITAND)) {
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
-
- switch (operPtr[1]) {
- case OP_MUL:
- valPtr[0] *= valPtr[2];
- break;
-
- case OP_DIV:
- valPtr[0] /= valPtr[2];
- break;
-
- case OP_MOD:
- valPtr[0] %= valPtr[2];
- break;
-
- case OP_BITAND:
- valPtr[0] &= valPtr[2];
- break;
- }
- } // if ((stkPos > 0) && (cmdPtr[-1] >= OP_MUL) && (cmdPtr[-1] <= OP_BITAND))
- varPos = 0;
- continue;
- }
-
- if ((operation >= OP_NEG) && (operation <= OP_BEGIN_EXPR)) {
- *operPtr = operation;
- continue;
- }
-
- while (stkPos >= 2) {
- if (operPtr[-2] == OP_BEGIN_EXPR) {
- stkPos--;
- operPtr--;
- valPtr--;
-
- operPtr[-1] = operPtr[0];
- valPtr[-1] = valPtr[0];
- if ((stkPos > 1) && (operPtr[-2] == OP_NEG)) {
- operPtr[-2] = OP_LOAD_IMM_INT16;
- valPtr[-2] = -valPtr[-1];
-
- stkPos--;
- operPtr--;
- valPtr--;
- }
-
- if ((stkPos > 2) && (operPtr[-2] >= OP_MUL) && (operPtr[-2] <= OP_BITAND)) {
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- switch (operPtr[0]) {
- case OP_MUL:
- valPtr[-1] *= valPtr[1];
- break;
-
- case OP_DIV:
- valPtr[-1] /= valPtr[1];
- break;
-
- case OP_MOD:
- valPtr[-1] %= valPtr[1];
- break;
-
- case OP_BITAND:
- valPtr[-1] &= valPtr[1];
- break;
- }
- }
- if (operation == OP_END_EXPR)
- break;
- } // operPtr[-2] == OP_BEGIN_EXPR
-
- for (brackPos = (stkPos - 2); (brackPos > 0) &&
- (operStack[brackPos] < OP_OR) && (operStack[brackPos] != OP_BEGIN_EXPR);
- brackPos--)
- ;
-
- if ((operStack[brackPos] >= OP_OR) || (operStack[brackPos] == OP_BEGIN_EXPR))
- brackPos++;
-
- if ((operPtr[-2] < 2) || (operPtr[-2] > 8))
- break;
-
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- switch (operPtr[0]) {
- case OP_ADD:
- values[brackPos] += valPtr[1];
- continue;
- case OP_SUB:
- values[brackPos] -= valPtr[1];
- continue;
- case OP_BITOR:
- values[brackPos] |= valPtr[1];
- continue;
- case OP_MUL:
- valPtr[-1] *= valPtr[1];
- continue;
- case OP_DIV:
- valPtr[-1] /= valPtr[1];
- continue;
- case OP_MOD:
- valPtr[-1] %= valPtr[1];
- continue;
- case OP_BITAND:
- valPtr[-1] &= valPtr[1];
- continue;
- }
- }
-
- if (operation != OP_END_EXPR) {
- if (operation != stopToken) {
- debugC(5, kDebugParser, "stoptoken error: %d != %d",
- operation, stopToken);
- }
- flag = oldflag;
- return values[0];
- }
-
- stkPos--;
- operPtr--;
- valPtr--;
- }
-}
-
-int16 Parse::parseExpr(byte stopToken, byte *arg_2) {
- int32 values[20];
- byte operStack[20];
- int32 prevPrevVal;
- int32 prevVal;
- int32 curVal;
- int32 *valPtr;
- byte *operPtr;
- byte *arrDescPtr;
- byte operation;
- int16 dimCount;
- int16 temp;
- int16 temp2;
- int16 offset;
- int16 dim;
- bool var_1A;
- int16 stkPos;
- int16 brackStart;
- uint32 varPos = 0;
-
- memset(operStack, 0, 20);
-
- stkPos = -1;
- operPtr = operStack - 1;
- valPtr = values - 1;
-
- while (true) {
- operation = *_vm->_global->_inter_execPtr++;
-
- while ((operation == 14) || (operation == 15)) {
- if (operation == 14) {
- uint16 n = _vm->_inter->load16();
- varPos += n * 4;
-
- _vm->_global->_inter_execPtr += 2;
- if (*_vm->_global->_inter_execPtr == 97)
- _vm->_global->_inter_execPtr++;
- } else if (operation == 15) {
- uint16 n = _vm->_inter->load16();
- varPos += n * 4;
-
- uint16 var_0C = _vm->_inter->load16();
- uint8 var_A = *_vm->_global->_inter_execPtr++;
-
- byte *var_12 = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += var_A;
-
- uint16 var_6 = 0;
-
- for (int i = 0; i < var_A; i++) {
- temp2 = parseValExpr(OP_END_MARKER);
-
- int16 ax = getOffset(temp2, var_12[i], varPos, 0, 0);
-
- var_6 = var_6 * var_12[i] + ax;
- }
-
- varPos += var_6 * var_0C * 4;
-
- if (*_vm->_global->_inter_execPtr == 97)
- _vm->_global->_inter_execPtr++;
- }
-
- debugC(2, kDebugParser, "parseExpr: Prefix %d (%d)", varPos, operation);
-
- operation = *_vm->_global->_inter_execPtr++;
- }
-
- stkPos++;
- operPtr++;
- valPtr++;
-
- if ((operation >= OP_ARRAY_UINT8) && (operation <= OP_FUNC)) {
- switch (operation) {
- case OP_ARRAY_UINT8:
- case OP_ARRAY_UINT32:
- case OP_ARRAY_UINT16:
- case OP_ARRAY_STR:
- *operPtr = (operation == OP_ARRAY_STR) ? OP_LOAD_IMM_STR : OP_LOAD_IMM_INT16;
- temp = _vm->_inter->load16();
- dimCount = *_vm->_global->_inter_execPtr++;
- arrDescPtr = _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += dimCount;
- offset = 0;
- for (dim = 0; dim < dimCount; dim++) {
- temp2 = parseValExpr(OP_END_MARKER);
- offset = offset * arrDescPtr[dim] + temp2;
- }
- if (operation == OP_ARRAY_UINT8)
- *valPtr = (int8) READ_VARO_UINT8(varPos + temp + offset);
- else if (operation == OP_ARRAY_UINT32)
- *valPtr = READ_VARO_UINT32(varPos + temp * 4 + offset * 4);
- else if (operation == OP_ARRAY_UINT16)
- *valPtr = (int16) READ_VARO_UINT16(varPos + temp * 2 + offset * 2);
- else if (operation == OP_ARRAY_STR) {
- *valPtr = encodePtr(_vm->_inter->_variables->getAddressOff8(
- varPos + temp * 4 + offset * _vm->_global->_inter_animDataSize * 4),
- kInterVar);
- if (*_vm->_global->_inter_execPtr == 13) {
- _vm->_global->_inter_execPtr++;
- temp2 = parseValExpr(OP_END_MARKER);
- *operPtr = OP_LOAD_IMM_INT16;
- *valPtr = READ_VARO_UINT8(varPos + temp * 4 +
- offset * 4 * _vm->_global->_inter_animDataSize + temp2);
- }
- }
- break;
-
- case OP_LOAD_VAR_INT16:
- *operPtr = OP_LOAD_IMM_INT16;
- *valPtr = (int16) READ_VARO_UINT16(varPos + _vm->_inter->load16() * 2);
- break;
-
- case OP_LOAD_VAR_INT8:
- *operPtr = OP_LOAD_IMM_INT16;
- *valPtr = (int8) READ_VARO_UINT8(varPos + _vm->_inter->load16());
- break;
-
- case OP_LOAD_IMM_INT32:
- *operPtr = OP_LOAD_IMM_INT16;
- *valPtr = READ_LE_UINT32(varPos + _vm->_global->_inter_execPtr);
- _vm->_global->_inter_execPtr += 4;
- break;
-
- case OP_LOAD_IMM_INT16:
- *operPtr = OP_LOAD_IMM_INT16;
- *valPtr = _vm->_inter->load16();
- break;
-
- case OP_LOAD_IMM_INT8:
- *operPtr = OP_LOAD_IMM_INT16;
- *valPtr = (int8) *_vm->_global->_inter_execPtr++;
- break;
-
- case OP_LOAD_IMM_STR:
- *operPtr = OP_LOAD_IMM_STR;
- *valPtr = encodePtr(_vm->_global->_inter_execPtr, kExecPtr);
- _vm->_global->_inter_execPtr +=
- strlen((char *) _vm->_global->_inter_execPtr) + 1;
- break;
-
- case 23:
- *operPtr = OP_LOAD_IMM_INT16;
- *valPtr = READ_VARO_UINT32(varPos + _vm->_inter->load16() * 4);
- break;
-
- case 24:
- *operPtr = OP_LOAD_IMM_INT16;
- *valPtr = (int16) READ_VARO_UINT16(varPos + _vm->_inter->load16() * 4);
- break;
-
- case OP_LOAD_VAR_STR:
- *operPtr = OP_LOAD_IMM_STR;
- temp = _vm->_inter->load16() * 4;
- *valPtr = encodePtr(_vm->_inter->_variables->getAddressOff8(varPos + temp), kInterVar);
- if (*_vm->_global->_inter_execPtr == 13) {
- _vm->_global->_inter_execPtr++;
- temp += parseValExpr(OP_END_MARKER);
- *operPtr = OP_LOAD_IMM_INT16;
- *valPtr = READ_VARO_UINT8(varPos + temp);
- }
- break;
-
- case OP_FUNC:
- operation = *_vm->_global->_inter_execPtr++;
- parseExpr(OP_END_EXPR, 0);
-
- switch (operation) {
- case FUNC_SQRT1:
- case FUNC_SQRT2:
- case FUNC_SQRT3:
- curVal = 1;
- prevVal = 1;
-
- do {
- prevPrevVal = prevVal;
- prevVal = curVal;
- curVal = (curVal + _vm->_global->_inter_resVal / curVal) / 2;
- } while ((curVal != prevVal) && (curVal != prevPrevVal));
- _vm->_global->_inter_resVal = curVal;
- break;
-
- case FUNC_SQR:
- _vm->_global->_inter_resVal =
- _vm->_global->_inter_resVal * _vm->_global->_inter_resVal;
- break;
-
- case FUNC_ABS:
- if (_vm->_global->_inter_resVal < 0)
- _vm->_global->_inter_resVal = -_vm->_global->_inter_resVal;
- break;
-
- case FUNC_RAND:
- _vm->_global->_inter_resVal =
- _vm->_util->getRandom(_vm->_global->_inter_resVal);
- break;
- }
-
- *operPtr = OP_LOAD_IMM_INT16;
- *valPtr = _vm->_global->_inter_resVal;
- break;
- }
-
- if ((stkPos > 0) && ((operPtr[-1] == OP_NEG) || (operPtr[-1] == OP_NOT))) {
- stkPos--;
- operPtr--;
- valPtr--;
-
- if (*operPtr == OP_NEG) {
- *operPtr = OP_LOAD_IMM_INT16;
- valPtr[0] = -valPtr[1];
- } else
- *operPtr = (operPtr[1] == GOB_FALSE) ? GOB_TRUE : GOB_FALSE;
- }
-
- if (stkPos <= 0) {
- varPos = 0;
- continue;
- }
-
- switch (operPtr[-1]) {
- case OP_ADD:
- if (operPtr[-2] == OP_LOAD_IMM_STR) {
- if ((char *) decodePtr(valPtr[-2]) != _vm->_global->_inter_resStr) {
- strcpy(_vm->_global->_inter_resStr, (char *) decodePtr(valPtr[-2]));
- valPtr[-2] = encodePtr((byte *) _vm->_global->_inter_resStr, kResStr);
- }
- strcat(_vm->_global->_inter_resStr, (char *) decodePtr(valPtr[0]));
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- }
- break;
-
- case OP_MUL:
- valPtr[-2] *= valPtr[0];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_DIV:
- valPtr[-2] /= valPtr[0];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_MOD:
- valPtr[-2] %= valPtr[0];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_BITAND:
- valPtr[-2] &= valPtr[0];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
- }
- varPos = 0;
- continue;
- } // (op >= OP_ARRAY_UINT8) && (op <= OP_FUNC)
-
- if ((operation == stopToken) || (operation == OP_OR) ||
- (operation == OP_AND) || (operation == OP_END_EXPR)) {
- while (stkPos >= 2) {
- var_1A = false;
- if ((operPtr[-2] == OP_BEGIN_EXPR) &&
- ((operation == OP_END_EXPR) || (operation == stopToken))) {
- operPtr[-2] = operPtr[-1];
- if ((operPtr[-2] == OP_LOAD_IMM_INT16) || (operPtr[-2] == OP_LOAD_IMM_STR))
- valPtr[-2] = valPtr[-1];
-
- stkPos--;
- operPtr--;
- valPtr--;
-
- if (stkPos > 1) {
- if (operPtr[-2] == OP_NEG) {
- operPtr[-2] = OP_LOAD_IMM_INT16;
- valPtr[-2] = -valPtr[-1];
- stkPos--;
- operPtr--;
- valPtr--;
- } else if (operPtr[-2] == OP_NOT) {
- operPtr[-2] = (operPtr[-1] == GOB_FALSE) ? GOB_TRUE : GOB_FALSE;
- stkPos--;
- operPtr--;
- valPtr--;
- }
- } // stkPos > 1
-
- if (stkPos > 2) {
- switch (operPtr[-2]) {
- case OP_MUL:
- valPtr[-3] *= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_DIV:
- valPtr[-3] /= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_MOD:
- valPtr[-3] %= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_BITAND:
- valPtr[-3] &= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
- } // switch
- } // stkPos > 2
-
- if (operation != stopToken)
- break;
- } // if ((operPtr[-2] == OP_BEGIN_EXPR) && ...)
-
- for (brackStart = (stkPos - 2); (brackStart > 0) &&
- (operStack[brackStart] < OP_OR) && (operStack[brackStart] != OP_BEGIN_EXPR);
- brackStart--)
- ;
-
- if ((operStack[brackStart] >= OP_OR) || (operStack[brackStart] == OP_BEGIN_EXPR))
- brackStart++;
-
- switch (operPtr[-2]) {
- case OP_ADD:
- if (operStack[brackStart] == OP_LOAD_IMM_INT16) {
- values[brackStart] += valPtr[-1];
- } else if (operStack[brackStart] == OP_LOAD_IMM_STR) {
- if ((char *) decodePtr(values[brackStart]) != _vm->_global->_inter_resStr) {
- strcpy(_vm->_global->_inter_resStr, (char *) decodePtr(values[brackStart]));
- values[brackStart] =
- encodePtr((byte *) _vm->_global->_inter_resStr, kResStr);
- }
- strcat(_vm->_global->_inter_resStr, (char *) decodePtr(valPtr[-1]));
- }
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- continue;
-
- case OP_SUB:
- values[brackStart] -= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- continue;
-
- case OP_BITOR:
- values[brackStart] |= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- continue;
-
- case OP_MUL:
- valPtr[-3] *= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_DIV:
- valPtr[-3] /= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_MOD:
- valPtr[-3] %= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_BITAND:
- valPtr[-3] &= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_OR:
- // (x OR false) == x
- // (x OR true) == true
- if (operPtr[-3] == GOB_FALSE)
- operPtr[-3] = operPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_AND:
- // (x AND false) == false
- // (x AND true) == x
- if (operPtr[-3] == GOB_TRUE)
- operPtr[-3] = operPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_LESS:
- operPtr[-3] = (cmpHelper(operPtr, valPtr) < 0) ? GOB_TRUE : GOB_FALSE;
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_LEQ:
- operPtr[-3] = (cmpHelper(operPtr, valPtr) <= 0) ? GOB_TRUE : GOB_FALSE;
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_GREATER:
- operPtr[-3] = (cmpHelper(operPtr, valPtr) > 0) ? GOB_TRUE : GOB_FALSE;
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_GEQ:
- operPtr[-3] = (cmpHelper(operPtr, valPtr) >= 0) ? GOB_TRUE : GOB_FALSE;
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_EQ:
- operPtr[-3] = (cmpHelper(operPtr, valPtr) == 0) ? GOB_TRUE : GOB_FALSE;
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
-
- case OP_NEQ: {
- int cmpTemp = 0;
-
- if (operPtr[-3] == OP_LOAD_IMM_INT16) {
- cmpTemp = valPtr[-3] - valPtr[-1];
- } else if (operPtr[-3] == OP_LOAD_IMM_STR) {
- if ((char *) decodePtr(valPtr[-3]) != _vm->_global->_inter_resStr) {
- strcpy(_vm->_global->_inter_resStr, (char *) decodePtr(valPtr[-3]));
- valPtr[-3] = encodePtr((byte *) _vm->_global->_inter_resStr, kResStr);
- }
- // FIXME: Why scumm_stricmp here and strcmp everywhere else?
- cmpTemp = scumm_stricmp(_vm->_global->_inter_resStr, (char *) decodePtr(valPtr[-1]));
- }
- operPtr[-3] = (cmpTemp != 0) ? GOB_TRUE : GOB_FALSE;
- //operPtr[-3] = (cmpHelper(operPtr, valPtr) != 0) ? GOB_TRUE : GOB_FALSE;
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- break;
- }
-
- default:
- var_1A = true;
- break;
- } // switch
-
- if (var_1A)
- break;
- } // while (stkPos >= 2)
-
- if ((operation == OP_OR) || (operation == OP_AND)) {
- if (operPtr[-1] == OP_LOAD_IMM_INT16) {
- if (valPtr[-1] != 0)
- operPtr[-1] = GOB_TRUE;
- else
- operPtr[-1] = GOB_FALSE;
- }
-
- if (((operation == OP_OR) && (operPtr[-1] == GOB_TRUE)) ||
- ((operation == OP_AND) && (operPtr[-1] == GOB_FALSE))) {
- if ((stkPos > 1) && (operPtr[-2] == OP_BEGIN_EXPR)) {
- skipExpr(OP_END_EXPR);
- operPtr[-2] = operPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- } else {
- skipExpr(stopToken);
- }
- operation = _vm->_global->_inter_execPtr[-1];
- if ((stkPos > 0) && (operPtr[-1] == OP_NOT)) {
- if (operPtr[0] == GOB_FALSE)
- operPtr[-1] = GOB_TRUE;
- else
- operPtr[-1] = GOB_FALSE;
-
- stkPos--;
- operPtr--;
- valPtr--;
- }
- } else
- operPtr[0] = operation;
- } else {
- stkPos--;
- operPtr--;
- valPtr--;
- }
-
- if (operation != stopToken)
- continue;
-
- if (arg_2 != 0)
- *arg_2 = operStack[0];
-
- switch (operStack[0]) {
- case OP_NOT:
- if (arg_2 != 0)
- *arg_2 ^= 1;
- break;
-
- case OP_LOAD_IMM_INT16:
- _vm->_global->_inter_resVal = values[0];
- break;
-
- case OP_LOAD_IMM_STR:
- if ((char *) decodePtr(values[0]) != _vm->_global->_inter_resStr)
- strcpy(_vm->_global->_inter_resStr, (char *) decodePtr(values[0]));
- break;
-
- case 23:
- case 24:
- break;
-
- default:
- _vm->_global->_inter_resVal = 0;
- if (arg_2 != 0)
- *arg_2 = OP_LOAD_IMM_INT16;
- break;
- }
- return 0;
- } // (operation == stopToken) || (operation == OP_OR) || (operation == OP_AND) || (operation == OP_END_EXPR)
-
- if ((operation < OP_NEG) || (operation > OP_NOT)) {
- if ((operation < OP_LESS) || (operation > OP_NEQ))
- continue;
-
- if (stkPos > 2) {
- if (operPtr[-2] == OP_ADD) {
- if (operPtr[-3] == OP_LOAD_IMM_INT16) {
- valPtr[-3] += valPtr[-1];
- } else if (operPtr[-3] == OP_LOAD_IMM_STR) {
- if ((char *) decodePtr(valPtr[-3]) != _vm->_global->_inter_resStr) {
- strcpy(_vm->_global->_inter_resStr, (char *) decodePtr(valPtr[-3]));
- valPtr[-3] = encodePtr((byte *) _vm->_global->_inter_resStr, kResStr);
- }
- strcat(_vm->_global->_inter_resStr, (char *) decodePtr(valPtr[-1]));
- }
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
-
- } else if (operPtr[-2] == OP_SUB) {
- valPtr[-3] -= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- } else if (operPtr[-2] == OP_BITOR) {
- valPtr[-3] |= valPtr[-1];
- stkPos -= 2;
- operPtr -= 2;
- valPtr -= 2;
- }
- }
- }
- *operPtr = operation;
- }
-}
-
-} // End of namespace Gob
diff --git a/engines/gob/parse.h b/engines/gob/parse.h
deleted file mode 100644
index 01f5762b6d..0000000000
--- a/engines/gob/parse.h
+++ /dev/null
@@ -1,128 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
-
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
-
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- * $URL$
- * $Id$
- *
- */
-
-#ifndef GOB_PARSE_H
-#define GOB_PARSE_H
-
-namespace Gob {
-
-enum {
- OP_NEG = 1,
- OP_ADD = 2,
- OP_SUB = 3,
- OP_BITOR = 4,
- OP_MUL = 5,
- OP_DIV = 6,
- OP_MOD = 7,
- OP_BITAND = 8,
- OP_BEGIN_EXPR = 9,
- OP_END_EXPR = 10,
- OP_NOT = 11,
-
- OP_END_MARKER = 12, // Marks end of an array or string
-
-
- OP_ARRAY_UINT8 = 16,
-
- OP_LOAD_VAR_INT16 = 17,
- OP_LOAD_VAR_INT8 = 18,
- OP_LOAD_IMM_INT32 = 19,
- OP_LOAD_IMM_INT16 = 20,
- OP_LOAD_IMM_INT8 = 21,
- OP_LOAD_IMM_STR = 22,
-
- OP_LOAD_VAR_UINT32 = 23, // ???
- OP_LOAD_VAR_UINT32_AS_UINT16 = 24, // ???
- OP_LOAD_VAR_STR = 25,
-
- OP_ARRAY_UINT32 = 26,
- OP_ARRAY_UINT16 = 27,
- OP_ARRAY_STR = 28,
-
- OP_FUNC = 29,
-
- OP_OR = 30, // Logical OR
- OP_AND = 31, // Logical AND
- OP_LESS = 32,
- OP_LEQ = 33,
- OP_GREATER = 34,
- OP_GEQ = 35,
- OP_EQ = 36,
- OP_NEQ = 37
-};
-
-enum {
- FUNC_SQRT1 = 0,
- FUNC_SQRT2 = 1,
- FUNC_SQRT3 = 6,
-
- FUNC_SQR = 5,
- FUNC_ABS = 7,
- FUNC_RAND = 10
-};
-
-enum {
- // FIXME: The following two 'truth values' are stored inside the list
- // of "operators". So they somehow coincide with OP_LOAD_VAR_UINT32
- // and OP_LOAD_VAR_UINT32_AS_UINT16. I haven't yet quite understood
- // how, resp. what that means. You have been warned.
- GOB_TRUE = 24,
- GOB_FALSE = 23
-};
-
-class Parse {
-public:
- void skipExpr(char stopToken);
- void printExpr(char stopToken);
- void printVarIndex(void);
-
- int16 parseVarIndex(uint16 *arg_0 = 0, uint16 *arg_4 = 0);
- int16 parseValExpr(byte stopToken = 99);
- int16 parseExpr(byte stopToken, byte *resultPtr);
-
- Parse(GobEngine *vm);
- virtual ~Parse() {}
-
-private:
- enum PointerType {
- kExecPtr = 0,
- kInterVar = 1,
- kResStr = 2
- };
-
- GobEngine *_vm;
-
- int32 encodePtr(byte *ptr, int type);
- byte *decodePtr(int32 n);
-
- void printExpr_internal(char stopToken);
-
- int16 getOffset(int16 arg_0, byte arg_2, uint32 arg_3, uint16 arg_7, uint16 arg_9);
- int cmpHelper(byte *operPtr, int32 *valPtr);
-};
-
-} // End of namespace Gob
-
-#endif // GOB_PARSE_H
diff --git a/engines/gob/resources.cpp b/engines/gob/resources.cpp
new file mode 100644
index 0000000000..20427e547b
--- /dev/null
+++ b/engines/gob/resources.cpp
@@ -0,0 +1,706 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/util.h"
+#include "common/endian.h"
+#include "common/stream.h"
+
+#include "gob/gob.h"
+#include "gob/resources.h"
+#include "gob/totfile.h"
+#include "gob/dataio.h"
+#include "gob/game.h"
+#include "gob/global.h"
+
+namespace Gob {
+
+Resource::Resource(byte *data, int32 size, bool needFree,
+ int16 width, int16 height) {
+
+ _data = data;
+ _size = size;
+ _width = width;
+ _height = height;
+ _needFree = needFree;
+
+ _stream = new Common::MemoryReadStream(data, size);
+}
+
+Resource::~Resource() {
+ delete _stream;
+
+ if (_needFree)
+ delete[] _data;
+}
+
+byte *Resource::getData() const {
+ return _data;
+}
+
+int32 Resource::getSize() const {
+ return _size;
+}
+
+int16 Resource::getWidth() const {
+ return _width;
+}
+
+int16 Resource::getHeight() const {
+ return _height;
+}
+
+Common::MemoryReadStream *Resource::stream() const {
+ return _stream;
+}
+
+
+TextItem::TextItem(byte *data, int32 size) {
+ _data = data;
+ _size = size;
+
+ _stream = new Common::MemoryReadStream(data, size);
+}
+
+TextItem::~TextItem() {
+ delete _stream;
+}
+
+byte *TextItem::getData() const {
+ return _data;
+}
+
+int32 TextItem::getSize() const {
+ return _size;
+}
+
+Common::MemoryReadStream *TextItem::stream() const {
+ return _stream;
+}
+
+
+Resources::TOTResourceTable::TOTResourceTable() {
+ items = 0;
+}
+
+Resources::TOTResourceTable::~TOTResourceTable() {
+ delete[] items;
+}
+
+
+Resources::EXTResourceTable::EXTResourceTable() {
+ itemsCount = 0;
+ unknown = 0;
+ items = 0;
+}
+
+Resources::EXTResourceTable::~EXTResourceTable() {
+ delete[] items;
+}
+
+
+Resources::TOTTextTable::TOTTextTable() {
+ items = 0;
+ data = 0;
+ needFree = false;
+}
+
+Resources::TOTTextTable::~TOTTextTable() {
+ delete[] items;
+ if (needFree)
+ delete[] data;
+}
+
+
+Resources::Resources(GobEngine *vm) : _vm(vm) {
+ unload(false);
+}
+
+Resources::~Resources() {
+ unload();
+}
+
+bool Resources::load(const Common::String &fileName) {
+ unload();
+
+ Common::String fileBase;
+
+ _totFile = TOTFile::createFileName(fileName, _hasLOM);
+
+ if (_hasLOM) {
+ warning("Stub: Resources::load(%s)", fileName.c_str());
+ unload();
+ return false;
+ }
+
+ fileBase = TOTFile::getFileBase(fileName);
+
+ _extFile = fileBase + ".ext";
+
+ if (!loadTOTResourceTable()) {
+ unload();
+ return false;
+ }
+
+ if (!loadEXTResourceTable()) {
+ unload();
+ return false;
+ }
+
+ if (!loadTOTTextTable(fileBase)) {
+ unload();
+ return false;
+ }
+
+ if (!loadIMFile()) {
+ unload();
+ return false;
+ }
+
+ if (!loadEXFile()) {
+ unload();
+ return false;
+ }
+
+ return true;
+}
+
+void Resources::unload(bool del) {
+ if (del) {
+ delete _totResourceTable;
+ delete _extResourceTable;
+ delete _totTextTable;
+
+ delete[] _totData;
+ delete[] _imData;
+
+ _totFile.clear();
+ _extFile.clear();
+ _exFile.clear();
+ }
+
+ _totResourceTable = 0;
+ _extResourceTable = 0;
+ _totTextTable = 0;
+ _totData = 0;
+ _totSize = 0;
+ _imData = 0;
+ _imSize = 0;
+}
+
+bool Resources::isLoaded() const {
+ return (_totResourceTable != 0);
+}
+
+bool Resources::loadTOTResourceTable() {
+ TOTFile totFile(_vm);
+
+ if (!totFile.load(_totFile))
+ return false;
+
+ TOTFile::Properties totProps;
+ if (!totFile.getProperties(totProps))
+ return false;
+
+ Common::SeekableReadStream *stream = totFile.getStream();
+ if (!stream)
+ return false;
+
+ if ((totProps.resourcesOffset == 0xFFFFFFFF) ||
+ (totProps.resourcesOffset == 0))
+ // No resources here
+ return false;
+
+ _totResourceTable = new TOTResourceTable;
+
+ stream->seek(totProps.resourcesOffset);
+ _totResourceTable->itemsCount = stream->readSint16LE();
+
+ _totResourceTable->dataOffset = totProps.resourcesOffset + kTOTResTableSize +
+ _totResourceTable->itemsCount * kTOTResItemSize;
+
+
+ uint32 resSize = _totResourceTable->itemsCount * kTOTResItemSize +
+ kTOTResTableSize;
+
+ // Would the table actually fit into the TOT?
+ if ((totProps.resourcesOffset + resSize) > ((uint32) stream->size()))
+ return false;
+
+ _totResourceTable->unknown = stream->readByte();
+ _totResourceTable->items = new TOTResourceItem[_totResourceTable->itemsCount];
+
+ for (int i = 0; i < _totResourceTable->itemsCount; ++i) {
+ TOTResourceItem &item = _totResourceTable->items[i];
+
+ item.offset = stream->readSint32LE();
+ item.size = stream->readSint16LE();
+ item.width = stream->readSint16LE();
+ item.height = stream->readSint16LE();
+
+ if (item.offset < 0) {
+ item.type = kResourceIM;
+ item.index = -item.offset - 1;
+ } else
+ item.type = kResourceTOT;
+ }
+
+ _totResStart = totProps.scriptEnd;
+ _totSize = stream->size() - _totResStart;
+ if (_totSize <= 0)
+ return false;
+
+ if (!stream->seek(totProps.scriptEnd))
+ return false;
+
+ _totData = new byte[_totSize];
+ if (stream->read(_totData, _totSize) != _totSize)
+ return false;
+
+ return !stream->err();
+}
+
+bool Resources::loadEXTResourceTable() {
+ _extResourceTable = new EXTResourceTable;
+
+ DataStream *stream = _vm->_dataIO->getDataStream(_extFile.c_str());
+ if (!stream)
+ return true;
+
+ _extResourceTable->itemsCount = stream->readSint16LE();
+ _extResourceTable->unknown = stream->readByte();
+
+ if (_extResourceTable->itemsCount > 0)
+ _extResourceTable->items = new EXTResourceItem[_extResourceTable->itemsCount];
+
+ for (int i = 0; i < _extResourceTable->itemsCount; i++) {
+ EXTResourceItem &item = _extResourceTable->items[i];
+
+ item.offset = stream->readUint32LE();
+ item.size = stream->readUint16LE();
+ item.width = stream->readUint16LE();
+ item.height = stream->readUint16LE();
+
+ if (item.offset < 0) {
+ item.type = kResourceEX;
+ item.offset = -item.offset - 1;
+ } else {
+ item.type = kResourceEXT;
+ item.offset += kEXTResTableSize +
+ kEXTResItemSize * _extResourceTable->itemsCount;
+ }
+
+ item.packed = (item.width & 0x8000) != 0;
+
+ item.width &= 0x7FFF;
+ }
+
+ delete stream;
+ return true;
+}
+
+bool Resources::loadTOTTextTable(const Common::String &fileBase) {
+ TOTFile totFile(_vm);
+
+ if (!totFile.load(_totFile))
+ return false;
+
+ TOTFile::Properties totProps;
+ if (!totFile.getProperties(totProps))
+ return false;
+
+ Common::SeekableReadStream *stream = totFile.getStream();
+ if (!stream)
+ return false;
+
+ if (totProps.textsOffset == ((uint32) -1))
+ // No texts
+ return true;
+
+ _totTextTable = new TOTTextTable;
+
+ bool fromTOT;
+ if (totProps.textsOffset == 0) {
+ fromTOT = false;
+ _totTextTable->data = loadTOTLocTexts(fileBase, _totTextTable->size);
+ _totTextTable->needFree = true;
+ } else {
+ fromTOT = true;
+ _totTextTable->data = _totData + totProps.textsOffset - _totResStart;
+ _totTextTable->needFree = false;
+ _totTextTable->size = _totSize - totProps.textsOffset;
+ }
+
+ if (_totTextTable->data) {
+ Common::MemoryReadStream totTextTable(_totTextTable->data, _totTextTable->size);
+ _totTextTable->itemsCount = totTextTable.readSint16LE() & 0x3FFF;
+
+ _totTextTable->items = new TOTTextItem[_totTextTable->itemsCount];
+ for (int i = 0; i < _totTextTable->itemsCount; ++i) {
+ TOTTextItem &item = _totTextTable->items[i];
+
+ item.offset = totTextTable.readSint16LE();
+ item.size = totTextTable.readSint16LE();
+
+ if (fromTOT)
+ item.offset -= (totProps.textsOffset - _totResStart);
+ }
+ }
+
+ return true;
+}
+
+bool Resources::loadIMFile() {
+ TOTFile totFile(_vm);
+
+ if (!totFile.load(_totFile))
+ return false;
+
+ TOTFile::Properties totProps;
+ if (!totFile.getProperties(totProps))
+ return false;
+
+ if ((totProps.communHandling != 0) && (totProps.imFileNumber == 0))
+ // No IM file
+ return true;
+
+ Common::String imFile = "commun.im";
+
+ char num = totProps.imFileNumber + '0';
+ if (num == '0')
+ num = '1';
+
+ imFile += num;
+
+ DataStream *stream = _vm->_dataIO->getDataStream(imFile.c_str());
+ if (!stream)
+ return true;
+
+ _imSize = stream->size();
+ if (_imSize <= 0) {
+ _imSize = 0;
+ delete stream;
+ return true;
+ }
+
+ _imData = new byte[_imSize];
+ if (stream->read(_imData, _imSize) != _imSize) {
+ delete[] _imData;
+ _imData = 0;
+ _imSize = 0;
+ }
+
+ delete stream;
+ return true;
+}
+
+bool Resources::loadEXFile() {
+ TOTFile totFile(_vm);
+
+ if (!totFile.load(_totFile))
+ return false;
+
+ TOTFile::Properties totProps;
+ if (!totFile.getProperties(totProps))
+ return false;
+
+ _exFile = "commun.ex";
+ _exFile += totProps.exFileNumber + '0';
+
+ if (!_vm->_dataIO->existData(_exFile.c_str())) {
+ _exFile.clear();
+ return true;
+ }
+
+ return true;
+}
+
+Common::String Resources::getLocTextFile(const Common::String &fileBase,
+ int language) {
+
+ Common::String locTextFile = fileBase + ".";
+ switch (language) {
+ case kLanguageFrench:
+ locTextFile += "dat";
+ break;
+ case kLanguageGerman:
+ locTextFile += "all";
+ break;
+ case kLanguageSpanish:
+ locTextFile += "esp";
+ break;
+ case kLanguageItalian:
+ locTextFile += "ita";
+ break;
+ case kLanguageAmerican:
+ locTextFile += "usa";
+ break;
+ case kLanguageDutch:
+ locTextFile += "ndl";
+ break;
+ case kLanguageKorean:
+ locTextFile += "kor";
+ break;
+ case kLanguageHebrew:
+ locTextFile += "isr";
+ break;
+ default:
+ locTextFile += "ang";
+ break;
+ }
+
+ if (!_vm->_dataIO->existData(locTextFile.c_str()))
+ locTextFile.clear();
+
+ return locTextFile;
+}
+
+byte *Resources::loadTOTLocTexts(const Common::String &fileBase, int32 &size) {
+ Common::String locTextFile;
+
+ locTextFile = getLocTextFile(fileBase, _vm->_global->_languageWanted);
+
+ if (!locTextFile.empty()) {
+
+ _vm->_global->_foundLanguage = true;
+ _vm->_global->_language = _vm->_global->_languageWanted;
+
+ } else if (!_vm->_global->_foundLanguage) {
+
+ // Trying US for GB and vice versa
+ if (_vm->_global->_languageWanted == kLanguageBritish) {
+
+ locTextFile = getLocTextFile(fileBase, kLanguageAmerican);
+ if (!locTextFile.empty())
+ _vm->_global->_language = kLanguageAmerican;
+
+ } else if (_vm->_global->_languageWanted == kLanguageAmerican) {
+
+ locTextFile = getLocTextFile(fileBase, kLanguageBritish);
+ if (!locTextFile.empty())
+ _vm->_global->_language = kLanguageBritish;
+
+ }
+
+ if (locTextFile.empty()) {
+ // Looking for the first existing language
+ for (int i = 0; i < 10; i++) {
+ locTextFile = getLocTextFile(fileBase, i);
+ if (!locTextFile.empty()) {
+ _vm->_global->_language = i;
+ break;
+ }
+ }
+ }
+
+ }
+
+ debugC(1, kDebugFileIO, "Using language %d for %s",
+ _vm->_global->_language, _totFile.c_str());
+
+ if (locTextFile.empty())
+ return 0;
+
+ size = _vm->_dataIO->getDataSize(locTextFile.c_str());
+ return _vm->_dataIO->getData(locTextFile.c_str());
+}
+
+Resource *Resources::getResource(uint16 id, int16 *width, int16 *height) const {
+ if (_hasLOM) {
+ warning("Stub: Resources::getResource(): Has LOM");
+ return 0;
+ }
+
+ Resource *resource = 0;
+ if (id >= 30000)
+ resource = getEXTResource(id - 30000);
+ else
+ resource = getTOTResource(id);
+
+ if (!resource)
+ return 0;
+
+ if (width)
+ *width = resource->getWidth();
+ if (height)
+ *height = resource->getHeight();
+
+ return resource;
+}
+
+TextItem *Resources::getTextItem(uint16 id) const {
+ if (!_totTextTable || !_totTextTable->data)
+ return 0;
+
+ if (id >= _totTextTable->itemsCount)
+ return 0;
+
+ TOTTextItem &totItem = _totTextTable->items[id];
+
+ if ((totItem.offset == 0xFFFF) || (totItem.size == 0))
+ return 0;
+ if ((totItem.offset + totItem.size) > (_totTextTable->size))
+ return 0;
+
+ return new TextItem(_totTextTable->data + totItem.offset, totItem.size);
+}
+
+byte *Resources::getTexts() const {
+ if (!_totTextTable)
+ return 0;
+
+ return _totTextTable->data;
+}
+
+Resource *Resources::getTOTResource(uint16 id) const {
+ if (id >= _totResourceTable->itemsCount) {
+ warning("Trying to load non-existent TOT resource (%s, %d/%d)",
+ _totFile.c_str(), id, _totResourceTable->itemsCount - 1);
+ return 0;
+ }
+
+ TOTResourceItem &totItem = _totResourceTable->items[id];
+
+ byte *data = 0;
+ if (totItem.type == kResourceIM)
+ data = getIMData(totItem);
+ if (totItem.type == kResourceTOT)
+ data = getTOTData(totItem);
+
+ if (!data)
+ return 0;
+
+ return new Resource(data, totItem.size, false, totItem.width, totItem.height);
+}
+
+Resource *Resources::getEXTResource(uint16 id) const {
+ if (!_extResourceTable || (id > _extResourceTable->itemsCount))
+ return 0;
+
+ EXTResourceItem &extItem = _extResourceTable->items[id];
+
+ uint32 size = extItem.size;
+
+ if (extItem.width & 0x4000)
+ size += 1 << 16;
+ if (extItem.width & 0x2000)
+ size += 2 << 16;
+ if (extItem.width & 0x1000)
+ size += 4 << 16;
+ if (extItem.height == 0)
+ size += extItem.width << 16;
+
+ byte *data = 0;
+ if (extItem.type == kResourceEXT)
+ data = getEXTData(extItem, size);
+ if (extItem.type == kResourceEX)
+ data = getEXData(extItem, size);
+
+ if (!data)
+ return 0;
+
+ if (extItem.packed) {
+ byte *packedData = data;
+
+ size = READ_LE_UINT32(packedData);
+ data = new byte[size];
+
+ _vm->_dataIO->unpackData(packedData, data);
+
+ delete[] packedData;
+ }
+
+ return new Resource(data, size, true, extItem.width & 0xFFF, extItem.height);
+}
+
+byte *Resources::getTOTData(TOTResourceItem &totItem) const {
+ if (totItem.size < 0)
+ return 0;
+
+ int32 offset = _totResourceTable->dataOffset + totItem.offset - _totResStart;
+
+ if ((offset < 0) || (((uint32) (offset + totItem.size)) > _totSize))
+ return 0;
+
+ return _totData + offset;
+}
+
+byte *Resources::getIMData(TOTResourceItem &totItem) const {
+ if (totItem.size < 0)
+ return 0;
+
+ int32 indexOffset = totItem.index * 4;
+ if ((indexOffset < 0) || (((uint32) indexOffset) >= _imSize))
+ return 0;
+
+ uint32 offset = READ_LE_UINT32(_imData + indexOffset);
+ if ((offset + totItem.size) > _imSize)
+ return 0;
+
+ return _imData + offset;
+}
+
+byte *Resources::getEXTData(EXTResourceItem &extItem, uint32 size) const {
+ DataStream *stream = _vm->_dataIO->getDataStream(_extFile.c_str());
+ if (!stream)
+ return 0;
+
+ if (!stream->seek(extItem.offset)) {
+ delete stream;
+ return 0;
+ }
+
+ byte *data = new byte[extItem.packed ? (size + 2) : size];
+ if (stream->read(data, size) != size) {
+ delete[] data;
+ delete stream;
+ return 0;
+ }
+
+ delete stream;
+ return data;
+}
+
+byte *Resources::getEXData(EXTResourceItem &extItem, uint32 size) const {
+ DataStream *stream = _vm->_dataIO->getDataStream(_exFile.c_str());
+ if (!stream)
+ return 0;
+
+ if (!stream->seek(extItem.offset)) {
+ delete stream;
+ return 0;
+ }
+
+ byte *data = new byte[extItem.packed ? (size + 2) : size];
+ if (stream->read(data, size) != size) {
+ delete[] data;
+ delete stream;
+ return 0;
+ }
+
+ delete stream;
+ return data;
+}
+
+} // End of namespace Gob
diff --git a/engines/gob/resources.h b/engines/gob/resources.h
new file mode 100644
index 0000000000..80acef645c
--- /dev/null
+++ b/engines/gob/resources.h
@@ -0,0 +1,207 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#ifndef GOB_RESOURCES_H
+#define GOB_RESOURCES_H
+
+#include "common/str.h"
+
+namespace Common {
+ class MemoryReadStream;
+}
+
+namespace Gob {
+
+class GobEngine;
+
+class Resource {
+public:
+ Resource(byte *data, int32 size, bool needFree = true,
+ int16 width = 0, int16 height = 0);
+ ~Resource();
+
+ byte *getData () const;
+ int32 getSize () const;
+ int16 getWidth () const;
+ int16 getHeight() const;
+
+ Common::MemoryReadStream *stream() const;
+
+private:
+ byte *_data;
+ int32 _size;
+ int16 _width;
+ int16 _height;
+ bool _needFree;
+
+ Common::MemoryReadStream *_stream;
+};
+
+class TextItem {
+public:
+ TextItem(byte *data, int32 size);
+ ~TextItem();
+
+ byte *getData() const;
+ int32 getSize() const;
+
+ Common::MemoryReadStream *stream() const;
+
+private:
+ byte *_data;
+ int32 _size;
+
+ Common::MemoryReadStream *_stream;
+};
+
+class Resources {
+public:
+ Resources(GobEngine *vm);
+ ~Resources();
+
+ bool load(const Common::String &fileName);
+ void unload(bool del = true);
+
+ bool isLoaded() const;
+
+ Resource *getResource(uint16 id, int16 *width = 0, int16 *height = 0) const;
+ TextItem *getTextItem(uint16 id) const;
+
+ byte *getTexts() const;
+
+private:
+ // Structure sizes in the files
+ static const int kTOTResItemSize = 4 + 2 + 2 + 2;
+ static const int kTOTResTableSize = 2 + 1;
+ static const int kEXTResItemSize = 4 + 2 + 2 + 2;
+ static const int kEXTResTableSize = 2 + 1;
+ static const int kTOTTextTableSize = 2;
+ static const int kTOTTextItemSize = 2 + 2;
+
+ enum ResourceType {
+ kResourceTOT,
+ kResourceIM,
+ kResourceEXT,
+ kResourceEX
+ };
+
+ struct TOTResourceItem {
+ ResourceType type;
+ int16 size;
+ int16 width;
+ int16 height;
+ union {
+ int32 offset;
+ int32 index;
+ };
+ };
+
+ struct TOTResourceTable {
+ int16 itemsCount;
+ byte unknown;
+ TOTResourceItem *items;
+ uint32 dataOffset;
+
+ TOTResourceTable();
+ ~TOTResourceTable();
+ };
+
+ struct EXTResourceItem {
+ ResourceType type;
+ int32 offset;
+ uint16 size;
+ int16 width;
+ int16 height;
+ bool packed;
+ };
+
+ struct EXTResourceTable {
+ int16 itemsCount;
+ byte unknown;
+ EXTResourceItem *items;
+
+ EXTResourceTable();
+ ~EXTResourceTable();
+ };
+
+ struct TOTTextItem {
+ uint16 offset;
+ int16 size;
+ };
+
+ struct TOTTextTable {
+ bool needFree;
+ int16 itemsCount;
+
+ byte *data;
+ int32 size;
+
+ TOTTextItem *items;
+
+ TOTTextTable();
+ ~TOTTextTable();
+ };
+
+ GobEngine *_vm;
+
+ Common::String _totFile;
+ Common::String _extFile;
+ Common::String _exFile;
+
+ byte *_totData;
+ uint32 _totSize;
+
+ byte *_imData;
+ uint32 _imSize;
+
+ bool _hasLOM;
+ int32 _totResStart;
+
+ TOTResourceTable *_totResourceTable;
+ EXTResourceTable *_extResourceTable;
+ TOTTextTable *_totTextTable;
+
+ bool loadTOTResourceTable();
+ bool loadEXTResourceTable();
+ bool loadTOTTextTable(const Common::String &fileBase);
+ bool loadIMFile();
+ bool loadEXFile();
+
+ byte *loadTOTLocTexts(const Common::String &fileBase, int32 &size);
+ bool getLocTextFile(char *locTextFile, int language);
+ Common::String getLocTextFile(const Common::String &fileBase, int language);
+
+ Resource *getTOTResource(uint16 id) const;
+ Resource *getEXTResource(uint16 id) const;
+
+ byte *getTOTData(TOTResourceItem &totItem) const;
+ byte *getIMData(TOTResourceItem &totItem) const;
+ byte *getEXTData(EXTResourceItem &extItem, uint32 size) const;
+ byte *getEXData(EXTResourceItem &extItem, uint32 size) const;
+};
+
+} // End of namespace Gob
+
+#endif // GOB_RESOURCES_H
diff --git a/engines/gob/save/savefile.h b/engines/gob/save/savefile.h
index 989a37277e..615be8e0f2 100644
--- a/engines/gob/save/savefile.h
+++ b/engines/gob/save/savefile.h
@@ -163,7 +163,7 @@ public:
bool readPalette(const byte *palette);
/** Read a sprite into the part. */
bool readSprite(const SurfaceDesc &sprite);
-
+
/** Read size bytes of raw data into the sprite. */
bool readSpriteRaw(const byte *data, uint32 size);
diff --git a/engines/gob/save/saveload.cpp b/engines/gob/save/saveload.cpp
index abda2f8a65..81239f07dc 100644
--- a/engines/gob/save/saveload.cpp
+++ b/engines/gob/save/saveload.cpp
@@ -61,7 +61,7 @@ int32 SaveLoad::getSize(const char *fileName) {
int32 size = handler->getSize();
debugC(4, kDebugSaveLoad, "Size is %d", size);
-
+
return size;
}
diff --git a/engines/gob/save/saveload_v3.cpp b/engines/gob/save/saveload_v3.cpp
index 2f89644ee0..58232e6991 100644
--- a/engines/gob/save/saveload_v3.cpp
+++ b/engines/gob/save/saveload_v3.cpp
@@ -302,7 +302,7 @@ bool SaveLoad_v3::GameHandler::createReader(int slot) {
if (!_reader || (_reader->getSlot() != ((uint32) slot))) {
Common::String slotFile = _slotFile->build(slot);
-
+
if (slotFile.empty())
return false;
@@ -319,7 +319,7 @@ bool SaveLoad_v3::GameHandler::createReader(int slot) {
} else
_reader = new SaveReader(_usesScreenshots ? 3 : 2, slot, slotFile);
-
+
if (!_reader->load()) {
delete _reader;
_reader = 0;
@@ -337,7 +337,7 @@ bool SaveLoad_v3::GameHandler::createWriter(int slot) {
if (!_writer || (_writer->getSlot() != ((uint32) slot))) {
Common::String slotFile = _slotFile->build(slot);
-
+
if (slotFile.empty())
return false;
@@ -495,7 +495,7 @@ SaveLoad_v3::SaveLoad_v3(GobEngine *vm, const char *targetName, ScreenshotType s
_gameHandler = new GameHandler(vm, targetName, true);
_screenshotHandler = new ScreenshotHandler(vm, _gameHandler, sShotType);
}
-
+
_tempSpriteHandler = new TempSpriteHandler(vm);
_notesHandler = new NotesHandler(2560, vm, targetName);
diff --git a/engines/gob/save/saveload_v4.cpp b/engines/gob/save/saveload_v4.cpp
index 6e1d5208ff..06280af2a6 100644
--- a/engines/gob/save/saveload_v4.cpp
+++ b/engines/gob/save/saveload_v4.cpp
@@ -317,7 +317,7 @@ bool SaveLoad_v4::GameHandler::createReader(int slot) {
if (!_reader || (_reader->getSlot() != ((uint32) slot))) {
Common::String slotFile = _slotFile->build(slot);
-
+
if (slotFile.empty())
return false;
@@ -334,7 +334,7 @@ bool SaveLoad_v4::GameHandler::createReader(int slot) {
} else
_reader = new SaveReader(3, slot, slotFile);
-
+
if (!_reader->load()) {
delete _reader;
_reader = 0;
@@ -352,7 +352,7 @@ bool SaveLoad_v4::GameHandler::createWriter(int slot) {
if (!_writer || (_writer->getSlot() != ((uint32) slot))) {
Common::String slotFile = _slotFile->build(slot);
-
+
if (slotFile.empty())
return false;
diff --git a/engines/gob/scenery.cpp b/engines/gob/scenery.cpp
index 71750509b4..7a4b8ad868 100644
--- a/engines/gob/scenery.cpp
+++ b/engines/gob/scenery.cpp
@@ -31,6 +31,8 @@
#include "gob/global.h"
#include "gob/draw.h"
#include "gob/game.h"
+#include "gob/script.h"
+#include "gob/resources.h"
#include "gob/inter.h"
#include "gob/map.h"
#include "gob/videoplayer.h"
@@ -39,33 +41,33 @@ namespace Gob {
Scenery::Scenery(GobEngine *vm) : _vm(vm) {
for (int i = 0; i < 20; i++) {
- _spriteRefs[i] = 0;
+ _spriteRefs[i] = 0;
_spriteResId[i] = 0;
}
for (int i = 0; i < 10; i++) {
_staticPictCount[i] = 0;
- _staticResId[i] = 0;
- _animPictCount[i] = 0;
- _animResId[i] = 0;
+ _staticResId[i] = 0;
+ _animPictCount[i] = 0;
+ _animResId[i] = 0;
}
- _curStatic = 0;
+ _curStatic = 0;
_curStaticLayer = 0;
- _toRedrawLeft = 0;
- _toRedrawRight = 0;
- _toRedrawTop = 0;
+ _toRedrawLeft = 0;
+ _toRedrawRight = 0;
+ _toRedrawTop = 0;
_toRedrawBottom = 0;
- _animTop = 0;
+ _animTop = 0;
_animLeft = 0;
_pCaptureCounter = 0;
for (int i = 0; i < 70; i++ ) {
_staticPictToSprite[i] = 0;
- _animPictToSprite[i] = 0;
+ _animPictToSprite[i] = 0;
}
}
@@ -78,17 +80,17 @@ Scenery::~Scenery() {
void Scenery::init() {
for (int i = 0; i < 10; i++) {
- _animPictCount[i] = 0;
+ _animPictCount[i] = 0;
_staticPictCount[i] = -1;
}
for (int i = 0; i < 20; i++) {
- _spriteRefs[i] = 0;
+ _spriteRefs[i] = 0;
_spriteResId[i] = -1;
}
_curStaticLayer = -1;
- _curStatic = -1;
+ _curStatic = -1;
}
int16 Scenery::loadStatic(char search) {
@@ -97,28 +99,26 @@ int16 Scenery::loadStatic(char search) {
int16 picsCount;
int16 resId;
int16 sceneryIndex;
- byte *extData = 0;
- byte *dataPtr;
Static *ptr;
int16 width;
int16 height;
int16 sprResId;
int16 sprIndex;
- _vm->_inter->evalExpr(&sceneryIndex);
+ _vm->_game->_script->evalExpr(&sceneryIndex);
- size = _vm->_inter->load16();
- backsPtr = (int16 *) _vm->_global->_inter_execPtr;
- _vm->_global->_inter_execPtr += size * 2;
- picsCount = _vm->_inter->load16();
- resId = _vm->_inter->load16();
+ size = _vm->_game->_script->readInt16();
+ backsPtr = (int16 *) (_vm->_game->_script->getData() + _vm->_game->_script->pos());
+ _vm->_game->_script->skip(size * 2);
+ picsCount = _vm->_game->_script->readInt16();
+ resId = _vm->_game->_script->readInt16();
if (search) {
int i;
for (i = 0; i < 10; i++) {
if ((_staticPictCount[i] != -1) && (_staticResId[i] == resId)) {
- _vm->_global->_inter_execPtr += 8 * _staticPictCount[i];
+ _vm->_game->_script->skip(8 * _staticPictCount[i]);
return i;
}
@@ -128,52 +128,54 @@ int16 Scenery::loadStatic(char search) {
}
_staticPictCount[sceneryIndex] = picsCount;
- _staticResId[sceneryIndex] = resId;
+ _staticResId[sceneryIndex] = resId;
- if (resId >= 30000) {
- extData = _vm->_game->loadExtData(resId, 0, 0);
- dataPtr = extData;
- } else
- dataPtr = _vm->_game->loadTotResource(resId);
+ Resource *resource = _vm->_game->_resources->getResource((uint16) resId);
+ if (!resource)
+ return 0;
ptr = &_statics[sceneryIndex];
- ptr->layersCount = (int16) READ_LE_UINT16(dataPtr);
- dataPtr += 2;
+ ptr->layersCount = resource->stream()->readSint16LE();
ptr->layers = new StaticLayer[ptr->layersCount];
for (int i = 0; i < ptr->layersCount; i++) {
- int16 offset = READ_LE_UINT16(dataPtr + i * 2);
- Common::MemoryReadStream layerData(dataPtr + offset, 4294967295U);
+ Common::SeekableReadStream &layerData = *resource->stream();
- ptr->layers[i].planeCount = layerData.readSint16LE();
+ layerData.seek(2 + i * 2);
+ layerData.seek(layerData.readUint16LE());
- ptr->layers[i].planes = new StaticPlane[ptr->layers[i].planeCount];
- for (int j = 0; j < ptr->layers[i].planeCount; ++j) {
- ptr->layers[i].planes[j].pictIndex = layerData.readByte();
- ptr->layers[i].planes[j].pieceIndex = layerData.readByte();
- ptr->layers[i].planes[j].drawOrder = layerData.readByte();
- ptr->layers[i].planes[j].destX = layerData.readSint16LE();
- ptr->layers[i].planes[j].destY = layerData.readSint16LE();
- ptr->layers[i].planes[j].transp = layerData.readSByte();
- }
+ ptr->layers[i].backResId = layerData.readSint16LE();
+ ptr->layers[i].planeCount = layerData.readSint16LE();
+ if (ptr->layers[i].planeCount > 0) {
+ ptr->layers[i].planes = new StaticPlane[ptr->layers[i].planeCount];
+ for (int j = 0; j < ptr->layers[i].planeCount; j++) {
+ ptr->layers[i].planes[j].pictIndex = layerData.readByte();
+ ptr->layers[i].planes[j].pieceIndex = layerData.readByte();
+ ptr->layers[i].planes[j].drawOrder = layerData.readByte();
+ ptr->layers[i].planes[j].destX = layerData.readSint16LE();
+ ptr->layers[i].planes[j].destY = layerData.readSint16LE();
+ ptr->layers[i].planes[j].transp = layerData.readSByte();
+ }
+ } else
+ ptr->layers[i].planes = 0;
ptr->layers[i].backResId = (int16) READ_LE_UINT16(backsPtr);
backsPtr++;
}
- ptr->pieces = new PieceDesc*[picsCount];
+ ptr->pieces = new PieceDesc*[picsCount];
ptr->piecesCount = new uint32[picsCount];
for (int i = 0; i < picsCount; i++) {
- int16 pictDescId = _vm->_inter->load16();
+ int16 pictDescId = _vm->_game->_script->readInt16();
loadPieces(pictDescId, ptr->pieces[i], ptr->piecesCount[i]);
- width = _vm->_inter->load16();
- height = _vm->_inter->load16();
- sprResId = _vm->_inter->load16();
+ width = _vm->_game->_script->readInt16();
+ height = _vm->_game->_script->readInt16();
+ sprResId = _vm->_game->_script->readInt16();
for (sprIndex = 0; sprIndex < 20; sprIndex++) {
if (_spriteResId[sprIndex] == sprResId)
break;
@@ -183,9 +185,7 @@ int16 Scenery::loadStatic(char search) {
_staticPictToSprite[7 * sceneryIndex + i] = sprIndex;
_spriteRefs[sprIndex]++;
} else {
- for (sprIndex = 19; _vm->_draw->_spritesArray[sprIndex] != 0;
- sprIndex--)
- ;
+ for (sprIndex = 19; _vm->_draw->_spritesArray[sprIndex] != 0; sprIndex--);
_staticPictToSprite[7 * sceneryIndex + i] = sprIndex;
_spriteRefs[sprIndex] = 1;
@@ -193,17 +193,16 @@ int16 Scenery::loadStatic(char search) {
_vm->_draw->initSpriteSurf(sprIndex, width, height, 2);
_vm->_video->clearSurf(*_vm->_draw->_spritesArray[sprIndex]);
- _vm->_draw->_destSurface = sprIndex;
- _vm->_draw->_spriteLeft = sprResId;
+ _vm->_draw->_destSurface = sprIndex;
+ _vm->_draw->_spriteLeft = sprResId;
_vm->_draw->_transparency = 0;
- _vm->_draw->_destSpriteX = 0;
- _vm->_draw->_destSpriteY = 0;
+ _vm->_draw->_destSpriteX = 0;
+ _vm->_draw->_destSpriteY = 0;
_vm->_draw->spriteOperation(DRAW_LOADSPRITE);
}
}
- delete[] extData;
-
+ delete resource;
return sceneryIndex + 100;
}
@@ -211,7 +210,7 @@ void Scenery::freeStatic(int16 index) {
int16 spr;
if (index == -1)
- _vm->_inter->evalExpr(&index);
+ _vm->_game->_script->evalExpr(&index);
if (_staticPictCount[index] == -1)
return;
@@ -229,12 +228,13 @@ void Scenery::freeStatic(int16 index) {
for (int i = 0; i < _statics[index].layersCount; i++)
delete[] _statics[index].layers[i].planes;
+
delete[] _statics[index].layers;
delete[] _statics[index].pieces;
delete[] _statics[index].piecesCount;
_statics[index].layersCount = 0;
- _staticPictCount[index] = -1;
+ _staticPictCount[index] = -1;
}
void Scenery::renderStatic(int16 scenery, int16 layer) {
@@ -261,22 +261,21 @@ void Scenery::renderStatic(int16 scenery, int16 layer) {
_vm->_draw->_spriteLeft = layerPtr->backResId;
if (_vm->_draw->_spriteLeft != -1) {
- _vm->_draw->_destSpriteX = 0;
- _vm->_draw->_destSpriteY = 0;
- _vm->_draw->_destSurface = 21;
- _vm->_draw->_transparency = 0;
+ _vm->_draw->_destSpriteX = 0;
+ _vm->_draw->_destSpriteY = 0;
+ _vm->_draw->_destSurface = 21;
+ _vm->_draw->_transparency = 0;
_vm->_draw->spriteOperation(DRAW_LOADSPRITE);
}
planeCount = layerPtr->planeCount;
for (order = 0; order < 100; order++) {
- for (plane = 0, planePtr = layerPtr->planes;
- plane < planeCount; plane++, planePtr++) {
+ for (plane = 0, planePtr = layerPtr->planes; plane < planeCount; plane++, planePtr++) {
if (planePtr->drawOrder != order)
continue;
pieceIndex = planePtr->pieceIndex;
- pictIndex = planePtr->pictIndex - 1;
+ pictIndex = planePtr->pictIndex - 1;
if (pictIndex >= _staticPictCount[scenery])
continue;
@@ -289,19 +288,19 @@ void Scenery::renderStatic(int16 scenery, int16 layer) {
_vm->_draw->_destSpriteX = planePtr->destX;
_vm->_draw->_destSpriteY = planePtr->destY;
- left = ptr->pieces[pictIndex][pieceIndex].left;
- right = ptr->pieces[pictIndex][pieceIndex].right;
- top = ptr->pieces[pictIndex][pieceIndex].top;
+ left = ptr->pieces[pictIndex][pieceIndex].left;
+ right = ptr->pieces[pictIndex][pieceIndex].right;
+ top = ptr->pieces[pictIndex][pieceIndex].top;
bottom = ptr->pieces[pictIndex][pieceIndex].bottom;
_vm->_draw->_sourceSurface =
_staticPictToSprite[scenery * 7 + pictIndex];
- _vm->_draw->_destSurface = 21;
- _vm->_draw->_spriteLeft = left;
- _vm->_draw->_spriteTop = top;
- _vm->_draw->_spriteRight = right - left + 1;
- _vm->_draw->_spriteBottom = bottom - top + 1;
- _vm->_draw->_transparency = planePtr->transp ? 3 : 0;
+ _vm->_draw->_destSurface = 21;
+ _vm->_draw->_spriteLeft = left;
+ _vm->_draw->_spriteTop = top;
+ _vm->_draw->_spriteRight = right - left + 1;
+ _vm->_draw->_spriteBottom = bottom - top + 1;
+ _vm->_draw->_transparency = planePtr->transp ? 3 : 0;
_vm->_draw->spriteOperation(DRAW_BLITSURF);
}
}
@@ -337,7 +336,7 @@ void Scenery::updateStatic(int16 orderFrom, byte index, byte layer) {
continue;
pieceIndex = planePtr->pieceIndex;
- pictIndex = planePtr->pictIndex - 1;
+ pictIndex = planePtr->pictIndex - 1;
if (pictIndex >= _staticPictCount[index])
continue;
@@ -351,9 +350,9 @@ void Scenery::updateStatic(int16 orderFrom, byte index, byte layer) {
_vm->_draw->_destSpriteX = planePtr->destX;
_vm->_draw->_destSpriteY = planePtr->destY;
- left = pictPtr[pictIndex][pieceIndex].left;
- right = pictPtr[pictIndex][pieceIndex].right;
- top = pictPtr[pictIndex][pieceIndex].top;
+ left = pictPtr[pictIndex][pieceIndex].left;
+ right = pictPtr[pictIndex][pieceIndex].right;
+ top = pictPtr[pictIndex][pieceIndex].top;
bottom = pictPtr[pictIndex][pieceIndex].bottom;
if (_vm->_draw->_destSpriteX > _toRedrawRight)
@@ -372,10 +371,10 @@ void Scenery::updateStatic(int16 orderFrom, byte index, byte layer) {
_vm->_draw->_destSpriteY = _toRedrawTop;
}
- _vm->_draw->_spriteLeft = left;
- _vm->_draw->_spriteTop = top;
- _vm->_draw->_spriteRight = right - left + 1;
- _vm->_draw->_spriteBottom = bottom - top + 1;
+ _vm->_draw->_spriteLeft = left;
+ _vm->_draw->_spriteTop = top;
+ _vm->_draw->_spriteRight = right - left + 1;
+ _vm->_draw->_spriteBottom = bottom - top + 1;
if ((_vm->_draw->_spriteRight <= 0) ||
(_vm->_draw->_spriteBottom <= 0))
@@ -393,8 +392,8 @@ void Scenery::updateStatic(int16 orderFrom, byte index, byte layer) {
_vm->_draw->_sourceSurface =
_staticPictToSprite[index * 7 + pictIndex];
- _vm->_draw->_destSurface = 21;
- _vm->_draw->_transparency = planePtr->transp ? 3 : 0;
+ _vm->_draw->_destSurface = 21;
+ _vm->_draw->_transparency = planePtr->transp ? 3 : 0;
_vm->_draw->spriteOperation(DRAW_BLITSURF);
}
}
@@ -422,8 +421,6 @@ int16 Scenery::loadAnim(char search) {
int16 j;
int16 sceneryIndex;
int16 framesCount;
- byte *extData;
- byte *dataPtr;
Animation *ptr;
int16 width;
int16 height;
@@ -431,15 +428,14 @@ int16 Scenery::loadAnim(char search) {
int16 sprIndex;
uint32 layerPos;
- extData = 0;
- _vm->_inter->evalExpr(&sceneryIndex);
- picsCount = _vm->_inter->load16();
- resId = _vm->_inter->load16();
+ _vm->_game->_script->evalExpr(&sceneryIndex);
+ picsCount = _vm->_game->_script->readInt16();
+ resId = _vm->_game->_script->readInt16();
if (search) {
for (i = 0; i < 10; i++) {
if ((_animPictCount[i] != 0) && (_animResId[i] == resId)) {
- _vm->_global->_inter_execPtr += 8 * _animPictCount[i];
+ _vm->_game->_script->skip(8 * _animPictCount[i]);
return i;
}
@@ -451,50 +447,50 @@ int16 Scenery::loadAnim(char search) {
_animPictCount[sceneryIndex] = picsCount;
_animResId[sceneryIndex] = resId;
- if (resId >= 30000) {
- extData = _vm->_game->loadExtData(resId, 0, 0);
- dataPtr = extData;
- } else
- dataPtr = _vm->_game->loadTotResource(resId);
+ Resource *resource = _vm->_game->_resources->getResource((uint16) resId);
+ if (!resource)
+ return 0;
ptr = &_animations[sceneryIndex];
- ptr->layersCount = READ_LE_UINT16(dataPtr);
- dataPtr += 2;
+ ptr->layersCount = resource->stream()->readSint16LE();
ptr->layers = new AnimLayer[ptr->layersCount];
for (i = 0; i < ptr->layersCount; i++) {
- int16 offset = READ_LE_UINT16(dataPtr + i * 2);
- Common::MemoryReadStream layerData(dataPtr + offset - 2, 4294967295U);
-
- ptr->layers[i].unknown0 = layerData.readSint16LE();
- ptr->layers[i].posX = layerData.readSint16LE();
- ptr->layers[i].posY = layerData.readSint16LE();
- ptr->layers[i].animDeltaX = layerData.readSint16LE();
- ptr->layers[i].animDeltaY = layerData.readSint16LE();
- ptr->layers[i].transp = layerData.readSByte();
+ Common::SeekableReadStream &layerData = *resource->stream();
+
+ layerData.seek(2 + i * 2);
+ layerData.seek(layerData.readUint16LE());
+
+ ptr->layers[i].unknown0 = layerData.readSint16LE();
+ ptr->layers[i].posX = layerData.readSint16LE();
+ ptr->layers[i].posY = layerData.readSint16LE();
+ ptr->layers[i].animDeltaX = layerData.readSint16LE();
+ ptr->layers[i].animDeltaY = layerData.readSint16LE();
+ ptr->layers[i].transp = layerData.readSByte();
ptr->layers[i].framesCount = layerData.readSint16LE();
+ // Going through the AnimFramePiece, finding the end for each
layerPos = layerData.pos();
framesCount = 0;
- layerData.seek(4, SEEK_CUR);
- for (j = 0; j < ptr->layers[i].framesCount;
- j++, framesCount++, layerData.seek(4, SEEK_CUR)) {
+ for (j = 0; j < ptr->layers[i].framesCount; j++) {
+ layerData.skip(4); // pictIndex, pieceIndex, destX, destY
while (layerData.readByte() == 1) {
framesCount++;
- layerData.seek(4, SEEK_CUR);
+ layerData.skip(4); // pictIndex, pieceIndex, destX, destY
}
+ framesCount++;
}
layerData.seek(layerPos);
ptr->layers[i].frames = new AnimFramePiece[framesCount];
for (j = 0; j < framesCount; j++) {
- ptr->layers[i].frames[j].pictIndex = layerData.readByte();
+ ptr->layers[i].frames[j].pictIndex = layerData.readByte();
ptr->layers[i].frames[j].pieceIndex = layerData.readByte();
- ptr->layers[i].frames[j].destX = layerData.readSByte();
- ptr->layers[i].frames[j].destY = layerData.readSByte();
- ptr->layers[i].frames[j].notFinal = layerData.readSByte();
+ ptr->layers[i].frames[j].destX = layerData.readSByte();
+ ptr->layers[i].frames[j].destY = layerData.readSByte();
+ ptr->layers[i].frames[j].notFinal = layerData.readSByte();
}
}
@@ -502,13 +498,13 @@ int16 Scenery::loadAnim(char search) {
ptr->piecesCount = new uint32[picsCount];
for (i = 0; i < picsCount; i++) {
- int16 pictDescId = _vm->_inter->load16();
+ int16 pictDescId = _vm->_game->_script->readInt16();
loadPieces(pictDescId, ptr->pieces[i], ptr->piecesCount[i]);
- width = _vm->_inter->load16();
- height = _vm->_inter->load16();
- sprResId = _vm->_inter->load16();
+ width = _vm->_game->_script->readInt16();
+ height = _vm->_game->_script->readInt16();
+ sprResId = _vm->_game->_script->readInt16();
for (sprIndex = 0; sprIndex < 20; sprIndex++)
if (_spriteResId[sprIndex] == sprResId)
break;
@@ -522,22 +518,21 @@ int16 Scenery::loadAnim(char search) {
;
_animPictToSprite[7 * sceneryIndex + i] = sprIndex;
- _spriteRefs[sprIndex] = 1;
+ _spriteRefs[sprIndex] = 1;
_spriteResId[sprIndex] = sprResId;
_vm->_draw->initSpriteSurf(sprIndex, width, height, 2);
_vm->_video->clearSurf(*_vm->_draw->_spritesArray[sprIndex]);
- _vm->_draw->_destSurface = sprIndex;
- _vm->_draw->_spriteLeft = sprResId;
+ _vm->_draw->_destSurface = sprIndex;
+ _vm->_draw->_spriteLeft = sprResId;
_vm->_draw->_transparency = 0;
- _vm->_draw->_destSpriteX = 0;
- _vm->_draw->_destSpriteY = 0;
+ _vm->_draw->_destSpriteX = 0;
+ _vm->_draw->_destSpriteY = 0;
_vm->_draw->spriteOperation(DRAW_LOADSPRITE);
}
}
- delete[] extData;
-
+ delete resource;
return sceneryIndex + 100;
}
@@ -545,7 +540,7 @@ void Scenery::freeAnim(int16 index) {
int16 spr;
if (index == -1)
- _vm->_inter->evalExpr(&index);
+ _vm->_game->_script->evalExpr(&index);
if (_animPictCount[index] == 0)
return;
@@ -563,6 +558,7 @@ void Scenery::freeAnim(int16 index) {
for (int i = 0; i < _animations[index].layersCount; i++)
delete[] _animations[index].layers[i].frames;
+
delete[] _animations[index].layers;
delete[] _animations[index].pieces;
delete[] _animations[index].piecesCount;
@@ -607,8 +603,8 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
return;
_vm->_game->capturePush(_toRedrawLeft, _toRedrawTop,
- _toRedrawRight - _toRedrawLeft + 1,
- _toRedrawBottom - _toRedrawTop + 1);
+ _toRedrawRight - _toRedrawLeft + 1,
+ _toRedrawBottom - _toRedrawTop + 1);
*_pCaptureCounter = *_pCaptureCounter + 1;
}
@@ -628,7 +624,7 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
while (_vm->_vidPlayer->getCurrentFrame(obj.videoSlot - 1) <= frame)
_vm->_vidPlayer->slotPlay(obj.videoSlot - 1);
} else {
- int16 curFrame = _vm->_vidPlayer->getCurrentFrame(obj.videoSlot - 1);
+ int16 curFrame = _vm->_vidPlayer->getCurrentFrame(obj.videoSlot - 1);
uint8 frameWrap = curFrame / 256;
frame = (frame + 1) % 256;
@@ -636,17 +632,17 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
_vm->_vidPlayer->slotPlay(obj.videoSlot - 1);
}
- destX = 0;
- destY = 0;
- left = *(obj.pPosX);
- top = *(obj.pPosY);
- right = left + _vm->_vidPlayer->getWidth(obj.videoSlot - 1) - 1;
- bottom = top + _vm->_vidPlayer->getHeight(obj.videoSlot - 1) - 1;
+ destX = 0;
+ destY = 0;
+ left = *(obj.pPosX);
+ top = *(obj.pPosY);
+ right = left + _vm->_vidPlayer->getWidth(obj.videoSlot - 1) - 1;
+ bottom = top + _vm->_vidPlayer->getHeight(obj.videoSlot - 1) - 1;
if (flags & 2) {
if (left < _vm->_mult->_animLeft) {
destX += _vm->_mult->_animLeft - left;
- left = _vm->_mult->_animLeft;
+ left = _vm->_mult->_animLeft;
}
if ((_vm->_mult->_animLeft + _vm->_mult->_animWidth) <= right)
@@ -654,7 +650,7 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
if (top < _vm->_mult->_animTop) {
destY += _vm->_mult->_animTop - top;
- top = _vm->_mult->_animTop;
+ top = _vm->_mult->_animTop;
}
if ((_vm->_mult->_animTop + _vm->_mult->_animHeight) <= bottom)
@@ -663,7 +659,7 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
} else if (flags & 4) {
if (left < _toRedrawLeft) {
destX += _toRedrawLeft - left;
- left = _toRedrawLeft;
+ left = _toRedrawLeft;
}
if (right > _toRedrawRight)
@@ -671,16 +667,16 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
if (top < _toRedrawTop) {
destY += _toRedrawTop - top;
- top = _toRedrawTop;
+ top = _toRedrawTop;
}
if (bottom > _toRedrawBottom)
bottom = _toRedrawBottom;
} else {
- _toRedrawTop = top;
- _toRedrawLeft = left;
- _toRedrawRight = right;
+ _toRedrawTop = top;
+ _toRedrawLeft = left;
+ _toRedrawRight = right;
_toRedrawBottom = bottom;
}
@@ -690,7 +686,7 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
if (left < _vm->_mult->_animLeft) {
destX += _vm->_mult->_animLeft - left;
- left = _vm->_mult->_animLeft;
+ left = _vm->_mult->_animLeft;
}
if ((_vm->_mult->_animLeft + _vm->_mult->_animWidth) <= right)
@@ -698,40 +694,40 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
if (top < _vm->_mult->_animTop) {
destY += _vm->_mult->_animTop - top;
- top = _vm->_mult->_animTop;
+ top = _vm->_mult->_animTop;
}
if ((_vm->_mult->_animTop + _vm->_mult->_animHeight) <= bottom)
bottom = _vm->_mult->_animTop + _vm->_mult->_animHeight - 1;
- _vm->_draw->_spriteLeft = destX;
- _vm->_draw->_spriteTop = destY;
- _vm->_draw->_spriteRight = right - left + 1;
- _vm->_draw->_spriteBottom = bottom - top + 1;
- _vm->_draw->_destSpriteX = left;
- _vm->_draw->_destSpriteY = top;
+ _vm->_draw->_spriteLeft = destX;
+ _vm->_draw->_spriteTop = destY;
+ _vm->_draw->_spriteRight = right - left + 1;
+ _vm->_draw->_spriteBottom = bottom - top + 1;
+ _vm->_draw->_destSpriteX = left;
+ _vm->_draw->_destSpriteY = top;
_vm->_draw->_transparency = layer;
if (layer & 0x80)
_vm->_draw->_spriteLeft = _vm->_vidPlayer->getWidth(obj.videoSlot - 1) -
(destX + _vm->_draw->_spriteRight);
_vm->_vidPlayer->slotCopyFrame(obj.videoSlot - 1, _vm->_draw->_backSurface->getVidMem(),
- _vm->_draw->_spriteLeft, _vm->_draw->_spriteTop,
+ _vm->_draw->_spriteLeft, _vm->_draw->_spriteTop,
_vm->_draw->_spriteRight, _vm->_draw->_spriteBottom,
_vm->_draw->_destSpriteX, _vm->_draw->_destSpriteY,
_vm->_draw->_backSurface->getWidth(),
(_vm->_draw->_transparency != 0) ? 0 : -1);
_vm->_draw->invalidateRect(_vm->_draw->_destSpriteX, _vm->_draw->_destSpriteY,
- _vm->_draw->_destSpriteX + _vm->_draw->_spriteRight - 1,
+ _vm->_draw->_destSpriteX + _vm->_draw->_spriteRight - 1,
_vm->_draw->_destSpriteY + _vm->_draw->_spriteBottom - 1);
}
if (!(flags & 4)) {
- _animLeft = _toRedrawLeft = left;
- _animTop = _toRedrawTop = top;
- _animRight = _toRedrawRight = right;
+ _animLeft = _toRedrawLeft = left;
+ _animTop = _toRedrawTop = top;
+ _animRight = _toRedrawRight = right;
_animBottom = _toRedrawBottom = bottom;
}
@@ -757,13 +753,13 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
return;
_vm->_game->capturePush(_toRedrawLeft, _toRedrawTop,
- _toRedrawRight - _toRedrawLeft + 1,
- _toRedrawBottom - _toRedrawTop + 1);
+ _toRedrawRight - _toRedrawLeft + 1,
+ _toRedrawBottom - _toRedrawTop + 1);
*_pCaptureCounter = *_pCaptureCounter + 1;
}
- pictPtr = _animations[animation].pieces;
+ pictPtr = _animations[animation].pieces;
framePtr = layerPtr->frames;
for (i = 0; i < frame; i++, framePtr++)
@@ -771,9 +767,9 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
framePtr++;
if (flags & 4) {
- _toRedrawLeft = MAX(_toRedrawLeft, _vm->_mult->_animLeft);
- _toRedrawTop = MAX(_toRedrawTop, _vm->_mult->_animTop);
- _toRedrawRight = MIN(_toRedrawRight,
+ _toRedrawLeft = MAX(_toRedrawLeft, _vm->_mult->_animLeft);
+ _toRedrawTop = MAX(_toRedrawTop, _vm->_mult->_animTop);
+ _toRedrawRight = MIN(_toRedrawRight,
(int16)(_vm->_mult->_animLeft + _vm->_mult->_animWidth - 1));
_toRedrawBottom = MIN(_toRedrawBottom,
(int16)(_vm->_mult->_animTop + _vm->_mult->_animHeight - 1));
@@ -844,7 +840,7 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
(_vm->_mult->_animLeft + _vm->_mult->_animWidth) + 1;
if (destY < _vm->_mult->_animTop) {
- top += _vm->_mult->_animTop - destY;
+ top += _vm->_mult->_animTop - destY;
destY = _vm->_mult->_animTop;
}
@@ -863,7 +859,7 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
right -= destX + right - left - _toRedrawRight;
if (destY < _toRedrawTop) {
- top += _toRedrawTop - destY;
+ top += _toRedrawTop - destY;
destY = _toRedrawTop;
}
@@ -877,33 +873,33 @@ void Scenery::updateAnim(int16 layer, int16 frame, int16 animation, int16 flags,
if (doDraw) {
_vm->_draw->_sourceSurface =
_animPictToSprite[animation * 7 + pictIndex];
- _vm->_draw->_destSurface = 21;
+ _vm->_draw->_destSurface = 21;
- _vm->_draw->_spriteLeft = left;
- _vm->_draw->_spriteTop = top;
- _vm->_draw->_spriteRight = right - left + 1;
+ _vm->_draw->_spriteLeft = left;
+ _vm->_draw->_spriteTop = top;
+ _vm->_draw->_spriteRight = right - left + 1;
_vm->_draw->_spriteBottom = bottom - top + 1;
- _vm->_draw->_destSpriteX = destX;
- _vm->_draw->_destSpriteY = destY;
+ _vm->_draw->_destSpriteX = destX;
+ _vm->_draw->_destSpriteY = destY;
_vm->_draw->_transparency = transp;
_vm->_draw->spriteOperation(DRAW_BLITSURF);
}
if (!(flags & 4)) {
if (_toRedrawLeft == -12345) {
- _toRedrawLeft = destX;
- _animLeft = destX;
- _toRedrawTop = destY;
- _animTop = destY;
- _toRedrawRight = destX + right - left;
- _animRight = destX + right - left;
+ _toRedrawLeft = destX;
+ _animLeft = destX;
+ _toRedrawTop = destY;
+ _animTop = destY;
+ _toRedrawRight = destX + right - left;
+ _animRight = destX + right - left;
_toRedrawBottom = destY + bottom - top;
- _animBottom = destY + bottom - top;
+ _animBottom = destY + bottom - top;
} else {
- _toRedrawLeft = MIN(_toRedrawLeft, destX);
- _toRedrawTop = MIN(_toRedrawTop, destY);
- _toRedrawRight =
- MAX(_toRedrawRight, (int16)(destX + right - left));
+ _toRedrawLeft = MIN(_toRedrawLeft, destX);
+ _toRedrawTop = MIN(_toRedrawTop, destY);
+ _toRedrawRight =
+ MAX(_toRedrawRight, (int16)(destX + right - left));
_toRedrawBottom =
MAX(_toRedrawBottom, (int16)(destY + bottom - top));
}
@@ -952,41 +948,23 @@ Scenery::AnimLayer *Scenery::getAnimLayer(uint16 index, uint16 layer) {
}
void Scenery::loadPieces(int16 pictDescId, PieceDesc *&pieceDesc, uint32 &piecesCount) {
- byte *data;
- uint32 size;
- bool fromExt = false;
-
- if (pictDescId >= 30000) {
- fromExt = true;
-
- uint32 eSize;
-
- data = _vm->_game->loadExtData(pictDescId, 0, 0, &eSize);
- size = eSize;
- } else {
- int16 tSize;
-
- data = _vm->_game->loadTotResource(pictDescId, &tSize);
- size = tSize;
+ Resource *resource = _vm->_game->_resources->getResource(pictDescId);
+ if (!resource) {
+ warning("Scenery::loadPieces(): Can't load %d", pictDescId);
+ return;
}
- if (!data)
- error("Scenery::loadPieces(): Can't load pictDescId %d", pictDescId);
-
- piecesCount = size / 8;
+ piecesCount = resource->getSize() / 8;
pieceDesc = new PieceDesc[piecesCount];
- Common::MemoryReadStream pieceData(data, size);
-
for (uint32 i = 0; i < piecesCount; i++) {
- pieceDesc[i].left = (int16) pieceData.readUint16LE();
- pieceDesc[i].right = (int16) pieceData.readUint16LE();
- pieceDesc[i].top = (int16) pieceData.readUint16LE();
- pieceDesc[i].bottom = (int16) pieceData.readUint16LE();
+ pieceDesc[i].left = resource->stream()->readSint16LE();
+ pieceDesc[i].right = resource->stream()->readSint16LE();
+ pieceDesc[i].top = resource->stream()->readSint16LE();
+ pieceDesc[i].bottom = resource->stream()->readSint16LE();
}
- if (fromExt)
- delete[] data;
+ delete resource;
}
} // End of namespace Gob
diff --git a/engines/gob/script.cpp b/engines/gob/script.cpp
new file mode 100644
index 0000000000..6162e943bf
--- /dev/null
+++ b/engines/gob/script.cpp
@@ -0,0 +1,522 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/util.h"
+#include "common/endian.h"
+
+#include "gob/gob.h"
+#include "gob/script.h"
+#include "gob/dataio.h"
+#include "gob/expression.h"
+#include "gob/videoplayer.h"
+
+namespace Gob {
+
+Script::Script(GobEngine *vm) : _vm(vm) {
+ _expression = new Expression(vm);
+
+ _finished = true;
+
+ _totData = 0;
+ _totPtr = 0;
+ _totSize = 0;
+
+ _lomHandle = -1;
+
+ memset(&_totProperties, 0, sizeof(TOTFile::Properties));
+}
+
+Script::~Script() {
+ unload();
+
+ delete _expression;
+}
+
+uint32 Script::read(byte *data, int32 size) {
+ int32 toRead = MIN<int32>(size, _totSize - (_totPtr - _totData));
+
+ if (toRead < 1)
+ return 0;
+
+ memcpy(data, _totPtr, toRead);
+ _totPtr += toRead;
+
+ return toRead;
+}
+
+uint32 Script::peek(byte *data, int32 size, int32 offset) const {
+ int32 totOffset = ((_totPtr + offset) - _totData);
+
+ if (totOffset < 1)
+ return 0;
+ if (((uint32) totOffset) >= _totSize)
+ return 0;
+
+ int32 toPeek = MIN<int32>(size, _totSize - totOffset);
+ if (toPeek < 1)
+ return 0;
+
+ memcpy(data, _totPtr + offset, toPeek);
+
+ return toPeek;
+}
+
+int32 Script::pos() const {
+ if (!_totData)
+ return -1;
+
+ return _totPtr - _totData;
+}
+
+int32 Script::getSize() const {
+ if (!_totData)
+ return -1;
+
+ return _totSize;
+}
+
+bool Script::seek(int32 offset, int whence) {
+ if (!_totData)
+ return false;
+
+ if (whence == SEEK_CUR)
+ offset += pos();
+ else if (whence == SEEK_END)
+ offset += _totSize;
+
+ if ((offset < 0) || (((uint32) offset) >= _totSize))
+ return false;
+
+ // Cannot seek into the header
+ if (offset < 128) {
+ _finished = true;
+ return false;
+ }
+
+ // A successful seek means the script file continues to be executed
+ _finished = false;
+
+ _totPtr = _totData + offset;
+
+ return true;
+}
+
+bool Script::skip(int32 offset) {
+ return seek(offset, SEEK_CUR);
+}
+
+int32 Script::getOffset(byte *ptr) const {
+ if (!_totData)
+ return -1;
+
+ if ((ptr < _totData) || (ptr >= (_totData + _totSize)))
+ return -1;
+
+ return ptr - _totData;
+}
+
+byte *Script::getData(int32 offset) const {
+ if (!_totData)
+ return 0;
+ if ((offset < 0) || (((uint32) offset) >= _totSize))
+ return 0;
+
+ return _totData + offset;
+}
+
+byte *Script::getData() {
+ return _totData;
+}
+
+byte Script::readByte() {
+ byte v;
+
+ read(&v, 1);
+
+ return v;
+}
+
+char Script::readChar() {
+ return (char) readByte();
+}
+
+uint8 Script::readUint8() {
+ return (uint8) readByte();
+}
+
+uint16 Script::readUint16() {
+ byte v[2];
+
+ read(v, 2);
+
+ return READ_LE_UINT16(v);
+}
+
+uint32 Script::readUint32() {
+ byte v[4];
+
+ read(v, 4);
+
+ return READ_LE_UINT32(v);
+}
+
+int8 Script::readInt8() {
+ return (int8) readByte();
+}
+
+int16 Script::readInt16() {
+ return (int16) readUint16();
+}
+
+int32 Script::readInt32() {
+ return (int32) readUint32();
+}
+
+char *Script::readString(int32 length) {
+ if (length < 0) {
+ length = 0;
+ while (_totPtr[length++] != '\0');
+ }
+
+ char *string = (char *) _totPtr;
+
+ _totPtr += length;
+
+ return string;
+}
+
+byte Script::peekByte(int32 offset) {
+ byte v;
+
+ peek(&v, 1, offset);
+
+ return v;
+}
+
+char Script::peekChar(int32 offset) {
+ return (char) peekByte(offset);
+}
+
+uint8 Script::peekUint8(int32 offset) {
+ return (uint8) peekByte(offset);
+}
+
+uint16 Script::peekUint16(int32 offset) {
+ byte v[2];
+
+ peek(v, 2, offset);
+
+ return READ_LE_UINT16(v);
+}
+
+uint32 Script::peekUint32(int32 offset) {
+ byte v[4];
+
+ peek(v, 4, offset);
+
+ return READ_LE_UINT32(v);
+}
+
+int8 Script::peekInt8(int32 offset) {
+ return (int8) peekByte(offset);
+}
+
+int16 Script::peekInt16(int32 offset) {
+ return (int16) peekUint16(offset);
+}
+
+int32 Script::peekInt32(int32 offset) {
+ return (int32) peekUint32(offset);
+}
+
+char *Script::peekString(int32 offset) {
+ return (char *) (_totPtr + offset);
+}
+
+int16 Script::readVarIndex(uint16 *size, uint16 *type) {
+ return _expression->parseVarIndex(size, type);
+}
+
+int16 Script::readValExpr(byte stopToken) {
+ return _expression->parseValExpr(stopToken);
+}
+
+int16 Script::readExpr(byte stopToken, byte *type) {
+ return _expression->parseExpr(stopToken, type);
+}
+
+void Script::skipExpr(char stopToken) {
+ _expression->skipExpr(stopToken);
+}
+
+char Script::evalExpr(int16 *pRes) {
+ byte type;
+
+ _expression->printExpr(99);
+
+ _expression->parseExpr(99, &type);
+ if (!pRes)
+ return type;
+
+ switch (type) {
+ case TYPE_IMM_INT16:
+ *pRes = _expression->getResultInt();
+ break;
+
+ case TYPE_IMM_STR:
+ case GOB_FALSE:
+ *pRes = 0;
+ break;
+
+ case GOB_TRUE:
+ *pRes = 1;
+ break;
+ }
+
+ return type;
+}
+
+bool Script::evalBoolResult() {
+ byte type;
+
+ _expression->printExpr(99);
+
+ _expression->parseExpr(99, &type);
+ if ( (type == GOB_TRUE) ||
+ ((type == TYPE_IMM_INT16) && _expression->getResultInt()))
+ return true;
+ else
+ return false;
+}
+
+int32 Script::getResultInt() const {
+ return _expression->getResultInt();
+}
+
+char *Script::getResultStr() const {
+ return _expression->getResultStr();
+}
+
+bool Script::load(const Common::String &fileName) {
+ unload();
+
+ _finished = false;
+
+ bool isLOM;
+
+ _totFile = TOTFile::createFileName(fileName, isLOM);
+
+ if (isLOM) {
+ if (!loadLOM(_totFile)) {
+ unload();
+ return false;
+ }
+ } else {
+ if (!loadTOT(_totFile)) {
+ unload();
+ return false;
+ }
+ }
+
+ return true;
+}
+
+bool Script::loadTOT(const Common::String &fileName) {
+ TOTFile totFile(_vm);
+
+ if (!totFile.load(fileName))
+ return false;
+
+ Common::SeekableReadStream *stream = totFile.getStream();
+ if (!stream)
+ return false;
+
+ if (!totFile.getProperties(_totProperties))
+ return false;
+
+ _totSize = _totProperties.scriptEnd;
+ if (_totSize <= 0)
+ return false;
+
+ _totData = new byte[_totSize];
+ if (stream->read(_totData, _totSize) != _totSize)
+ return false;
+
+ return true;
+}
+
+bool Script::loadLOM(const Common::String &fileName) {
+ warning("Stub: Script::loadLOM(%s)", _totFile.c_str());
+
+ _lomHandle = _vm->_dataIO->openData(_totFile.c_str());
+ if (_lomHandle < 0)
+ return false;
+
+ DataStream *stream = _vm->_dataIO->openAsStream(_lomHandle);
+
+ stream->seek(48);
+ _totSize = stream->readUint32LE();
+ stream->seek(0);
+
+ _totData = new byte[_totSize];
+ stream->read(_totData, _totSize);
+
+ delete stream;
+
+ return false;
+}
+
+void Script::unload() {
+ unloadTOT();
+}
+
+void Script::unloadTOT() {
+ if (_lomHandle >= 0)
+ _vm->_dataIO->closeData(_lomHandle);
+
+ // Unwind the call stack
+ while (!_callStack.empty())
+ pop();
+
+ delete[] _totData;
+
+ _totData = 0;
+ _totSize = 0;
+ _totPtr = 0;
+ _lomHandle = -1;
+ _totFile.clear();
+
+ _finished = true;
+}
+
+bool Script::isLoaded() const {
+ return _totData != 0;
+}
+
+void Script::setFinished(bool finished) {
+ _finished = finished;
+}
+
+bool Script::isFinished() const {
+ return _finished;
+}
+
+void Script::push() {
+ if (!isLoaded())
+ // Nothing to do
+ return;
+
+ CallEntry currentCall;
+
+ currentCall.totPtr = _totPtr;
+ currentCall.finished = _finished;
+
+ _callStack.push(currentCall);
+}
+
+void Script::pop(bool ret) {
+ if (!isLoaded())
+ // Nothing to do
+ return;
+
+ // Unmatched pop?
+ assert(!_callStack.empty());
+
+ CallEntry lastCall = _callStack.pop();
+
+ if (ret) {
+ _totPtr = lastCall.totPtr;
+ _finished = lastCall.finished;
+ }
+}
+
+void Script::call(uint32 offset) {
+ if (!isLoaded())
+ // Nothing to do
+ return;
+
+ push();
+ seek(offset);
+}
+
+uint8 Script::getVersionMajor() const {
+ return _totProperties.versionMajor;
+}
+
+uint8 Script::getVersionMinor() const {
+ return _totProperties.versionMinor;
+}
+
+uint32 Script::getVariablesCount() const {
+ return _totProperties.variablesCount;
+}
+
+uint32 Script::getTextsOffset() const {
+ return _totProperties.textsOffset;
+}
+
+uint32 Script::getResourcesOffset() const {
+ return _totProperties.resourcesOffset;
+}
+
+uint16 Script::getAnimDataSize() const {
+ return _totProperties.animDataSize;
+}
+
+uint8 Script::getImFileNumber() const {
+ return _totProperties.imFileNumber;
+}
+
+uint8 Script::getExFileNumber() const {
+ return _totProperties.exFileNumber;
+}
+
+uint8 Script::getCommunHandling() const {
+ return _totProperties.communHandling;
+}
+
+uint16 Script::getFunctionOffset(uint8 function) const {
+ if (!_totData)
+ return 0;
+
+ // Offsets 100-128, 2 bytes per function
+ assert(function <= 13);
+
+ return _totProperties.functions[function];
+}
+
+uint32 Script::getVariablesCount(const char *fileName, GobEngine *vm) {
+ DataStream *stream = vm->_dataIO->getDataStream(fileName);
+ if (!stream)
+ return 0;
+
+ stream->seek(0x2C);
+ uint32 variablesCount = stream->readUint32LE();
+ delete stream;
+
+ return variablesCount;
+}
+
+} // End of namespace Gob
diff --git a/engines/gob/script.h b/engines/gob/script.h
new file mode 100644
index 0000000000..64a04503b1
--- /dev/null
+++ b/engines/gob/script.h
@@ -0,0 +1,169 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#ifndef GOB_SCRIPT_H
+#define GOB_SCRIPT_H
+
+#include "common/str.h"
+#include "common/stack.h"
+
+#include "gob/totfile.h"
+
+namespace Gob {
+
+class GobEngine;
+class Expression;
+
+class Script {
+public:
+ Script(GobEngine *vm);
+ ~Script();
+
+ /** Read data and move the pointer accordingly. */
+ uint32 read(byte *data, int32 size);
+ /** Read data (from an optional offset) without moving the pointer. */
+ uint32 peek(byte *data, int32 size, int32 offset = 0) const;
+
+ // Stream properties
+ int32 pos() const;
+ int32 getSize() const;
+
+ // Stream seeking
+ bool seek(int32 offset, int whence = SEEK_SET);
+ bool skip(int32 offset);
+
+ // Reading data
+ byte readByte ();
+ char readChar ();
+ uint8 readUint8 ();
+ uint16 readUint16();
+ uint32 readUint32();
+ int8 readInt8 ();
+ int16 readInt16 ();
+ int32 readInt32 ();
+ char *readString(int32 length = -1);
+
+ // Peeking data
+ byte peekByte (int32 offset = 0);
+ char peekChar (int32 offset = 0);
+ uint8 peekUint8 (int32 offset = 0);
+ uint16 peekUint16(int32 offset = 0);
+ uint32 peekUint32(int32 offset = 0);
+ int8 peekInt8 (int32 offset = 0);
+ int16 peekInt16 (int32 offset = 0);
+ int32 peekInt32 (int32 offset = 0);
+ char *peekString(int32 offset = 0);
+
+ // Expression parsing functions
+ int16 readVarIndex(uint16 *size = 0, uint16 *type = 0);
+ int16 readValExpr(byte stopToken = 99);
+ int16 readExpr(byte stopToken, byte *type);
+ void skipExpr(char stopToken);
+
+ // Higher-level expression parsing functions
+ char evalExpr(int16 *pRes);
+ bool evalBoolResult();
+
+ // Accessing the result of expressions
+ int32 getResultInt() const;
+ char *getResultStr() const;
+
+ /** Returns the offset the specified pointer is within the script data. */
+ int32 getOffset(byte *ptr) const;
+ /** Returns the data pointer to the offset. */
+ byte *getData(int32 offset) const;
+
+ /** Returns the raw data pointer. */
+ byte *getData();
+
+ /** Load a script file. */
+ bool load(const Common::String &fileName);
+ /** Unload the script. */
+ void unload();
+ /** Was a script loaded? */
+ bool isLoaded() const;
+
+ /** Setting the 'finished' property. */
+ void setFinished(bool finished);
+ /** Querying the 'finished' property. */
+ bool isFinished() const;
+
+ // Call stack operations
+ /** Push the current script position onto the call stack. */
+ void push();
+ /** Pop a script position from the call stack (and return there). */
+ void pop(bool ret = true);
+ /** Push the current script position and branch to the specified offset. */
+ void call(uint32 offset);
+
+ // Fixed properties
+ uint8 getVersionMajor () const;
+ uint8 getVersionMinor () const;
+ uint32 getVariablesCount () const;
+ uint32 getTextsOffset () const;
+ uint32 getResourcesOffset() const;
+ uint16 getAnimDataSize () const;
+ uint8 getImFileNumber () const;
+ uint8 getExFileNumber () const;
+ uint8 getCommunHandling () const;
+
+ uint16 getFunctionOffset (uint8 function) const;
+
+ static uint32 getVariablesCount(const char *fileName, GobEngine *vm);
+
+private:
+ struct CallEntry {
+ byte *totPtr;
+ bool finished;
+ };
+
+ GobEngine *_vm;
+ Expression *_expression;
+
+ bool _finished;
+
+ Common::String _totFile;
+ byte *_totData;
+ byte *_totPtr;
+ uint32 _totSize;
+
+ int16 _lomHandle;
+
+ TOTFile::Properties _totProperties;
+
+ Common::Stack<CallEntry> _callStack;
+
+ /** Loading a TOT file. */
+ bool loadTOT(const Common::String &fileName);
+ /** Loading a LOM file. */
+ bool loadLOM(const Common::String &fileName);
+
+ /** Unloading a TOT file. */
+ void unloadTOT();
+};
+
+} // End of namespace Gob
+
+#endif // GOB_SCRIPT_H
diff --git a/engines/gob/sound/adlib.cpp b/engines/gob/sound/adlib.cpp
index 07481431b6..7ab8e1f8dd 100644
--- a/engines/gob/sound/adlib.cpp
+++ b/engines/gob/sound/adlib.cpp
@@ -39,18 +39,33 @@ const unsigned char AdLib::_volRegNums[] = {
};
AdLib::AdLib(Audio::Mixer &mixer) : _mixer(&mixer) {
+ init();
+}
+
+AdLib::~AdLib() {
+ Common::StackLock slock(_mutex);
+
+ _mixer->stopHandle(_handle);
+ OPLDestroy(_opl);
+ if (_data && _freeData)
+ delete[] _data;
+}
+
+void AdLib::init() {
_index = -1;
_data = 0;
_playPos = 0;
_dataSize = 0;
_rate = _mixer->getOutputRate();
+
_opl = makeAdlibOPL(_rate);
_first = true;
_ended = false;
_playing = false;
- _needFree = false;
+
+ _freeData = false;
_repCount = -1;
_samplesTillPoll = 0;
@@ -63,15 +78,6 @@ AdLib::AdLib(Audio::Mixer &mixer) : _mixer(&mixer) {
this, -1, 255, 0, false, true);
}
-AdLib::~AdLib() {
- Common::StackLock slock(_mutex);
-
- _mixer->stopHandle(_handle);
- OPLDestroy(_opl);
- if (_data && _needFree)
- delete[] _data;
-}
-
int AdLib::readBuffer(int16 *buffer, const int numSamples) {
Common::StackLock slock(_mutex);
int samples;
@@ -107,7 +113,9 @@ int AdLib::readBuffer(int16 *buffer, const int numSamples) {
if (_ended) {
_first = true;
_ended = false;
- _playPos = _data + 3 + (_data[1] + 1) * 0x38;
+
+ rewind();
+
_samplesTillPoll = 0;
if (_repCount == -1) {
reset();
@@ -120,7 +128,6 @@ int AdLib::readBuffer(int16 *buffer, const int numSamples) {
else
_playing = false;
}
-
return numSamples;
}
@@ -173,48 +180,6 @@ void AdLib::reset() {
writeOPL(0x01, 0x20);
}
-void AdLib::setVoices() {
- // Definitions of the 9 instruments
- for (int i = 0; i < 9; i++)
- setVoice(i, i, true);
-}
-
-void AdLib::setVoice(byte voice, byte instr, bool set) {
- int i;
- int j;
- uint16 strct[27];
- byte channel;
- byte *dataPtr;
-
- // i = 0 : 0 1 2 3 4 5 6 7 8 9 10 11 12 26
- // i = 1 : 13 14 15 16 17 18 19 20 21 22 23 24 25 27
- for (i = 0; i < 2; i++) {
- dataPtr = _data + 3 + instr * 0x38 + i * 0x1A;
- for (j = 0; j < 27; j++) {
- strct[j] = READ_LE_UINT16(dataPtr);
- dataPtr += 2;
- }
- channel = _operators[voice] + i * 3;
- writeOPL(0xBD, 0x00);
- writeOPL(0x08, 0x00);
- writeOPL(0x40 | channel, ((strct[0] & 3) << 6) | (strct[8] & 0x3F));
- if (!i)
- writeOPL(0xC0 | voice,
- ((strct[2] & 7) << 1) | (1 - (strct[12] & 1)));
- writeOPL(0x60 | channel, ((strct[3] & 0xF) << 4) | (strct[6] & 0xF));
- writeOPL(0x80 | channel, ((strct[4] & 0xF) << 4) | (strct[7] & 0xF));
- writeOPL(0x20 | channel, ((strct[9] & 1) << 7) |
- ((strct[10] & 1) << 6) | ((strct[5] & 1) << 5) |
- ((strct[11] & 1) << 4) | (strct[1] & 0xF));
- if (!i)
- writeOPL(0xE0 | channel, (strct[26] & 3));
- else
- writeOPL(0xE0 | channel, (strct[14] & 3));
- if (i && set)
- writeOPL(0x40 | channel, 0);
- }
-}
-
void AdLib::setKey(byte voice, byte note, bool on, bool spec) {
short freq = 0;
short octa = 0;
@@ -278,7 +243,7 @@ void AdLib::setKey(byte voice, byte note, bool on, bool spec) {
writeOPL(0xB0 + voice, (freq >> 8) | (octa << 2) | 0x20 * on);
if (!freq)
- warning("Voice %d, note %02X unknown", voice, note);
+ warning("AdLib: Voice %d, note %02X unknown", voice, note);
}
void AdLib::setVolume(byte voice, byte volume) {
@@ -287,17 +252,102 @@ void AdLib::setVolume(byte voice, byte volume) {
}
void AdLib::pollMusic() {
+ if ((_playPos > (_data + _dataSize)) && (_dataSize != 0xFFFFFFFF)) {
+ _ended = true;
+ return;
+ }
+
+ interpret();
+}
+
+void AdLib::unload() {
+ _playing = false;
+ _index = -1;
+
+ if (_data && _freeData)
+ delete[] _data;
+
+ _freeData = false;
+}
+
+bool AdLib::isPlaying() const {
+ return _playing;
+}
+
+bool AdLib::getRepeating() const {
+ return _repCount != 0;
+}
+
+void AdLib::setRepeating(int32 repCount) {
+ _repCount = repCount;
+}
+
+int AdLib::getIndex() const {
+ return _index;
+}
+
+void AdLib::startPlay() {
+ if (_data) _playing = true;
+}
+
+void AdLib::stopPlay() {
+ Common::StackLock slock(_mutex);
+ _playing = false;
+}
+
+ADLPlayer::ADLPlayer(Audio::Mixer &mixer) : AdLib(mixer) {
+}
+
+ADLPlayer::~ADLPlayer() {
+}
+
+bool ADLPlayer::load(const char *fileName) {
+ Common::File song;
+
+ unload();
+ song.open(fileName);
+ if (!song.isOpen())
+ return false;
+
+ _freeData = true;
+ _dataSize = song.size();
+ _data = new byte[_dataSize];
+ song.read(_data, _dataSize);
+ song.close();
+
+ reset();
+ setVoices();
+ _playPos = _data + 3 + (_data[1] + 1) * 0x38;
+
+ return true;
+}
+
+bool ADLPlayer::load(byte *data, uint32 size, int index) {
+ unload();
+ _repCount = 0;
+
+ _dataSize = size;
+ _data = data;
+ _index = index;
+
+ reset();
+ setVoices();
+ _playPos = _data + 3 + (_data[1] + 1) * 0x38;
+
+ return true;
+}
+
+void ADLPlayer::unload() {
+ AdLib::unload();
+}
+
+void ADLPlayer::interpret() {
unsigned char instr;
byte channel;
byte note;
byte volume;
uint16 tempo;
- if ((_playPos > (_data + _dataSize)) && (_dataSize != 0xFFFFFFFF)) {
- _ended = true;
- return;
- }
-
// First tempo, we'll ignore it...
if (_first) {
tempo = *(_playPos++);
@@ -352,7 +402,7 @@ void AdLib::pollMusic() {
_samplesTillPoll = 0;
return;
default:
- warning("Unknown special command in ADL, stopping playback: %X",
+ warning("ADLPlayer: Unknown special command %X, stopping playback",
instr & 0x0F);
_repCount = 0;
_ended = true;
@@ -360,7 +410,7 @@ void AdLib::pollMusic() {
}
break;
default:
- warning("Unknown command in ADL, stopping playback: %X",
+ warning("ADLPlayer: Unknown command %X, stopping playback",
instr & 0xF0);
_repCount = 0;
_ended = true;
@@ -383,75 +433,349 @@ void AdLib::pollMusic() {
_samplesTillPoll = tempo * (_rate / 1000);
}
-bool AdLib::load(const char *fileName) {
+void ADLPlayer::reset() {
+ AdLib::reset();
+}
+
+void ADLPlayer::rewind() {
+ _playPos = _data + 3 + (_data[1] + 1) * 0x38;
+}
+
+void ADLPlayer::setVoices() {
+ // Definitions of the 9 instruments
+ for (int i = 0; i < 9; i++)
+ setVoice(i, i, true);
+}
+
+void ADLPlayer::setVoice(byte voice, byte instr, bool set) {
+ uint16 strct[27];
+ byte channel;
+ byte *dataPtr;
+
+ // i = 0 : 0 1 2 3 4 5 6 7 8 9 10 11 12 26
+ // i = 1 : 13 14 15 16 17 18 19 20 21 22 23 24 25 27
+ for (int i = 0; i < 2; i++) {
+ dataPtr = _data + 3 + instr * 0x38 + i * 0x1A;
+ for (int j = 0; j < 27; j++) {
+ strct[j] = READ_LE_UINT16(dataPtr);
+ dataPtr += 2;
+ }
+ channel = _operators[voice] + i * 3;
+ writeOPL(0xBD, 0x00);
+ writeOPL(0x08, 0x00);
+ writeOPL(0x40 | channel, ((strct[0] & 3) << 6) | (strct[8] & 0x3F));
+ if (!i)
+ writeOPL(0xC0 | voice,
+ ((strct[2] & 7) << 1) | (1 - (strct[12] & 1)));
+ writeOPL(0x60 | channel, ((strct[3] & 0xF) << 4) | (strct[6] & 0xF));
+ writeOPL(0x80 | channel, ((strct[4] & 0xF) << 4) | (strct[7] & 0xF));
+ writeOPL(0x20 | channel, ((strct[9] & 1) << 7) |
+ ((strct[10] & 1) << 6) | ((strct[5] & 1) << 5) |
+ ((strct[11] & 1) << 4) | (strct[1] & 0xF));
+ if (!i)
+ writeOPL(0xE0 | channel, (strct[26] & 3));
+ else
+ writeOPL(0xE0 | channel, (strct[14] & 3));
+ if (i && set)
+ writeOPL(0x40 | channel, 0);
+ }
+}
+
+
+MDYPlayer::MDYPlayer(Audio::Mixer &mixer) : AdLib(mixer) {
+ init();
+}
+
+MDYPlayer::~MDYPlayer() {
+}
+
+void MDYPlayer::init() {
+ _soundMode = 0;
+
+ _timbres = 0;
+ _tbrCount = 0;
+ _tbrStart = 0;
+ _timbresSize = 0;
+}
+
+bool MDYPlayer::loadMDY(Common::SeekableReadStream &stream) {
+ unloadMDY();
+
+ _freeData = true;
+
+ byte mdyHeader[70];
+ stream.read(mdyHeader, 70);
+
+ _tickBeat = mdyHeader[36];
+ _beatMeasure = mdyHeader[37];
+ _totalTick = mdyHeader[38] + (mdyHeader[39] << 8) + (mdyHeader[40] << 16) + (mdyHeader[41] << 24);
+ _dataSize = mdyHeader[42] + (mdyHeader[43] << 8) + (mdyHeader[44] << 16) + (mdyHeader[45] << 24);
+ _nrCommand = mdyHeader[46] + (mdyHeader[47] << 8) + (mdyHeader[48] << 16) + (mdyHeader[49] << 24);
+// _soundMode is either 0 (melodic) or 1 (percussive)
+ _soundMode = mdyHeader[58];
+ _pitchBendRangeStep = 25*mdyHeader[59];
+ _basicTempo = mdyHeader[60] + (mdyHeader[61] << 8);
+
+ if (_pitchBendRangeStep < 25)
+ _pitchBendRangeStep = 25;
+ else if (_pitchBendRangeStep > 300)
+ _pitchBendRangeStep = 300;
+
+ _data = new byte[_dataSize];
+ stream.read(_data, _dataSize);
+
+ reset();
+ _playPos = _data;
+
+ return true;
+}
+
+bool MDYPlayer::loadMDY(const char *fileName) {
Common::File song;
- unload();
song.open(fileName);
if (!song.isOpen())
return false;
- _needFree = true;
- _dataSize = song.size();
- _data = new byte[_dataSize];
- song.read(_data, _dataSize);
- song.close();
+ bool loaded = loadMDY(song);
- reset();
- setVoices();
- _playPos = _data + 3 + (_data[1] + 1) * 0x38;
+ song.close();
- return true;
+ return loaded;
}
-bool AdLib::load(byte *data, uint32 size, int index) {
- unload();
- _repCount = 0;
+bool MDYPlayer::loadTBR(Common::SeekableReadStream &stream) {
+ unloadTBR();
- _dataSize = size;
- _data = data;
- _index = index;
+ _timbresSize = stream.size();
+
+ _timbres = new byte[_timbresSize];
+ stream.read(_timbres, _timbresSize);
reset();
setVoices();
- _playPos = _data + 3 + (_data[1] + 1) * 0x38;
return true;
}
-void AdLib::unload() {
- _playing = false;
- _index = -1;
+bool MDYPlayer::loadTBR(const char *fileName) {
+ Common::File timbres;
- if (_data && _needFree)
- delete[] _data;
+ timbres.open(fileName);
+ if (!timbres.isOpen())
+ return false;
+
+ bool loaded = loadTBR(timbres);
- _needFree = false;
+ timbres.close();
+
+ return loaded;
}
-bool AdLib::isPlaying() const {
- return _playing;
+void MDYPlayer::unload() {
+ unloadTBR();
+ unloadMDY();
}
-bool AdLib::getRepeating() const {
- return _repCount != 0;
+void MDYPlayer::unloadMDY() {
+ AdLib::unload();
}
-void AdLib::setRepeating(int32 repCount) {
- _repCount = repCount;
+void MDYPlayer::unloadTBR() {
+ delete[] _timbres;
+
+ _timbres = 0;
+ _timbresSize = 0;
}
-int AdLib::getIndex() const {
- return _index;
+void MDYPlayer::interpret() {
+ unsigned char instr;
+ byte channel;
+ byte note;
+ byte volume;
+ uint8 tempoMult, tempoFrac;
+ uint8 ctrlByte1, ctrlByte2;
+ uint8 timbre;
+
+ if (_first) {
+ for (int i = 0; i < 11; i ++)
+ setVolume(i, 0);
+
+// TODO : Set pitch range
+
+ _tempo = _basicTempo;
+ _wait = *(_playPos++);
+ _first = false;
+ }
+ do {
+ instr = *_playPos;
+// printf("instr 0x%X\n", instr);
+ switch(instr) {
+ case 0xF8:
+ _wait = *(_playPos++);
+ break;
+ case 0xFC:
+ _ended = true;
+ _samplesTillPoll = 0;
+ return;
+ case 0xF0:
+ _playPos++;
+ ctrlByte1 = *(_playPos++);
+ ctrlByte2 = *(_playPos++);
+ if (ctrlByte1 != 0x7F || ctrlByte2 != 0) {
+ _playPos -= 2;
+ while (*(_playPos++) != 0xF7);
+ } else {
+ tempoMult = *(_playPos++);
+ tempoFrac = *(_playPos++);
+ _tempo = _basicTempo * tempoMult + (unsigned)(((long)_basicTempo * tempoFrac) >> 7);
+ _playPos++;
+ }
+ _wait = *(_playPos++);
+ break;
+ default:
+ if (instr >= 0x80) {
+ _playPos++;
+ }
+ channel = (int)(instr & 0x0f);
+
+ switch(instr & 0xf0) {
+ case 0x90:
+ note = *(_playPos++);
+ volume = *(_playPos++);
+ _pollNotes[channel] = note;
+ setVolume(channel, volume);
+ setKey(channel, note, true, false);
+ break;
+ case 0x80:
+ _playPos += 2;
+ note = _pollNotes[channel];
+ setKey(channel, note, false, false);
+ break;
+ case 0xA0:
+ setVolume(channel, *(_playPos++));
+ break;
+ case 0xC0:
+ timbre = *(_playPos++);
+ setVoice(channel, timbre, false);
+ break;
+ case 0xE0:
+ warning("MDYPlayer: Pitch bend not yet implemented");
+
+ note = *(_playPos)++;
+ note += (unsigned)(*(_playPos++)) << 7;
+
+ setKey(channel, note, _notOn[channel], true);
+
+ break;
+ case 0xB0:
+ _playPos += 2;
+ break;
+ case 0xD0:
+ _playPos++;
+ break;
+ default:
+ warning("MDYPlayer: Bad MIDI instr byte: 0%X", instr);
+ while ((*_playPos) < 0x80)
+ _playPos++;
+ if (*_playPos != 0xF8)
+ _playPos--;
+ break;
+ } //switch instr & 0xF0
+ _wait = *(_playPos++);
+ break;
+ } //switch instr
+ } while (_wait == 0);
+
+ if (_wait == 0xF8) {
+ _wait = 0xF0;
+ if (*_playPos != 0xF8)
+ _wait += *(_playPos++);
+ }
+// _playPos++;
+ _samplesTillPoll = _wait * (_rate / 1000);
}
-void AdLib::startPlay() {
- if (_data) _playing = true;
+void MDYPlayer::reset() {
+ AdLib::reset();
+
+// _soundMode 1 : Percussive mode.
+ if (_soundMode == 1) {
+ writeOPL(0xA6, 0);
+ writeOPL(0xB6, 0);
+ writeOPL(0xA7, 0);
+ writeOPL(0xB7, 0);
+ writeOPL(0xA8, 0);
+ writeOPL(0xB8, 0);
+
+// TODO set the correct frequency for the last 4 percussive voices
+ }
}
-void AdLib::stopPlay() {
- Common::StackLock slock(_mutex);
- _playing = false;
+void MDYPlayer::rewind() {
+ _playPos = _data;
+}
+
+void MDYPlayer::setVoices() {
+ byte *timbrePtr;
+
+ timbrePtr = _timbres;
+ debugC(6, kDebugSound, "TBR version: %X.%X", timbrePtr[0], timbrePtr[1]);
+ timbrePtr += 2;
+
+ _tbrCount = READ_LE_UINT16(timbrePtr);
+ debugC(6, kDebugSound, "Timbres counter: %d", _tbrCount);
+ timbrePtr += 2;
+ _tbrStart = READ_LE_UINT16(timbrePtr);
+
+ timbrePtr += 2;
+ for (int i = 0; i < _tbrCount ; i++)
+ setVoice(i, i, true);
+}
+
+void MDYPlayer::setVoice(byte voice, byte instr, bool set) {
+ uint16 strct[27];
+ byte channel;
+ byte *timbrePtr;
+ char timbreName[10];
+
+ timbreName[9] = '\0';
+ for (int j = 0; j < 9; j++)
+ timbreName[j] = _timbres[6 + j + (instr * 9)];
+ debugC(6, kDebugSound, "Loading timbre %s", timbreName);
+
+ // i = 0 : 0 1 2 3 4 5 6 7 8 9 10 11 12 26
+ // i = 1 : 13 14 15 16 17 18 19 20 21 22 23 24 25 27
+ for (int i = 0; i < 2; i++) {
+ timbrePtr = _timbres + _tbrStart + instr * 0x38 + i * 0x1A;
+ for (int j = 0; j < 27; j++) {
+ if (timbrePtr >= (_timbres + _timbresSize)) {
+ warning("MDYPlayer: Instrument %d out of range (%d, %d)", instr,
+ (uint32) (timbrePtr - _timbres), _timbresSize);
+ strct[j] = 0;
+ } else
+ strct[j] = READ_LE_UINT16(timbrePtr);
+ timbrePtr += 2;
+ }
+ channel = _operators[voice] + i * 3;
+ writeOPL(0xBD, 0x00);
+ writeOPL(0x08, 0x00);
+ writeOPL(0x40 | channel, ((strct[0] & 3) << 6) | (strct[8] & 0x3F));
+ if (!i)
+ writeOPL(0xC0 | voice,
+ ((strct[2] & 7) << 1) | (1 - (strct[12] & 1)));
+ writeOPL(0x60 | channel, ((strct[3] & 0xF) << 4) | (strct[6] & 0xF));
+ writeOPL(0x80 | channel, ((strct[4] & 0xF) << 4) | (strct[7] & 0xF));
+ writeOPL(0x20 | channel, ((strct[9] & 1) << 7) |
+ ((strct[10] & 1) << 6) | ((strct[5] & 1) << 5) |
+ ((strct[11] & 1) << 4) | (strct[1] & 0xF));
+ if (!i)
+ writeOPL(0xE0 | channel, (strct[26] & 3));
+ else {
+ writeOPL(0xE0 | channel, (strct[14] & 3));
+ writeOPL(0x40 | channel, 0);
+ }
+ }
}
} // End of namespace Gob
diff --git a/engines/gob/sound/adlib.h b/engines/gob/sound/adlib.h
index 4cd83d5883..3f7b46643f 100644
--- a/engines/gob/sound/adlib.h
+++ b/engines/gob/sound/adlib.h
@@ -38,7 +38,7 @@ class GobEngine;
class AdLib : public Audio::AudioStream {
public:
AdLib(Audio::Mixer &mixer);
- ~AdLib();
+ virtual ~AdLib();
bool isPlaying() const;
int getIndex() const;
@@ -49,9 +49,7 @@ public:
void startPlay();
void stopPlay();
- bool load(const char *fileName);
- bool load(byte *data, uint32 size, int index = -1);
- void unload();
+ virtual void unload();
// AudioStream API
int readBuffer(int16 *buffer, const int numSamples);
@@ -89,18 +87,88 @@ protected:
bool _playing;
bool _first;
bool _ended;
- bool _needFree;
+
+ bool _freeData;
int _index;
+ unsigned char _wait;
+ uint8 _tickBeat;
+ uint8 _beatMeasure;
+ uint32 _totalTick;
+ uint32 _nrCommand;
+ uint16 _pitchBendRangeStep;
+ uint16 _basicTempo, _tempo;
+
void writeOPL(byte reg, byte val);
void setFreqs();
- void reset();
- void setVoices();
- void setVoice(byte voice, byte instr, bool set);
void setKey(byte voice, byte note, bool on, bool spec);
void setVolume(byte voice, byte volume);
void pollMusic();
+
+ virtual void interpret() = 0;
+
+ virtual void reset();
+ virtual void rewind() = 0;
+ virtual void setVoices() = 0;
+
+private:
+ void init();
+};
+
+class ADLPlayer : public AdLib {
+public:
+ ADLPlayer(Audio::Mixer &mixer);
+ ~ADLPlayer();
+
+ bool load(const char *fileName);
+ bool load(byte *data, uint32 size, int index = -1);
+
+ void unload();
+
+protected:
+ void interpret();
+
+ void reset();
+ void rewind();
+
+ void setVoices();
+ void setVoice(byte voice, byte instr, bool set);
+};
+
+class MDYPlayer : public AdLib {
+public:
+ MDYPlayer(Audio::Mixer &mixer);
+ ~MDYPlayer();
+
+ bool loadMDY(const char *fileName);
+ bool loadMDY(Common::SeekableReadStream &stream);
+ bool loadTBR(const char *fileName);
+ bool loadTBR(Common::SeekableReadStream &stream);
+
+ void unload();
+
+protected:
+ byte _soundMode;
+
+ byte *_timbres;
+ uint16 _tbrCount;
+ uint16 _tbrStart;
+ uint32 _timbresSize;
+
+ void interpret();
+
+ void reset();
+ void rewind();
+
+ void setVoices();
+ void setVoice(byte voice, byte instr, bool set);
+
+ void unloadTBR();
+ void unloadMDY();
+
+private:
+ void init();
};
} // End of namespace Gob
diff --git a/engines/gob/sound/bgatmosphere.cpp b/engines/gob/sound/bgatmosphere.cpp
index 12ceb031b7..6ce184155e 100644
--- a/engines/gob/sound/bgatmosphere.cpp
+++ b/engines/gob/sound/bgatmosphere.cpp
@@ -27,6 +27,7 @@
#include "common/events.h"
#include "gob/sound/bgatmosphere.h"
+#include "gob/sound/sounddesc.h"
namespace Gob {
diff --git a/engines/gob/sound/bgatmosphere.h b/engines/gob/sound/bgatmosphere.h
index 3fa648b94d..aa8cf58e10 100644
--- a/engines/gob/sound/bgatmosphere.h
+++ b/engines/gob/sound/bgatmosphere.h
@@ -29,11 +29,12 @@
#include "sound/mixer.h"
#include "common/mutex.h"
-#include "gob/sound/sounddesc.h"
#include "gob/sound/soundmixer.h"
namespace Gob {
+class SoundDesc;
+
class BackgroundAtmosphere : private SoundMixer {
public:
enum PlayMode {
diff --git a/engines/gob/sound/cdrom.cpp b/engines/gob/sound/cdrom.cpp
index ec9b2aaccb..4d6a7ec966 100644
--- a/engines/gob/sound/cdrom.cpp
+++ b/engines/gob/sound/cdrom.cpp
@@ -30,6 +30,7 @@
#include "gob/gob.h"
#include "gob/sound/cdrom.h"
#include "gob/helper.h"
+#include "gob/dataio.h"
namespace Gob {
@@ -86,7 +87,7 @@ void CDROM::startTrack(const char *trackName) {
byte *matchPtr = getTrackBuffer(trackName);
if (!matchPtr) {
- warning("Track \"%s\" not found", trackName);
+ warning("CDROM: Track \"%s\" not found", trackName);
return;
}
diff --git a/engines/gob/sound/cdrom.h b/engines/gob/sound/cdrom.h
index 201f7adb75..6f01e6f90a 100644
--- a/engines/gob/sound/cdrom.h
+++ b/engines/gob/sound/cdrom.h
@@ -26,10 +26,10 @@
#ifndef GOB_SOUND_CDROM_H
#define GOB_SOUND_CDROM_H
-#include "gob/dataio.h"
-
namespace Gob {
+class DataStream;
+
class CDROM {
public:
CDROM();
diff --git a/engines/gob/sound/infogrames.cpp b/engines/gob/sound/infogrames.cpp
index 0b46f3485c..c955dba43f 100644
--- a/engines/gob/sound/infogrames.cpp
+++ b/engines/gob/sound/infogrames.cpp
@@ -55,7 +55,7 @@ bool Infogrames::loadSong(const char *fileName) {
_mixer->getOutputRate(), _mixer->getOutputRate() / 75);
if (!_song->load(fileName)) {
- warning("Couldn't load infogrames music");
+ warning("Infogrames: Couldn't load music \"%s\"", fileName);
clearSong();
return false;
}
@@ -92,7 +92,7 @@ void Infogrames::clearSong() {
bool Infogrames::loadInst(const char *fileName) {
_instruments = new Audio::Infogrames::Instruments;
if (!_instruments->load(fileName)) {
- warning("Couldn't load instruments file");
+ warning("Infogrames: Couldn't load instruments \"%s\"", fileName);
clearInstruments();
return false;
}
diff --git a/engines/gob/sound/protracker.cpp b/engines/gob/sound/protracker.cpp
index 891580ef40..3e33cfd494 100644
--- a/engines/gob/sound/protracker.cpp
+++ b/engines/gob/sound/protracker.cpp
@@ -25,6 +25,8 @@
#include "common/file.h"
+#include "sound/mods/protracker.h"
+
#include "gob/sound/protracker.h"
namespace Gob {
diff --git a/engines/gob/sound/protracker.h b/engines/gob/sound/protracker.h
index 6270530427..73cae0d510 100644
--- a/engines/gob/sound/protracker.h
+++ b/engines/gob/sound/protracker.h
@@ -28,7 +28,6 @@
#include "sound/mixer.h"
#include "sound/audiostream.h"
-#include "sound/mods/protracker.h"
namespace Gob {
diff --git a/engines/gob/sound/sound.cpp b/engines/gob/sound/sound.cpp
index f0cf17b989..d3afc9baa3 100644
--- a/engines/gob/sound/sound.cpp
+++ b/engines/gob/sound/sound.cpp
@@ -31,20 +31,28 @@
#include "gob/game.h"
#include "gob/inter.h"
+#include "gob/sound/pcspeaker.h"
+#include "gob/sound/soundblaster.h"
+#include "gob/sound/adlib.h"
+#include "gob/sound/infogrames.h"
+#include "gob/sound/protracker.h"
+#include "gob/sound/cdrom.h"
+
namespace Gob {
Sound::Sound(GobEngine *vm) : _vm(vm) {
_pcspeaker = new PCSpeaker(*_vm->_mixer);
_blaster = new SoundBlaster(*_vm->_mixer);
- _adlib = 0;
+ _adlPlayer = 0;
+ _mdyPlayer = 0;
_infogrames = 0;
_protracker = 0;
_cdrom = 0;
_bgatmos = 0;
- if (!_vm->_noMusic && _vm->hasAdlib())
- _adlib = new AdLib(*_vm->_mixer);
+ _hasAdLib = (!_vm->_noMusic && _vm->hasAdlib());
+
if (!_vm->_noMusic && (_vm->getPlatform() == Common::kPlatformAmiga)) {
_infogrames = new Infogrames(*_vm->_mixer);
_protracker = new Protracker(*_vm->_mixer);
@@ -62,7 +70,8 @@ Sound::Sound(GobEngine *vm) : _vm(vm) {
Sound::~Sound() {
delete _pcspeaker;
delete _blaster;
- delete _adlib;
+ delete _adlPlayer;
+ delete _mdyPlayer;
delete _infogrames;
delete _protracker;
delete _cdrom;
@@ -105,14 +114,11 @@ bool Sound::sampleLoad(SoundDesc *sndDesc, SoundType type, const char *fileName,
debugC(2, kDebugSound, "Loading sample \"%s\"", fileName);
- int16 handle = _vm->_dataIO->openData(fileName);
- if (handle < 0) {
+ if (!_vm->_dataIO->existData(fileName)) {
warning("Can't open sample file \"%s\"", fileName);
return false;
}
- _vm->_dataIO->closeData(handle);
-
byte *data;
uint32 size;
@@ -121,7 +127,7 @@ bool Sound::sampleLoad(SoundDesc *sndDesc, SoundType type, const char *fileName,
return false;
size = _vm->_dataIO->getDataSize(fileName);
- return sndDesc->load(type, SOUND_FILE, data, size);
+ return sndDesc->load(type, data, size);
}
void Sound::sampleFree(SoundDesc *sndDesc, bool noteAdlib, int index) {
@@ -130,9 +136,14 @@ void Sound::sampleFree(SoundDesc *sndDesc, bool noteAdlib, int index) {
if (sndDesc->getType() == SOUND_ADL) {
- if (_adlib && noteAdlib)
- if ((index == -1) || (_adlib->getIndex() == index))
- _adlib->stopPlay();
+ if (noteAdlib) {
+ if (_adlPlayer)
+ if ((index == -1) || (_adlPlayer->getIndex() == index))
+ _adlPlayer->stopPlay();
+ if (_mdyPlayer)
+ if ((index == -1) || (_mdyPlayer->getIndex() == index))
+ _mdyPlayer->stopPlay();
+ }
} else {
@@ -223,50 +234,112 @@ void Sound::infogramesStop() {
_infogrames->stop();
}
-bool Sound::adlibLoad(const char *fileName) {
- if (!_adlib)
+bool Sound::adlibLoadADL(const char *fileName) {
+ if (!_hasAdLib)
return false;
- debugC(1, kDebugSound, "Adlib: Loading data (\"%s\")", fileName);
+ if (!_adlPlayer)
+ _adlPlayer = new ADLPlayer(*_vm->_mixer);
+
+ debugC(1, kDebugSound, "Adlib: Loading ADL data (\"%s\")", fileName);
- return _adlib->load(fileName);
+ return _adlPlayer->load(fileName);
}
-bool Sound::adlibLoad(byte *data, uint32 size, int index) {
- if (!_adlib)
+bool Sound::adlibLoadADL(byte *data, uint32 size, int index) {
+ if (!_hasAdLib)
return false;
- debugC(1, kDebugSound, "Adlib: Loading data (%d)", index);
+ if (!_adlPlayer)
+ _adlPlayer = new ADLPlayer(*_vm->_mixer);
+
+ debugC(1, kDebugSound, "Adlib: Loading ADL data (%d)", index);
- return _adlib->load(data, size, index);
+ return _adlPlayer->load(data, size, index);
}
void Sound::adlibUnload() {
- if (!_adlib)
+ if (!_hasAdLib)
return;
debugC(1, kDebugSound, "Adlib: Unloading data");
- _adlib->unload();
+ if (_adlPlayer)
+ _adlPlayer->unload();
+ if (_mdyPlayer)
+ _mdyPlayer->unload();
+}
+
+bool Sound::adlibLoadMDY(const char *fileName) {
+ if (!_hasAdLib)
+ return false;
+
+ if (!_mdyPlayer)
+ _mdyPlayer = new MDYPlayer(*_vm->_mixer);
+
+ debugC(1, kDebugSound, "Adlib: Loading MDY data (\"%s\")", fileName);
+
+ if (!_vm->_dataIO->existData(fileName)) {
+ warning("Can't open MDY file \"%s\"", fileName);
+ return false;
+ }
+
+ DataStream *stream = _vm->_dataIO->getDataStream(fileName);
+
+ bool loaded = _mdyPlayer->loadMDY(*stream);
+
+ delete stream;
+
+ return loaded;
+}
+
+bool Sound::adlibLoadTBR(const char *fileName) {
+ if (!_hasAdLib)
+ return false;
+
+ if (!_mdyPlayer)
+ _mdyPlayer = new MDYPlayer(*_vm->_mixer);
+
+ if (!_vm->_dataIO->existData(fileName)) {
+ warning("Can't open TBR file \"%s\"", fileName);
+ return false;
+ }
+
+ debugC(1, kDebugSound, "Adlib: Loading MDY instruments (\"%s\")", fileName);
+
+ DataStream *stream = _vm->_dataIO->getDataStream(fileName);
+
+ bool loaded = _mdyPlayer->loadTBR(*stream);
+
+ delete stream;
+
+ return loaded;
}
void Sound::adlibPlayTrack(const char *trackname) {
- if (!_adlib || _adlib->isPlaying())
+ if (!_hasAdLib)
return;
- debugC(1, kDebugSound, "Adlib: Playing track \"%s\"", trackname);
+ if (!_adlPlayer)
+ _adlPlayer = new ADLPlayer(*_vm->_mixer);
- _adlib->unload();
- _adlib->load(trackname);
- _adlib->startPlay();
+ if (_adlPlayer->isPlaying())
+ return;
+
+ debugC(1, kDebugSound, "Adlib: Playing ADL track \"%s\"", trackname);
+
+ _adlPlayer->unload();
+ _adlPlayer->load(trackname);
+ _adlPlayer->startPlay();
}
void Sound::adlibPlayBgMusic() {
- int track;
-
- if (!_adlib)
+ if (!_hasAdLib)
return;
+ if (!_adlPlayer)
+ _adlPlayer = new ADLPlayer(*_vm->_mixer);
+
static const char *tracksMac[] = {
// "musmac1.adl", // TODO: This track isn't played correctly at all yet
"musmac2.adl",
@@ -285,58 +358,82 @@ void Sound::adlibPlayBgMusic() {
};
if (_vm->getPlatform() == Common::kPlatformWindows) {
- track = _vm->_util->getRandom(ARRAYSIZE(tracksWin));
+ int track = _vm->_util->getRandom(ARRAYSIZE(tracksWin));
adlibPlayTrack(tracksWin[track]);
} else {
- track = _vm->_util->getRandom(ARRAYSIZE(tracksMac));
+ int track = _vm->_util->getRandom(ARRAYSIZE(tracksMac));
adlibPlayTrack(tracksMac[track]);
}
}
void Sound::adlibPlay() {
- if (!_adlib)
+ if (!_hasAdLib)
return;
debugC(1, kDebugSound, "Adlib: Starting playback");
- _adlib->startPlay();
+ if (_adlPlayer)
+ _adlPlayer->startPlay();
+ if (_mdyPlayer)
+ _mdyPlayer->startPlay();
}
void Sound::adlibStop() {
- if (!_adlib)
+ if (!_hasAdLib)
return;
debugC(1, kDebugSound, "Adlib: Stopping playback");
- _adlib->stopPlay();
+ if (_adlPlayer)
+ _adlPlayer->stopPlay();
+ if (_mdyPlayer)
+ _mdyPlayer->stopPlay();
}
bool Sound::adlibIsPlaying() const {
- if (!_adlib)
+ if (!_hasAdLib)
return false;
- return _adlib->isPlaying();
+ if (_adlPlayer && _adlPlayer->isPlaying())
+ return true;
+ if (_mdyPlayer && _mdyPlayer->isPlaying())
+ return true;
+
+ return false;
}
int Sound::adlibGetIndex() const {
- if (!_adlib)
+ if (!_hasAdLib)
return -1;
- return _adlib->getIndex();
+ if (_adlPlayer)
+ return _adlPlayer->getIndex();
+ if (_mdyPlayer)
+ return _mdyPlayer->getIndex();
+
+ return -1;
}
bool Sound::adlibGetRepeating() const {
- if (!_adlib)
+ if (!_hasAdLib)
return false;
- return _adlib->getRepeating();
+ if (_adlPlayer)
+ return _adlPlayer->getRepeating();
+ if (_mdyPlayer)
+ return _mdyPlayer->getRepeating();
+
+ return false;
}
void Sound::adlibSetRepeating(int32 repCount) {
- if (!_adlib)
+ if (!_hasAdLib)
return;
- _adlib->setRepeating(repCount);
+ if (_adlPlayer)
+ _adlPlayer->setRepeating(repCount);
+ if (_mdyPlayer)
+ _mdyPlayer->setRepeating(repCount);
}
void Sound::blasterPlay(SoundDesc *sndDesc, int16 repCount,
@@ -425,17 +522,12 @@ void Sound::cdLoadLIC(const char *fname) {
debugC(1, kDebugSound, "CDROM: Loading LIC \"%s\"", fname);
- int handle = _vm->_dataIO->openData(fname);
-
- if (handle == -1)
+ if (!_vm->_dataIO->existData(fname))
return;
- _vm->_dataIO->closeData(handle);
-
_vm->_dataIO->getUnpackedData(fname);
- handle = _vm->_dataIO->openData(fname);
- DataStream *stream = _vm->_dataIO->openAsStream(handle, true);
+ DataStream *stream = _vm->_dataIO->getDataStream(fname);
_cdrom->readLIC(*stream);
diff --git a/engines/gob/sound/sound.h b/engines/gob/sound/sound.h
index dbdd580ec7..6f6c1d0469 100644
--- a/engines/gob/sound/sound.h
+++ b/engines/gob/sound/sound.h
@@ -27,16 +27,19 @@
#define GOB_SOUND_SOUND_H
#include "gob/sound/sounddesc.h"
-#include "gob/sound/pcspeaker.h"
-#include "gob/sound/soundblaster.h"
-#include "gob/sound/adlib.h"
-#include "gob/sound/infogrames.h"
-#include "gob/sound/protracker.h"
-#include "gob/sound/cdrom.h"
#include "gob/sound/bgatmosphere.h"
namespace Gob {
+class GobEngine;
+class PCSpeaker;
+class SoundBlaster;
+class ADLPlayer;
+class MDYPlayer;
+class Infogrames;
+class Protracker;
+class CDROM;
+
class Sound {
public:
static const int kSoundsCount = 60;
@@ -77,8 +80,10 @@ public:
// AdLib
- bool adlibLoad(const char *fileName);
- bool adlibLoad(byte *data, uint32 size, int index = -1);
+ bool adlibLoadADL(const char *fileName);
+ bool adlibLoadADL(byte *data, uint32 size, int index = -1);
+ bool adlibLoadMDY(const char *fileName);
+ bool adlibLoadTBR(const char *fileName);
void adlibUnload();
void adlibPlayTrack(const char *trackname);
@@ -139,11 +144,14 @@ public:
private:
GobEngine *_vm;
+ bool _hasAdLib;
+
SoundDesc _sounds[kSoundsCount];
PCSpeaker *_pcspeaker;
SoundBlaster *_blaster;
- AdLib *_adlib;
+ ADLPlayer *_adlPlayer;
+ MDYPlayer *_mdyPlayer;
Infogrames *_infogrames;
Protracker *_protracker;
CDROM *_cdrom;
diff --git a/engines/gob/sound/soundblaster.cpp b/engines/gob/sound/soundblaster.cpp
index 23eea90688..69610dc949 100644
--- a/engines/gob/sound/soundblaster.cpp
+++ b/engines/gob/sound/soundblaster.cpp
@@ -24,6 +24,7 @@
*/
#include "gob/sound/soundblaster.h"
+#include "gob/sound/sounddesc.h"
namespace Gob {
diff --git a/engines/gob/sound/soundblaster.h b/engines/gob/sound/soundblaster.h
index c57e4a443e..a2dc87267c 100644
--- a/engines/gob/sound/soundblaster.h
+++ b/engines/gob/sound/soundblaster.h
@@ -29,11 +29,12 @@
#include "common/mutex.h"
#include "sound/mixer.h"
-#include "gob/sound/sounddesc.h"
#include "gob/sound/soundmixer.h"
namespace Gob {
+class SoundDesc;
+
class SoundBlaster : public SoundMixer {
public:
SoundBlaster(Audio::Mixer &mixer);
diff --git a/engines/gob/sound/sounddesc.cpp b/engines/gob/sound/sounddesc.cpp
index c4c78eebbd..b9b327d105 100644
--- a/engines/gob/sound/sounddesc.cpp
+++ b/engines/gob/sound/sounddesc.cpp
@@ -29,15 +29,17 @@
#include "sound/wave.h"
#include "gob/sound/sounddesc.h"
+#include "gob/resources.h"
namespace Gob {
SoundDesc::SoundDesc() {
+ _resource = 0;
+
_data = _dataPtr = 0;
_size = 0;
_type = SOUND_SND;
- _source = SOUND_FILE;
_repCount = 0;
_frequency = 0;
@@ -50,23 +52,31 @@ SoundDesc::~SoundDesc() {
free();
}
-void SoundDesc::set(SoundType type, SoundSource src,
- byte *data, uint32 dSize) {
-
+void SoundDesc::set(SoundType type, byte *data, uint32 dSize) {
free();
_type = type;
- _source = src;
_data = _dataPtr = data;
_size = dSize;
}
-bool SoundDesc::load(SoundType type, SoundSource src,
- byte *data, uint32 dSize) {
+void SoundDesc::set(SoundType type, Resource *resource) {
+ byte *data = 0;
+ uint32 dSize = 0;
+
+ if (resource && (resource->getSize() > 0)) {
+ data = resource->getData();
+ dSize = resource->getSize();
+ }
+
+ set(type, data, dSize);
+ _resource = resource;
+}
+
+bool SoundDesc::load(SoundType type, byte *data, uint32 dSize) {
free();
- _source = src;
switch (type) {
case SOUND_ADL:
return loadADL(data, dSize);
@@ -79,10 +89,28 @@ bool SoundDesc::load(SoundType type, SoundSource src,
return false;
}
+bool SoundDesc::load(SoundType type, Resource *resource) {
+ if (!resource || (resource->getSize() <= 0))
+ return false;
+
+ if (!load(type, resource->getData(), resource->getSize()))
+ return false;
+
+ _resource = resource;
+ return true;
+}
+
void SoundDesc::free() {
- if (_source != SOUND_TOT)
- delete[] _data;
- _data = _dataPtr = 0;
+ if (_resource) {
+ delete _resource;
+ _data = 0;
+ }
+
+ delete[] _data;
+
+ _resource = 0;
+ _data = 0;
+ _dataPtr = 0;
_id = 0;
}
diff --git a/engines/gob/sound/sounddesc.h b/engines/gob/sound/sounddesc.h
index 83efd61e6d..9e5d20e138 100644
--- a/engines/gob/sound/sounddesc.h
+++ b/engines/gob/sound/sounddesc.h
@@ -30,18 +30,14 @@
namespace Gob {
+class Resource;
+
enum SoundType {
SOUND_SND,
SOUND_WAV,
SOUND_ADL
};
-enum SoundSource {
- SOUND_FILE,
- SOUND_TOT,
- SOUND_EXT
-};
-
class SoundDesc {
public:
int16 _repCount;
@@ -58,8 +54,11 @@ public:
bool isId(int16 id) const { return _dataPtr && (_id == id); }
- void set(SoundType type, SoundSource src, byte *data, uint32 dSize);
- bool load(SoundType type, SoundSource src, byte *data, uint32 dSize);
+ void set(SoundType type, byte *data, uint32 dSize);
+ void set(SoundType type, Resource *resource);
+ bool load(SoundType type, byte *data, uint32 dSize);
+ bool load(SoundType type, Resource *resource);
+
void free();
void convToSigned();
@@ -71,12 +70,12 @@ public:
~SoundDesc();
private:
+ Resource *_resource;
byte *_data;
byte *_dataPtr;
uint32 _size;
SoundType _type;
- SoundSource _source;
bool loadSND(byte *data, uint32 dSize);
bool loadWAV(byte *data, uint32 dSize);
diff --git a/engines/gob/sound/soundmixer.cpp b/engines/gob/sound/soundmixer.cpp
index ea1dd2ef82..68a96d3b01 100644
--- a/engines/gob/sound/soundmixer.cpp
+++ b/engines/gob/sound/soundmixer.cpp
@@ -24,6 +24,7 @@
*/
#include "gob/sound/soundmixer.h"
+#include "gob/sound/sounddesc.h"
namespace Gob {
diff --git a/engines/gob/sound/soundmixer.h b/engines/gob/sound/soundmixer.h
index f32beb149f..20376b5152 100644
--- a/engines/gob/sound/soundmixer.h
+++ b/engines/gob/sound/soundmixer.h
@@ -31,10 +31,10 @@
#include "sound/audiostream.h"
#include "sound/mixer.h"
-#include "gob/sound/sounddesc.h"
-
namespace Gob {
+class SoundDesc;
+
class SoundMixer : public Audio::AudioStream {
public:
SoundMixer(Audio::Mixer &mixer, Audio::Mixer::SoundType type);
diff --git a/engines/gob/totfile.cpp b/engines/gob/totfile.cpp
new file mode 100644
index 0000000000..bbf62c143b
--- /dev/null
+++ b/engines/gob/totfile.cpp
@@ -0,0 +1,135 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/str.h"
+#include "common/stream.h"
+
+#include "gob/gob.h"
+#include "gob/totfile.h"
+#include "gob/dataio.h"
+#include "gob/videoplayer.h"
+
+namespace Gob {
+
+TOTFile::TOTFile(GobEngine *vm) : _vm(vm) {
+ _stream = 0;
+
+ memset(_header, 0, 128);
+}
+
+TOTFile::~TOTFile() {
+ unload();
+}
+
+bool TOTFile::load(const Common::String &fileName) {
+ // Trying to open normally
+ _stream = _vm->_dataIO->getDataStream(fileName.c_str());
+
+ if (!_stream)
+ // Trying to open from video
+ _stream = _vm->_vidPlayer->getExtraData(fileName.c_str());
+
+ if (!_stream)
+ return false;
+
+ if (_stream->read(_header, 128) != 128)
+ return false;
+
+ _stream->seek(0);
+
+ return true;
+}
+
+void TOTFile::unload() {
+ delete _stream;
+
+ _stream = 0;
+}
+
+Common::SeekableReadStream *TOTFile::getStream() const {
+ return _stream;
+}
+
+bool TOTFile::getProperties(Properties &props) const {
+ if (!_stream)
+ return false;
+
+ // Offset 39-41: Version in "Major.Minor" string form
+ if (_header[40] != '.')
+ return false;
+
+ props.versionMajor = _header[39] - '0';
+ props.versionMinor = _header[41] - '0';
+
+ props.variablesCount = READ_LE_UINT32(_header + 44);
+
+ props.textsOffset = READ_LE_UINT32(_header + 48);
+ props.resourcesOffset = READ_LE_UINT32(_header + 52);
+
+ props.animDataSize = READ_LE_UINT16(_header + 56);
+
+ props.imFileNumber = _header[59];
+ props.exFileNumber = _header[60];
+ props.communHandling = _header[61];
+
+ for (int i = 0; i < 14; i++)
+ props.functions[i] = READ_LE_UINT16(_header + 100 + i * 2);
+
+ props.scriptEnd = _stream->size();
+ if (props.textsOffset > 0)
+ props.scriptEnd = MIN(props.scriptEnd, props.textsOffset);
+ if (props.resourcesOffset > 0)
+ props.scriptEnd = MIN(props.scriptEnd, props.resourcesOffset);
+
+ return true;
+}
+
+Common::String TOTFile::createFileName(const Common::String &base, bool &isLOM) {
+ isLOM = false;
+
+ const char *dot;
+ if ((dot = strrchr(base.c_str(), '.'))) {
+ // fileName includes an extension
+
+ if (!scumm_stricmp(dot + 1, "LOM"))
+ isLOM = true;
+
+ return base;
+ }
+
+ return base + ".tot";
+}
+
+Common::String TOTFile::getFileBase(const Common::String &fileName) {
+ const char *dot;
+ if ((dot = strrchr(fileName.c_str(), '.'))) {
+ // fileName includes an extension
+ return Common::String(fileName.c_str(), dot);
+ }
+
+ return fileName;
+}
+
+} // End of namespace Gob
diff --git a/engines/gob/totfile.h b/engines/gob/totfile.h
new file mode 100644
index 0000000000..00963d36a2
--- /dev/null
+++ b/engines/gob/totfile.h
@@ -0,0 +1,80 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#ifndef GOB_TOTFILE_H
+#define GOB_TOTFILE_H
+
+#include "common/str.h"
+
+namespace Common {
+ class SeekableReadStream;
+}
+
+namespace Gob {
+
+class TOTFile {
+public:
+ enum Function {
+ kFunctionStart = 0,
+ kFunctionCenter = 13
+ };
+
+ struct Properties {
+ uint8 versionMajor;
+ uint8 versionMinor;
+ uint32 variablesCount;
+ uint32 textsOffset;
+ uint32 resourcesOffset;
+ uint16 animDataSize;
+ uint8 imFileNumber;
+ uint8 exFileNumber;
+ uint8 communHandling;
+ uint16 functions[14];
+ uint32 scriptEnd;
+ };
+
+ TOTFile(GobEngine *vm);
+ ~TOTFile();
+
+ bool load(const Common::String &fileName);
+ void unload();
+
+ Common::SeekableReadStream *getStream() const;
+ bool getProperties(Properties &props) const;
+
+ static Common::String createFileName(const Common::String &base, bool &isLOM);
+ static Common::String getFileBase(const Common::String &fileName);
+
+private:
+ GobEngine *_vm;
+
+ Common::SeekableReadStream *_stream;
+
+ byte _header[128];
+};
+
+} // End of namespace Gob
+
+#endif // GOB_TOTFILE_H
diff --git a/engines/gob/util.cpp b/engines/gob/util.cpp
index e1148dacb9..b0e7691c07 100644
--- a/engines/gob/util.cpp
+++ b/engines/gob/util.cpp
@@ -331,6 +331,12 @@ void Util::setFrameRate(int16 rate) {
_frameRate = rate;
_frameWaitTime = 1000 / rate;
_startFrameTime = getTimeKey();
+ _frameWaitLag = 0;
+}
+
+void Util::notifyNewAnim() {
+ _startFrameTime = getTimeKey();
+ _frameWaitLag = 0;
}
void Util::waitEndFrame() {
diff --git a/engines/gob/util.h b/engines/gob/util.h
index 3d7520fe69..0a76ee40ab 100644
--- a/engines/gob/util.h
+++ b/engines/gob/util.h
@@ -76,6 +76,7 @@ public:
void clearPalette(void);
int16 getFrameRate();
void setFrameRate(int16 rate);
+ void notifyNewAnim();
void waitEndFrame();
void setScrollOffset(int16 x = -1, int16 y = -1);
diff --git a/engines/gob/videoplayer.cpp b/engines/gob/videoplayer.cpp
index e82805d6ac..6c07d22333 100644
--- a/engines/gob/videoplayer.cpp
+++ b/engines/gob/videoplayer.cpp
@@ -201,15 +201,11 @@ bool VideoPlayer::findFile(char *fileName, Type &which) {
int i;
for (i = 0; i < ARRAYSIZE(_extensions); i++) {
if ((which == kVideoTypeTry) || (which == ((Type) i))) {
- int16 handle;
-
fileName[len] = '.';
fileName[len + 1] = 0;
strcat(fileName, _extensions[i]);
- handle = _vm->_dataIO->openData(fileName);
- if (handle >= 0) {
- _vm->_dataIO->closeData(handle);
+ if (_vm->_dataIO->existData(fileName)) {
which = (Type) i;
break;
}