aboutsummaryrefslogtreecommitdiff
path: root/engines/kyra/script_v1.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'engines/kyra/script_v1.cpp')
-rw-r--r--engines/kyra/script_v1.cpp1713
1 files changed, 1713 insertions, 0 deletions
diff --git a/engines/kyra/script_v1.cpp b/engines/kyra/script_v1.cpp
new file mode 100644
index 0000000000..08ff4a6d9f
--- /dev/null
+++ b/engines/kyra/script_v1.cpp
@@ -0,0 +1,1713 @@
+/* ScummVM - Scumm Interpreter
+ * Copyright (C) 2004-2006 The ScummVM project
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/stdafx.h"
+#include "kyra/kyra.h"
+#include "kyra/script.h"
+#include "kyra/screen.h"
+#include "kyra/sprites.h"
+#include "kyra/wsamovie.h"
+#include "kyra/animator.h"
+#include "kyra/text.h"
+#include "common/system.h"
+
+namespace Kyra {
+#define stackPos(x) script->stack[script->sp+x]
+#define stackPosString(x) (char*)&script->dataPtr->text[READ_BE_UINT16(&((uint16 *)script->dataPtr->text)[stackPos(x)])]
+
+int KyraEngine::cmd_magicInMouseItem(ScriptState *script) {
+ debug(3, "cmd_magicInMouseItem(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ magicInMouseItem(stackPos(0), stackPos(1), -1);
+ return 0;
+}
+
+int KyraEngine::cmd_characterSays(ScriptState *script) {
+ _skipFlag = false;
+ if (_features & GF_TALKIE) {
+ debug(3, "cmd_characterSays(0x%X) (%d, '%s', %d, %d)", script, stackPos(0), stackPosString(1), stackPos(2), stackPos(3));
+ snd_voiceWaitForFinish();
+ snd_playVoiceFile(stackPos(0));
+ characterSays(stackPosString(1), stackPos(2), stackPos(3));
+ } else {
+ debug(3, "cmd_characterSays(0x%X) ('%s', %d, %d)", script, stackPosString(0), stackPos(1), stackPos(2));
+ characterSays(stackPosString(0), stackPos(1), stackPos(2));
+ }
+
+ return 0;
+}
+
+int KyraEngine::cmd_pauseTicks(ScriptState *script) {
+ debug(3, "cmd_pauseTicks(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ if (stackPos(1)) {
+ warning("STUB: special cmd_pauseTicks");
+ // delete this after correct implementing
+ delayWithTicks(stackPos(0));
+ } else {
+ delayWithTicks(stackPos(0));
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_drawSceneAnimShape(ScriptState *script) {
+ debug(3, "cmd_drawSceneAnimShape(0x%X) (%d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4));
+ _screen->drawShape(stackPos(4), _sprites->_sceneShapes[stackPos(0)], stackPos(1), stackPos(2), 0, (stackPos(3) != 0) ? 1 : 0);
+ return 0;
+}
+
+int KyraEngine::cmd_queryGameFlag(ScriptState *script) {
+ debug(3, "cmd_queryGameFlag(0x%X) (0x%X)", script, stackPos(0));
+ return queryGameFlag(stackPos(0));
+}
+
+int KyraEngine::cmd_setGameFlag(ScriptState *script) {
+ debug(3, "cmd_setGameFlag(0x%X) (0x%X)", script, stackPos(0));
+ return setGameFlag(stackPos(0));
+}
+
+int KyraEngine::cmd_resetGameFlag(ScriptState *script) {
+ debug(3, "cmd_resetGameFlag(0x%X) (0x%X)", script, stackPos(0));
+ return resetGameFlag(stackPos(0));
+}
+
+int KyraEngine::cmd_runNPCScript(ScriptState *script) {
+ warning("STUB: cmd_runNPCScript");
+ return 0;
+}
+
+int KyraEngine::cmd_setSpecialExitList(ScriptState *script) {
+ debug(3, "cmd_setSpecialExitList(0x%X) (%d, %d, %d, %d, %d, %d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4), stackPos(5), stackPos(6), stackPos(7), stackPos(8), stackPos(9));
+
+ for (int i = 0; i < 10; ++i) {
+ _exitList[i] = stackPos(i);
+ }
+ _exitListPtr = _exitList;
+
+ return 0;
+}
+
+int KyraEngine::cmd_blockInWalkableRegion(ScriptState *script) {
+ debug(3, "cmd_blockInWalkableRegion(0x%X) (%d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ _screen->blockInRegion(stackPos(0), stackPos(1), stackPos(2)-stackPos(0)+1, stackPos(3)-stackPos(1)+1);
+ return 0;
+}
+
+int KyraEngine::cmd_blockOutWalkableRegion(ScriptState *script) {
+ debug(3, "cmd_blockOutWalkableRegion(0x%X) (%d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ _screen->blockOutRegion(stackPos(0), stackPos(1), stackPos(2)-stackPos(0)+1, stackPos(3)-stackPos(1)+1);
+ return 0;
+}
+
+int KyraEngine::cmd_walkPlayerToPoint(ScriptState *script) {
+ debug(3, "cmd_walkPlayerToPoint(0x%X) (%d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+
+ int normalTimers = stackPos(2);
+ if (!normalTimers) {
+ disableTimer(19);
+ disableTimer(14);
+ disableTimer(18);
+ }
+
+ int reinitScript = handleSceneChange(stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+
+ if (!normalTimers) {
+ enableTimer(19);
+ enableTimer(14);
+ enableTimer(18);
+ }
+
+ if (reinitScript) {
+ _scriptInterpreter->initScript(script, script->dataPtr);
+ }
+
+ if (_sceneChangeState) {
+ _sceneChangeState = 0;
+ return 1;
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_dropItemInScene(ScriptState *script) {
+ debug(3, "cmd_dropItemInScene(0x%X) (%d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2));
+ int item = stackPos(0);
+ int xpos = stackPos(1);
+ int ypos = stackPos(2);
+
+ byte freeItem = findFreeItemInScene(_currentCharacter->sceneId);
+ if (freeItem != 0xFF) {
+ int sceneId = _currentCharacter->sceneId;
+ Room *room = &_roomTable[sceneId];
+ room->itemsXPos[freeItem] = xpos;
+ room->itemsYPos[freeItem] = ypos;
+ room->itemsTable[freeItem] = item;
+
+ _animator->animAddGameItem(freeItem, sceneId);
+ _animator->updateAllObjectShapes();
+ } else {
+ if (item == 43) {
+ placeItemInGenericMapScene(item, 0);
+ } else {
+ placeItemInGenericMapScene(item, 1);
+ }
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_drawAnimShapeIntoScene(ScriptState *script) {
+ debug(3, "cmd_drawAnimShapeIntoScene(0x%X) (%d, %d, %d, %d)", stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ _screen->hideMouse();
+ _animator->restoreAllObjectBackgrounds();
+ int shape = stackPos(0);
+ int xpos = stackPos(1);
+ int ypos = stackPos(2);
+ int flags = (stackPos(3) != 0) ? 1 : 0;
+ _screen->drawShape(2, _sprites->_sceneShapes[shape], xpos, ypos, 0, flags);
+ _screen->drawShape(0, _sprites->_sceneShapes[shape], xpos, ypos, 0, flags);
+ _animator->flagAllObjectsForBkgdChange();
+ _animator->preserveAnyChangedBackgrounds();
+ _animator->flagAllObjectsForRefresh();
+ _animator->updateAllObjectShapes();
+ _screen->showMouse();
+ return 0;
+}
+
+int KyraEngine::cmd_createMouseItem(ScriptState *script) {
+ debug(3, "cmd_createMouseItem(0x%X) (%d)", script, stackPos(0));
+ createMouseItem(stackPos(0));
+ return 0;
+}
+
+int KyraEngine::cmd_savePageToDisk(ScriptState *script) {
+ debug(3, "cmd_savePageToDisk(0x%X) ('%s', %d)", script, stackPosString(0), stackPos(1));
+ _screen->savePageToDisk(stackPosString(0), stackPos(1));
+ return 0;
+}
+
+int KyraEngine::cmd_sceneAnimOn(ScriptState *script) {
+ debug(3, "cmd_sceneAnimOn(0x%X) (%d)", script, stackPos(0));
+ _sprites->_anims[stackPos(0)].play = true;
+ return 0;
+}
+
+int KyraEngine::cmd_sceneAnimOff(ScriptState *script) {
+ debug(3, "cmd_sceneAnimOff(0x%X) (%d)", script, stackPos(0));
+ _sprites->_anims[stackPos(0)].play = false;
+ return 0;
+}
+
+int KyraEngine::cmd_getElapsedSeconds(ScriptState *script) {
+ debug(3, "cmd_getElapsedSeconds(0x%X) ()", script);
+ return _system->getMillis() / 1000;
+}
+
+int KyraEngine::cmd_mouseIsPointer(ScriptState *script) {
+ debug(3, "cmd_mouseIsPointer(0x%X) ()", script);
+ if (_itemInHand == -1) {
+ return 1;
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_destroyMouseItem(ScriptState *script) {
+ debug(3, "cmd_destroyMouseItem(0x%X) ()", script);
+ destroyMouseItem();
+ return 0;
+}
+
+int KyraEngine::cmd_runSceneAnimUntilDone(ScriptState *script) {
+ debug(3, "cmd_runSceneAnimUntilDone(0x%X) (%d)", script, stackPos(0));
+ _screen->hideMouse();
+ _animator->restoreAllObjectBackgrounds();
+ _sprites->_anims[stackPos(0)].play = true;
+ _animator->sprites()[stackPos(0)].active = 1;
+ _animator->flagAllObjectsForBkgdChange();
+ _animator->preserveAnyChangedBackgrounds();
+ while (_sprites->_anims[stackPos(0)].play) {
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ delay(10);
+ }
+ _animator->restoreAllObjectBackgrounds();
+ _screen->showMouse();
+ return 0;
+}
+
+int KyraEngine::cmd_fadeSpecialPalette(ScriptState *script) {
+ debug(3, "cmd_fadeSpecialPalette(0x%X) (%d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ _screen->fadeSpecialPalette(stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ return 0;
+}
+
+int KyraEngine::cmd_playAdlibSound(ScriptState *script) {
+ debug(3, "cmd_playAdlibSound(0x%X) (%d)", script, stackPos(0));
+ snd_playSoundEffect(stackPos(0));
+ return 0;
+}
+
+int KyraEngine::cmd_playAdlibScore(ScriptState *script) {
+ debug(3, "cmd_playAdlibScore(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ snd_playWanderScoreViaMap(stackPos(0), stackPos(1));
+ return 0;
+}
+
+int KyraEngine::cmd_phaseInSameScene(ScriptState *script) {
+ debug(3, "cmd_phaseInSameScene(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ transcendScenes(stackPos(0), stackPos(1));
+ return 0;
+}
+
+int KyraEngine::cmd_setScenePhasingFlag(ScriptState *script) {
+ debug(3, "cmd_setScenePhasingFlag(0x%X) ()", script);
+ _scenePhasingFlag = 1;
+ return 1;
+}
+
+int KyraEngine::cmd_resetScenePhasingFlag(ScriptState *script) {
+ debug(3, "cmd_resetScenePhasingFlag(0x%X) ()", script);
+ _scenePhasingFlag = 0;
+ return 0;
+}
+
+int KyraEngine::cmd_queryScenePhasingFlag(ScriptState *script) {
+ debug(3, "cmd_queryScenePhasingFlag(0x%X) ()", script);
+ return _scenePhasingFlag;
+}
+
+int KyraEngine::cmd_sceneToDirection(ScriptState *script) {
+ debug(3, "cmd_sceneToDirection(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ assert(stackPos(0) < _roomTableSize);
+ Room *curRoom = &_roomTable[stackPos(0)];
+ uint16 returnValue = 0xFFFF;
+ switch (stackPos(1)) {
+ case 0:
+ returnValue = curRoom->northExit;
+ break;
+
+ case 2:
+ returnValue = curRoom->eastExit;
+ break;
+
+ case 4:
+ returnValue = curRoom->southExit;
+ break;
+
+ case 6:
+ returnValue = curRoom->westExit;
+ break;
+
+ default:
+ break;
+ }
+ if (returnValue == 0xFFFF)
+ return -1;
+ return returnValue;
+}
+
+int KyraEngine::cmd_setBirthstoneGem(ScriptState *script) {
+ debug(3, "cmd_setBirthstoneGem(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ int index = stackPos(0);
+ if (index < 4 && index >= 0) {
+ _birthstoneGemTable[index] = stackPos(1);
+ return 1;
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_placeItemInGenericMapScene(ScriptState *script) {
+ debug(3, "cmd_placeItemInGenericMapScene(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ placeItemInGenericMapScene(stackPos(0), stackPos(1));
+ return 0;
+}
+
+int KyraEngine::cmd_setBrandonStatusBit(ScriptState *script) {
+ debug(3, "cmd_setBrandonStatusBit(0x%X) (%d)", script, stackPos(0));
+ _brandonStatusBit |= stackPos(0);
+ return 0;
+}
+
+int KyraEngine::cmd_pauseSeconds(ScriptState *script) {
+ debug(3, "cmd_pauseSeconds(0x%X) (%d)", script, stackPos(0));
+ if (stackPos(0) > 0 && !_skipFlag)
+ delay(stackPos(0)*1000, true);
+ _skipFlag = false;
+ return 0;
+}
+
+int KyraEngine::cmd_getCharactersLocation(ScriptState *script) {
+ debug(3, "cmd_getCharactersLocation(0x%X) (%d)", script, stackPos(0));
+ return _characterList[stackPos(0)].sceneId;
+}
+
+int KyraEngine::cmd_runNPCSubscript(ScriptState *script) {
+ warning("STUB: cmd_runNPCSubscript");
+ return 0;
+}
+
+int KyraEngine::cmd_magicOutMouseItem(ScriptState *script) {
+ debug(3, "cmd_magicOutMouseItem(0x%X) (%d)", script, stackPos(0));
+ magicOutMouseItem(stackPos(0), -1);
+ return 0;
+}
+
+int KyraEngine::cmd_internalAnimOn(ScriptState *script) {
+ debug(3, "cmd_internalAnimOn(0x%X) (%d)", script, stackPos(0));
+ _animator->sprites()[stackPos(0)].active = 1;
+ return 0;
+}
+
+int KyraEngine::cmd_forceBrandonToNormal(ScriptState *script) {
+ debug(3, "cmd_forceBrandonToNormal(0x%X) ()", script);
+ checkAmuletAnimFlags();
+ return 0;
+}
+
+int KyraEngine::cmd_poisonDeathNow(ScriptState *script) {
+ debug(3, "cmd_poisonDeathNow(0x%X) ()", script);
+ seq_poisonDeathNow(1);
+ return 0;
+}
+
+int KyraEngine::cmd_setScaleMode(ScriptState *script) {
+ debug(3, "cmd_setScaleMode(0x%X) (%d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ int len = stackPos(0);
+ int setValue1 = stackPos(1);
+ int start2 = stackPos(2);
+ int setValue2 = stackPos(3);
+ for (int i = 0; i < len; ++i) {
+ _scaleTable[i] = setValue1;
+ }
+ int temp = setValue2 - setValue1;
+ int temp2 = start2 - len;
+ for (int i = len, offset = 0; i < start2; ++i, ++offset) {
+ _scaleTable[i] = (offset * temp) / temp2 + setValue1;
+ }
+ for (int i = start2; i < 145; ++i) {
+ _scaleTable[i] = setValue2;
+ }
+ _scaleMode = 1;
+ return _scaleMode;
+}
+
+int KyraEngine::cmd_openWSAFile(ScriptState *script) {
+ debug(3, "cmd_openWSAFile(0x%X) ('%s', %d, %d)", script, stackPosString(0), stackPos(1), stackPos(2));
+
+ char *filename = stackPosString(0);
+ int wsaIndex = stackPos(1);
+
+ _movieObjects[wsaIndex]->open(filename, (stackPos(2) != 0) ? 1 : 0, 0);
+ assert(_movieObjects[wsaIndex]->opened());
+
+ return 0;
+}
+
+int KyraEngine::cmd_closeWSAFile(ScriptState *script) {
+ debug(3, "cmd_closeWSAFile(0x%X) (%d)", script, stackPos(0));
+
+ int wsaIndex = stackPos(0);
+ if (_movieObjects[wsaIndex]) {
+ _movieObjects[wsaIndex]->close();
+ }
+
+ return 0;
+}
+
+int KyraEngine::cmd_runWSAFromBeginningToEnd(ScriptState *script) {
+ debug(3, "cmd_runWSAFromBeginningToEnd(0x%X) (%d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4));
+
+ _screen->hideMouse();
+
+ bool running = true;
+
+ int xpos = stackPos(0);
+ int ypos = stackPos(1);
+ int waitTime = stackPos(2);
+ int wsaIndex = stackPos(3);
+ int worldUpdate = stackPos(4);
+ int wsaFrame = 0;
+
+ _movieObjects[wsaIndex]->_x = xpos;
+ _movieObjects[wsaIndex]->_y = ypos;
+ _movieObjects[wsaIndex]->_drawPage = 0;
+ while (running) {
+ _movieObjects[wsaIndex]->displayFrame(wsaFrame++);
+ _animator->_updateScreen = true;
+ if (wsaFrame >= _movieObjects[wsaIndex]->frames())
+ running = false;
+
+ uint32 continueTime = waitTime * _tickLength + _system->getMillis();
+ while (_system->getMillis() < continueTime) {
+ if (worldUpdate) {
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ } else {
+ _screen->updateScreen();
+ }
+ if (continueTime - _system->getMillis() >= 10)
+ delay(10);
+ }
+ }
+
+ _screen->showMouse();
+
+ return 0;
+}
+
+int KyraEngine::cmd_displayWSAFrame(ScriptState *script) {
+ debug(3, "cmd_displayWSAFrame(0x%X) (%d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4));
+ int frame = stackPos(0);
+ int xpos = stackPos(1);
+ int ypos = stackPos(2);
+ int waitTime = stackPos(3);
+ int wsaIndex = stackPos(4);
+ _screen->hideMouse();
+ _movieObjects[wsaIndex]->_x = xpos;
+ _movieObjects[wsaIndex]->_y = ypos;
+ _movieObjects[wsaIndex]->_drawPage = 0;
+ _movieObjects[wsaIndex]->displayFrame(frame);
+ _animator->_updateScreen = true;
+ uint32 continueTime = waitTime * _tickLength + _system->getMillis();
+ while (_system->getMillis() < continueTime && !_skipFlag) {
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ if (continueTime - _system->getMillis() >= 10)
+ delay(10);
+ }
+ _screen->showMouse();
+ return 0;
+}
+
+int KyraEngine::cmd_enterNewScene(ScriptState *script) {
+ debug(3, "cmd_enterNewScene(0x%X) (%d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4));
+ enterNewScene(stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4));
+ return 0;
+}
+
+int KyraEngine::cmd_setSpecialEnterXAndY(ScriptState *script) {
+ debug(3, "cmd_setSpecialEnterXAndY(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ _brandonPosX = stackPos(0);
+ _brandonPosY = stackPos(1);
+ if (_brandonPosX + 1 == 0 && _brandonPosY + 1 == 0)
+ _currentCharacter->currentAnimFrame = 88;
+ return 0;
+}
+
+int KyraEngine::cmd_runWSAFrames(ScriptState *script) {
+ debug(3, "cmd_runWSAFrames(0x%X) (%d, %d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4), stackPos(5));
+ int xpos = stackPos(0);
+ int ypos = stackPos(1);
+ int delayTime = stackPos(2);
+ int startFrame = stackPos(3);
+ int endFrame = stackPos(4);
+ int wsaIndex = stackPos(5);
+ _screen->hideMouse();
+ _movieObjects[wsaIndex]->_x = xpos;
+ _movieObjects[wsaIndex]->_y = ypos;
+ _movieObjects[wsaIndex]->_drawPage = 0;
+ for (; startFrame <= endFrame; ++startFrame) {
+ uint32 nextRun = _system->getMillis() + delayTime * _tickLength;
+ _movieObjects[wsaIndex]->displayFrame(startFrame);
+ _animator->_updateScreen = true;
+ while (_system->getMillis() < nextRun) {
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ if (nextRun - _system->getMillis() >= 10)
+ delay(10);
+ }
+ }
+ _screen->showMouse();
+ return 0;
+}
+
+int KyraEngine::cmd_popBrandonIntoScene(ScriptState *script) {
+ debug(3, "cmd_popBrandonIntoScene(0x%X) (%d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ int changeScaleMode = stackPos(3);
+ int xpos = (int16)(stackPos(0) & 0xFFFC);
+ int ypos = (int16)(stackPos(1) & 0xFFFE);
+ int facing = stackPos(2);
+ _currentCharacter->x1 = _currentCharacter->x2 = xpos;
+ _currentCharacter->y1 = _currentCharacter->y2 = ypos;
+ _currentCharacter->facing = facing;
+ _currentCharacter->currentAnimFrame = 7;
+ int xOffset = _defaultShapeTable[0].xOffset;
+ int yOffset = _defaultShapeTable[0].yOffset;
+ int width = _defaultShapeTable[0].w << 3;
+ int height = _defaultShapeTable[0].h;
+ AnimObject *curAnim = _animator->actors();
+
+ if (changeScaleMode) {
+ curAnim->x1 = _currentCharacter->x1;
+ curAnim->y1 = _currentCharacter->y1;
+ _animator->_brandonScaleY = _scaleTable[_currentCharacter->y1];
+ _animator->_brandonScaleX = _animator->_brandonScaleY;
+
+ int animWidth = _animator->fetchAnimWidth(curAnim->sceneAnimPtr, _animator->_brandonScaleX) >> 1;
+ int animHeight = _animator->fetchAnimHeight(curAnim->sceneAnimPtr, _animator->_brandonScaleY);
+
+ animWidth = (xOffset * animWidth) / width;
+ animHeight = (yOffset * animHeight) / height;
+
+ curAnim->x2 = curAnim->x1 += animWidth;
+ curAnim->y2 = curAnim->y1 += animHeight;
+ } else {
+ curAnim->x2 = curAnim->x1 = _currentCharacter->x1 + xOffset;
+ curAnim->y2 = curAnim->y1 = _currentCharacter->y1 + yOffset;
+ }
+
+ int scaleModeBackup = _scaleMode;
+ if (changeScaleMode) {
+ _scaleMode = 1;
+ }
+
+ _animator->animRefreshNPC(0);
+ _animator->preserveAllBackgrounds();
+ _animator->prepDrawAllObjects();
+ _animator->copyChangedObjectsForward(0);
+
+ _scaleMode = scaleModeBackup;
+
+ return 0;
+}
+
+int KyraEngine::cmd_restoreAllObjectBackgrounds(ScriptState *script) {
+ debug(3, "cmd_restoreAllObjectBackgrounds(0x%X) ()", script);
+ _animator->restoreAllObjectBackgrounds();
+ return 0;
+}
+
+int KyraEngine::cmd_setCustomPaletteRange(ScriptState *script) {
+ debug(3, "cmd_setCustomPaletteRange(0x%X) (%d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2));
+ uint8 *screenPal = _screen->_currentPalette;
+ memcpy(&screenPal[stackPos(1)*3], _specialPalettes[stackPos(0)], stackPos(2)*3);
+ _screen->setScreenPalette(screenPal);
+ return 0;
+}
+
+int KyraEngine::cmd_loadPageFromDisk(ScriptState *script) {
+ debug(3, "cmd_loadPageFromDisk(0x%X) ('%s', %d)", script, stackPosString(0), stackPos(1));
+ _screen->loadPageFromDisk(stackPosString(0), stackPos(1));
+ _animator->_updateScreen = true;
+ return 0;
+}
+
+int KyraEngine::cmd_customPrintTalkString(ScriptState *script) {
+ if (_features & GF_TALKIE) {
+ debug(3, "cmd_customPrintTalkString(0x%X) (%d, '%s', %d, %d, %d)", script, stackPos(0), stackPosString(1), stackPos(2), stackPos(3), stackPos(4) & 0xFF);
+ snd_voiceWaitForFinish();
+ snd_playVoiceFile(stackPos(0));
+ _skipFlag = false;
+ _text->printTalkTextMessage(stackPosString(1), stackPos(2), stackPos(3), stackPos(4) & 0xFF, 0, 2);
+ } else {
+ debug(3, "cmd_customPrintTalkString(0x%X) ('%s', %d, %d, %d)", script, stackPosString(0), stackPos(1), stackPos(2), stackPos(3) & 0xFF);
+ _skipFlag = false;
+ _text->printTalkTextMessage(stackPosString(0), stackPos(1), stackPos(2), stackPos(3) & 0xFF, 0, 2);
+ }
+ _screen->updateScreen();
+ return 0;
+}
+
+int KyraEngine::cmd_restoreCustomPrintBackground(ScriptState *script) {
+ debug(3, "cmd_restoreCustomPrintBackground(0x%X) ()", script);
+ _text->restoreTalkTextMessageBkgd(2, 0);
+ return 0;
+}
+
+int KyraEngine::cmd_hideMouse(ScriptState *script) {
+ debug(3, "cmd_hideMouse(0x%X) ()", script);
+ _screen->hideMouse();
+ return 0;
+}
+
+int KyraEngine::cmd_showMouse(ScriptState *script) {
+ debug(3, "cmd_showMouse(0x%X) ()", script);
+ _screen->showMouse();
+ return 0;
+}
+
+int KyraEngine::cmd_getCharacterX(ScriptState *script) {
+ debug(3, "cmd_getCharacterX(0x%X) (%d)", script, stackPos(0));
+ return _characterList[stackPos(0)].x1;
+}
+
+int KyraEngine::cmd_getCharacterY(ScriptState *script) {
+ debug(3, "cmd_getCharacterY(0x%X) (%d)", script, stackPos(0));
+ return _characterList[stackPos(0)].y1;
+}
+
+int KyraEngine::cmd_changeCharactersFacing(ScriptState *script) {
+ debug(3, "cmd_changeCharactersFacing(0x%X) (%d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2));
+ int character = stackPos(0);
+ int facing = stackPos(1);
+ int newAnimFrame = stackPos(2);
+
+ _animator->restoreAllObjectBackgrounds();
+ if (newAnimFrame != -1) {
+ _characterList[character].currentAnimFrame = newAnimFrame;
+ }
+ _characterList[character].facing = facing;
+ _animator->animRefreshNPC(character);
+ _animator->preserveAllBackgrounds();
+ _animator->prepDrawAllObjects();
+ _animator->copyChangedObjectsForward(0);
+
+ return 0;
+}
+
+int KyraEngine::cmd_copyWSARegion(ScriptState *script) {
+ debug(3, "cmd_copyWSARegion(0x%X) (%d, %d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4), stackPos(5));
+ int xpos = stackPos(0);
+ int ypos = stackPos(1);
+ int width = stackPos(2);
+ int height = stackPos(3);
+ int srcPage = stackPos(4);
+ int dstPage = stackPos(5);
+ _screen->copyRegion(xpos, ypos, xpos, ypos, width, height, srcPage, dstPage);
+ _animator->_updateScreen = true;
+ return 0;
+}
+
+int KyraEngine::cmd_printText(ScriptState *script) {
+ debug(3, "cmd_printText(0x%X) ('%s', %d, %d, 0x%X, 0x%X)", script, stackPosString(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4));
+ _screen->printText(stackPosString(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4));
+ _screen->updateScreen();
+ return 0;
+}
+
+int KyraEngine::cmd_random(ScriptState *script) {
+ debug(3, "cmd_random(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ assert(stackPos(0) < stackPos(1));
+ return _rnd.getRandomNumberRng(stackPos(0), stackPos(1));
+}
+
+int KyraEngine::cmd_loadSoundFile(ScriptState *script) {
+ warning("STUB: cmd_loadSoundFile");
+ return 0;
+}
+
+int KyraEngine::cmd_displayWSAFrameOnHidPage(ScriptState *script) {
+ debug(3, "cmd_displayWSAFrameOnHidPage(0x%X) (%d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4));
+ int frame = stackPos(0);
+ int xpos = stackPos(1);
+ int ypos = stackPos(2);
+ int waitTime = stackPos(3);
+ int wsaIndex = stackPos(4);
+
+ _screen->hideMouse();
+ uint32 continueTime = waitTime * _tickLength + _system->getMillis();
+ _movieObjects[wsaIndex]->_x = xpos;
+ _movieObjects[wsaIndex]->_y = ypos;
+ _movieObjects[wsaIndex]->_drawPage = 2;
+ _movieObjects[wsaIndex]->displayFrame(frame);
+ _animator->_updateScreen = true;
+ while (_system->getMillis() < continueTime) {
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ if (continueTime - _system->getMillis() >= 10)
+ delay(10);
+ }
+ _screen->showMouse();
+
+ return 0;
+}
+
+int KyraEngine::cmd_displayWSASequentialFrames(ScriptState *script) {
+ debug(3, "cmd_displayWSASequentialFrames(0x%X) (%d, %d, %d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4), stackPos(5), stackPos(6));
+ int startFrame = stackPos(0);
+ int endFrame = stackPos(1);
+ int xpos = stackPos(2);
+ int ypos = stackPos(3);
+ int waitTime = stackPos(4);
+ int wsaIndex = stackPos(5);
+ int maxTime = stackPos(6);
+ if (maxTime - 1 <= 0)
+ maxTime = 1;
+
+ _movieObjects[wsaIndex]->_x = xpos;
+ _movieObjects[wsaIndex]->_y = ypos;
+ _movieObjects[wsaIndex]->_drawPage = 0;
+
+ int curTime = 0;
+ _screen->hideMouse();
+ while (curTime < maxTime) {
+ if (endFrame >= startFrame) {
+ int frame = startFrame;
+ while (endFrame >= frame) {
+ _movieObjects[wsaIndex]->displayFrame(frame);
+ _animator->_updateScreen = true;
+ uint32 continueTime = waitTime * _tickLength + _system->getMillis();
+ while (_system->getMillis() < continueTime && !_skipFlag) {
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ if (continueTime - _system->getMillis() >= 10)
+ delay(10);
+ }
+ ++frame;
+ }
+ } else {
+ int frame = startFrame;
+ while (endFrame <= frame) {
+ _movieObjects[wsaIndex]->displayFrame(frame);
+ _animator->_updateScreen = true;
+ uint32 continueTime = waitTime * _tickLength + _system->getMillis();
+ while (_system->getMillis() < continueTime && !_skipFlag) {
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ if (continueTime - _system->getMillis() >= 10)
+ delay(10);
+ }
+ --frame;
+ }
+ }
+ if (!_skipFlag)
+ break;
+ else
+ ++curTime;
+ }
+ _screen->showMouse();
+
+ return 0;
+}
+
+int KyraEngine::cmd_drawCharacterStanding(ScriptState *script) {
+ debug(3, "cmd_drawCharacterStanding(0x%X) (%d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ int character = stackPos(0);
+ int animFrame = stackPos(1);
+ int newFacing = stackPos(2);
+ int updateShapes = stackPos(3);
+ _characterList[character].currentAnimFrame = animFrame;
+ if (newFacing != -1) {
+ _characterList[character].facing = newFacing;
+ }
+ _animator->animRefreshNPC(character);
+ if (updateShapes) {
+ _animator->updateAllObjectShapes();
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_internalAnimOff(ScriptState *script) {
+ debug(3, "cmd_internalAnimOff(0x%X) (%d)", script, stackPos(0));
+ _animator->sprites()[stackPos(0)].active = 0;
+ return 0;
+}
+
+int KyraEngine::cmd_changeCharactersXAndY(ScriptState *script) {
+ debug(3, "cmd_changeCharactersXAndY(0x%X) (%d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2));
+ Character *ch = &_characterList[stackPos(0)];
+ int16 x = stackPos(1);
+ int16 y = stackPos(2);
+ if (x != -1 && y != -1) {
+ x &= 0xFFFC;
+ y &= 0xFFFE;
+ }
+ _animator->restoreAllObjectBackgrounds();
+ ch->x1 = ch->x2 = x;
+ ch->y1 = ch->y2 = y;
+ _animator->preserveAllBackgrounds();
+ return 0;
+}
+
+int KyraEngine::cmd_clearSceneAnimatorBeacon(ScriptState *script) {
+ debug(3, "cmd_clearSceneAnimatorBeacon(0x%X) ()", script);
+ _sprites->_sceneAnimatorBeaconFlag = 0;
+ return 0;
+}
+
+int KyraEngine::cmd_querySceneAnimatorBeacon(ScriptState *script) {
+ debug(3, "cmd_querySceneAnimatorBeacon(0x%X) ()", script);
+ return _sprites->_sceneAnimatorBeaconFlag;
+}
+
+int KyraEngine::cmd_refreshSceneAnimator(ScriptState *script) {
+ debug(3, "cmd_refreshSceneAnimator(0x%X) ()", script);
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ return 0;
+}
+
+int KyraEngine::cmd_placeItemInOffScene(ScriptState *script) {
+ debug(3, "cmd_placeItemInOffScene(0x%X) (%d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ int item = stackPos(0);
+ int xpos = stackPos(1);
+ int ypos = stackPos(2);
+ int sceneId = stackPos(3);
+
+ byte freeItem = findFreeItemInScene(sceneId);
+ if (freeItem != 0xFF) {
+ assert(sceneId < _roomTableSize);
+ Room *room = &_roomTable[sceneId];
+
+ room->itemsTable[freeItem] = item;
+ room->itemsXPos[freeItem] = xpos;
+ room->itemsYPos[freeItem] = ypos;
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_wipeDownMouseItem(ScriptState *script) {
+ debug(3, "cmd_wipeDownMouseItem(0x%X) (%d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2));
+ _screen->hideMouse();
+ wipeDownMouseItem(stackPos(1), stackPos(2));
+ destroyMouseItem();
+ _screen->showMouse();
+ return 0;
+}
+
+int KyraEngine::cmd_placeCharacterInOtherScene(ScriptState *script) {
+ debug(3, "cmd_placeCharacterInOtherScene(0x%X) (%d, %d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4), stackPos(5));
+ int id = stackPos(0);
+ int sceneId = stackPos(1);
+ int xpos = (int16)(stackPos(2) & 0xFFFC);
+ int ypos = (int16)(stackPos(3) & 0xFFFE);
+ int facing = stackPos(4);
+ int animFrame = stackPos(5);
+
+ _characterList[id].sceneId = sceneId;
+ _characterList[id].x1 = _characterList[id].x2 = xpos;
+ _characterList[id].y1 = _characterList[id].y2 = ypos;
+ _characterList[id].facing = facing;
+ _characterList[id].currentAnimFrame = animFrame;
+ return 0;
+}
+
+int KyraEngine::cmd_getKey(ScriptState *script) {
+ debug(3, "cmd_getKey(0x%X) ()", script);
+ waitForEvent();
+ return 0;
+}
+
+int KyraEngine::cmd_specificItemInInventory(ScriptState *script) {
+ warning("STUB: cmd_specificItemInInventory");
+ return 0;
+}
+
+int KyraEngine::cmd_popMobileNPCIntoScene(ScriptState *script) {
+ debug(3, "cmd_popMobileNPCIntoScene(0x%X) (%d, %d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), (int16)(stackPos(4) & 0xFFFC), (int8)(stackPos(5) & 0xFE));
+ int character = stackPos(0);
+ int sceneId = stackPos(1);
+ int animFrame = stackPos(2);
+ int facing = stackPos(3);
+ int16 xpos = (int16)(stackPos(4) & 0xFFFC);
+ int8 ypos = (int16)(stackPos(5) & 0xFFFE);
+ Character *curChar = &_characterList[character];
+
+ curChar->sceneId = sceneId;
+ curChar->currentAnimFrame = animFrame;
+ curChar->facing = facing;
+ curChar->x1 = curChar->x2 = xpos;
+ curChar->y1 = curChar->y2 = ypos;
+
+ _animator->animAddNPC(character);
+ _animator->updateAllObjectShapes();
+ return 0;
+}
+
+int KyraEngine::cmd_mobileCharacterInScene(ScriptState *script) {
+ warning("STUB: cmd_mobileCharacterInScene");
+ return 0;
+}
+
+int KyraEngine::cmd_hideMobileCharacter(ScriptState *script) {
+ warning("STUB: cmd_hideMobileCharacter");
+ return 0;
+}
+
+int KyraEngine::cmd_unhideMobileCharacter(ScriptState *script) {
+ warning("STUB: cmd_unhideMobileCharacter");
+ return 0;
+}
+
+int KyraEngine::cmd_setCharactersLocation(ScriptState *script) {
+ debug(3, "cmd_setCharactersLocation(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ Character *ch = &_characterList[stackPos(0)];
+ AnimObject *animObj = &_animator->actors()[stackPos(0)];
+ int newScene = stackPos(1);
+ if (_currentCharacter->sceneId == ch->sceneId) {
+ if (_currentCharacter->sceneId != newScene)
+ animObj->active = 0;
+ } else if (_currentCharacter->sceneId == newScene) {
+ if (_currentCharacter->sceneId != ch->sceneId)
+ animObj->active = 1;
+ }
+
+ ch->sceneId = stackPos(1);
+ return 0;
+}
+
+int KyraEngine::cmd_walkCharacterToPoint(ScriptState *script) {
+ debug(3, "cmd_walkCharacterToPoint(0x%X) (%d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2));
+ int character = stackPos(0);
+ int toX = stackPos(1);
+ int toY = stackPos(2);
+ _pathfinderFlag2 = 1;
+ uint32 nextFrame;
+ int findWayReturn = findWay(_characterList[character].x1, _characterList[character].y1, toX, toY, _movFacingTable, 150);
+ _pathfinderFlag2 = 0;
+ if (_lastFindWayRet < findWayReturn) {
+ _lastFindWayRet = findWayReturn;
+ }
+ if (findWayReturn == 0x7D00 || findWayReturn == 0) {
+ return 0;
+ }
+ int *curPos = _movFacingTable;
+ bool running = true;
+ while (running) {
+ bool forceContinue = false;
+ switch (*curPos) {
+ case 0:
+ _characterList[character].facing = 2;
+ break;
+
+ case 1:
+ _characterList[character].facing = 1;
+ break;
+
+ case 2:
+ _characterList[character].facing = 0;
+ break;
+
+ case 3:
+ _characterList[character].facing = 7;
+ break;
+
+ case 4:
+ _characterList[character].facing = 6;
+ break;
+
+ case 5:
+ _characterList[character].facing = 5;
+ break;
+
+ case 6:
+ _characterList[character].facing = 4;
+ break;
+
+ case 7:
+ _characterList[character].facing = 3;
+ break;
+
+ case 8:
+ running = 0;
+ break;
+
+ default:
+ ++curPos;
+ forceContinue = true;
+ break;
+ }
+
+ if (forceContinue || !running) {
+ continue;
+ }
+
+ setCharacterPosition(character, 0);
+ ++curPos;
+
+ nextFrame = getTimerDelay(5 + character) * _tickLength + _system->getMillis();
+ while (_system->getMillis() < nextFrame) {
+ _sprites->updateSceneAnims();
+ updateMousePointer();
+ updateGameTimers();
+ _animator->updateAllObjectShapes();
+ updateTextFade();
+ if ((nextFrame - _system->getMillis()) >= 10)
+ delay(10);
+ }
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_specialEventDisplayBrynnsNote(ScriptState *script) {
+ debug(3, "cmd_specialEventDisplayBrynnsNote(0x%X) ()", script);
+ _screen->hideMouse();
+ _screen->savePageToDisk("HIDPAGE.TMP", 2);
+ _screen->savePageToDisk("SEENPAGE.TMP", 0);
+ if (_features & GF_TALKIE) {
+ if (_features & GF_ENGLISH) {
+ loadBitmap("NOTEENG.CPS", 3, 3, 0);
+ } else if (_features & GF_FRENCH) {
+ loadBitmap("NOTEFRE.CPS", 3, 3, 0);
+ } else if (_features & GF_GERMAN) {
+ loadBitmap("NOTEGER.CPS", 3, 3, 0);
+ }
+ } else {
+ loadBitmap("NOTE.CPS", 3, 3, 0);
+ }
+ _screen->copyRegion(63, 8, 63, 8, 194, 128, 2, 0);
+ _screen->updateScreen();
+ _screen->showMouse();
+ _screen->setFont(Screen::FID_6_FNT);
+ return 0;
+}
+
+int KyraEngine::cmd_specialEventRemoveBrynnsNote(ScriptState *script) {
+ debug(3, "cmd_specialEventRemoveBrynnsNote(0x%X) ()", script);
+ _screen->hideMouse();
+ _screen->loadPageFromDisk("SEENPAGE.TMP", 0);
+ _screen->loadPageFromDisk("HIDPAGE.TMP", 2);
+ _screen->updateScreen();
+ _screen->showMouse();
+ _screen->setFont(Screen::FID_8_FNT);
+ return 0;
+}
+
+int KyraEngine::cmd_setLogicPage(ScriptState *script) {
+ debug(3, "cmd_setLogicPage(0x%X) (%d)", script, stackPos(0));
+ _screen->_curPage = stackPos(0);
+ return stackPos(0);
+}
+
+int KyraEngine::cmd_fatPrint(ScriptState *script) {
+ debug(3, "cmd_fatPrint(0x%X) ('%s', %d, %d, %d, %d, %d)", script, stackPosString(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4), stackPos(5));
+ _text->printText(stackPosString(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4), stackPos(5));
+ return 0;
+}
+
+int KyraEngine::cmd_preserveAllObjectBackgrounds(ScriptState *script) {
+ debug(3, "cmd_preserveAllObjectBackgrounds(0x%X) ()", script);
+ _animator->preserveAllBackgrounds();
+ return 0;
+}
+
+int KyraEngine::cmd_updateSceneAnimations(ScriptState *script) {
+ debug(3, "cmd_updateSceneAnimations(0x%X) (%d)", script, stackPos(0));
+ if (stackPos(0)) {
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_sceneAnimationActive(ScriptState *script) {
+ debug(3, "cmd_sceneAnimationActive(0x%X) (%d)", script, stackPos(0));
+ return _sprites->_anims[stackPos(0)].play;
+}
+
+int KyraEngine::cmd_setCharactersMovementDelay(ScriptState *script) {
+ debug(3, "cmd_setCharactersMovementDelay(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ setTimerDelay(stackPos(0)+5, stackPos(1));
+ return 0;
+}
+
+int KyraEngine::cmd_getCharactersFacing(ScriptState *script) {
+ debug(3, "cmd_getCharactersFacing(0x%X) (%d)", script, stackPos(0));
+ return _characterList[stackPos(0)].facing;
+}
+
+int KyraEngine::cmd_bkgdScrollSceneAndMasksRight(ScriptState *script) {
+ debug(3, "cmd_bkgdScrollSceneAndMasksRight(0x%X) (%d)", script, stackPos(0));
+ _screen->copyBackgroundBlock(stackPos(0), 2, 0);
+ _screen->copyBackgroundBlock2(stackPos(0));
+ // update the whole screen
+ _screen->copyRegion(7, 7, 7, 7, 305, 129, 3, 0);
+ _screen->updateScreen();
+ return 0;
+}
+
+int KyraEngine::cmd_dispelMagicAnimation(ScriptState *script) {
+ debug(3, "cmd_dispelMagicAnimation(0x%X) ()", script);
+ seq_dispelMagicAnimation();
+ return 0;
+}
+
+int KyraEngine::cmd_findBrightestFireberry(ScriptState *script) {
+ debug(3, "cmd_findBrightestFireberry(0x%X) ()", script);
+ if (_currentCharacter->sceneId >= 187 && _currentCharacter->sceneId <= 198) {
+ return 29;
+ }
+ if (_currentCharacter->sceneId == 133 || _currentCharacter->sceneId == 137 ||
+ _currentCharacter->sceneId == 165 || _currentCharacter->sceneId == 173) {
+ return 29;
+ }
+ if (_itemInHand == 28)
+ return 28;
+ int brightestFireberry = 107;
+ if (_itemInHand >= 29 && _itemInHand <= 33)
+ brightestFireberry = _itemInHand;
+ for (int i = 0; i < 10; ++i) {
+ uint8 item = _currentCharacter->inventoryItems[i];
+ if (item == 0xFF)
+ continue;
+ if (item == 28)
+ return 28;
+ if (item >= 29 && item <= 33) {
+ if (item < brightestFireberry)
+ brightestFireberry = item;
+ }
+ }
+ assert(_currentCharacter->sceneId < _roomTableSize);
+ Room *curRoom = &_roomTable[_currentCharacter->sceneId];
+ for (int i = 0; i < 12; ++i) {
+ uint8 item = curRoom->itemsTable[i];
+ if (item == 0xFF)
+ continue;
+ if (item == 28)
+ return 28;
+ if (item >= 29 && item <= 33) {
+ if (item < brightestFireberry)
+ brightestFireberry = item;
+ }
+ }
+ if (brightestFireberry == 107)
+ return -1;
+ return brightestFireberry;
+}
+
+int KyraEngine::cmd_setFireberryGlowPalette(ScriptState *script) {
+ debug(3, "cmd_setFireberryGlowPalette(0x%X) (%d)", script, stackPos(0));
+ int palIndex = 0;
+ switch (stackPos(0)) {
+ case 0x1E:
+ palIndex = 9;
+ break;
+
+ case 0x1F:
+ palIndex = 10;
+ break;
+
+ case 0x20:
+ palIndex = 11;
+ break;
+
+ case 0x21:
+ case -1:
+ palIndex = 12;
+ break;
+
+ default:
+ palIndex = 8;
+ break;
+ }
+ if (_brandonStatusBit & 2) {
+ if (_currentCharacter->sceneId != 133 && _currentCharacter->sceneId != 137 &&
+ _currentCharacter->sceneId != 165 && _currentCharacter->sceneId != 173 &&
+ (_currentCharacter->sceneId < 187 || _currentCharacter->sceneId > 198)) {
+ palIndex = 14;
+ }
+ }
+ uint8 *palette = _specialPalettes[palIndex];
+ memcpy(&_screen->_currentPalette[684], palette, 44);
+ _screen->setScreenPalette(_screen->_currentPalette);
+ return 0;
+}
+
+int KyraEngine::cmd_setDeathHandlerFlag(ScriptState *script) {
+ debug(3, "cmd_setDeathHandlerFlag(0x%X) (%d)", script, stackPos(0));
+ _deathHandler = stackPos(0);
+ return 0;
+}
+
+int KyraEngine::cmd_drinkPotionAnimation(ScriptState *script) {
+ debug(3, "cmd_drinkPotionAnimation(0x%X) (%d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2));
+ seq_playDrinkPotionAnim(stackPos(0), stackPos(1), stackPos(2));
+ return 0;
+}
+
+int KyraEngine::cmd_makeAmuletAppear(ScriptState *script) {
+ debug(3, "cmd_makeAmuletAppear(0x%X) ()", script);
+ WSAMovieV1 amulet(this);
+ amulet.open("AMULET.WSA", 1, 0);
+ amulet._drawPage = 0;
+ amulet._x = 224;
+ amulet._y = 152;
+ if (amulet.opened()) {
+ assert(_amuleteAnim);
+ _screen->hideMouse();
+ snd_playSoundEffect(0x70);
+ uint32 nextTime = 0;
+ for (int i = 0; _amuleteAnim[i] != 0xFF; ++i) {
+ nextTime = _system->getMillis() + 5 * _tickLength;
+
+ uint8 code = _amuleteAnim[i];
+ if (code == 3 || code == 7) {
+ snd_playSoundEffect(0x71);
+ }
+
+ if (code == 5) {
+ snd_playSoundEffect(0x72);
+ }
+
+ if (code == 14) {
+ snd_playSoundEffect(0x73);
+ }
+
+
+ amulet.displayFrame(code);
+ _animator->_updateScreen = true;
+
+ while (_system->getMillis() < nextTime) {
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ if (nextTime - _system->getMillis() >= 10)
+ delay(10);
+ }
+ }
+ _screen->showMouse();
+ }
+ setGameFlag(0x2D);
+ return 0;
+}
+
+int KyraEngine::cmd_drawItemShapeIntoScene(ScriptState *script) {
+ debug(3, "cmd_drawItemShapeIntoScene(0x%X) (%d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4));
+ int item = stackPos(0);
+ int x = stackPos(1);
+ int y = stackPos(2);
+ int flags = stackPos(3);
+ int onlyHidPage = stackPos(4);
+ if (flags)
+ flags = 1;
+ if (onlyHidPage) {
+ _screen->drawShape(2, _shapes[220+item], x, y, 0, flags);
+ } else {
+ _screen->hideMouse();
+ _animator->restoreAllObjectBackgrounds();
+ _screen->drawShape(2, _shapes[220+item], x, y, 0, flags);
+ _screen->drawShape(0, _shapes[220+item], x, y, 0, flags);
+ _animator->flagAllObjectsForBkgdChange();
+ _animator->flagAllObjectsForRefresh();
+ _animator->updateAllObjectShapes();
+ _screen->showMouse();
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_setCharactersCurrentFrame(ScriptState *script) {
+ debug(3, "cmd_setCharactersCurrentFrame(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ _characterList[stackPos(0)].currentAnimFrame = stackPos(1);
+ return 0;
+}
+
+int KyraEngine::cmd_waitForConfirmationMouseClick(ScriptState *script) {
+ debug(3, "cmd_waitForConfirmationMouseClick(0x%X) ()", script);
+ // if (mouseEnabled) {
+ while (!_mousePressFlag) {
+ updateMousePointer();
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ delay(10);
+ }
+
+ while (_mousePressFlag) {
+ updateMousePointer();
+ _sprites->updateSceneAnims();
+ _animator->updateAllObjectShapes();
+ delay(10);
+ }
+ // }
+ // XXX processButtonList calls
+ script->variables[1] = _mouseX;
+ script->variables[2] = _mouseY;
+ return 0;
+}
+
+int KyraEngine::cmd_pageFlip(ScriptState *script) {
+ warning("STUB: cmd_pageFlip");
+ return 0;
+}
+
+int KyraEngine::cmd_setSceneFile(ScriptState *script) {
+ debug(3, "cmd_setSceneFile(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ setSceneFile(stackPos(0), stackPos(1));
+ return 0;
+}
+
+int KyraEngine::cmd_getItemInMarbleVase(ScriptState *script) {
+ debug(3, "cmd_getItemInMarbleVase(0x%X) ()", script);
+ return _marbleVaseItem;
+}
+
+int KyraEngine::cmd_setItemInMarbleVase(ScriptState *script) {
+ debug(3, "cmd_setItemInMarbleVase(0x%X) (%d)", script, stackPos(0));
+ _marbleVaseItem = stackPos(0);
+ return 0;
+}
+
+int KyraEngine::cmd_addItemToInventory(ScriptState *script) {
+ warning("STUB: cmd_addItemToInventory");
+ return 0;
+}
+
+int KyraEngine::cmd_intPrint(ScriptState *script) {
+ warning("STUB: cmd_intPrint");
+ return 0;
+}
+
+int KyraEngine::cmd_shakeScreen(ScriptState *script) {
+ warning("STUB: cmd_shakeScreen");
+ return 0;
+}
+
+int KyraEngine::cmd_createAmuletJewel(ScriptState *script) {
+ debug(3, "cmd_createAmuletJewel(0x%X) (%d)", script, stackPos(0));
+ seq_createAmuletJewel(stackPos(0), 0, 0, 0);
+ return 0;
+}
+
+int KyraEngine::cmd_setSceneAnimCurrXY(ScriptState *script) {
+ debug(3, "cmd_setSceneAnimCurrXY(0x%X) (%d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2));
+ _sprites->_anims[stackPos(0)].x = stackPos(1);
+ _sprites->_anims[stackPos(0)].y = stackPos(2);
+ return 0;
+}
+
+int KyraEngine::cmd_poisonBrandonAndRemaps(ScriptState *script) {
+ debug(3, "cmd_poisonBrandonAndRemaps(0x%X) ()", script);
+ setBrandonPoisonFlags(1);
+ return 0;
+}
+
+int KyraEngine::cmd_fillFlaskWithWater(ScriptState *script) {
+ debug(3, "cmd_fillFlaskWithWater(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ seq_fillFlaskWithWater(stackPos(0), stackPos(1));
+ return 0;
+}
+
+int KyraEngine::cmd_getCharactersMovementDelay(ScriptState *script) {
+ debug(3, "cmd_getCharactersMovementDelay(0x%X) (%d)", script, stackPos(0));
+ return getTimerDelay(stackPos(0)+5);
+}
+
+int KyraEngine::cmd_getBirthstoneGem(ScriptState *script) {
+ debug(3, "cmd_getBirthstoneGem(0x%X) (%d)", script, stackPos(0));
+ if (stackPos(0) < 4) {
+ return _birthstoneGemTable[stackPos(0)];
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_queryBrandonStatusBit(ScriptState *script) {
+ debug(3, "cmd_queryBrandonStatusBit(0x%X) (%d)", script, stackPos(0));
+ if (_brandonStatusBit & stackPos(0)) {
+ return 1;
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_playFluteAnimation(ScriptState *script) {
+ debug(3, "cmd_playFluteAnimation(0x%X) ()", script);
+ seq_playFluteAnimation();
+ return 0;
+}
+
+int KyraEngine::cmd_playWinterScrollSequence(ScriptState *script) {
+ debug(3, "cmd_playWinterScrollSequence(0x%X) (%d)", script, stackPos(0));
+ if (!stackPos(0)) {
+ seq_winterScroll2();
+ } else {
+ seq_winterScroll1();
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_getIdolGem(ScriptState *script) {
+ debug(3, "cmd_getIdolGem(0x%X) (%d)", script, stackPos(0));
+ return _idolGemsTable[stackPos(0)];;
+}
+
+int KyraEngine::cmd_setIdolGem(ScriptState *script) {
+ debug(3, "cmd_setIdolGem(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ _idolGemsTable[stackPos(0)] = stackPos(1);
+ return 0;
+}
+
+int KyraEngine::cmd_totalItemsInScene(ScriptState *script) {
+ debug(3, "cmd_totalItemsInScene(0x%X) (%d)", script, stackPos(0));
+ return countItemsInScene(stackPos(0));
+}
+
+int KyraEngine::cmd_restoreBrandonsMovementDelay(ScriptState *script) {
+ debug(3, "cmd_restoreBrandonsMovementDelay(0x%X) ()", script);
+ //TODO: Use movement set by menu, instead of 5.
+ setTimerDelay(5, 5);
+ return 0;
+}
+
+int KyraEngine::cmd_setMousePos(ScriptState *script) {
+ debug(3, "cmd_setMousePos(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ _system->warpMouse(stackPos(0), stackPos(1));
+ _mouseX = stackPos(0);
+ _mouseY = stackPos(1);
+ return 0;
+}
+
+int KyraEngine::cmd_getMouseState(ScriptState *script) {
+ debug(3, "cmd_getMouseState(0x%X) ()", script);
+ return _mouseState;
+}
+
+int KyraEngine::cmd_setEntranceMouseCursorTrack(ScriptState *script) {
+ debug(3, "cmd_setEntranceMouseCursorTrack(0x%X) (%d, %d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4));
+ _entranceMouseCursorTracks[0] = stackPos(0);
+ _entranceMouseCursorTracks[1] = stackPos(1);
+ _entranceMouseCursorTracks[2] = stackPos(0) + stackPos(2) - 1;
+ _entranceMouseCursorTracks[3] = stackPos(1) + stackPos(3) - 1;
+ _entranceMouseCursorTracks[4] = stackPos(4);
+ return 0;
+}
+
+int KyraEngine::cmd_itemAppearsOnGround(ScriptState *script) {
+ debug(3, "cmd_itemAppearsOnGround(0x%X) (%d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2));
+ processItemDrop(_currentCharacter->sceneId, stackPos(0), stackPos(1), stackPos(2), 2, 0);
+ return 0;
+}
+
+int KyraEngine::cmd_setNoDrawShapesFlag(ScriptState *script) {
+ debug(3, "cmd_setNoDrawShapesFlag(0x%X) (%d)", script, stackPos(0));
+ _animator->_noDrawShapesFlag = stackPos(0);
+ return 0;
+}
+
+int KyraEngine::cmd_fadeEntirePalette(ScriptState *script) {
+ warning("STUB: cmd_fadeEntirePalette");
+ return 0;
+}
+
+int KyraEngine::cmd_itemOnGroundHere(ScriptState *script) {
+ debug(3, "cmd_itemOnGroundHere(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ assert(stackPos(0) < _roomTableSize);
+ Room *curRoom = &_roomTable[stackPos(0)];
+ for (int i = 0; i < 12; ++i) {
+ if (curRoom->itemsTable[i] == stackPos(1))
+ return 1;
+ }
+ return 0;
+}
+
+int KyraEngine::cmd_queryCauldronState(ScriptState *script) {
+ debug(3, "cmd_queryCauldronState(0x%X) ()", script);
+ return _cauldronState;
+}
+
+int KyraEngine::cmd_setCauldronState(ScriptState *script) {
+ debug(3, "cmd_setCauldronState(0x%X) (%d)", script, stackPos(0));
+ _cauldronState = stackPos(0);
+ return _cauldronState;
+}
+
+int KyraEngine::cmd_queryCrystalState(ScriptState *script) {
+ debug(3, "cmd_queryCrystalState(0x%X) (%d)", script, stackPos(0));
+ if (!stackPos(0)) {
+ return _crystalState[0];
+ } else if (stackPos(0) == 1) {
+ return _crystalState[1];
+ }
+ return -1;
+}
+
+int KyraEngine::cmd_setCrystalState(ScriptState *script) {
+ debug(3, "cmd_setCrystalState(0x%X) (%d)", script, stackPos(0), stackPos(1));
+ if (!stackPos(0)) {
+ _crystalState[0] = stackPos(1);
+ } else if (stackPos(0) == 1) {
+ _crystalState[1] = stackPos(1);
+ }
+ return stackPos(1);
+}
+
+int KyraEngine::cmd_setPaletteRange(ScriptState *script) {
+ warning("STUB: cmd_setPaletteRange");
+ return 0;
+}
+
+int KyraEngine::cmd_shrinkBrandonDown(ScriptState *script) {
+ debug(3, "cmd_shrinkBrandonDown(0x%X) (%d)", script, stackPos(0));
+ int delayTime = stackPos(0);
+ checkAmuletAnimFlags();
+ int scaleValue = _scaleTable[_currentCharacter->y1];
+ int scale = 0;
+ if (_scaleMode) {
+ scale = scaleValue;
+ } else {
+ scale = 256;
+ }
+ int scaleModeBackUp = _scaleMode;
+ _scaleMode = 1;
+ int scaleEnd = scale >> 1;
+ for (; scaleEnd <= scale; --scale) {
+ _scaleTable[_currentCharacter->y1] = scale;
+ _animator->animRefreshNPC(0);
+ delayWithTicks(1);
+ }
+ delayWithTicks(delayTime); // XXX
+ _scaleTable[_currentCharacter->y1] = scaleValue;
+ _scaleMode = scaleModeBackUp;
+ return 0;
+}
+
+int KyraEngine::cmd_growBrandonUp(ScriptState *script) {
+ debug(3, "cmd_growBrandonUp(0x%X) ()", script);
+ int scaleValue = _scaleTable[_currentCharacter->y1];
+ int scale = 0;
+ if (_scaleMode) {
+ scale = scaleValue;
+ } else {
+ scale = 256;
+ }
+ int scaleModeBackUp = _scaleMode;
+ _scaleMode = 1;
+ for (int curScale = scale >> 1; curScale <= scale; ++curScale) {
+ _scaleTable[_currentCharacter->y1] = curScale;
+ _animator->animRefreshNPC(0);
+ delayWithTicks(1);
+ }
+ _scaleTable[_currentCharacter->y1] = scaleValue;
+ _scaleMode = scaleModeBackUp;
+ return 0;
+}
+
+int KyraEngine::cmd_setBrandonScaleXAndY(ScriptState *script) {
+ debug(3, "cmd_setBrandonScaleXAndY(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ _animator->_brandonScaleX = stackPos(0);
+ _animator->_brandonScaleY = stackPos(1);
+ return 0;
+}
+
+int KyraEngine::cmd_resetScaleMode(ScriptState *script) {
+ debug(3, "cmd_resetScaleMode(0x%X) ()", script);
+ _scaleMode = 0;
+ return 0;
+}
+
+int KyraEngine::cmd_getScaleDepthTableValue(ScriptState *script) {
+ debug(3, "cmd_getScaleDepthTableValue(0x%X) (%d)", script, stackPos(0));
+ assert(stackPos(0) < ARRAYSIZE(_scaleTable));
+ return _scaleTable[stackPos(0)];
+}
+
+int KyraEngine::cmd_setScaleDepthTableValue(ScriptState *script) {
+ debug(3, "cmd_setScaleDepthTableValue(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ assert(stackPos(0) < ARRAYSIZE(_scaleTable));
+ _scaleTable[stackPos(0)] = stackPos(1);
+ return stackPos(1);
+}
+
+int KyraEngine::cmd_message(ScriptState *script) {
+ if (_features & GF_TALKIE) {
+ debug(3, "cmd_message(0x%X) (%d, '%s', %d)", script, stackPos(0), stackPosString(1), stackPos(2));
+ drawSentenceCommand(stackPosString(1), stackPos(2));
+ } else {
+ debug(3, "cmd_message(0x%X) ('%s', %d)", script, stackPosString(0), stackPos(1));
+ drawSentenceCommand(stackPosString(0), stackPos(1));
+ }
+
+ return 0;
+}
+
+int KyraEngine::cmd_checkClickOnNPC(ScriptState *script) {
+ debug(3, "cmd_checkClickOnNPC(0x%X) (%d, %d)", script, stackPos(0), stackPos(1));
+ return checkForNPCScriptRun(stackPos(0), stackPos(1));
+}
+
+int KyraEngine::cmd_getFoyerItem(ScriptState *script) {
+ debug(3, "cmd_getFoyerItem(0x%X) (%d)", stackPos(0));
+ assert(stackPos(0) < ARRAYSIZE(_foyerItemTable));
+ return _foyerItemTable[stackPos(0)];
+}
+
+int KyraEngine::cmd_setFoyerItem(ScriptState *script) {
+ debug(3, "cmd_setFoyerItem(0x%X) (%d, %d)", stackPos(0), stackPos(1));
+ assert(stackPos(0) < ARRAYSIZE(_foyerItemTable));
+ _foyerItemTable[stackPos(0)] = stackPos(1);
+ return stackPos(1);
+}
+
+int KyraEngine::cmd_setNoItemDropRegion(ScriptState *script) {
+ debug(3, "cmd_setNoItemDropRegion(0x%X) (%d, %d, %d, %d)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ addToNoDropRects(stackPos(0), stackPos(1), stackPos(2), stackPos(3));
+ return 0;
+}
+
+int KyraEngine::cmd_walkMalcolmOn(ScriptState *script) {
+ debug(3, "cmd_walkMalcolmOn(0x%X) ()", script);
+ if (!_malcolmFlag)
+ _malcolmFlag = 1;
+ return 0;
+}
+
+int KyraEngine::cmd_passiveProtection(ScriptState *script) {
+ debug(3, "cmd_passiveProtection(0x%X) ()", script);
+ return 1;
+}
+
+int KyraEngine::cmd_setPlayingLoop(ScriptState *script) {
+ warning("STUB: cmd_setPlayingLoop");
+ return 0;
+}
+
+int KyraEngine::cmd_brandonToStoneSequence(ScriptState *script) {
+ warning("STUB: cmd_brandonToStoneSequence");
+ return 0;
+}
+
+int KyraEngine::cmd_brandonHealingSequence(ScriptState *script) {
+ debug(3, "cmd_brandonHealingSequence(0x%X) ()", script);
+ seq_brandonHealing();
+ return 0;
+}
+
+int KyraEngine::cmd_protectCommandLine(ScriptState *script) {
+ debug(3, "cmd_protectCommandLine(0x%X) (%d)", script, stackPos(0));
+ return stackPos(0);
+}
+
+int KyraEngine::cmd_pauseMusicSeconds(ScriptState *script) {
+ warning("STUB: cmd_pauseMusicSeconds");
+ return 0;
+}
+
+int KyraEngine::cmd_resetMaskRegion(ScriptState *script) {
+ warning("STUB: cmd_resetMaskRegion");
+ return 0;
+}
+
+int KyraEngine::cmd_setPaletteChangeFlag(ScriptState *script) {
+ debug(3, "cmd_setPaletteChangeFlag(0x%X) (%d)", script, stackPos(0));
+ _paletteChanged = stackPos(0);
+ return _paletteChanged;
+}
+
+int KyraEngine::cmd_fillRect(ScriptState *script) {
+ debug(3, "cmd_fillRect(0x%X) (%d, %d, %d, %d, %d, 0x%X)", script, stackPos(0), stackPos(1), stackPos(2), stackPos(3), stackPos(4), stackPos(5));
+ int videoPageBackup = _screen->_curPage;
+ _screen->_curPage = stackPos(0);
+ _screen->fillRect(stackPos(1), stackPos(2), stackPos(3), stackPos(4), stackPos(5));
+ _screen->_curPage = videoPageBackup;
+ return 0;
+}
+
+int KyraEngine::cmd_vocUnload(ScriptState *script) {
+ debug(3, "cmd_vocUnload(0x%X) ()", script);
+ // this should unload all voc files (not needed)
+ return 0;
+}
+
+int KyraEngine::cmd_vocLoad(ScriptState *script) {
+ debug(3, "cmd_vocLoad(0x%X) (%d)", script, stackPos(0));
+ // this should load the specified voc file (not needed)
+ return 0;
+}
+
+int KyraEngine::cmd_dummy(ScriptState *script) {
+ debug(3, "cmd_dummy(0x%X) ()", script);
+ return 0;
+}
+
+} // end of namespace Kyra