diff options
author | Travis Howell | 2003-07-18 05:49:21 +0000 |
---|---|---|
committer | Travis Howell | 2003-07-18 05:49:21 +0000 |
commit | f20c47bb216210ed681d3d24698de90821de2703 (patch) | |
tree | 2315359358817c8841c89c7f518a94ddc3b6af03 /scumm | |
parent | 0c47e125af56afb47c1eaa205ea7370fc2e4e747 (diff) | |
download | scummvm-rg350-f20c47bb216210ed681d3d24698de90821de2703.tar.gz scummvm-rg350-f20c47bb216210ed681d3d24698de90821de2703.tar.bz2 scummvm-rg350-f20c47bb216210ed681d3d24698de90821de2703.zip |
Add Indy3 FM Towns support, patch #773434
svn-id: r9062
Diffstat (limited to 'scumm')
-rw-r--r-- | scumm/charset.cpp | 4 | ||||
-rw-r--r-- | scumm/help.cpp | 5 | ||||
-rw-r--r-- | scumm/resource.cpp | 2 | ||||
-rw-r--r-- | scumm/resource_v3.cpp | 4 | ||||
-rw-r--r-- | scumm/script.cpp | 11 | ||||
-rw-r--r-- | scumm/script_v5.cpp | 22 | ||||
-rw-r--r-- | scumm/scumm.h | 4 | ||||
-rw-r--r-- | scumm/scummvm.cpp | 6 | ||||
-rw-r--r-- | scumm/sound.cpp | 2 |
9 files changed, 38 insertions, 22 deletions
diff --git a/scumm/charset.cpp b/scumm/charset.cpp index 49365cbc4e..46253071a4 100644 --- a/scumm/charset.cpp +++ b/scumm/charset.cpp @@ -928,8 +928,8 @@ int CharsetRendererV3::getCharWidth(byte chr) { void CharsetRendererV3::setColor(byte color) { _color = color; - _shadowColor = (_vm->_gameId == GID_ZAK256) ? 8 : 0; - if (_vm->_gameId == GID_ZAK256) { + _shadowColor = (_vm->_features & GF_FMTOWNS) ? 8 : 0; + if (_vm->_features & GF_FMTOWNS) { _dropShadow = ((_color & 0x80) != 0); _color &= 0x7f; } else if (_vm->_features & GF_16COLOR) { diff --git a/scumm/help.cpp b/scumm/help.cpp index 29d53052f3..677bfc08d3 100644 --- a/scumm/help.cpp +++ b/scumm/help.cpp @@ -31,6 +31,7 @@ int ScummHelp::numPages(byte gameId) { break; case GID_INDY3: case GID_INDY3_256: + case GID_INDY3_TOWNS: return 6; break; case GID_LOOM: @@ -141,6 +142,7 @@ void ScummHelp::updateStrings(byte gameId, byte version, int page, break; case GID_INDY3: case GID_INDY3_256: + case GID_INDY3_TOWNS: ADD_BIND("q", "Push"); ADD_BIND("a", "Pull"); ADD_BIND("z", "Give"); @@ -264,6 +266,7 @@ void ScummHelp::updateStrings(byte gameId, byte version, int page, case GID_INDY3: case GID_ZAK256: case GID_INDY3_256: + case GID_INDY3_TOWNS: title = "Other game controls:"; ADD_TEXT("Inventory:"); ADD_BIND("y", "Upper left item"); @@ -289,6 +292,7 @@ void ScummHelp::updateStrings(byte gameId, byte version, int page, switch (gameId) { case GID_INDY3: case GID_INDY3_256: + case GID_INDY3_TOWNS: title = "Fighting controls (numpad):"; ADD_BIND("7", "Step back"); ADD_BIND("4", "Step back"); @@ -312,6 +316,7 @@ void ScummHelp::updateStrings(byte gameId, byte version, int page, switch (gameId) { case GID_INDY3: case GID_INDY3_256: + case GID_INDY3_TOWNS: title = "Biplane controls (numpad):"; ADD_BIND("7", "Fly to upper left"); ADD_BIND("4", "Fly to left"); diff --git a/scumm/resource.cpp b/scumm/resource.cpp index e1bfa4347f..6f2f5f08d2 100644 --- a/scumm/resource.cpp +++ b/scumm/resource.cpp @@ -652,7 +652,7 @@ int Scumm::loadResource(int type, int idx) { tag = _fileHandle.readUint16LE(); _fileHandle.seek(-6, SEEK_CUR); /* FIXME */ - if ((type == rtSound) && !(_features & GF_AMIGA) && (_gameId != GID_ZAK256)) { + if ((type == rtSound) && !(_features & GF_AMIGA) && !(_features & GF_FMTOWNS)) { return readSoundResourceSmallHeader(type, idx); } } else { diff --git a/scumm/resource_v3.cpp b/scumm/resource_v3.cpp index 92b103ef34..d4c38d2c23 100644 --- a/scumm/resource_v3.cpp +++ b/scumm/resource_v3.cpp @@ -152,7 +152,9 @@ void Scumm_v3::readIndexFile() { break; default: - error("Bad ID %c%c found in directory!", blocktype & 0xFF, blocktype >> 8); + // FIXME: this is a little hack because Indy3 FM Towns has 32 bytes appended to 00.LFL. + if (_gameId != GID_INDY3_TOWNS) + error("Bad ID %c%c found in directory!", blocktype & 0xFF, blocktype >> 8); return; } } diff --git a/scumm/script.cpp b/scumm/script.cpp index 151b8dcb4a..8281f7ce55 100644 --- a/scumm/script.cpp +++ b/scumm/script.cpp @@ -507,13 +507,18 @@ int Scumm::readVar(uint var) { return (_scummVars[ var ] & ( 1 << bit ) ) ? 1 : 0; } else { var &= 0x7FFF; +#if defined(BYPASS_COPY_PROT) + if (_gameId == GID_INDY3_TOWNS && var == 1508) { + return 0; + } +#endif checkRange(_numBitVariables - 1, 0, var, "Bit variable %d out of range(r)"); return (_bitVars[var >> 3] & (1 << (var & 7))) ? 1 : 0; } } if (var & 0x4000) { - if (_gameId == GID_INDY3_256) { + if (_gameId == GID_INDY3_256 || _gameId == GID_INDY3_TOWNS) { var &= 0xF; } else { var &= 0xFFF; @@ -580,7 +585,7 @@ void Scumm::writeVar(uint var, int value) { } if (var & 0x4000) { - if (_gameId == GID_INDY3_256) { + if (_gameId == GID_INDY3_256 || _gameId == GID_INDY3_TOWNS) { var &= 0xF; } else { var &= 0xFFF; @@ -758,7 +763,7 @@ void Scumm::runExitScript() { // not actual data not even a 00 (stop code) // maybe we should be limiting ourselves to strictly reading the size // described in the header? - if (_gameId == GID_INDY3_256) { + if (_gameId == GID_INDY3_256 || _gameId == GID_INDY3_TOWNS) { // FIXME: Oddly, Indy3 seems to contain exit scripts with only a size // and a tag - not even a terminating NULL! byte *roomptr = getResourceAddress(rtRoom, _roomResource); diff --git a/scumm/script_v5.cpp b/scumm/script_v5.cpp index 0d77cef1d3..bdff5aa004 100644 --- a/scumm/script_v5.cpp +++ b/scumm/script_v5.cpp @@ -599,7 +599,7 @@ void Scumm_v5::o5_chainScript() { // the actor ID of the opposing soldier. So, we copy that value // over to the Local[5] variable of script 33. // See also bug #743314. - if (_gameId == GID_INDY3_256 && vm.slot[cur].number == 32 && script == 33) { + if ((_gameId == GID_INDY3_256 || _gameId == GID_INDY3_TOWNS) && vm.slot[cur].number == 32 && script == 33) { vars[5] = vm.localvar[cur][5]; } @@ -667,7 +667,7 @@ void Scumm_v5::o5_cursorCommand() { initCharset(getVarOrDirectByte(0x80)); break; case 14: /* unk */ - if (_features & GF_OLD_BUNDLE || _gameId == GID_INDY3_256) { + if (_features & GF_OLD_BUNDLE || _gameId == GID_INDY3_256 || _gameId == GID_INDY3_TOWNS) { // FIXME: What is this supposed to do? From comparing // Indy3's script 118 to the Passport Demo's script 58 // my guess is that it's some sort of "init charset", @@ -690,7 +690,7 @@ void Scumm_v5::o5_cursorCommand() { break; } - if (!(_features & GF_OLD_BUNDLE) && _gameId != GID_INDY3_256) { + if (!(_features & GF_OLD_BUNDLE) && _gameId != GID_INDY3_256 && _gameId != GID_INDY3_TOWNS) { VAR(VAR_CURSORSTATE) = _cursor.state; VAR(VAR_USERPUT) = _userPut; } @@ -975,7 +975,7 @@ void Scumm_v5::o5_getActorScale() { return; // INDY3 uses this opcode as a wait_for_actor(); - if ((_gameId == GID_INDY3_256) || (_gameId == GID_INDY3)) { + if ((_gameId == GID_INDY3_TOWNS) || (_gameId == GID_INDY3_256) || (_gameId == GID_INDY3)) { const byte *oldaddr = _scriptPointer - 1; a = derefActor(getVarOrDirectByte(0x80), "o5_getActorScale (wait)"); if (a->moving) { @@ -1009,7 +1009,7 @@ void Scumm_v5::o5_getActorX() { int a; getResultPos(); - if (_gameId == GID_INDY3_256 || _gameId == GID_INDY3) + if (_gameId == GID_INDY3_TOWNS || _gameId == GID_INDY3_256 || _gameId == GID_INDY3) a = getVarOrDirectByte(0x80); else a = getVarOrDirectWord(0x80); @@ -1021,7 +1021,7 @@ void Scumm_v5::o5_getActorY() { int a; getResultPos(); - if (_gameId == GID_INDY3_256 || _gameId == GID_INDY3) { + if (_gameId == GID_INDY3_TOWNS || _gameId == GID_INDY3_256 || _gameId == GID_INDY3) { a = getVarOrDirectByte(0x80); // FIXME - bug 636433 workaround (can't get into Zeppelin) @@ -1505,7 +1505,7 @@ void Scumm_v5::o5_resourceRoutines() { _opcode = fetchScriptByte(); if (_opcode != 17) resid = getVarOrDirectByte(0x80); - if (_gameId != GID_ZAK256) { + if (!(_features & GF_FMTOWNS)) { // FIXME - this probably can be removed eventually, I don't think the following // check will ever be triggered, but then I could be wrong and it's better // to play it safe. @@ -2014,7 +2014,7 @@ void Scumm_v5::o5_setVarRange() { } void Scumm_v5::o5_startMusic() { - if (_gameId == GID_ZAK256) { + if (_features & GF_FMTOWNS) { // In Zak256, this seems to be some kind of Audio CD status query function. // See also bug #762589 (thanks to Hibernatus for providing the information). getResultPos(); @@ -2341,7 +2341,7 @@ void Scumm_v5::o5_verbOps() { void Scumm_v5::o5_wait() { const byte *oldaddr = _scriptPointer - 1; - if ((_gameId == GID_INDY3_256) || (_gameId == GID_INDY3)) { + if ((_gameId == GID_INDY3_TOWNS) || (_gameId == GID_INDY3_256) || (_gameId == GID_INDY3)) { _opcode = 2; } else _opcode = fetchScriptByte(); @@ -2584,7 +2584,7 @@ void Scumm_v5::decodeParseString() { // It's also needed for Loom, or the lines Bobbin // speaks during the intro are put at position 0,0. // In addition, Loom needs to remember the text colour. - if (_gameId == GID_INDY3_256 || _gameId == GID_INDY3 || _gameId == GID_LOOM) { + if (_gameId == GID_INDY3_TOWNS || _gameId == GID_INDY3_256 || _gameId == GID_INDY3 || _gameId == GID_LOOM) { _string[textSlot].t_xpos = _string[textSlot].xpos; _string[textSlot].t_ypos = _string[textSlot].ypos; _string[textSlot].t_color = _string[textSlot].color; @@ -2615,7 +2615,7 @@ void Scumm_v5::o5_oldRoomEffect() { a = getVarOrDirectWord(0x80); #if 1 - if (_gameId == GID_ZAK256) { + if (_features & GF_FMTOWNS) { // FIXME / TODO: OK the first thing to note is: at least in Zak256, // maybe also in other games, this opcode does a bit more. I added // some stubs here, but somebody with a full IDA or more knowledge diff --git a/scumm/scumm.h b/scumm/scumm.h index 07c23e5dae..082514fe54 100644 --- a/scumm/scumm.h +++ b/scumm/scumm.h @@ -84,6 +84,7 @@ enum GameFeatures { GF_AMIGA = 1 << 14, GF_HUMONGOUS = 1 << 15, GF_AFTER_HEV7 = 1 << 16, + GF_FMTOWNS = 1 << 17, GF_EXTERNAL_CHARSET = GF_SMALL_HEADER }; @@ -212,7 +213,8 @@ enum ScummGameId { GID_ZAK, GID_PUTTDEMO, GID_PUTTPUTT, - GID_MONKEY_SEGA + GID_MONKEY_SEGA, + GID_INDY3_TOWNS }; #define _maxRooms res.num[rtRoom] diff --git a/scumm/scummvm.cpp b/scumm/scummvm.cpp index e3543de13b..482e597fbd 100644 --- a/scumm/scummvm.cpp +++ b/scumm/scummvm.cpp @@ -90,10 +90,12 @@ static const VersionSettings scumm_settings[] = { /* Scumm Version 3 */ {"indy3EGA", "Indiana Jones and the Last Crusade", GID_INDY3, 3, VersionSettings::ADLIB_ALWAYS, GF_SMALL_HEADER | GF_SMALL_NAMES | GF_NO_SCALLING | GF_USE_KEY | GF_16COLOR | GF_OLD_BUNDLE, "00.LFL"}, + {"indy3Towns", "Indiana Jones and the Last Crusade (FM Towns)", GID_INDY3_TOWNS, 3, VersionSettings::ADLIB_ALWAYS, + GF_SMALL_HEADER | GF_SMALL_NAMES | GF_NO_SCALLING | GF_OLD256 | GF_FMTOWNS | GF_AUDIOTRACKS, "00.LFL"}, {"indy3", "Indiana Jones and the Last Crusade (256)", GID_INDY3_256, 3, VersionSettings::ADLIB_ALWAYS, GF_SMALL_HEADER | GF_SMALL_NAMES | GF_NO_SCALLING | GF_OLD256 | GF_ADLIB_DEFAULT, "00.LFL"}, {"zak256", "Zak McKracken and the Alien Mindbenders (256)", GID_ZAK256, 3, VersionSettings::ADLIB_ALWAYS, - GF_SMALL_HEADER | GF_SMALL_NAMES | GF_NO_SCALLING | GF_OLD256 | GF_AUDIOTRACKS, "00.LFL"}, + GF_SMALL_HEADER | GF_SMALL_NAMES | GF_NO_SCALLING | GF_OLD256 | GF_FMTOWNS | GF_AUDIOTRACKS, "00.LFL"}, {"loom", "Loom", GID_LOOM, 3, VersionSettings::ADLIB_ALWAYS, GF_SMALL_HEADER | GF_SMALL_NAMES | GF_NO_SCALLING | GF_USE_KEY | GF_16COLOR | GF_OLD_BUNDLE, "00.LFL"}, @@ -567,7 +569,7 @@ Scumm::Scumm (GameDetector *detector, OSystem *syst) _hexdumpScripts = false; _showStack = false; - if (_gameId == GID_ZAK256) { // FmTowns is 320x240 + if (_features & GF_FMTOWNS) { // FmTowns is 320x240 _screenWidth = 320; _screenHeight = 240; } else if (_gameId == GID_CMI) { diff --git a/scumm/sound.cpp b/scumm/sound.cpp index 375d8d0eba..37dd6c5f88 100644 --- a/scumm/sound.cpp +++ b/scumm/sound.cpp @@ -803,7 +803,7 @@ void Sound::stopSound(int a) { stopCD(); } - if (_scumm->_gameId == GID_ZAK256) { + if (_scumm->_features & GF_FMTOWNS) { _scumm->_mixer->stopID(a); } else if (_scumm->_imuseDigital) { _scumm->_imuseDigital->stopSound(a); |