diff options
54 files changed, 661 insertions, 545 deletions
diff --git a/backends/platform/androidsdl/androidsdl.mk b/backends/platform/androidsdl/androidsdl.mk index 1defb81b97..53c0d27666 100644 --- a/backends/platform/androidsdl/androidsdl.mk +++ b/backends/platform/androidsdl/androidsdl.mk @@ -4,8 +4,8 @@ androidsdl: $(INSTALL) -c -m 644 $(DIST_FILES_THEMES) $(DIST_FILES_ENGINEDATA) release $(INSTALL) -c -m 644 $(DIST_FILES_DOCS) release $(CP) $(srcdir)/backends/vkeybd/packs/vkeybd_default.zip release - zip -j scummvm190-git-appdata.zip release/* - split -d -b 1000000 scummvm190-git-appdata.zip scummvm190-git-appdata.zip0 - $(RM) -r scummvm190-git-appdata.zip + zip -j scummvm_1_10_0-git-appdata.zip release/* + split -d -b 1000000 scummvm_1_10_0-git-appdata.zip scummvm_1_10_0-git-appdata.zip0 + $(RM) -r scummvm_1_10_0-git-appdata.zip .PHONY: androidsdl diff --git a/dists/androidsdl/scummvm/AndroidAppSettings.cfg b/dists/androidsdl/scummvm/AndroidAppSettings.cfg index 1c044fef3e..55300e6edd 100644 --- a/dists/androidsdl/scummvm/AndroidAppSettings.cfg +++ b/dists/androidsdl/scummvm/AndroidAppSettings.cfg @@ -23,7 +23,7 @@ InhibitSuspend=y # If the URL does not contain 'http://' it is treated as file from 'project/jni/application/src/AndroidData' dir - # these files are put inside .apk package by build system # Also please avoid 'https://' URLs, many Android devices do not have trust certificates and will fail to connect to SF.net over HTTPS -AppDataDownloadUrl="!!App data|scummvm190-git-appdata.zip" +AppDataDownloadUrl="!!App data|scummvm_1_10_0-git-appdata.zip" # Video color depth - 16 BPP is the fastest and supported for all modes, 24 bpp is supported only # with SwVideoMode=y, SDL_OPENGL mode supports everything. (16)/(24)/(32) diff --git a/dists/androidsdl/scummvm/AndroidAppSettings.cfg.in b/dists/androidsdl/scummvm/AndroidAppSettings.cfg.in index 78756b0da6..897389a36f 100644 --- a/dists/androidsdl/scummvm/AndroidAppSettings.cfg.in +++ b/dists/androidsdl/scummvm/AndroidAppSettings.cfg.in @@ -23,7 +23,7 @@ InhibitSuspend=y # If the URL does not contain 'http://' it is treated as file from 'project/jni/application/src/AndroidData' dir - # these files are put inside .apk package by build system # Also please avoid 'https://' URLs, many Android devices do not have trust certificates and will fail to connect to SF.net over HTTPS -AppDataDownloadUrl="!!App data|scummvm190-git-appdata.zip" +AppDataDownloadUrl="!!App data|scummvm_1_10_0-git-appdata.zip" # Video color depth - 16 BPP is the fastest and supported for all modes, 24 bpp is supported only # with SwVideoMode=y, SDL_OPENGL mode supports everything. (16)/(24)/(32) diff --git a/engines/adl/adl.cpp b/engines/adl/adl.cpp index 58d5fa9e67..3887fa92d9 100644 --- a/engines/adl/adl.cpp +++ b/engines/adl/adl.cpp @@ -56,6 +56,7 @@ AdlEngine::AdlEngine(OSystem *syst, const AdlGameDescription *gd) : _display(nullptr), _graphics(nullptr), _textMode(false), + _linesPrinted(0), _isRestarting(false), _isRestoring(false), _isQuitting(false), @@ -635,6 +636,8 @@ void AdlEngine::gameLoop() { if (shouldQuit()) return; + _linesPrinted = 0; + // If we just restored from the GMM, we skip this command // set, as no command has been input by the user if (!_isRestoring) @@ -888,6 +891,12 @@ bool AdlEngine::canSaveGameStateCurrently() { // Here we check whether or not the game currently accepts the command // "SAVE GAME". This prevents saving via the GMM in situations where // it wouldn't otherwise be possible to do so. + for (cmd = _roomData.commands.begin(); cmd != _roomData.commands.end(); ++cmd) { + ScriptEnv env(*cmd, _state.room, _saveVerb, _saveNoun); + if (matchCommand(env)) + return env.op() == IDO_ACT_SAVE; + } + for (cmd = _roomCommands.begin(); cmd != _roomCommands.end(); ++cmd) { ScriptEnv env(*cmd, _state.room, _saveVerb, _saveNoun); if (matchCommand(env)) diff --git a/engines/adl/adl.h b/engines/adl/adl.h index d71d40816e..75c6485a1f 100644 --- a/engines/adl/adl.h +++ b/engines/adl/adl.h @@ -239,6 +239,7 @@ protected: // Engine Common::Error loadGameState(int slot); Common::Error saveGameState(int slot, const Common::String &desc); + bool canSaveGameStateCurrently(); virtual void gameLoop(); virtual void loadState(Common::ReadStream &stream); @@ -390,6 +391,7 @@ protected: // Game state State _state; + uint _linesPrinted; bool _isRestarting, _isRestoring, _isQuitting; bool _canSaveNow, _canRestoreNow; bool _abortScript; @@ -410,7 +412,6 @@ private: Common::Error run(); bool hasFeature(EngineFeature f) const; bool canLoadGameStateCurrently(); - bool canSaveGameStateCurrently(); // Text input byte convertKey(uint16 ascii) const; diff --git a/engines/adl/adl_v2.cpp b/engines/adl/adl_v2.cpp index 272e7801e7..23294391ab 100644 --- a/engines/adl/adl_v2.cpp +++ b/engines/adl/adl_v2.cpp @@ -36,7 +36,6 @@ AdlEngine_v2::~AdlEngine_v2() { AdlEngine_v2::AdlEngine_v2(OSystem *syst, const AdlGameDescription *gd) : AdlEngine(syst, gd), - _linesPrinted(0), _maxLines(4), _disk(nullptr), _itemRemoved(false), @@ -285,9 +284,6 @@ void AdlEngine_v2::showRoom() { _display->updateHiResScreen(); printString(_roomData.description); - - // FIXME: move to main loop? - _linesPrinted = 0; } // TODO: Merge this into AdlEngine? @@ -615,6 +611,16 @@ int AdlEngine_v2::o2_initDisk(ScriptEnv &e) { return 0; } +bool AdlEngine_v2::canSaveGameStateCurrently() { + // Back up first visit flag as it may be changed by this test + const bool isFirstTime = getCurRoom().isFirstTime; + const bool retval = AdlEngine::canSaveGameStateCurrently(); + + getCurRoom().isFirstTime = isFirstTime; + + return retval; +} + int AdlEngine_v2::askForSlot(const Common::String &question) { while (1) { _display->printString(question); diff --git a/engines/adl/adl_v2.h b/engines/adl/adl_v2.h index 5447974a2e..9d4d5fa600 100644 --- a/engines/adl/adl_v2.h +++ b/engines/adl/adl_v2.h @@ -51,6 +51,9 @@ protected: virtual void showRoom(); void takeItem(byte noun); + // Engine + bool canSaveGameStateCurrently(); + virtual DataBlockPtr readDataBlockPtr(Common::ReadStream &f) const; virtual void adjustDataBlockPtr(byte &track, byte §or, byte &offset, byte &size) const { } void loadItems(Common::ReadStream &stream); @@ -86,7 +89,7 @@ protected: Common::String restoreInsert, restoreReplace; } _strings_v2; - uint _linesPrinted, _maxLines; + uint _maxLines; DiskImage *_disk; Common::Array<DataBlockPtr> _itemPics; bool _itemRemoved; diff --git a/engines/adl/detection.cpp b/engines/adl/detection.cpp index 02fadd255b..c0b8a8fc75 100644 --- a/engines/adl/detection.cpp +++ b/engines/adl/detection.cpp @@ -210,7 +210,7 @@ static const AdlGameDescription gameDescriptions[] = { }, Common::EN_ANY, Common::kPlatformApple2, - ADGF_UNSTABLE, + ADGF_TESTING, GUIO2(GAMEOPTION_COLOR_DEFAULT_ON, GAMEOPTION_SCANLINES) }, GAME_TYPE_HIRES6 diff --git a/engines/adl/hires6.cpp b/engines/adl/hires6.cpp index b3b66f6873..0eb47de7fc 100644 --- a/engines/adl/hires6.cpp +++ b/engines/adl/hires6.cpp @@ -58,6 +58,9 @@ private: // AdlEngine_v2 void printString(const Common::String &str); + // Engine + bool canSaveGameStateCurrently(); + template <Direction D> int o_goDirection(ScriptEnv &e); int o_fluteSound(ScriptEnv &e); @@ -167,6 +170,7 @@ int HiRes6Engine::o_goDirection(ScriptEnv &e) { byte room = getCurRoom().connections[D]; if (room == 0) { + // Don't penalize invalid directions at escapable Garthim encounter if (getVar(33) == 2) setVar(34, getVar(34) + 1); @@ -176,6 +180,7 @@ int HiRes6Engine::o_goDirection(ScriptEnv &e) { switchRoom(room); + // Escapes an escapable Garthim encounter by going to a different room if (getVar(33) == 2) { printMessage(102); setVar(33, 0); @@ -200,6 +205,22 @@ int HiRes6Engine::o_fluteSound(ScriptEnv &e) { return 0; } +bool HiRes6Engine::canSaveGameStateCurrently() { + // Back up variables that may be changed by this test + const byte var2 = getVar(2); + const byte var24 = getVar(24); + const bool abortScript = _abortScript; + + const bool retval = AdlEngine_v5::canSaveGameStateCurrently(); + + setVar(2, var2); + setVar(24, var24); + _abortScript = abortScript; + + return retval; +} + + #define SECTORS_PER_TRACK 16 #define BYTES_PER_SECTOR 256 @@ -370,9 +391,6 @@ void HiRes6Engine::showRoom() { _display->updateHiResScreen(); setVar(2, 0xff); printString(_roomData.description); - - // FIXME: move to main loop? - _linesPrinted = 0; } Common::String HiRes6Engine::formatVerbError(const Common::String &verb) const { @@ -451,9 +469,12 @@ void HiRes6Engine::printString(const Common::String &str) { if (getVar(2) == 0xff) { if (getVar(26) == 0) { // This checks for special room description string " " - if (str.size() != 1 || APPLECHAR(str[0]) != APPLECHAR(' ')) - return AdlEngine_v5::printString(s); - setVar(2, 160); + if (str.size() == 1 && APPLECHAR(str[0]) == APPLECHAR(' ')) { + setVar(2, 160); + } else { + AdlEngine_v5::printString(s); + setVar(2, 1); + } } else if (getVar(26) == 0xff) { // Storing the room number in a variable allows for range comparisons setVar(26, _state.room); diff --git a/engines/agi/agi.cpp b/engines/agi/agi.cpp index b293a8e9e5..55872940f5 100644 --- a/engines/agi/agi.cpp +++ b/engines/agi/agi.cpp @@ -394,7 +394,6 @@ AgiEngine::AgiEngine(OSystem *syst, const AGIGameDescription *gameDesc) : AgiBas resetControllers(); - setupOpcodes(); _game._curLogic = NULL; _veryFirstInitialCycle = true; _instructionCounter = 0; @@ -498,6 +497,8 @@ void AgiEngine::initialize() { } else { warning("Could not open AGI game"); } + // finally set up actual VM opcodes, because we should now have figured out the right AGI version + setupOpCodes(getVersion()); debugC(2, kDebugLevelMain, "Init sound"); } diff --git a/engines/agi/agi.h b/engines/agi/agi.h index 2b62f9757a..2294593427 100644 --- a/engines/agi/agi.h +++ b/engines/agi/agi.h @@ -466,8 +466,6 @@ struct AgiGame { ScreenObjEntry addToPicView; - int32 ver; /**< detected game version */ - bool automaticSave; /**< set by CmdSetSimple() */ char automaticSaveDescription[SAVEDGAME_DESCRIPTION_LEN + 1]; @@ -718,7 +716,20 @@ struct AgiArtificialDelayEntry { uint16 millisecondsDelay; }; -typedef void (*AgiCommand)(AgiGame *state, AgiEngine *vm, uint8 *p); +typedef void (*AgiOpCodeFunction)(AgiGame *state, AgiEngine *vm, uint8 *p); + +struct AgiOpCodeEntry { + const char *name; + const char *parameters; + AgiOpCodeFunction functionPtr; + uint16 parameterSize; +}; + +struct AgiOpCodeDefinitionEntry { + const char *name; + const char *parameters; + AgiOpCodeFunction functionPtr; +}; class AgiEngine : public AgiBase { protected: @@ -856,7 +867,7 @@ public: void unloadLogic(int16 logicNr); int runLogic(int16 logicNr); void debugConsole(int, int, const char *); - int testIfCode(int); + bool testIfCode(int16 logicNr); void executeAgiCommand(uint8, uint8 *); private: @@ -985,10 +996,13 @@ private: uint32 _passedPlayTimeCycles; // increased by 1 every time we passed a cycle private: - AgiCommand _agiCommands[183]; - AgiCommand _agiCondCommands[256]; + AgiOpCodeEntry _opCodes[256]; // always keep those at 256, so that there is no way for invalid memory access + AgiOpCodeEntry _opCodesCond[256]; + + void setupOpCodes(uint16 version); - void setupOpcodes(); +public: + const AgiOpCodeEntry *getOpCodesTable() { return _opCodes; } }; } // End of namespace Agi diff --git a/engines/agi/console.cpp b/engines/agi/console.cpp index 9a4a357b44..3729cd3be6 100644 --- a/engines/agi/console.cpp +++ b/engines/agi/console.cpp @@ -94,16 +94,18 @@ bool Console::Cmd_SetObj(int argc, const char **argv) { } bool Console::Cmd_RunOpcode(int argc, const char **argv) { + const AgiOpCodeEntry *opCodes = _vm->getOpCodesTable(); + if (argc < 2) { debugPrintf("Usage: runopcode <name> <parameter0> ....\n"); return true; } - for (int i = 0; logicNamesCmd[i].name; i++) { - if (!strcmp(argv[1], logicNamesCmd[i].name)) { + for (int i = 0; opCodes[i].name; i++) { + if (!strcmp(argv[1], opCodes[i].name)) { uint8 p[16]; - if ((argc - 2) != logicNamesCmd[i].argumentsLength()) { - debugPrintf("AGI command wants %d arguments\n", logicNamesCmd[i].argumentsLength()); + if ((argc - 2) != opCodes[i].parameterSize) { + debugPrintf("AGI command wants %d arguments\n", opCodes[i].parameterSize); return 0; } p[0] = argv[2] ? (char)strtoul(argv[2], NULL, 0) : 0; @@ -112,7 +114,7 @@ bool Console::Cmd_RunOpcode(int argc, const char **argv) { p[3] = argv[5] ? (char)strtoul(argv[5], NULL, 0) : 0; p[4] = argv[6] ? (char)strtoul(argv[6], NULL, 0) : 0; - debugC(5, kDebugLevelMain, "Opcode: %s %s %s %s", logicNamesCmd[i].name, argv[1], argv[2], argv[3]); + debugC(5, kDebugLevelMain, "Opcode: %s %s %s %s", opCodes[i].name, argv[1], argv[2], argv[3]); _vm->executeAgiCommand(i, p); @@ -392,24 +394,26 @@ bool Console::Cmd_Room(int argc, const char **argv) { } bool Console::Cmd_BT(int argc, const char **argv) { + const AgiOpCodeEntry *opCodes = _vm->getOpCodesTable(); + debugPrintf("Current script: %d\nStack depth: %d\n", _vm->_game.curLogicNr, _vm->_game.execStack.size()); uint8 *code = NULL; uint8 op = 0; uint8 p[CMD_BSIZE] = { 0 }; - int num; + int parameterSize; Common::Array<ScriptPos>::iterator it; for (it = _vm->_game.execStack.begin(); it != _vm->_game.execStack.end(); ++it) { code = _vm->_game.logics[it->script].data; op = code[it->curIP]; - num = logicNamesCmd[op].argumentsLength(); - memmove(p, &code[it->curIP], num); - memset(p + num, 0, CMD_BSIZE - num); + parameterSize = opCodes[op].parameterSize; + memmove(p, &code[it->curIP], parameterSize); + memset(p + parameterSize, 0, CMD_BSIZE - parameterSize); - debugPrintf("%d(%d): %s(", it->script, it->curIP, logicNamesCmd[op].name); + debugPrintf("%d(%d): %s(", it->script, it->curIP, opCodes[op].name); - for (int i = 0; i < num; i++) + for (int i = 0; i < parameterSize; i++) debugPrintf("%d, ", p[i]); debugPrintf(")\n"); diff --git a/engines/agi/id.cpp b/engines/agi/id.cpp deleted file mode 100644 index 7985d3b9e4..0000000000 --- a/engines/agi/id.cpp +++ /dev/null @@ -1,97 +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. - * - */ - -#include "agi/agi.h" -#include "agi/opcodes.h" - -namespace Agi { - -// -// Currently, there is no known difference between v3.002.098 -> v3.002.149 -// So version emulated; -// -// 0x0086, -// 0x0149 -// - -/** - * - */ -int AgiEngine::setupV2Game(int ver) { - int ec = errOK; - - // Should this go above the previous lines, so we can force emulation versions - // even for AGDS games? -- dsymonds - if (getFeatures() & GF_AGDS) - setVersion(ver = 0x2440); // ALL AGDS games built for 2.440 - - debug(0, "Setting up for version 0x%04X", ver); - - // 'quit' takes 0 args for 2.089 - if (ver == 0x2089) -// logicNamesCmd[0x86].numArgs = 0; - logicNamesCmd[0x86].args = ""; - - // 'print.at' and 'print.at.v' take 3 args before 2.272 - // This is documented in the specs as only < 2.440, but it seems - // that KQ3 (2.272) needs a 'print.at' taking 4 args. - if (ver < 0x2272) { -// logicNamesCmd[0x97].numArgs = 3; -// logicNamesCmd[0x98].numArgs = 3; - logicNamesCmd[0x97].args = "vvv"; - logicNamesCmd[0x98].args = "vvv"; - } - - return ec; -} - -/** - * - */ -int AgiEngine::setupV3Game(int ver) { - int ec = errOK; - - debug(0, "Setting up for version 0x%04X", ver); - - // 'unknown176' takes 1 arg for 3.002.086, not 0 args. - // 'unknown173' also takes 1 arg for 3.002.068, not 0 args. - // Is this actually used anywhere? -- dsymonds - if (ver == 0x3086) { -// logicNamesCmd[0xb0].numArgs = 1; -// logicNamesCmd[0xad].numArgs = 1; - logicNamesCmd[0xb0].args = "n"; - logicNamesCmd[0xad].args = "n"; - } - - // FIXME: Apply this fix to other games also that use 2 arguments for command 182. - // 'adj.ego.move.to.x.y' (i.e. command 182) takes 2 arguments for at least the - // Amiga Gold Rush! (v2.05 1989-03-09) using Amiga AGI 2.316. Amiga's Gold Rush - // has been set to use AGI 3.149 in ScummVM so that's why this initialization is - // here and not in setupV2Game. - if (getGameID() == GID_GOLDRUSH && getPlatform() == Common::kPlatformAmiga) -// logicNamesCmd[182].numArgs = 2; - logicNamesCmd[182].args = "vv"; - - return ec; -} - -} // End of namespace Agi diff --git a/engines/agi/loader_v1.cpp b/engines/agi/loader_v1.cpp index 0c569382cf..159e13772a 100644 --- a/engines/agi/loader_v1.cpp +++ b/engines/agi/loader_v1.cpp @@ -61,7 +61,7 @@ int AgiLoader_v1::detectGame() { _filenameDisk0 = _vm->getDiskName(BooterDisk1); _filenameDisk1 = _vm->getDiskName(BooterDisk2); - return _vm->setupV2Game(_vm->getVersion()); + return errOK; } int AgiLoader_v1::loadDir_DDP(AgiDir *agid, int offset, int max) { diff --git a/engines/agi/loader_v2.cpp b/engines/agi/loader_v2.cpp index 43ef46bd72..bebde69fe9 100644 --- a/engines/agi/loader_v2.cpp +++ b/engines/agi/loader_v2.cpp @@ -34,7 +34,12 @@ int AgiLoader_v2::detectGame() { !Common::File::exists(VIEWDIR)) return errInvalidAGIFile; - return _vm->setupV2Game(_vm->getVersion()); + // Should this go above the previous lines, so we can force emulation versions + // even for AGDS games? -- dsymonds + if (_vm->getFeatures() & GF_AGDS) + _vm->setVersion(0x2440); // ALL AGDS games built for 2.440 + + return errOK; } int AgiLoader_v2::loadDir(AgiDir *agid, const char *fname) { diff --git a/engines/agi/loader_v3.cpp b/engines/agi/loader_v3.cpp index 5a208a5114..c21ad41cc5 100644 --- a/engines/agi/loader_v3.cpp +++ b/engines/agi/loader_v3.cpp @@ -52,7 +52,7 @@ int AgiLoader_v3::detectGame() { strncpy(_vm->_game.name, f.c_str(), MIN((uint)8, f.size() > 5 ? f.size() - 5 : f.size())); debugC(3, kDebugLevelMain, "game.name = %s", _vm->_game.name); - ec = _vm->setupV3Game(_vm->getVersion()); + ec = errOK; found = true; } diff --git a/engines/agi/module.mk b/engines/agi/module.mk index 32c3ac23ed..8ca261f55b 100644 --- a/engines/agi/module.mk +++ b/engines/agi/module.mk @@ -9,7 +9,6 @@ MODULE_OBJS := \ font.o \ global.o \ graphics.o \ - id.o \ inv.o \ keyboard.o \ loader_v1.o \ diff --git a/engines/agi/op_cmd.cpp b/engines/agi/op_cmd.cpp index 8a62fce86c..32400b5afe 100644 --- a/engines/agi/op_cmd.cpp +++ b/engines/agi/op_cmd.cpp @@ -1051,9 +1051,10 @@ void cmdReleaseKey(AgiGame *state, AgiEngine *vm, uint8 *parameter) { } void cmdAdjEgoMoveToXY(AgiGame *state, AgiEngine *vm, uint8 *parameter) { + const AgiOpCodeEntry *opCodeTable = vm->getOpCodesTable(); int8 x, y; - switch (logicNamesCmd[182].argumentsLength()) { + switch (opCodeTable[182].parameterSize) { // The 2 arguments version is used at least in Amiga Gold Rush! // (v2.05 1989-03-09, Amiga AGI 2.316) in logics 130 and 150 // (Using arguments (0, 0), (0, 7), (0, 8), (9, 9) and (-9, 9)). @@ -2308,7 +2309,7 @@ int AgiEngine::runLogic(int16 logicNr) { AgiGame *state = &_game; uint8 op = 0; uint8 p[CMD_BSIZE] = { 0 }; - int num = 0; + int curParameterSize = 0; ScriptPos sp; //int logic_index = 0; @@ -2390,14 +2391,18 @@ int AgiEngine::runLogic(int16 logicNr) { _game.execStack.pop_back(); return 1; default: - num = logicNamesCmd[op].argumentsLength(); - memmove(p, state->_curLogic->data + state->_curLogic->cIP, num); - memset(p + num, 0, CMD_BSIZE - num); + curParameterSize = _opCodes[op].parameterSize; + memmove(p, state->_curLogic->data + state->_curLogic->cIP, curParameterSize); + memset(p + curParameterSize, 0, CMD_BSIZE - curParameterSize); - debugC(2, kDebugLevelScripts, "%s%s(%d %d %d)", st, logicNamesCmd[op].name, p[0], p[1], p[2]); + debugC(2, kDebugLevelScripts, "%s%s(%d %d %d)", st, _opCodes[op].name, p[0], p[1], p[2]); - _agiCommands[op](&_game, this, p); - state->_curLogic->cIP += num; + if (!_opCodes[op].functionPtr) { + error("Illegal opcode %x in logic %d, ip %d", op, state->curLogicNr, state->_curLogic->cIP); + } + + _opCodes[op].functionPtr(&_game, this, p); + state->_curLogic->cIP += curParameterSize; } // if ((op == 0x0B || op == 0x3F || op == 0x40) && logic_index < state->max_logics) { @@ -2418,9 +2423,9 @@ int AgiEngine::runLogic(int16 logicNr) { } void AgiEngine::executeAgiCommand(uint8 op, uint8 *p) { - debugC(2, kDebugLevelScripts, "%s(%d %d %d)", logicNamesCmd[op].name, p[0], p[1], p[2]); + debugC(2, kDebugLevelScripts, "%s(%d %d %d)", _opCodes[op].name, p[0], p[1], p[2]); - _agiCommands[op](&_game, this, p); + _opCodes[op].functionPtr(&_game, this, p); } } // End of namespace Agi diff --git a/engines/agi/op_dbg.cpp b/engines/agi/op_dbg.cpp index c57782acd5..b35bd3928c 100644 --- a/engines/agi/op_dbg.cpp +++ b/engines/agi/op_dbg.cpp @@ -28,16 +28,14 @@ namespace Agi { #define ip (_game.logics[lognum].cIP) #define code (_game.logics[lognum].data) -AgiInstruction logicNamesIf[] = { - { "OR", "", NULL }, - { "NOT", "", NULL }, - { "ELSE", "", NULL }, - { "IF", "", NULL } +const char *logicNamesIf[] = { + "OR", "NOT", "ELSE", "IF" }; void AgiEngine::debugConsole(int lognum, int mode, const char *str) { - AgiInstruction *x; - uint8 a, z; + AgiOpCodeEntry *curOpCodeTable; + uint8 parametersLeft, z; + uint8 logicNameIdx; const char *c; if (str) { @@ -52,8 +50,6 @@ void AgiEngine::debugConsole(int lognum, int mode, const char *str) { case 0xFD: case 0xFE: case 0xFF: - x = logicNamesIf; - if (_debug.opcodes) { debugN(0, "%02X %02X %02X %02X %02X %02X %02X %02X %02X\n" " ", @@ -67,12 +63,13 @@ void AgiEngine::debugConsole(int lognum, int mode, const char *str) { (uint8) * (code + (7 + ip)) & 0xFF, (uint8) * (code + (8 + ip)) & 0xFF); } - debugN(0, "%s ", (x + * (code + ip) - 0xFC)->name); + logicNameIdx = (*(code + ip)) - 0xFC; + debugN(0, "%s ", logicNamesIf[logicNameIdx]); break; default: - x = mode == lCOMMAND_MODE ? logicNamesCmd : logicNamesTest; - a = x[*(code + ip)].argumentsLength(); - c = x[*(code + ip)].args; + curOpCodeTable = mode == lCOMMAND_MODE ? _opCodes : _opCodesCond; + parametersLeft = curOpCodeTable[*(code + ip)].parameterSize; + c = curOpCodeTable[*(code + ip)].parameters; if (_debug.opcodes) { debugN(0, "%02X %02X %02X %02X %02X %02X %02X %02X %02X\n" @@ -87,9 +84,9 @@ void AgiEngine::debugConsole(int lognum, int mode, const char *str) { (uint8) * (code + (7 + ip)) & 0xFF, (uint8) * (code + (8 + ip)) & 0xFF); } - debugN(0, "%s ", (x + * (code + ip))->name); + debugN(0, "%s ", (curOpCodeTable + * (code + ip))->name); - for (z = 1; a > 0;) { + for (z = 1; parametersLeft > 0;) { if (*c == 'n') { debugN(0, "%d", *(code + (ip + z))); } else { @@ -97,7 +94,7 @@ void AgiEngine::debugConsole(int lognum, int mode, const char *str) { } c++; z++; - if (--a > 0) + if (--parametersLeft > 0) debugN(0, ","); } break; diff --git a/engines/agi/op_test.cpp b/engines/agi/op_test.cpp index 4505668fd1..6afddf844a 100644 --- a/engines/agi/op_test.cpp +++ b/engines/agi/op_test.cpp @@ -376,7 +376,7 @@ uint8 AgiEngine::testSaid(uint8 nwords, uint8 *cc) { return true; } -int AgiEngine::testIfCode(int lognum) { +bool AgiEngine::testIfCode(int16 logicNr) { AgiGame *state = &_game; uint8 op; uint8 p[16]; @@ -387,8 +387,8 @@ int AgiEngine::testIfCode(int lognum) { int result = true; while (!(shouldQuit() || _restartGame) && !endTest) { - if (_debug.enabled && (_debug.logic0 || lognum)) - debugConsole(lognum, lTEST_MODE, NULL); + if (_debug.enabled && (_debug.logic0 || logicNr)) + debugConsole(logicNr, lTEST_MODE, NULL); op = *(code + ip++); memmove(p, (code + ip), 16); @@ -418,7 +418,14 @@ int AgiEngine::testIfCode(int lognum) { default: // Evaluate the command and skip the rest of the instruction - _agiCondCommands[op](state, this, p); + _opCodesCond[op].functionPtr(state, this, p); + if (state->exitAllLogics) { + // required even here, because of at least the timer heuristic + // which when triggered waits a bit and processes ScummVM events and user may therefore restore a saved game + // fixes bug #9707 + // TODO: maybe delay restoring the game instead, when GMM is used? + return true; + } skipInstruction(op); // NOT mode is enabled only for one instruction @@ -457,8 +464,8 @@ int AgiEngine::testIfCode(int lognum) { else ip += READ_LE_UINT16(code + ip) + 2; - if (_debug.enabled && (_debug.logic0 || lognum)) - debugConsole(lognum, 0xFF, result ? "=true" : "=false"); + if (_debug.enabled && (_debug.logic0 || logicNr)) + debugConsole(logicNr, 0xFF, result ? "=true" : "=false"); return result; } @@ -469,16 +476,26 @@ void AgiEngine::skipInstruction(byte op) { return; if (op == 0x0E && state->_vm->getVersion() >= 0x2000) // said ip += *(code + ip) * 2 + 1; - else - ip += logicNamesTest[op].argumentsLength(); + else { + ip += _opCodesCond[op].parameterSize; + } } void AgiEngine::skipInstructionsUntil(byte v) { AgiGame *state = &_game; + int originalIP = state->_curLogic->cIP; + while (1) { byte op = *(code + ip++); if (op == v) return; + + if (op < 0xFC) { + if (!_opCodesCond[op].functionPtr) { + // security-check + error("illegal opcode %x during skipinstructions in script %d at %d (triggered at %d)", op, state->curLogicNr, ip, originalIP); + } + } skipInstruction(op); } } diff --git a/engines/agi/opcodes.cpp b/engines/agi/opcodes.cpp index 472917de77..be6748b40c 100644 --- a/engines/agi/opcodes.cpp +++ b/engines/agi/opcodes.cpp @@ -25,10 +25,7 @@ namespace Agi { -AgiInstruction *logicNamesTest; -AgiInstruction *logicNamesCmd; - -AgiInstruction insV1Test[] = { +const AgiOpCodeDefinitionEntry opCodesV1Cond[] = { { "", "", &condUnknown }, // 00 { "equaln", "vn", &condEqual }, // 01 { "equalv", "vv", &condEqualV }, // 02 @@ -48,7 +45,7 @@ AgiInstruction insV1Test[] = { { "bit", "nv", &condBit }, // 10 }; -AgiInstruction insV1[] = { +const AgiOpCodeDefinitionEntry opCodesV1[] = { { "return", "", NULL }, // 00 { "increment", "v", &cmdIncrement }, // 01 { "decrement", "v", &cmdDecrement }, // 02 @@ -149,7 +146,7 @@ AgiInstruction insV1[] = { { "...", "nv", &cmdUnknown }, // 61 # clearbit }; -AgiInstruction insV2Test[] = { +AgiOpCodeDefinitionEntry opCodesV2Cond[] = { { "", "", &condUnknown }, // 00 { "equaln", "vn", &condEqual }, // 01 { "equalv", "vv", &condEqualV }, // 02 @@ -172,7 +169,7 @@ AgiInstruction insV2Test[] = { { "in.motion.using.mouse", "", &condUnknown13 } // 13 }; -AgiInstruction insV2[] = { +AgiOpCodeDefinitionEntry opCodesV2[] = { { "return", "", NULL }, // 00 { "increment", "v", &cmdIncrement }, // 01 { "decrement", "v", &cmdDecrement }, // 02 @@ -358,36 +355,115 @@ AgiInstruction insV2[] = { { "adj.ego.move.to.xy", "", &cmdAdjEgoMoveToXY } // C6 }; -void AgiEngine::setupOpcodes() { - if (getVersion() >= 0x2000) { - for (int i = 0; i < ARRAYSIZE(insV2Test); ++i) - _agiCondCommands[i] = insV2Test[i].func; - for (int i = 0; i < ARRAYSIZE(insV2); ++i) - _agiCommands[i] = insV2[i].func; +// +// Currently, there is no known difference between v3.002.098 -> v3.002.149 +// So version emulated; +// 0x0086, +// 0x0149 +// - logicNamesTest = insV2Test; - logicNamesCmd = insV2; +void AgiEngine::setupOpCodes(uint16 version) { + const AgiOpCodeDefinitionEntry *opCodesTable = nullptr; + const AgiOpCodeDefinitionEntry *opCodesCondTable = nullptr; + uint16 opCodesTableSize = 0; + uint16 opCodesCondTableSize = 0; + uint16 opCodesTableMaxSize = sizeof(_opCodes) / sizeof(AgiOpCodeEntry); + uint16 opCodesCondTableMaxSize = sizeof(_opCodesCond) / sizeof(AgiOpCodeEntry); - // Alter opcode parameters for specific games - // TODO: This could be either turned into a game feature, or a version - // specific check, instead of a game version check + debug(0, "Setting up for version 0x%04X", version); - // The Apple IIGS versions of MH1 and Goldrush both have a parameter for - // show.mouse and hide.mouse. Fixes bugs #3577754 and #3426946. - if ((getGameID() == GID_MH1 || getGameID() == GID_GOLDRUSH) && - getPlatform() == Common::kPlatformApple2GS) { - logicNamesCmd[176].args = "n"; // hide.mouse - logicNamesCmd[178].args = "n"; // show.mouse - } + if (version >= 0x2000) { + opCodesTable = opCodesV2; + opCodesCondTable = opCodesV2Cond; + opCodesTableSize = ARRAYSIZE(opCodesV2); + opCodesCondTableSize = ARRAYSIZE(opCodesV2Cond); } else { - for (int i = 0; i < ARRAYSIZE(insV1Test); ++i) - _agiCondCommands[i] = insV1Test[i].func; - for (int i = 0; i < ARRAYSIZE(insV1); ++i) - _agiCommands[i] = insV1[i].func; + opCodesTable = opCodesV1; + opCodesCondTable = opCodesV1Cond; + opCodesTableSize = ARRAYSIZE(opCodesV1); + opCodesCondTableSize = ARRAYSIZE(opCodesV1Cond); + } - logicNamesTest = insV1Test; - logicNamesCmd = insV1; + // copy data over + for (int opCodeNr = 0; opCodeNr < opCodesTableSize; opCodeNr++) { + _opCodes[opCodeNr].name = opCodesTable[opCodeNr].name; + _opCodes[opCodeNr].parameters = opCodesTable[opCodeNr].parameters; + _opCodes[opCodeNr].functionPtr = opCodesTable[opCodeNr].functionPtr; } -} + for (int opCodeNr = 0; opCodeNr < opCodesCondTableSize; opCodeNr++) { + _opCodesCond[opCodeNr].name = opCodesCondTable[opCodeNr].name; + _opCodesCond[opCodeNr].parameters = opCodesCondTable[opCodeNr].parameters; + _opCodesCond[opCodeNr].functionPtr = opCodesCondTable[opCodeNr].functionPtr; + } + + // Alter opcode parameters for specific games + if ((version >= 0x2000) && (version < 0x3000)) { + // AGI3 adjustments + + // 'quit' takes 0 args for 2.089 + if (version == 0x2089) + _opCodes[0x86].parameters = ""; + + // 'print.at' and 'print.at.v' take 3 args before 2.272 + // This is documented in the specs as only < 2.440, but it seems + // that KQ3 (2.272) needs a 'print.at' taking 4 args. + if (version < 0x2272) { + _opCodes[0x97].parameters = "vvv"; + _opCodes[0x98].parameters = "vvv"; + } + } + + if (version >= 0x3000) { + // AGI3 adjustments + // 'unknown176' takes 1 arg for 3.002.086, not 0 args. + // 'unknown173' also takes 1 arg for 3.002.068, not 0 args. + // Is this actually used anywhere? -- dsymonds + if (version == 0x3086) { + _opCodes[0xb0].parameters = "n"; + _opCodes[0xad].parameters = "n"; + } + } + + // TODO: This could be either turned into a game feature, or a version + // specific check, instead of a game version check + // The Apple IIGS versions of MH1 and Goldrush both have a parameter for + // show.mouse and hide.mouse. Fixes bugs #3577754 and #3426946. + if ((getGameID() == GID_MH1 || getGameID() == GID_GOLDRUSH) && + getPlatform() == Common::kPlatformApple2GS) { + _opCodes[176].parameters = "n"; // hide.mouse + _opCodes[178].parameters = "n"; // show.mouse + } + + // FIXME: Apply this fix to other games also that use 2 arguments for command 182. + // 'adj.ego.move.to.x.y' (i.e. command 182) takes 2 arguments for at least the + // Amiga Gold Rush! (v2.05 1989-03-09) using Amiga AGI 2.316. Amiga's Gold Rush + // has been set to use AGI 3.149 in ScummVM so that's why this initialization is + // here and not in setupV2Game. + if (getGameID() == GID_GOLDRUSH && getPlatform() == Common::kPlatformAmiga) + _opCodes[182].parameters = "vv"; + + // add invalid entries for every opcode, that is not defined at all + for (int opCodeNr = opCodesTableSize; opCodeNr < opCodesTableMaxSize; opCodeNr++) { + _opCodes[opCodeNr].name = "illegal"; + _opCodes[opCodeNr].parameters = ""; + _opCodes[opCodeNr].functionPtr = nullptr; + } + + for (int opCodeNr = opCodesCondTableSize; opCodeNr < opCodesCondTableMaxSize; opCodeNr++) { + _opCodesCond[opCodeNr].name = "illegal"; + _opCodesCond[opCodeNr].parameters = ""; + _opCodesCond[opCodeNr].functionPtr = nullptr; + } + + // calculate parameter size + for (int opCodeNr = 0; opCodeNr < opCodesTableSize; opCodeNr++) { + _opCodes[opCodeNr].parameterSize = strlen( _opCodes[opCodeNr].parameters); + } + + for (int opCodeNr = 0; opCodeNr < opCodesCondTableSize; opCodeNr++) { + _opCodesCond[opCodeNr].parameterSize = strlen( _opCodesCond[opCodeNr].parameters); + } } + +} // End of namespace Agi diff --git a/engines/agi/opcodes.h b/engines/agi/opcodes.h index d9644bdcda..63c922dc39 100644 --- a/engines/agi/opcodes.h +++ b/engines/agi/opcodes.h @@ -25,17 +25,6 @@ namespace Agi { -struct AgiInstruction { - const char *name; - const char *args; - AgiCommand func; - - int argumentsLength() { return strlen(args); } -}; - -extern AgiInstruction *logicNamesTest; -extern AgiInstruction *logicNamesCmd; - void cmdIncrement(AgiGame *state, AgiEngine *vm, uint8 *p); void cmdDecrement(AgiGame *state, AgiEngine *vm, uint8 *p); void cmdAssignN(AgiGame *state, AgiEngine *vm, uint8 *p); diff --git a/engines/director/cast.cpp b/engines/director/cast.cpp index ed5b05643c..4b391bd8cc 100644 --- a/engines/director/cast.cpp +++ b/engines/director/cast.cpp @@ -83,7 +83,7 @@ TextCast::TextCast(Common::ReadStreamEndian &stream, uint16 version) { textSlant = 0; palinfo1 = palinfo2 = palinfo3 = 0; - if (version < 4) { + if (version <= 3) { flags1 = stream.readByte(); borderSize = static_cast<SizeType>(stream.readByte()); gutterSize = static_cast<SizeType>(stream.readByte()); @@ -115,7 +115,7 @@ TextCast::TextCast(Common::ReadStreamEndian &stream, uint16 version) { fontId = stream.readByte(); fontSize = stream.readByte(); textSlant = 0; - } else if (version < 5) { + } else if (version == 4) { borderSize = static_cast<SizeType>(stream.readByte()); gutterSize = static_cast<SizeType>(stream.readByte()); boxShadow = static_cast<SizeType>(stream.readByte()); @@ -134,7 +134,7 @@ TextCast::TextCast(Common::ReadStreamEndian &stream, uint16 version) { byte flags = stream.readByte(); if (flags) - warning("Unproxessed text cast flags: %x", flags); + warning("Unprocessed text cast flags: %x", flags); fontSize = stream.readUint16(); textSlant = 0; diff --git a/engines/director/director.cpp b/engines/director/director.cpp index bfe9a724be..a1ee253087 100644 --- a/engines/director/director.cpp +++ b/engines/director/director.cpp @@ -78,7 +78,7 @@ DirectorEngine::DirectorEngine(OSystem *syst, const DirectorGameDescription *gam _movies = nullptr; - _nextMovieFrameI = -1; + _nextMovie.frameI = -1; _wm = nullptr; @@ -165,21 +165,25 @@ Common::Error DirectorEngine::run() { _currentScore->loadArchive(); // If we came in a loop, then skip as requested - if (!_nextMovieFrameS.empty()) - _currentScore->setStartToLabel(_nextMovieFrameS); + if (!_nextMovie.frameS.empty()) { + _currentScore->setStartToLabel(_nextMovie.frameS); + _nextMovie.frameS.clear(); + } - if (_nextMovieFrameI != -1) - _currentScore->setCurrentFrame(_nextMovieFrameI); + if (_nextMovie.frameI != -1) { + _currentScore->setCurrentFrame(_nextMovie.frameI); + _nextMovie.frameI = -1; + } _currentScore->startLoop(); // If a loop was requested, do it - if (!_nextMovie.empty()) { + if (!_nextMovie.movie.empty()) { _lingo->restartLingo(); delete _currentScore; - Archive *mov = openMainArchive(_nextMovie); + Archive *mov = openMainArchive(_nextMovie.movie); if (!mov) { warning("nextMovie: No score is loaded"); @@ -190,7 +194,7 @@ Common::Error DirectorEngine::run() { _currentScore = new Score(this, mov); debug(0, "Score name %s", _currentScore->getMacName().c_str()); - _nextMovie.clear(); + _nextMovie.movie.clear(); loop = true; } } diff --git a/engines/director/director.h b/engines/director/director.h index fdbe8ded48..1c3d77fc71 100644 --- a/engines/director/director.h +++ b/engines/director/director.h @@ -62,6 +62,14 @@ enum { kDebugLingoParse = 1 << 6 }; +struct MovieReference { + Common::String movie; + Common::String frameS; + int frameI; + + MovieReference() { frameI = -1; } +}; + extern byte defaultPalette[768]; class DirectorEngine : public ::Engine { @@ -112,9 +120,8 @@ public: bool _playbackPaused; bool _skipFrameAdvance; - Common::String _nextMovie; - Common::String _nextMovieFrameS; - int _nextMovieFrameI; + MovieReference _nextMovie; + Common::List<MovieReference> _movieStack; protected: virtual Common::Error run(); diff --git a/engines/director/frame.cpp b/engines/director/frame.cpp index 3c73b82af1..d20026cb62 100644 --- a/engines/director/frame.cpp +++ b/engines/director/frame.cpp @@ -915,6 +915,11 @@ void Frame::renderText(Graphics::ManagedSurface &surface, uint16 spriteId, Commo // textCast->fontId = _vm->_wm->_fontMan->getFontIdByName(_vm->getCurrentScore()->_fontMap[textCast->fontId]); } + if (width == 0 || height == 0) { + warning("renderText: Requested to draw on an empty surface: %d x %d", width, height); + return; + } + Graphics::MacFont macFont = Graphics::MacFont(textCast->fontId, textCast->fontSize, textCast->textSlant); const Graphics::Font *font = _vm->_wm->_fontMan->getFont(macFont); diff --git a/engines/director/lingo/lingo-builtins.cpp b/engines/director/lingo/lingo-builtins.cpp index f4c26a2193..6411c59d4f 100644 --- a/engines/director/lingo/lingo-builtins.cpp +++ b/engines/director/lingo/lingo-builtins.cpp @@ -1505,7 +1505,21 @@ void Lingo::b_cast(int nargs) { void Lingo::b_field(int nargs) { Datum d = g_lingo->pop(); - warning("STUB: b_field"); + int id; + + if (d.type == STRING) { + if (g_director->getCurrentScore()->_castsNames.contains(*d.u.s)) + id = g_director->getCurrentScore()->_castsNames[*d.u.s]; + else + error("b_filed: Reference to non-existent field: %s", d.u.s->c_str()); + } else if (d.type == INT || d.type == FLOAT) { + d.toInt(); + id = d.u.i; + } else { + error("b_field: Incorrect reference type: %s", d.type2str()); + } + + d.u.i = id; d.type = REFERENCE; diff --git a/engines/director/lingo/lingo-code.cpp b/engines/director/lingo/lingo-code.cpp index eeae0534d8..b7fc484d91 100644 --- a/engines/director/lingo/lingo-code.cpp +++ b/engines/director/lingo/lingo-code.cpp @@ -43,6 +43,7 @@ // ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF // THIS SOFTWARE. +#include "director/cast.h" #include "director/lingo/lingo.h" #include "director/lingo/lingo-gr.h" @@ -142,7 +143,7 @@ void Lingo::pushVoid() { Datum Lingo::pop(void) { if (_stack.size() == 0) - error("stack underflow"); + assert(0); Datum ret = _stack.back(); _stack.pop_back(); @@ -212,7 +213,7 @@ void Lingo::c_voidpush() { void Lingo::c_fconstpush() { Datum d; inst i = (*g_lingo->_currentScript)[g_lingo->_pc]; - d.u.i = READ_UINT32(&i); // d.u.f value will be read + d.u.f = *(double *)(&i); d.type = FLOAT; g_lingo->_pc += g_lingo->calcCodeAlignment(sizeof(double)); @@ -305,9 +306,14 @@ void Lingo::c_assign() { } if (d1.type == REFERENCE) { + if (!g_director->getCurrentScore()->_castsInfo.contains(d1.u.i)) { + warning("c_assign: Unknown REFERENCE %d", d1.u.i); + g_lingo->pushVoid(); + return; + } + warning("STUB: c_assing REFERENCE"); - g_lingo->push(d1); return; } @@ -343,8 +349,6 @@ void Lingo::c_assign() { } d1.u.sym->type = d2.type; - - g_lingo->push(d1); } bool Lingo::verify(Symbol *s) { @@ -422,8 +426,6 @@ void Lingo::c_theentityassign() { Datum d = g_lingo->pop(); g_lingo->setTheEntity(entity, id, field, d); - - g_lingo->push(d); // Dummy value } void Lingo::c_swap() { @@ -833,7 +835,7 @@ void Lingo::c_repeatwhilecode(void) { d.toInt(); while (d.u.i) { - g_lingo->execute(body); /* body */ + g_lingo->execute(body + savepc - 1); /* body */ if (g_lingo->_returning) break; @@ -848,7 +850,7 @@ void Lingo::c_repeatwhilecode(void) { } if (!g_lingo->_returning) - g_lingo->_pc = end; /* next stmt */ + g_lingo->_pc = end + savepc - 1; /* next stmt */ } void Lingo::c_repeatwithcode(void) { @@ -867,14 +869,14 @@ void Lingo::c_repeatwithcode(void) { error("Cast ref used as index: %s", countername.c_str()); } - g_lingo->execute(init); /* condition */ + g_lingo->execute(init + savepc - 1); /* condition */ d = g_lingo->pop(); d.toInt(); counter->u.i = d.u.i; counter->type = INT; while (true) { - g_lingo->execute(body); /* body */ + g_lingo->execute(body + savepc - 1); /* body */ if (g_lingo->_returning) break; @@ -884,7 +886,7 @@ void Lingo::c_repeatwithcode(void) { } counter->u.i += inc; - g_lingo->execute(finish); /* condition */ + g_lingo->execute(finish + savepc - 1); /* condition */ d = g_lingo->pop(); d.toInt(); @@ -893,7 +895,7 @@ void Lingo::c_repeatwithcode(void) { } if (!g_lingo->_returning) - g_lingo->_pc = end; /* next stmt */ + g_lingo->_pc = end + savepc - 1; /* next stmt */ } void Lingo::c_exitRepeat(void) { @@ -916,14 +918,14 @@ void Lingo::c_ifcode() { if (d.toInt()) { debugC(8, kDebugLingoExec, "executing then"); - g_lingo->execute(then); + g_lingo->execute(then + savepc - 1); } else if (elsep) { /* else part? */ debugC(8, kDebugLingoExec, "executing else"); - g_lingo->execute(elsep); + g_lingo->execute(elsep + savepc - 1); } if (!g_lingo->_returning && !skipEnd) { - g_lingo->_pc = end; /* next stmt */ + g_lingo->_pc = end + savepc - 1; /* next stmt */ debugC(8, kDebugLingoExec, "executing end"); } else { debugC(8, kDebugLingoExec, "Skipped end"); @@ -933,20 +935,25 @@ void Lingo::c_ifcode() { void Lingo::c_whencode() { Datum d; uint start = g_lingo->_pc; - uint end = READ_UINT32(&(*g_lingo->_currentScript)[start]); + uint end = READ_UINT32(&(*g_lingo->_currentScript)[start]) + start - 1; Common::String eventname((char *)&(*g_lingo->_currentScript)[start + 1]); start += g_lingo->calcStringAlignment(eventname.c_str()) + 1; - debugC(3, kDebugLingoExec, "c_whencode([%5d][%5d], %s)", start, end, eventname.c_str()); + debugC(1, kDebugLingoExec, "c_whencode([%5d][%5d], %s)", start, end, eventname.c_str()); + + int entity = g_lingo->_currentEntityId; + g_lingo->_currentEntityId = 0; g_lingo->define(eventname, start, 0, NULL, end); - if (debugChannelSet(3, kDebugLingoExec)) { + g_lingo->_currentEntityId = entity; + + if (debugChannelSet(1, kDebugLingoExec)) { uint pc = start; while (pc <= end) { Common::String instr = g_lingo->decodeInstruction(pc, &pc); - debugC(3, kDebugLingoExec, "[%5d] %s", pc, instr.c_str()); + debugC(1, kDebugLingoExec, "[%5d] %s", pc, instr.c_str()); } } @@ -996,23 +1003,11 @@ void Lingo::c_play() { if (mode.u.i == 1 || mode.u.i == 3) frame = g_lingo->pop(); - if (frame.type == VOID) { - frame.u.s = new Common::String("<void>"); - frame.type = STRING; - } - frame.toString(); - - if (movie.type == VOID) { - movie.u.s = new Common::String("<void>"); - movie.type = STRING; - } - movie.toString(); - - warning("STUB: c_play(%s, %s)", frame.u.s->c_str(), movie.u.s->c_str()); + g_lingo->func_play(frame, movie); } void Lingo::c_playdone() { - warning("STUB: c_playdone()"); + g_lingo->func_playdone(); } void Lingo::c_call() { @@ -1121,7 +1116,7 @@ void Lingo::call(Common::String name, int nargs) { void Lingo::c_procret() { if (!g_lingo->_callstack.size()) { - warning("Call stack underflow"); + warning("c_procret: Call stack underflow"); g_lingo->_returning = true; return; } diff --git a/engines/director/lingo/lingo-codegen.cpp b/engines/director/lingo/lingo-codegen.cpp index 0d771ec44e..d69de85e9a 100644 --- a/engines/director/lingo/lingo-codegen.cpp +++ b/engines/director/lingo/lingo-codegen.cpp @@ -103,7 +103,7 @@ Common::String Lingo::decodeInstruction(uint pc, uint *newPc) { { Datum d; i = (*_currentScript)[pc++]; - d.u.i = READ_UINT32(&i); + d.u.f = *(double *)(&i); res += Common::String::format(" %f", d.u.f); break; @@ -214,7 +214,7 @@ void Lingo::define(Common::String &name, int start, int nargs, Common::String *p if (prefix) name = *prefix + "-" + name; - debugC(3, kDebugLingoCompile, "define(\"%s\", %d, %d, %d)", name.c_str(), start, _currentScript->size() - 1, nargs); + debugC(1, kDebugLingoCompile, "define(\"%s\", %d, %d, %d)", name.c_str(), start, _currentScript->size() - 1, nargs); Symbol *sym = getHandler(name); if (sym == NULL) { // Create variable if it was not defined @@ -311,7 +311,6 @@ void Lingo::codeArgStore() { code1(c_varpush); codeString(arg->c_str()); code1(c_assign); - code1(c_xpop); delete arg; } @@ -380,6 +379,9 @@ void Lingo::processIf(int elselabel, int endlabel) { if (!label) break; + if (else1) + else1 = else1 - label; + WRITE_UINT32(&ielse1, else1); (*_currentScript)[label + 2] = ielse1; /* elsepart */ (*_currentScript)[label + 3] = iend; /* end, if cond fails */ diff --git a/engines/director/lingo/lingo-funcs.cpp b/engines/director/lingo/lingo-funcs.cpp index ddc51f4149..f21f01a967 100644 --- a/engines/director/lingo/lingo-funcs.cpp +++ b/engines/director/lingo/lingo-funcs.cpp @@ -172,7 +172,7 @@ void Lingo::func_mciwait(Common::String &s) { } void Lingo::func_goto(Datum &frame, Datum &movie) { - g_director->_playbackPaused = false; + _vm->_playbackPaused = false; if (!_vm->getCurrentScore()) return; @@ -180,17 +180,29 @@ void Lingo::func_goto(Datum &frame, Datum &movie) { if (movie.type != VOID) { movie.toString(); + Common::String cleanedFilename; + + for (const char *p = movie.u.s->c_str(); *p; p++) + if (*p >= 0x20 && *p <= 0x7f) + cleanedFilename += *p; + bool fileExists = false; if (_vm->getPlatform() == Common::kPlatformMacintosh) { Common::MacResManager resMan; if (resMan.open(*movie.u.s)) { fileExists = true; + cleanedFilename = *movie.u.s; + } else if (!movie.u.s->equals(cleanedFilename) && resMan.open(cleanedFilename)) { + fileExists = true; } } else { Common::File file; if (file.open(*movie.u.s)) { fileExists = true; + cleanedFilename = *movie.u.s; + } else if (!movie.u.s->equals(cleanedFilename) && file.open(cleanedFilename)) { + fileExists = true; } } @@ -199,23 +211,23 @@ void Lingo::func_goto(Datum &frame, Datum &movie) { return; } - _vm->_nextMovie = *movie.u.s; + _vm->_nextMovie.movie = cleanedFilename; _vm->getCurrentScore()->_stopPlay = true; - _vm->_nextMovieFrameS.clear(); - _vm->_nextMovieFrameI = -1; + _vm->_nextMovie.frameS.clear(); + _vm->_nextMovie.frameI = -1; if (frame.type == VOID) return; if (frame.type == STRING) { - _vm->_nextMovieFrameS = *frame.u.s; + _vm->_nextMovie.frameS = *frame.u.s; return; } frame.toInt(); - _vm->_nextMovieFrameI = frame.u.i; + _vm->_nextMovie.frameI = frame.u.i; return; } @@ -243,7 +255,7 @@ void Lingo::func_gotoloop() { _vm->getCurrentScore()->gotoLoop(); - g_director->_skipFrameAdvance = true; + _vm->_skipFrameAdvance = true; } void Lingo::func_gotonext() { @@ -252,7 +264,7 @@ void Lingo::func_gotonext() { _vm->getCurrentScore()->gotoNext(); - g_director->_skipFrameAdvance = true; + _vm->_skipFrameAdvance = true; } void Lingo::func_gotoprevious() { @@ -261,7 +273,43 @@ void Lingo::func_gotoprevious() { _vm->getCurrentScore()->gotoPrevious(); - g_director->_skipFrameAdvance = true; + _vm->_skipFrameAdvance = true; +} + +void Lingo::func_play(Datum &frame, Datum &movie) { + MovieReference ref; + + if (movie.type != VOID) { + warning("STUB: func_play()"); + + return; + } + + ref.frameI = _vm->getCurrentScore()->getCurrentFrame(); + + _vm->_movieStack.push_back(ref); + + func_goto(frame, movie); +} + +void Lingo::func_playdone() { + MovieReference ref = _vm->_movieStack.back(); + + _vm->_movieStack.pop_back(); + + Datum m, f; + + if (ref.movie.empty()) { + m.type = VOID; + } else { + m.type = STRING; + m.u.s = new Common::String(ref.movie); + } + + f.type = INT; + f.u.i = ref.frameI; + + func_goto(f, m); } void Lingo::func_cursor(int c) { diff --git a/engines/director/lingo/lingo-gr.cpp b/engines/director/lingo/lingo-gr.cpp index 8d1e84856b..da928f7c09 100644 --- a/engines/director/lingo/lingo-gr.cpp +++ b/engines/director/lingo/lingo-gr.cpp @@ -701,13 +701,13 @@ static const yytype_uint16 yyrline[] = 438, 444, 445, 446, 447, 448, 449, 450, 451, 452, 453, 454, 455, 456, 457, 458, 459, 460, 461, 462, 463, 464, 465, 466, 467, 468, 469, 470, 471, 472, - 473, 474, 475, 478, 483, 484, 485, 486, 487, 489, - 490, 491, 492, 495, 498, 501, 505, 506, 507, 508, - 509, 510, 511, 514, 515, 518, 519, 522, 523, 534, - 535, 536, 537, 540, 543, 548, 549, 552, 553, 556, - 557, 560, 563, 566, 566, 596, 596, 602, 605, 605, - 610, 611, 610, 621, 622, 623, 624, 627, 631, 639, - 640, 641, 644, 645 + 473, 474, 475, 478, 483, 484, 485, 486, 487, 488, + 489, 490, 491, 494, 497, 500, 504, 505, 506, 507, + 508, 509, 510, 513, 514, 517, 518, 521, 522, 533, + 534, 535, 536, 539, 542, 547, 548, 551, 552, 555, + 556, 559, 562, 565, 565, 595, 595, 600, 603, 603, + 608, 609, 608, 618, 619, 620, 621, 624, 628, 636, + 637, 638, 641, 642 }; #endif @@ -2261,17 +2261,12 @@ yyreduce: (yyval.code) = (yyvsp[(5) - (5)].code); ;} break; - case 20: -#line 191 "engines/director/lingo/lingo-gr.y" - { g_lingo->code1(g_lingo->c_xpop); ;} - break; - case 24: #line 201 "engines/director/lingo/lingo-gr.y" { inst body = 0, end = 0; - WRITE_UINT32(&body, (yyvsp[(5) - (7)].code)); - WRITE_UINT32(&end, (yyvsp[(6) - (7)].code)); + WRITE_UINT32(&body, (yyvsp[(5) - (7)].code) - (yyvsp[(1) - (7)].code)); + WRITE_UINT32(&end, (yyvsp[(6) - (7)].code) - (yyvsp[(1) - (7)].code)); (*g_lingo->_currentScript)[(yyvsp[(1) - (7)].code) + 1] = body; /* body of loop */ (*g_lingo->_currentScript)[(yyvsp[(1) - (7)].code) + 2] = end; /* end, if cond fails */ @@ -2282,10 +2277,10 @@ yyreduce: #line 214 "engines/director/lingo/lingo-gr.y" { inst init = 0, finish = 0, body = 0, end = 0, inc = 0; - WRITE_UINT32(&init, (yyvsp[(3) - (10)].code)); - WRITE_UINT32(&finish, (yyvsp[(6) - (10)].code)); - WRITE_UINT32(&body, (yyvsp[(8) - (10)].code)); - WRITE_UINT32(&end, (yyvsp[(9) - (10)].code)); + WRITE_UINT32(&init, (yyvsp[(3) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&finish, (yyvsp[(6) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&body, (yyvsp[(8) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&end, (yyvsp[(9) - (10)].code) - (yyvsp[(1) - (10)].code)); WRITE_UINT32(&inc, 1); (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 1] = init; /* initial count value */ (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 2] = finish;/* final count value */ @@ -2300,10 +2295,10 @@ yyreduce: #line 232 "engines/director/lingo/lingo-gr.y" { inst init = 0, finish = 0, body = 0, end = 0, inc = 0; - WRITE_UINT32(&init, (yyvsp[(3) - (11)].code)); - WRITE_UINT32(&finish, (yyvsp[(7) - (11)].code)); - WRITE_UINT32(&body, (yyvsp[(9) - (11)].code)); - WRITE_UINT32(&end, (yyvsp[(10) - (11)].code)); + WRITE_UINT32(&init, (yyvsp[(3) - (11)].code) - (yyvsp[(1) - (11)].code)); + WRITE_UINT32(&finish, (yyvsp[(7) - (11)].code) - (yyvsp[(1) - (11)].code)); + WRITE_UINT32(&body, (yyvsp[(9) - (11)].code) - (yyvsp[(1) - (11)].code)); + WRITE_UINT32(&end, (yyvsp[(10) - (11)].code) - (yyvsp[(1) - (11)].code)); WRITE_UINT32(&inc, -1); (*g_lingo->_currentScript)[(yyvsp[(1) - (11)].code) + 1] = init; /* initial count value */ (*g_lingo->_currentScript)[(yyvsp[(1) - (11)].code) + 2] = finish;/* final count value */ @@ -2318,7 +2313,7 @@ yyreduce: #line 246 "engines/director/lingo/lingo-gr.y" { inst end = 0; - WRITE_UINT32(&end, (yyvsp[(3) - (3)].code)); + WRITE_UINT32(&end, (yyvsp[(3) - (3)].code) - (yyvsp[(1) - (3)].code)); g_lingo->code1(STOP); (*g_lingo->_currentScript)[(yyvsp[(1) - (3)].code) + 1] = end; ;} @@ -2342,8 +2337,8 @@ yyreduce: #line 260 "engines/director/lingo/lingo-gr.y" { inst then = 0, end = 0; - WRITE_UINT32(&then, (yyvsp[(5) - (7)].code)); - WRITE_UINT32(&end, (yyvsp[(6) - (7)].code)); + WRITE_UINT32(&then, (yyvsp[(5) - (7)].code) - (yyvsp[(1) - (7)].code)); + WRITE_UINT32(&end, (yyvsp[(6) - (7)].code) - (yyvsp[(1) - (7)].code)); (*g_lingo->_currentScript)[(yyvsp[(1) - (7)].code) + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (7)].code) + 3] = end; /* end, if cond fails */ @@ -2356,9 +2351,9 @@ yyreduce: #line 270 "engines/director/lingo/lingo-gr.y" { inst then = 0, else1 = 0, end = 0; - WRITE_UINT32(&then, (yyvsp[(5) - (10)].code)); - WRITE_UINT32(&else1, (yyvsp[(8) - (10)].code)); - WRITE_UINT32(&end, (yyvsp[(9) - (10)].code)); + WRITE_UINT32(&then, (yyvsp[(5) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&else1, (yyvsp[(8) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&end, (yyvsp[(9) - (10)].code) - (yyvsp[(1) - (10)].code)); (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 2] = else1; /* elsepart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 3] = end; /* end, if cond fails */ @@ -2372,25 +2367,25 @@ yyreduce: #line 282 "engines/director/lingo/lingo-gr.y" { inst then = 0, else1 = 0, end = 0; - WRITE_UINT32(&then, (yyvsp[(5) - (10)].code)); - WRITE_UINT32(&else1, (yyvsp[(7) - (10)].code)); - WRITE_UINT32(&end, (yyvsp[(9) - (10)].code)); + WRITE_UINT32(&then, (yyvsp[(5) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&else1, (yyvsp[(7) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&end, (yyvsp[(9) - (10)].code) - (yyvsp[(1) - (10)].code)); (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 2] = else1; /* elsepart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 3] = end; /* end, if cond fails */ checkEnd((yyvsp[(10) - (10)].s), "if", true); - g_lingo->processIf(0, (yyvsp[(9) - (10)].code)); ;} + g_lingo->processIf(0, (yyvsp[(9) - (10)].code) - (yyvsp[(1) - (10)].code)); ;} break; case 33: #line 294 "engines/director/lingo/lingo-gr.y" { inst then = 0, else1 = 0, end = 0; - WRITE_UINT32(&then, (yyvsp[(4) - (6)].code)); + WRITE_UINT32(&then, (yyvsp[(4) - (6)].code) - (yyvsp[(1) - (6)].code)); WRITE_UINT32(&else1, 0); - WRITE_UINT32(&end, (yyvsp[(6) - (6)].code)); + WRITE_UINT32(&end, (yyvsp[(6) - (6)].code) - (yyvsp[(1) - (6)].code)); (*g_lingo->_currentScript)[(yyvsp[(1) - (6)].code) + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (6)].code) + 2] = else1; /* elsepart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (6)].code) + 3] = end; /* end, if cond fails */ @@ -2402,9 +2397,9 @@ yyreduce: #line 304 "engines/director/lingo/lingo-gr.y" { inst then = 0, else1 = 0, end = 0; - WRITE_UINT32(&then, (yyvsp[(4) - (10)].code)); - WRITE_UINT32(&else1, (yyvsp[(8) - (10)].code)); - WRITE_UINT32(&end, (yyvsp[(10) - (10)].code)); + WRITE_UINT32(&then, (yyvsp[(4) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&else1, (yyvsp[(8) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&end, (yyvsp[(10) - (10)].code) - (yyvsp[(1) - (10)].code)); (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 2] = else1; /* elsepart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 3] = end; /* end, if cond fails */ @@ -2416,14 +2411,14 @@ yyreduce: #line 314 "engines/director/lingo/lingo-gr.y" { inst then = 0, else1 = 0, end = 0; - WRITE_UINT32(&then, (yyvsp[(4) - (10)].code)); - WRITE_UINT32(&else1, (yyvsp[(6) - (10)].code)); - WRITE_UINT32(&end, (yyvsp[(10) - (10)].code)); + WRITE_UINT32(&then, (yyvsp[(4) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&else1, (yyvsp[(6) - (10)].code) - (yyvsp[(1) - (10)].code)); + WRITE_UINT32(&end, (yyvsp[(10) - (10)].code) - (yyvsp[(1) - (10)].code)); (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 2] = else1; /* elsepart */ (*g_lingo->_currentScript)[(yyvsp[(1) - (10)].code) + 3] = end; /* end, if cond fails */ - g_lingo->processIf(0, (yyvsp[(10) - (10)].code)); ;} + g_lingo->processIf(0, (yyvsp[(10) - (10)].code) - (yyvsp[(1) - (10)].code)); ;} break; case 36: @@ -2440,7 +2435,7 @@ yyreduce: #line 338 "engines/director/lingo/lingo-gr.y" { inst then = 0; - WRITE_UINT32(&then, (yyvsp[(4) - (6)].code)); + WRITE_UINT32(&then, (yyvsp[(4) - (6)].code) - (yyvsp[(1) - (6)].code)); (*g_lingo->_currentScript)[(yyvsp[(1) - (6)].code) + 1] = then; /* thenpart */ g_lingo->codeLabel((yyvsp[(1) - (6)].code)); ;} @@ -2450,7 +2445,7 @@ yyreduce: #line 347 "engines/director/lingo/lingo-gr.y" { inst then = 0; - WRITE_UINT32(&then, (yyvsp[(5) - (6)].code)); + WRITE_UINT32(&then, (yyvsp[(5) - (6)].code) - (yyvsp[(1) - (6)].code)); (*g_lingo->_currentScript)[(yyvsp[(1) - (6)].code) + 1] = then; /* thenpart */ g_lingo->codeLabel((yyvsp[(1) - (6)].code)); ;} @@ -2790,33 +2785,32 @@ yyreduce: case 108: #line 487 "engines/director/lingo/lingo-gr.y" - { g_lingo->codeConst(0); // Push fake value on stack - g_lingo->code1(g_lingo->c_procret); ;} + { g_lingo->code1(g_lingo->c_procret); ;} break; case 112: -#line 492 "engines/director/lingo/lingo-gr.y" +#line 491 "engines/director/lingo/lingo-gr.y" { g_lingo->codeFunc((yyvsp[(1) - (1)].s), 0); delete (yyvsp[(1) - (1)].s); ;} break; case 113: -#line 495 "engines/director/lingo/lingo-gr.y" +#line 494 "engines/director/lingo/lingo-gr.y" { g_lingo->codeFunc((yyvsp[(1) - (2)].s), 1); delete (yyvsp[(1) - (2)].s); ;} break; case 114: -#line 498 "engines/director/lingo/lingo-gr.y" +#line 497 "engines/director/lingo/lingo-gr.y" { g_lingo->codeFunc((yyvsp[(1) - (2)].s), 1); delete (yyvsp[(1) - (2)].s); ;} break; case 115: -#line 501 "engines/director/lingo/lingo-gr.y" +#line 500 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_voidpush); g_lingo->codeFunc((yyvsp[(1) - (1)].s), 1); @@ -2824,172 +2818,171 @@ yyreduce: break; case 116: -#line 505 "engines/director/lingo/lingo-gr.y" +#line 504 "engines/director/lingo/lingo-gr.y" { g_lingo->codeFunc((yyvsp[(1) - (2)].s), (yyvsp[(2) - (2)].narg)); ;} break; case 117: -#line 506 "engines/director/lingo/lingo-gr.y" +#line 505 "engines/director/lingo/lingo-gr.y" { g_lingo->codeFunc((yyvsp[(1) - (4)].s), (yyvsp[(3) - (4)].narg)); ;} break; case 118: -#line 507 "engines/director/lingo/lingo-gr.y" +#line 506 "engines/director/lingo/lingo-gr.y" { g_lingo->codeMe((yyvsp[(3) - (4)].s), 0); ;} break; case 119: -#line 508 "engines/director/lingo/lingo-gr.y" +#line 507 "engines/director/lingo/lingo-gr.y" { g_lingo->codeMe((yyvsp[(3) - (6)].s), (yyvsp[(5) - (6)].narg)); ;} break; case 120: -#line 509 "engines/director/lingo/lingo-gr.y" +#line 508 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_open); ;} break; case 121: -#line 510 "engines/director/lingo/lingo-gr.y" +#line 509 "engines/director/lingo/lingo-gr.y" { g_lingo->code2(g_lingo->c_voidpush, g_lingo->c_open); ;} break; case 122: -#line 511 "engines/director/lingo/lingo-gr.y" +#line 510 "engines/director/lingo/lingo-gr.y" { Common::String s(*(yyvsp[(1) - (3)].s)); s += '-'; s += *(yyvsp[(2) - (3)].s); g_lingo->codeFunc(&s, (yyvsp[(3) - (3)].narg)); ;} break; case 123: -#line 514 "engines/director/lingo/lingo-gr.y" +#line 513 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_global); g_lingo->codeString((yyvsp[(1) - (1)].s)->c_str()); delete (yyvsp[(1) - (1)].s); ;} break; case 124: -#line 515 "engines/director/lingo/lingo-gr.y" +#line 514 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_global); g_lingo->codeString((yyvsp[(3) - (3)].s)->c_str()); delete (yyvsp[(3) - (3)].s); ;} break; case 125: -#line 518 "engines/director/lingo/lingo-gr.y" +#line 517 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_property); g_lingo->codeString((yyvsp[(1) - (1)].s)->c_str()); delete (yyvsp[(1) - (1)].s); ;} break; case 126: -#line 519 "engines/director/lingo/lingo-gr.y" +#line 518 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_property); g_lingo->codeString((yyvsp[(3) - (3)].s)->c_str()); delete (yyvsp[(3) - (3)].s); ;} break; case 127: -#line 522 "engines/director/lingo/lingo-gr.y" +#line 521 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_instance); g_lingo->codeString((yyvsp[(1) - (1)].s)->c_str()); delete (yyvsp[(1) - (1)].s); ;} break; case 128: -#line 523 "engines/director/lingo/lingo-gr.y" +#line 522 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_instance); g_lingo->codeString((yyvsp[(3) - (3)].s)->c_str()); delete (yyvsp[(3) - (3)].s); ;} break; case 129: -#line 534 "engines/director/lingo/lingo-gr.y" +#line 533 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_gotoloop); ;} break; case 130: -#line 535 "engines/director/lingo/lingo-gr.y" +#line 534 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_gotonext); ;} break; case 131: -#line 536 "engines/director/lingo/lingo-gr.y" +#line 535 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_gotoprevious); ;} break; case 132: -#line 537 "engines/director/lingo/lingo-gr.y" +#line 536 "engines/director/lingo/lingo-gr.y" { g_lingo->codeConst(1); g_lingo->code1(g_lingo->c_goto); ;} break; case 133: -#line 540 "engines/director/lingo/lingo-gr.y" +#line 539 "engines/director/lingo/lingo-gr.y" { g_lingo->codeConst(3); g_lingo->code1(g_lingo->c_goto); ;} break; case 134: -#line 543 "engines/director/lingo/lingo-gr.y" +#line 542 "engines/director/lingo/lingo-gr.y" { g_lingo->codeConst(2); g_lingo->code1(g_lingo->c_goto); ;} break; case 139: -#line 556 "engines/director/lingo/lingo-gr.y" +#line 555 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_playdone); ;} break; case 140: -#line 557 "engines/director/lingo/lingo-gr.y" +#line 556 "engines/director/lingo/lingo-gr.y" { g_lingo->codeConst(1); g_lingo->code1(g_lingo->c_play); ;} break; case 141: -#line 560 "engines/director/lingo/lingo-gr.y" +#line 559 "engines/director/lingo/lingo-gr.y" { g_lingo->codeConst(3); g_lingo->code1(g_lingo->c_play); ;} break; case 142: -#line 563 "engines/director/lingo/lingo-gr.y" +#line 562 "engines/director/lingo/lingo-gr.y" { g_lingo->codeConst(2); g_lingo->code1(g_lingo->c_play); ;} break; case 143: -#line 566 "engines/director/lingo/lingo-gr.y" +#line 565 "engines/director/lingo/lingo-gr.y" { g_lingo->codeSetImmediate(true); ;} break; case 144: -#line 566 "engines/director/lingo/lingo-gr.y" +#line 565 "engines/director/lingo/lingo-gr.y" { g_lingo->codeSetImmediate(false); g_lingo->codeFunc((yyvsp[(1) - (3)].s), (yyvsp[(3) - (3)].narg)); ;} break; case 145: -#line 596 "engines/director/lingo/lingo-gr.y" +#line 595 "engines/director/lingo/lingo-gr.y" { g_lingo->_indef = true; g_lingo->_currentFactory.clear(); ;} break; case 146: -#line 597 "engines/director/lingo/lingo-gr.y" +#line 596 "engines/director/lingo/lingo-gr.y" { - g_lingo->codeConst(0); // Push fake value on stack g_lingo->code1(g_lingo->c_procret); g_lingo->define(*(yyvsp[(2) - (8)].s), (yyvsp[(4) - (8)].code), (yyvsp[(5) - (8)].narg)); g_lingo->_indef = false; ;} break; case 147: -#line 602 "engines/director/lingo/lingo-gr.y" +#line 600 "engines/director/lingo/lingo-gr.y" { g_lingo->codeFactory(*(yyvsp[(2) - (2)].s)); ;} break; case 148: -#line 605 "engines/director/lingo/lingo-gr.y" +#line 603 "engines/director/lingo/lingo-gr.y" { g_lingo->_indef = true; ;} break; case 149: -#line 606 "engines/director/lingo/lingo-gr.y" +#line 604 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_procret); g_lingo->define(*(yyvsp[(2) - (8)].s), (yyvsp[(4) - (8)].code), (yyvsp[(5) - (8)].narg) + 1, &g_lingo->_currentFactory); @@ -2997,19 +2990,18 @@ yyreduce: break; case 150: -#line 610 "engines/director/lingo/lingo-gr.y" +#line 608 "engines/director/lingo/lingo-gr.y" { g_lingo->_indef = true; g_lingo->_currentFactory.clear(); ;} break; case 151: -#line 611 "engines/director/lingo/lingo-gr.y" +#line 609 "engines/director/lingo/lingo-gr.y" { g_lingo->_ignoreMe = true; ;} break; case 152: -#line 611 "engines/director/lingo/lingo-gr.y" +#line 609 "engines/director/lingo/lingo-gr.y" { - g_lingo->codeConst(0); // Push fake value on stack g_lingo->code1(g_lingo->c_procret); g_lingo->define(*(yyvsp[(2) - (10)].s), (yyvsp[(4) - (10)].code), (yyvsp[(6) - (10)].narg)); g_lingo->_indef = false; @@ -3020,32 +3012,32 @@ yyreduce: break; case 153: -#line 621 "engines/director/lingo/lingo-gr.y" +#line 618 "engines/director/lingo/lingo-gr.y" { (yyval.narg) = 0; ;} break; case 154: -#line 622 "engines/director/lingo/lingo-gr.y" +#line 619 "engines/director/lingo/lingo-gr.y" { g_lingo->codeArg((yyvsp[(1) - (1)].s)); (yyval.narg) = 1; ;} break; case 155: -#line 623 "engines/director/lingo/lingo-gr.y" +#line 620 "engines/director/lingo/lingo-gr.y" { g_lingo->codeArg((yyvsp[(3) - (3)].s)); (yyval.narg) = (yyvsp[(1) - (3)].narg) + 1; ;} break; case 156: -#line 624 "engines/director/lingo/lingo-gr.y" +#line 621 "engines/director/lingo/lingo-gr.y" { g_lingo->codeArg((yyvsp[(4) - (4)].s)); (yyval.narg) = (yyvsp[(1) - (4)].narg) + 1; ;} break; case 157: -#line 627 "engines/director/lingo/lingo-gr.y" +#line 624 "engines/director/lingo/lingo-gr.y" { g_lingo->codeArgStore(); ;} break; case 158: -#line 631 "engines/director/lingo/lingo-gr.y" +#line 628 "engines/director/lingo/lingo-gr.y" { g_lingo->code1(g_lingo->c_call); g_lingo->codeString((yyvsp[(1) - (2)].s)->c_str()); @@ -3055,33 +3047,33 @@ yyreduce: break; case 159: -#line 639 "engines/director/lingo/lingo-gr.y" +#line 636 "engines/director/lingo/lingo-gr.y" { (yyval.narg) = 0; ;} break; case 160: -#line 640 "engines/director/lingo/lingo-gr.y" +#line 637 "engines/director/lingo/lingo-gr.y" { (yyval.narg) = 1; ;} break; case 161: -#line 641 "engines/director/lingo/lingo-gr.y" +#line 638 "engines/director/lingo/lingo-gr.y" { (yyval.narg) = (yyvsp[(1) - (3)].narg) + 1; ;} break; case 162: -#line 644 "engines/director/lingo/lingo-gr.y" +#line 641 "engines/director/lingo/lingo-gr.y" { (yyval.narg) = 1; ;} break; case 163: -#line 645 "engines/director/lingo/lingo-gr.y" +#line 642 "engines/director/lingo/lingo-gr.y" { (yyval.narg) = (yyvsp[(1) - (3)].narg) + 1; ;} break; /* Line 1267 of yacc.c. */ -#line 3085 "engines/director/lingo/lingo-gr.cpp" +#line 3077 "engines/director/lingo/lingo-gr.cpp" default: break; } YY_SYMBOL_PRINT ("-> $$ =", yyr1[yyn], &yyval, &yyloc); @@ -3295,6 +3287,6 @@ yyreturn: } -#line 648 "engines/director/lingo/lingo-gr.y" +#line 645 "engines/director/lingo/lingo-gr.y" diff --git a/engines/director/lingo/lingo-gr.y b/engines/director/lingo/lingo-gr.y index 86f8743560..35290c67eb 100644 --- a/engines/director/lingo/lingo-gr.y +++ b/engines/director/lingo/lingo-gr.y @@ -188,7 +188,7 @@ asgn: tPUT expr tINTO ID { $$ = $5; } ; -stmtoneliner: expr { g_lingo->code1(g_lingo->c_xpop); } +stmtoneliner: expr | proc ; @@ -200,8 +200,8 @@ stmt: stmtoneliner // | repeatwhile '(' cond ')' stmtlist end ENDCLAUSE { inst body = 0, end = 0; - WRITE_UINT32(&body, $5); - WRITE_UINT32(&end, $6); + WRITE_UINT32(&body, $5 - $1); + WRITE_UINT32(&end, $6 - $1); (*g_lingo->_currentScript)[$1 + 1] = body; /* body of loop */ (*g_lingo->_currentScript)[$1 + 2] = end; /* end, if cond fails */ @@ -213,10 +213,10 @@ stmt: stmtoneliner // | repeatwith '=' expr end tTO expr end stmtlist end ENDCLAUSE { inst init = 0, finish = 0, body = 0, end = 0, inc = 0; - WRITE_UINT32(&init, $3); - WRITE_UINT32(&finish, $6); - WRITE_UINT32(&body, $8); - WRITE_UINT32(&end, $9); + WRITE_UINT32(&init, $3 - $1); + WRITE_UINT32(&finish, $6 - $1); + WRITE_UINT32(&body, $8 - $1); + WRITE_UINT32(&end, $9 - $1); WRITE_UINT32(&inc, 1); (*g_lingo->_currentScript)[$1 + 1] = init; /* initial count value */ (*g_lingo->_currentScript)[$1 + 2] = finish;/* final count value */ @@ -231,10 +231,10 @@ stmt: stmtoneliner // | repeatwith '=' expr end tDOWN tTO expr end stmtlist end ENDCLAUSE { inst init = 0, finish = 0, body = 0, end = 0, inc = 0; - WRITE_UINT32(&init, $3); - WRITE_UINT32(&finish, $7); - WRITE_UINT32(&body, $9); - WRITE_UINT32(&end, $10); + WRITE_UINT32(&init, $3 - $1); + WRITE_UINT32(&finish, $7 - $1); + WRITE_UINT32(&body, $9 - $1); + WRITE_UINT32(&end, $10 - $1); WRITE_UINT32(&inc, -1); (*g_lingo->_currentScript)[$1 + 1] = init; /* initial count value */ (*g_lingo->_currentScript)[$1 + 2] = finish;/* final count value */ @@ -245,7 +245,7 @@ stmt: stmtoneliner checkEnd($11, "repeat", true); } | when stmtoneliner end { inst end = 0; - WRITE_UINT32(&end, $3); + WRITE_UINT32(&end, $3 - $1); g_lingo->code1(STOP); (*g_lingo->_currentScript)[$1 + 1] = end; } @@ -259,8 +259,8 @@ stmt: stmtoneliner ifstmt: if cond tTHEN nl stmtlist end ENDCLAUSE { inst then = 0, end = 0; - WRITE_UINT32(&then, $5); - WRITE_UINT32(&end, $6); + WRITE_UINT32(&then, $5 - $1); + WRITE_UINT32(&end, $6 - $1); (*g_lingo->_currentScript)[$1 + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[$1 + 3] = end; /* end, if cond fails */ @@ -269,9 +269,9 @@ ifstmt: if cond tTHEN nl stmtlist end ENDCLAUSE { g_lingo->processIf(0, 0); } | if cond tTHEN nl stmtlist end tNLELSE stmtlist end ENDCLAUSE { inst then = 0, else1 = 0, end = 0; - WRITE_UINT32(&then, $5); - WRITE_UINT32(&else1, $8); - WRITE_UINT32(&end, $9); + WRITE_UINT32(&then, $5 - $1); + WRITE_UINT32(&else1, $8 - $1); + WRITE_UINT32(&end, $9 - $1); (*g_lingo->_currentScript)[$1 + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[$1 + 2] = else1; /* elsepart */ (*g_lingo->_currentScript)[$1 + 3] = end; /* end, if cond fails */ @@ -281,21 +281,21 @@ ifstmt: if cond tTHEN nl stmtlist end ENDCLAUSE { g_lingo->processIf(0, 0); } | if cond tTHEN nl stmtlist end begin elseifstmt end ENDCLAUSE { inst then = 0, else1 = 0, end = 0; - WRITE_UINT32(&then, $5); - WRITE_UINT32(&else1, $7); - WRITE_UINT32(&end, $9); + WRITE_UINT32(&then, $5 - $1); + WRITE_UINT32(&else1, $7 - $1); + WRITE_UINT32(&end, $9 - $1); (*g_lingo->_currentScript)[$1 + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[$1 + 2] = else1; /* elsepart */ (*g_lingo->_currentScript)[$1 + 3] = end; /* end, if cond fails */ checkEnd($10, "if", true); - g_lingo->processIf(0, $9); } + g_lingo->processIf(0, $9 - $1); } | if cond tTHEN begin stmtoneliner end { inst then = 0, else1 = 0, end = 0; - WRITE_UINT32(&then, $4); + WRITE_UINT32(&then, $4 - $1); WRITE_UINT32(&else1, 0); - WRITE_UINT32(&end, $6); + WRITE_UINT32(&end, $6 - $1); (*g_lingo->_currentScript)[$1 + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[$1 + 2] = else1; /* elsepart */ (*g_lingo->_currentScript)[$1 + 3] = end; /* end, if cond fails */ @@ -303,9 +303,9 @@ ifstmt: if cond tTHEN nl stmtlist end ENDCLAUSE { g_lingo->processIf(0, 0); } | if cond tTHEN begin stmtoneliner end tNLELSE begin stmtoneliner end { inst then = 0, else1 = 0, end = 0; - WRITE_UINT32(&then, $4); - WRITE_UINT32(&else1, $8); - WRITE_UINT32(&end, $10); + WRITE_UINT32(&then, $4 - $1); + WRITE_UINT32(&else1, $8 - $1); + WRITE_UINT32(&end, $10 - $1); (*g_lingo->_currentScript)[$1 + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[$1 + 2] = else1; /* elsepart */ (*g_lingo->_currentScript)[$1 + 3] = end; /* end, if cond fails */ @@ -313,14 +313,14 @@ ifstmt: if cond tTHEN nl stmtlist end ENDCLAUSE { g_lingo->processIf(0, 0); } | if cond tTHEN begin stmtoneliner end elseifstmtoneliner end elsestmtoneliner end { inst then = 0, else1 = 0, end = 0; - WRITE_UINT32(&then, $4); - WRITE_UINT32(&else1, $6); - WRITE_UINT32(&end, $10); + WRITE_UINT32(&then, $4 - $1); + WRITE_UINT32(&else1, $6 - $1); + WRITE_UINT32(&end, $10 - $1); (*g_lingo->_currentScript)[$1 + 1] = then; /* thenpart */ (*g_lingo->_currentScript)[$1 + 2] = else1; /* elsepart */ (*g_lingo->_currentScript)[$1 + 3] = end; /* end, if cond fails */ - g_lingo->processIf(0, $10); } + g_lingo->processIf(0, $10 - $1); } ; elsestmtoneliner: /* nothing */ { $$ = 0; } @@ -337,7 +337,7 @@ elseifstmtoneliner: elseifstmtoneliner elseifstmtoneliner1 elseifstmtoneliner1: elseif cond tTHEN begin stmt end { inst then = 0; - WRITE_UINT32(&then, $4); + WRITE_UINT32(&then, $4 - $1); (*g_lingo->_currentScript)[$1 + 1] = then; /* thenpart */ g_lingo->codeLabel($1); } @@ -346,7 +346,7 @@ elseifstmtoneliner1: elseif cond tTHEN begin stmt end { elseifstmt1: elseifstmtoneliner | elseif cond tTHEN begin stmtlist end { inst then = 0; - WRITE_UINT32(&then, $5); + WRITE_UINT32(&then, $5 - $1); (*g_lingo->_currentScript)[$1 + 1] = then; /* thenpart */ g_lingo->codeLabel($1); } @@ -484,8 +484,7 @@ proc: tPUT expr { g_lingo->code1(g_lingo->c_printtop); } | gotofunc | playfunc | tEXIT tREPEAT { g_lingo->code1(g_lingo->c_exitRepeat); } - | tEXIT { g_lingo->codeConst(0); // Push fake value on stack - g_lingo->code1(g_lingo->c_procret); } + | tEXIT { g_lingo->code1(g_lingo->c_procret); } | tGLOBAL globallist | tPROPERTY propertylist | tINSTANCE instancelist @@ -595,7 +594,6 @@ playfunc: tPLAY tDONE { g_lingo->code1(g_lingo->c_playdone); } // on keyword defn: tMACRO ID { g_lingo->_indef = true; g_lingo->_currentFactory.clear(); } begin argdef nl argstore stmtlist { - g_lingo->codeConst(0); // Push fake value on stack g_lingo->code1(g_lingo->c_procret); g_lingo->define(*$2, $4, $5); g_lingo->_indef = false; } @@ -609,7 +607,6 @@ defn: tMACRO ID { g_lingo->_indef = true; g_lingo->_currentFactory.clear(); } g_lingo->_indef = false; } ; | tON ID { g_lingo->_indef = true; g_lingo->_currentFactory.clear(); } // D3 begin { g_lingo->_ignoreMe = true; } argdef nl argstore stmtlist ENDCLAUSE { - g_lingo->codeConst(0); // Push fake value on stack g_lingo->code1(g_lingo->c_procret); g_lingo->define(*$2, $4, $6); g_lingo->_indef = false; diff --git a/engines/director/lingo/lingo-lex.cpp b/engines/director/lingo/lingo-lex.cpp index 48a5166b95..c931dc8a56 100644 --- a/engines/director/lingo/lingo-lex.cpp +++ b/engines/director/lingo/lingo-lex.cpp @@ -746,7 +746,7 @@ using namespace Director; int yyparse(); static void count() { - if (debugChannelSet(-1, kDebugLingoCompile)) + if (debugChannelSet(-1, kDebugLingoParse)) debug("LEXER: Read '%s' at %d:%d", yytext, g_lingo->_linenumber, g_lingo->_colnumber); g_lingo->_colnumber += strlen(yytext); diff --git a/engines/director/lingo/lingo-lex.l b/engines/director/lingo/lingo-lex.l index 37bad1247d..6a38bac047 100644 --- a/engines/director/lingo/lingo-lex.l +++ b/engines/director/lingo/lingo-lex.l @@ -37,7 +37,7 @@ using namespace Director; int yyparse(); static void count() { - if (debugChannelSet(-1, kDebugLingoCompile)) + if (debugChannelSet(-1, kDebugLingoParse)) debug("LEXER: Read '%s' at %d:%d", yytext, g_lingo->_linenumber, g_lingo->_colnumber); g_lingo->_colnumber += strlen(yytext); diff --git a/engines/director/lingo/lingo.cpp b/engines/director/lingo/lingo.cpp index cf0038bfdc..ffbbdab933 100644 --- a/engines/director/lingo/lingo.cpp +++ b/engines/director/lingo/lingo.cpp @@ -136,17 +136,17 @@ const char *Lingo::findNextDefinition(const char *s) { return NULL; if (!strncmp(res, "macro ", 6)) { - debugC(3, kDebugLingoCompile, "See macro"); + debugC(1, kDebugLingoCompile, "See macro"); return res; } if (!strncmp(res, "factory ", 8)) { - debugC(3, kDebugLingoCompile, "See factory"); + debugC(1, kDebugLingoCompile, "See factory"); return res; } if (!strncmp(res, "method ", 7)) { - debugC(3, kDebugLingoCompile, "See method"); + debugC(1, kDebugLingoCompile, "See method"); return res; } @@ -158,7 +158,7 @@ const char *Lingo::findNextDefinition(const char *s) { } void Lingo::addCode(const char *code, ScriptType type, uint16 id) { - debugC(2, kDebugLingoCompile, "Add code \"%s\" for type %s with id %d", code, scriptType2str(type), id); + debugC(1, kDebugLingoCompile, "Add code \"%s\" for type %s with id %d", code, scriptType2str(type), id); if (_scripts[type].contains(id)) { delete _scripts[type][id]; @@ -175,7 +175,7 @@ void Lingo::addCode(const char *code, ScriptType type, uint16 id) { const char *begin, *end; if (!strncmp(code, "menu:", 5)) { - debugC(2, kDebugLingoCompile, "Parsing menu"); + debugC(1, kDebugLingoCompile, "Parsing menu"); parseMenu(code); return; @@ -200,7 +200,7 @@ void Lingo::addCode(const char *code, ScriptType type, uint16 id) { else _inFactory = false; - debugC(2, kDebugLingoCompile, "Code chunk:\n#####\n%s#####", chunk.c_str()); + debugC(1, kDebugLingoCompile, "Code chunk:\n#####\n%s#####", chunk.c_str()); parse(chunk.c_str()); @@ -208,7 +208,7 @@ void Lingo::addCode(const char *code, ScriptType type, uint16 id) { uint pc = 0; while (pc < _currentScript->size()) { Common::String instr = decodeInstruction(pc, &pc); - debugC(3, kDebugLingoCompile, "[%5d] %s", pc, instr.c_str()); + debugC(2, kDebugLingoCompile, "[%5d] %s", pc, instr.c_str()); } } @@ -219,7 +219,7 @@ void Lingo::addCode(const char *code, ScriptType type, uint16 id) { _hadError = true; // HACK: This is for preventing test execution - debugC(2, kDebugLingoCompile, "Code chunk:\n#####\n%s#####", begin); + debugC(1, kDebugLingoCompile, "Code chunk:\n#####\n%s#####", begin); parse(begin); } else { parse(code); @@ -236,7 +236,7 @@ void Lingo::addCode(const char *code, ScriptType type, uint16 id) { uint pc = 0; while (pc < _currentScript->size()) { Common::String instr = decodeInstruction(pc, &pc); - debugC(3, kDebugLingoCompile, "[%5d] %s", pc, instr.c_str()); + debugC(2, kDebugLingoCompile, "[%5d] %s", pc, instr.c_str()); } } } @@ -247,7 +247,7 @@ void Lingo::executeScript(ScriptType type, uint16 id) { return; } - debugC(2, kDebugLingoExec, "Executing script type: %s, id: %d", scriptType2str(type), id); + debugC(1, kDebugLingoExec, "Executing script type: %s, id: %d", scriptType2str(type), id); _currentScript = _scripts[type][id]; _pc = 0; @@ -291,7 +291,7 @@ Symbol *Lingo::getHandler(Common::String &name) { } void Lingo::processEvent(LEvent event, ScriptType st, int entityId) { - if (entityId <= 0) + if (entityId < 0) return; debugC(1, kDebugEvents, "Lingo::processEvent(%s, %s, %d)", _eventHandlerTypes[event], scriptType2str(st), entityId); @@ -303,11 +303,10 @@ void Lingo::processEvent(LEvent event, ScriptType st, int entityId) { if (_handlers.contains(ENTITY_INDEX(event, entityId))) { call(_eventHandlerTypes[event], 0); // D4+ Events - pop(); } else if (_scripts[st].contains(entityId)) { executeScript(st, entityId); // D3 list of scripts. } else { - debugC(8, kDebugLingoExec, "STUB: processEvent(%s) for %d", _eventHandlerTypes[event], entityId); + debugC(3, kDebugLingoExec, "STUB: processEvent(%s) for %d", _eventHandlerTypes[event], entityId); } } @@ -429,6 +428,8 @@ const char *Datum::type2str(bool isk) { return isk ? "#symbol" : "SYMBOL"; case OBJECT: return isk ? "#object" : "OBJECT"; + case REFERENCE: + return "REFERENCE"; case VAR: return isk ? "#var" : "VAR"; default: diff --git a/engines/director/lingo/lingo.h b/engines/director/lingo/lingo.h index 550156c1c7..516e91c6ed 100644 --- a/engines/director/lingo/lingo.h +++ b/engines/director/lingo/lingo.h @@ -498,6 +498,8 @@ public: void func_gotoloop(); void func_gotonext(); void func_gotoprevious(); + void func_play(Datum &frame, Datum &movie); + void func_playdone(); void func_cursor(int c); int func_marker(int m); diff --git a/engines/director/score.cpp b/engines/director/score.cpp index 975c6efe33..b876b777bf 100644 --- a/engines/director/score.cpp +++ b/engines/director/score.cpp @@ -302,6 +302,9 @@ void Score::loadCastDataVWCR(Common::SeekableSubReadStreamEndian &stream) { if (size == 0) continue; + if (debugChannelSet(5, kDebugLoading)) + stream.hexdump(size); + uint8 castType = stream.readByte(); switch (castType) { @@ -361,7 +364,7 @@ void Score::loadCastData(Common::SeekableSubReadStreamEndian &stream, uint16 id, uint32 size1, size2, size3, castType; byte unk1 = 0, unk2 = 0, unk3 = 0; - if (_vm->getVersion() < 4) { + if (_vm->getVersion() <= 3) { size1 = stream.readUint16(); size2 = stream.readUint32(); size3 = 0; @@ -369,7 +372,7 @@ void Score::loadCastData(Common::SeekableSubReadStreamEndian &stream, uint16 id, unk1 = stream.readByte(); unk2 = stream.readByte(); unk3 = stream.readByte(); - } else if (_vm->getVersion() < 5) { + } else if (_vm->getVersion() == 4) { size1 = stream.readUint16() + 2; size2 = stream.readUint32(); size3 = 0; @@ -647,6 +650,12 @@ void Score::loadCastInfo(Common::SeekableSubReadStreamEndian &stream, uint16 id) ci->fileName = getString(castStrings[3]); ci->type = castStrings[4]; + debugC(5, kDebugLoading, "CastInfo: name: '%s' directory: '%s', fileName: '%s', type: '%s'", + ci->name.c_str(), ci->directory.c_str(), ci->fileName.c_str(), ci->type.c_str()); + + if (!ci->name.empty()) + _castsNames[ci->name] = id; + _castsInfo[id] = ci; } diff --git a/engines/director/score.h b/engines/director/score.h index 6db5e33988..2e762f0dad 100644 --- a/engines/director/score.h +++ b/engines/director/score.h @@ -102,6 +102,7 @@ public: Common::Array<Frame *> _frames; Common::HashMap<int, Cast *> _casts; Common::HashMap<uint16, CastInfo *> _castsInfo; + Common::HashMap<Common::String, int> _castsNames; Common::SortedArray<Label *> *_labels; Common::HashMap<uint16, Common::String> _actions; Common::HashMap<uint16, Common::String> _fontMap; diff --git a/engines/titanic/game/end_explode_ship.cpp b/engines/titanic/game/end_explode_ship.cpp index 10c80f5863..6253a4df02 100644 --- a/engines/titanic/game/end_explode_ship.cpp +++ b/engines/titanic/game/end_explode_ship.cpp @@ -33,25 +33,25 @@ END_MESSAGE_MAP() void CEndExplodeShip::save(SimpleFile *file, int indent) { file->writeNumberLine(1, indent); - file->writeNumberLine(_value1, indent); - file->writeNumberLine(_value2, indent); + file->writeNumberLine(_isExploding, indent); + file->writeNumberLine(_unused5, indent); CGameObject::save(file, indent); } void CEndExplodeShip::load(SimpleFile *file) { file->readNumber(); - _value1 = file->readNumber(); - _value2 = file->readNumber(); + _isExploding = file->readNumber(); + _unused5 = file->readNumber(); CGameObject::load(file); } bool CEndExplodeShip::ActMsg(CActMsg *msg) { if (msg->_action == "Arm Bomb") { - _value1 = 1; + _isExploding = true; } else if (msg->_action == "Disarm Bomb") { - _value1 = 0; + _isExploding = false; } else if (msg->_action == "TakeOff") { loadSound("a#31.wav"); loadSound("a#14.wav"); @@ -67,12 +67,12 @@ bool CEndExplodeShip::TimerMsg(CTimerMsg *msg) { setVisible(true); playMovie(0, 449, 0); movieEvent(58); - playMovie(516, _value1 ? 550 : 551, MOVIE_NOTIFY_OBJECT); + playMovie(516, _isExploding ? 550 : 551, MOVIE_NOTIFY_OBJECT); } if (msg->_actionVal == 3) { setGlobalSoundVolume(-4, 2, -1); - CActMsg actMsg(_value1 ? "ExplodeCredits" : "Credits"); + CActMsg actMsg(_isExploding ? "ExplodeCredits" : "Credits"); actMsg.execute("EndGameCredits"); } diff --git a/engines/titanic/game/end_explode_ship.h b/engines/titanic/game/end_explode_ship.h index c48f822af8..592741e5c0 100644 --- a/engines/titanic/game/end_explode_ship.h +++ b/engines/titanic/game/end_explode_ship.h @@ -34,10 +34,11 @@ class CEndExplodeShip : public CGameObject { bool MovieEndMsg(CMovieEndMsg *msg); bool MovieFrameMsg(CMovieFrameMsg *msg); public: - int _value1, _value2; + bool _isExploding; + int _unused5; public: CLASSDEF; - CEndExplodeShip() : CGameObject(), _value1(0), _value2(0) {} + CEndExplodeShip() : CGameObject(), _isExploding(false), _unused5(0) {} /** * Save the data for the class to file diff --git a/engines/titanic/game/end_game_credits.cpp b/engines/titanic/game/end_game_credits.cpp index 4edcef0a17..c816f22706 100644 --- a/engines/titanic/game/end_game_credits.cpp +++ b/engines/titanic/game/end_game_credits.cpp @@ -31,7 +31,7 @@ BEGIN_MESSAGE_MAP(CEndGameCredits, CGameObject) ON_MESSAGE(TimerMsg) END_MESSAGE_MAP() -CEndGameCredits::CEndGameCredits() : CGameObject(), _flag(0), +CEndGameCredits::CEndGameCredits() : CGameObject(), _flag(false), _frameRange(0, 28) { } @@ -75,6 +75,7 @@ bool CEndGameCredits::MovieEndMsg(CMovieEndMsg *msg) { visibleMsg.execute("CreditsBackdrop"); } + addTimer(4000, 0); return true; } diff --git a/engines/titanic/npcs/bellbot.cpp b/engines/titanic/npcs/bellbot.cpp index 36c57fe467..1782161aea 100644 --- a/engines/titanic/npcs/bellbot.cpp +++ b/engines/titanic/npcs/bellbot.cpp @@ -135,7 +135,9 @@ bool CBellBot::MovieEndMsg(CMovieEndMsg *msg) { } bool CBellBot::Use(CUse *msg) { - dynamic_cast<CCarry *>(msg->_item)->_npcUse = "Bellbot"; + CCarry *item = dynamic_cast<CCarry *>(msg->_item); + assert(item); + item->_npcUse = "Bellbot"; return true; } diff --git a/engines/titanic/support/credit_text.cpp b/engines/titanic/support/credit_text.cpp index da6de6278e..e8da605658 100644 --- a/engines/titanic/support/credit_text.cpp +++ b/engines/titanic/support/credit_text.cpp @@ -25,10 +25,10 @@ namespace Titanic { -CCreditText::CCreditText() : _screenManagerP(nullptr), _field14(0), - _ticks(0), _fontHeight(1), _objectP(nullptr), _totalHeight(0), - _field40(0), _field44(0), _field48(0), _field4C(0), _field50(0), - _field54(0), _field58(0), _counter(0) { +CCreditText::CCreditText() : _screenManagerP(nullptr), _ticks(0), + _fontHeight(1), _objectP(nullptr), _totalHeight(0), + _yPos(0), _textR(0), _textG(0), _textB(0), _destR(0), + _destG(0), _destB(0), _counter(0) { } void CCreditText::clear() { @@ -37,21 +37,21 @@ void CCreditText::clear() { } void CCreditText::load(CGameObject *obj, CScreenManager *screenManager, - const Rect &rect, int v) { + const Rect &rect) { _objectP = obj; _screenManagerP = screenManager; - _field14 = v; + _rect = rect; setup(); _ticks = g_vm->_events->getTicksCount(); - _field40 = 0; - _field44 = 0xFF; - _field48 = 0xFF; - _field4C = 0xFF; - _field50 = 0; - _field54 = 0; - _field58 = 0; + _yPos = 0; + _textR = 0xFF; + _textG = 0xFF; + _textB = 0xFF; + _destR = 0; + _destG = 0; + _destB = 0; _counter = 0; } @@ -154,26 +154,26 @@ bool CCreditText::draw() { return false; if (++_counter > 200) { - _field44 += _field50; - _field48 += _field54; - _field4C += _field58; - _field50 = g_vm->getRandomNumber(63) + 192 - _field44; - _field54 = g_vm->getRandomNumber(63) + 192 - _field48; - _field58 = g_vm->getRandomNumber(63) + 192 - _field4C; + _textR += _destR; + _textG += _destG; + _textB += _destB; + _destR = g_vm->getRandomNumber(63) + 192 - _textR; + _destG = g_vm->getRandomNumber(63) + 192 - _textG; + _destB = g_vm->getRandomNumber(63) + 192 - _textB; _counter = 0; } // Positioning adjustment, changing lines and/or group if necessary - int yDiff = (int)(g_vm->_events->getTicksCount() - _ticks) / 22 - _field40; + int yDiff = (int)(g_vm->_events->getTicksCount() - _ticks) / 22 - _yPos; while (yDiff > 0) { if (_totalHeight > 0) { if (yDiff < _totalHeight) { _totalHeight -= yDiff; - _field40 += yDiff; + _yPos += yDiff; yDiff = 0; } else { yDiff -= _totalHeight; - _field40 += _totalHeight; + _yPos += _totalHeight; _totalHeight = 0; } } else { @@ -182,7 +182,7 @@ bool CCreditText::draw() { ++_lineIt; yDiff -= _fontHeight; - _field40 += _fontHeight; + _yPos += _fontHeight; if (_lineIt == (*_groupIt)->_lines.end()) { // Move to next line group @@ -204,9 +204,9 @@ bool CCreditText::draw() { Point textPos; for (textPos.y = _rect.top + _totalHeight; textPos.y <= _rect.bottom; textPos.y += _fontHeight) { - int textR = _field44 + _field50 * _counter / 200; - int textG = _field48 + _field54 * _counter / 200; - int textB = _field4C + _field58 * _counter / 200; + int textR = _textR + _destR * _counter / 200; + int textG = _textG + _destG * _counter / 200; + int textB = _textB + _destB * _counter / 200; // Single iteration loop to figure out RGB values for the line do { diff --git a/engines/titanic/support/credit_text.h b/engines/titanic/support/credit_text.h index 3e5bfca0c2..05392f5048 100644 --- a/engines/titanic/support/credit_text.h +++ b/engines/titanic/support/credit_text.h @@ -65,7 +65,6 @@ private: public: CScreenManager *_screenManagerP; Rect _rect; - int _field14; CCreditLineGroups _groups; uint _ticks; int _fontHeight; @@ -73,13 +72,9 @@ public: CCreditLineGroups::iterator _groupIt; CCreditLines::iterator _lineIt; int _totalHeight; - int _field40; - int _field44; - int _field48; - int _field4C; - int _field50; - int _field54; - int _field58; + int _yPos; + int _textR, _textG, _textB; + int _destR, _destG, _destB; int _counter; public: CCreditText(); @@ -93,7 +88,7 @@ public: * Sets the game object this override is associated with */ void load(CGameObject *obj, CScreenManager *screenManager, - const Rect &rect, int v = 0); + const Rect &rect); /** * Draw the item diff --git a/engines/titanic/support/font.cpp b/engines/titanic/support/font.cpp index f81251b10b..56f1af4718 100644 --- a/engines/titanic/support/font.cpp +++ b/engines/titanic/support/font.cpp @@ -214,6 +214,7 @@ void STFont::writeString(CVideoSurface *surface, const Point &destPos, Rect &cli // Form a rect of the area of the next character to draw Rect charRect(_chars[c]._offset, textRect.top, _chars[c]._offset + _chars[c]._width, textRect.bottom); + int textX = textPt.x; if (textPt.x < clipRect.left) { // Character is either partially or entirely left off-screen @@ -237,6 +238,7 @@ void STFont::writeString(CVideoSurface *surface, const Point &destPos, Rect &cli // At this point, we know we've got to draw at least part of a character, // and have figured out the area of the character to draw copyRect(surface, textPt, charRect); + textPt.x = textX + _chars[c]._width; } } diff --git a/engines/tsage/ringworld2/ringworld2_logic.cpp b/engines/tsage/ringworld2/ringworld2_logic.cpp index b41abe8cf9..e8d51109b1 100644 --- a/engines/tsage/ringworld2/ringworld2_logic.cpp +++ b/engines/tsage/ringworld2/ringworld2_logic.cpp @@ -1228,7 +1228,8 @@ void Ringworld2Game::processEvent(Event &event) { case Common::KEYCODE_F8: // F8 - Credits - R2_GLOBALS._sceneManager.changeScene(205); + if (R2_GLOBALS._sceneManager._sceneNumber != 205) + R2_GLOBALS._sceneManager.changeScene(205); break; case Common::KEYCODE_F10: diff --git a/graphics/managed_surface.cpp b/graphics/managed_surface.cpp index fe524724cd..60b2941efa 100644 --- a/graphics/managed_surface.cpp +++ b/graphics/managed_surface.cpp @@ -256,7 +256,7 @@ void transBlit(const Surface &src, const Common::Rect &srcRect, Surface &dest, c for (int destY = destRect.top, scaleYCtr = 0; destY < destRect.bottom; ++destY, scaleYCtr += scaleY) { if (destY < 0 || destY >= dest.h) continue; - const TSRC *srcLine = (const TSRC *)src.getBasePtr(0, scaleYCtr / SCALE_THRESHOLD); + const TSRC *srcLine = (const TSRC *)src.getBasePtr(srcRect.left, scaleYCtr / SCALE_THRESHOLD + srcRect.top); TDEST *destLine = (TDEST *)dest.getBasePtr(destRect.left, destY); // Loop through drawing the pixels of the row diff --git a/po/de_DE.po b/po/de_DE.po index 190e4698fb..9b988fb2d5 100644 --- a/po/de_DE.po +++ b/po/de_DE.po @@ -8,10 +8,10 @@ msgstr "" "Project-Id-Version: ScummVM 1.10.0git\n" "Report-Msgid-Bugs-To: scummvm-devel@lists.scummvm.org\n" "POT-Creation-Date: 2017-02-21 23:29+0100\n" -"PO-Revision-Date: 2017-02-08 21:48+0000\n" -"Last-Translator: Lothar Serra Mari <rootfather@scummvm.org>\n" -"Language-Team: German <https://translations.scummvm.org/projects/scummvm/" -"scummvm/de/>\n" +"PO-Revision-Date: 2017-02-24 12:05+0000\n" +"Last-Translator: Rouven Bauer <r_bauer11@cs.uni-kl.de>\n" +"Language-Team: German " +"<https://translations.scummvm.org/projects/scummvm/scummvm/de/>\n" "Language: de_DE\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=iso-8859-1\n" @@ -857,16 +857,15 @@ msgstr "Die Filtereinstellung konnte nicht geändert werden" #: gui/options.cpp:884 msgid "Show On-screen control" -msgstr "" +msgstr "Virtuelle Bedienelemente anzeigen" #: gui/options.cpp:888 -#, fuzzy msgid "Touchpad mouse mode" -msgstr "Touchpad-Modus ausgeschaltet." +msgstr "Touchpad-Mausmodus" #: gui/options.cpp:892 msgid "Swap Menu and Back buttons" -msgstr "" +msgstr "Vertausche Menü- und Zurück-Buttons" #: gui/options.cpp:904 msgid "Graphics mode:" @@ -1117,9 +1116,8 @@ msgid "Speech volume:" msgstr "Sprachlautst.:" #: gui/options.cpp:1351 -#, fuzzy msgid "Control" -msgstr "Maus steuern" +msgstr "Steuerung" #: gui/options.cpp:1383 msgid "FluidSynth Settings" @@ -7,10 +7,10 @@ msgstr "" "Project-Id-Version: ScummVM 1.10.0git\n" "Report-Msgid-Bugs-To: scummvm-devel@lists.scummvm.org\n" "POT-Creation-Date: 2017-02-21 23:29+0100\n" -"PO-Revision-Date: 2017-01-07 02:29+0000\n" -"Last-Translator: Filippos Karapetis <bluegr@gmail.com>\n" -"Language-Team: Greek <https://translations.scummvm.org/projects/scummvm/" -"scummvm/el/>\n" +"PO-Revision-Date: 2017-02-22 19:57+0000\n" +"Last-Translator: Arius <alidop@pathfinder.gr>\n" +"Language-Team: Greek " +"<https://translations.scummvm.org/projects/scummvm/scummvm/el/>\n" "Language: el\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=iso-8859-7\n" @@ -873,7 +873,7 @@ msgstr "Ëåéôïõñãßá Touchpad áðåíåñãïðïéçìÝíç." #: gui/options.cpp:892 msgid "Swap Menu and Back buttons" -msgstr "" +msgstr "ÅíáëëáãÞ ôùí êïõìðéþí Ìåíïý êáé Ðßóù" #: gui/options.cpp:904 msgid "Graphics mode:" diff --git a/po/fi_FI.po b/po/fi_FI.po index 07d754c166..8afdbad484 100644 --- a/po/fi_FI.po +++ b/po/fi_FI.po @@ -8,10 +8,10 @@ msgstr "" "Project-Id-Version: ScummVM 1.6.0git\n" "Report-Msgid-Bugs-To: scummvm-devel@lists.scummvm.org\n" "POT-Creation-Date: 2017-02-21 23:29+0100\n" -"PO-Revision-Date: 2017-01-06 16:03+0000\n" +"PO-Revision-Date: 2017-02-22 17:44+0000\n" "Last-Translator: Timo Mikkolainen <tmikkola@gmail.com>\n" -"Language-Team: Finnish <https://translations.scummvm.org/projects/scummvm/" -"scummvm/fi/>\n" +"Language-Team: Finnish " +"<https://translations.scummvm.org/projects/scummvm/scummvm/fi/>\n" "Language: fi_FI\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=iso-8859-1\n" @@ -849,16 +849,15 @@ msgstr "Suodatusasetusta ei voitu muuttaa" #: gui/options.cpp:884 msgid "Show On-screen control" -msgstr "" +msgstr "Virtuaalikontrollit" #: gui/options.cpp:888 -#, fuzzy msgid "Touchpad mouse mode" -msgstr "Touchpad tila pois päältä." +msgstr "Touchpad hiiritila" #: gui/options.cpp:892 msgid "Swap Menu and Back buttons" -msgstr "" +msgstr "Vaihda Menu ja Takaisin nappien paikkaa" #: gui/options.cpp:904 msgid "Graphics mode:" @@ -1107,9 +1106,8 @@ msgid "Speech volume:" msgstr "Puhe:" #: gui/options.cpp:1351 -#, fuzzy msgid "Control" -msgstr "Ohjaa hiirtä" +msgstr "Kontrollit" #: gui/options.cpp:1383 msgid "FluidSynth Settings" diff --git a/po/fr_FR.po b/po/fr_FR.po index cb0ee2ceeb..3886b99799 100644 --- a/po/fr_FR.po +++ b/po/fr_FR.po @@ -8,10 +8,10 @@ msgstr "" "Project-Id-Version: ScummVM 1.8.0git\n" "Report-Msgid-Bugs-To: scummvm-devel@lists.scummvm.org\n" "POT-Creation-Date: 2017-02-21 23:29+0100\n" -"PO-Revision-Date: 2017-02-04 10:14+0000\n" +"PO-Revision-Date: 2017-02-23 11:45+0000\n" "Last-Translator: Purple T <zeonk@hotmail.com>\n" -"Language-Team: French <https://translations.scummvm.org/projects/scummvm/" -"scummvm/fr/>\n" +"Language-Team: French " +"<https://translations.scummvm.org/projects/scummvm/scummvm/fr/>\n" "Language: fr_FR\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=iso-8859-1\n" @@ -854,16 +854,15 @@ msgstr "le mode de filtrage n'a pu être changé" #: gui/options.cpp:884 msgid "Show On-screen control" -msgstr "" +msgstr "Afficher les contrôles sur l'écran" #: gui/options.cpp:888 -#, fuzzy msgid "Touchpad mouse mode" -msgstr "Mode touchpad désactivé." +msgstr "Souris en mode Touchpad" #: gui/options.cpp:892 msgid "Swap Menu and Back buttons" -msgstr "" +msgstr "Inverser les boutons Menu et Retour" #: gui/options.cpp:904 msgid "Graphics mode:" @@ -1117,9 +1116,8 @@ msgid "Speech volume:" msgstr "Dialogues :" #: gui/options.cpp:1351 -#, fuzzy msgid "Control" -msgstr "Contrôles la Souris" +msgstr "Contrôles" #: gui/options.cpp:1383 msgid "FluidSynth Settings" diff --git a/po/hu_HU.po b/po/hu_HU.po index b4d75d00bc..7f90a1309d 100644 --- a/po/hu_HU.po +++ b/po/hu_HU.po @@ -7,10 +7,10 @@ msgstr "" "Project-Id-Version: ScummVM 1.3.0svn\n" "Report-Msgid-Bugs-To: scummvm-devel@lists.scummvm.org\n" "POT-Creation-Date: 2017-02-21 23:29+0100\n" -"PO-Revision-Date: 2017-01-08 06:09+0000\n" -"Last-Translator: George Kormendi <grubycza@hotmail.com>\n" -"Language-Team: Hungarian <https://translations.scummvm.org/projects/scummvm/" -"scummvm/hu/>\n" +"PO-Revision-Date: 2017-02-24 12:04+0000\n" +"Last-Translator: Eugene Sandulenko <sev@scummvm.org>\n" +"Language-Team: Hungarian " +"<https://translations.scummvm.org/projects/scummvm/scummvm/hu/>\n" "Language: hu_HU\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=iso-8859-2\n" @@ -849,9 +849,8 @@ msgid "Show On-screen control" msgstr "" #: gui/options.cpp:888 -#, fuzzy msgid "Touchpad mouse mode" -msgstr "Touchpad mód letiltva." +msgstr "Touchpad egér mód" #: gui/options.cpp:892 msgid "Swap Menu and Back buttons" @@ -1101,9 +1100,8 @@ msgid "Speech volume:" msgstr "Beszéd hangerõ:" #: gui/options.cpp:1351 -#, fuzzy msgid "Control" -msgstr "Egér irányitás" +msgstr "Irányitás" #: gui/options.cpp:1383 msgid "FluidSynth Settings" @@ -4257,7 +4255,6 @@ msgid "The \"sky.cpt\" engine data file has an incorrect size." msgstr "A \"sky.cpt\" motor adatfájl mérete inkorrekt.." #: engines/sky/detection.cpp:44 -#, fuzzy msgid "Floppy intro" msgstr "Floppy intro" @@ -4379,9 +4376,9 @@ msgid "Saved game #%d quick loaded" msgstr "Játékállás nem menthetõ %d slotba" #: engines/toon/toon.cpp:243 -#, fuzzy, c-format +#, c-format msgid "Could not quick load the saved game #%d" -msgstr "Akarod hogy betöltésem a játékállást?" +msgstr "Nem történt meg a #%d mentett játék gyors betöltése" #: engines/wintermute/detection.cpp:58 msgid "Show FPS-counter" diff --git a/po/ru_RU.po b/po/ru_RU.po index 3b2672575b..fd4caf197b 100644 --- a/po/ru_RU.po +++ b/po/ru_RU.po @@ -8,16 +8,16 @@ msgstr "" "Project-Id-Version: ScummVM 1.8.0svn\n" "Report-Msgid-Bugs-To: scummvm-devel@lists.scummvm.org\n" "POT-Creation-Date: 2017-02-21 23:29+0100\n" -"PO-Revision-Date: 2016-12-31 21:04+0000\n" -"Last-Translator: Ivan Lukyanov <lid-gr@tut.by>\n" -"Language-Team: Russian <https://translations.scummvm.org/projects/scummvm/" -"scummvm/ru/>\n" +"PO-Revision-Date: 2017-02-22 19:56+0000\n" +"Last-Translator: Eugene Sandulenko <sev@scummvm.org>\n" +"Language-Team: Russian " +"<https://translations.scummvm.org/projects/scummvm/scummvm/ru/>\n" "Language: ru_RU\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=iso-8859-5\n" "Content-Transfer-Encoding: 8bit\n" -"Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n" -"%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2;\n" +"Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%10<=" +"4 && (n%100<10 || n%100>=20) ? 1 : 2;\n" "X-Generator: Weblate 2.9\n" "X-Language-name: Russian\n" @@ -851,16 +851,15 @@ msgstr "àÕÖØÜ äØÛìâàÐæØØ ÝÕ ÜÞÖÕâ Ñëâì Ø×ÜÕÝñÝ" #: gui/options.cpp:884 msgid "Show On-screen control" -msgstr "" +msgstr "¿ÞÚÐ×Ðâì ãßàÐÒÛÕÝØÕ íÚàÐÝÞÜ" #: gui/options.cpp:888 -#, fuzzy msgid "Touchpad mouse mode" -msgstr "ÀÕÖØÜ âÐçßÐÔÐ ÒëÚÛîçÕÝ." +msgstr "ÀÕÖØÜ âÐçßÐÔÐ" #: gui/options.cpp:892 msgid "Swap Menu and Back buttons" -msgstr "" +msgstr "¿ÞÜÕÝïâì ÜÕáâÐÜØ ÚÝÞßÚØ ¼ÕÝî Ø ½Ð×ÐÔ" #: gui/options.cpp:904 msgid "Graphics mode:" @@ -1111,9 +1110,8 @@ msgid "Speech volume:" msgstr "³àÞÜÚ. Þ×ÒãçÚØ:" #: gui/options.cpp:1351 -#, fuzzy msgid "Control" -msgstr "ÃßàÐÒÛÕÝØÕ Üëèìî" +msgstr "ÃßàÐÒÛÕÝØÕ" #: gui/options.cpp:1383 msgid "FluidSynth Settings" diff --git a/po/uk_UA.po b/po/uk_UA.po index 1d4774c020..c503bcf091 100644 --- a/po/uk_UA.po +++ b/po/uk_UA.po @@ -9,16 +9,16 @@ msgstr "" "Project-Id-Version: ScummVM 1.9.0git\n" "Report-Msgid-Bugs-To: scummvm-devel@lists.scummvm.org\n" "POT-Creation-Date: 2017-02-21 23:29+0100\n" -"PO-Revision-Date: 2017-01-01 00:02+0000\n" +"PO-Revision-Date: 2017-02-22 19:54+0000\n" "Last-Translator: Eugene Sandulenko <sev@scummvm.org>\n" -"Language-Team: Ukrainian <https://translations.scummvm.org/projects/scummvm/" -"scummvm/uk/>\n" +"Language-Team: Ukrainian " +"<https://translations.scummvm.org/projects/scummvm/scummvm/uk/>\n" "Language: uk_UA\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=iso-8859-5\n" "Content-Transfer-Encoding: 8bit\n" -"Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n" -"%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2;\n" +"Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%10<=" +"4 && (n%100<10 || n%100>=20) ? 1 : 2;\n" "X-Generator: Weblate 2.9\n" "X-Language-name: Ukrainian\n" @@ -851,16 +851,15 @@ msgstr "ÝÕ ÒÔÐÛÞáï ×ÜöÝØâØ àÕÖØÜ äöÛìâàãÒÐÝÝï" #: gui/options.cpp:884 msgid "Show On-screen control" -msgstr "" +msgstr "¿ÞÚÐ×ãÒÐâØ ÕÚàÐÝÝÕ ÚÕàãÒÐÝÝï" #: gui/options.cpp:888 -#, fuzzy msgid "Touchpad mouse mode" -msgstr "ÀÕÖØÜ âÐçßÐÔã ÒØÜÚÝÕÝÞ." +msgstr "ÀÕÖØÜ âÐçßÐÔã" #: gui/options.cpp:892 msgid "Swap Menu and Back buttons" -msgstr "" +msgstr "¿ÞÜöÝïâØ ÜöáæïÜØ ÚÝÞßÚØ ¼ÕÝî ö ½Ð×ÐÔ" #: gui/options.cpp:904 msgid "Graphics mode:" @@ -1109,9 +1108,8 @@ msgid "Speech volume:" msgstr "³ãçÝ. Þ×ÒãçÚØ:" #: gui/options.cpp:1351 -#, fuzzy msgid "Control" -msgstr "ÃßàÐÒÛöÝÝï ÜØèÕî" +msgstr "ºÕàãÒÐÝÝï" #: gui/options.cpp:1383 msgid "FluidSynth Settings" @@ -2304,7 +2302,7 @@ msgstr "·ÜöéÕÝÝï ÔÞâØÚöÒ ßÞ Þáö Y" #: backends/platform/ds/arm9/source/dsoptions.cpp:87 msgid "Use laptop trackpad-style cursor control" -msgstr "²ØÚÞàØáâÞÒãÒÐâØ ãßàÐÒÛöÝÝï ÚãàáÞàÞÜ ïÚ ÝÐ âàÕÚßÐÔö ÛÐßâÞßöÒ" +msgstr "²ØÚÞàØáâÞÒãÒÐâØ ÚÕàãÒÐÝÝï ÚãàáÞàÞÜ ïÚ ÝÐ âàÕÚßÐÔö ÛÐßâÞßöÒ" #: backends/platform/ds/arm9/source/dsoptions.cpp:88 msgid "Tap for left click, double tap right click" @@ -2495,7 +2493,7 @@ msgstr "¿ÞÚÐ×ÐâØ ÚÛÐÒöÐâãàã" #: backends/platform/tizen/form.cpp:309 msgid "Control Mouse" -msgstr "ÃßàÐÒÛöÝÝï ÜØèÕî" +msgstr "ºÕàãÒÐÝÝï ÜØèÕî" #: backends/platform/tizen/fs.cpp:259 msgid "[ Data ]" |