From 8269a94bcd55200f7ae8aba00c7b6fd0d37b9a37 Mon Sep 17 00:00:00 2001 From: Martin Kiewitz Date: Tue, 2 Feb 2016 22:26:39 +0100 Subject: AGI: Use inner loop functionality for have.key Also do it like the original interpreter did it --- engines/agi/agi.h | 6 ++++-- engines/agi/cycle.cpp | 6 ++++++ engines/agi/op_test.cpp | 49 ++++++++++++++++++++++++------------------------- 3 files changed, 34 insertions(+), 27 deletions(-) (limited to 'engines') diff --git a/engines/agi/agi.h b/engines/agi/agi.h index 83f4cbc103..3ee9d71089 100644 --- a/engines/agi/agi.h +++ b/engines/agi/agi.h @@ -394,7 +394,8 @@ enum CycleInnerLoopType { CYCLE_INNERLOOP_INVENTORY = 2, CYCLE_INNERLOOP_MENU_VIA_KEYBOARD = 3, CYCLE_INNERLOOP_MENU_VIA_MOUSE = 4, - CYCLE_INNERLOOP_SYSTEMUI_SELECTSAVEDGAMESLOT = 5 + CYCLE_INNERLOOP_SYSTEMUI_SELECTSAVEDGAMESLOT = 5, + CYCLE_INNERLOOP_HAVEKEY = 6 }; enum State { @@ -880,9 +881,10 @@ public: uint8 testPosn(uint8, uint8, uint8, uint8, uint8); uint8 testSaid(uint8, uint8 *); uint8 testController(uint8); - uint8 testKeypressed(); uint8 testCompareStrings(uint8, uint8); + void testHaveKeyCharPress(uint16 newChar); + // View private: diff --git a/engines/agi/cycle.cpp b/engines/agi/cycle.cpp index 553eda541e..2591713272 100644 --- a/engines/agi/cycle.cpp +++ b/engines/agi/cycle.cpp @@ -303,6 +303,12 @@ int AgiEngine::mainCycle(bool onlyCheckForEvents) { } break; + case CYCLE_INNERLOOP_HAVEKEY: + if (key) { + testHaveKeyCharPress(key); + } + break; + default: break; } diff --git a/engines/agi/op_test.cpp b/engines/agi/op_test.cpp index aad1d94cee..2fbdaab2c7 100644 --- a/engines/agi/op_test.cpp +++ b/engines/agi/op_test.cpp @@ -32,7 +32,7 @@ namespace Agi { #define ip (state->_curLogic->cIP) #define code (state->_curLogic->data) -#define getVar(a) state->_vm->getVar(a) +#define getVar(a) vm->getVar(a) #define testEqual(v1, v2) (getVar(v1) == (v2)) #define testLess(v1, v2) (getVar(v1) < (v2)) @@ -98,7 +98,29 @@ void condController(AgiGame *state, AgiEngine *vm, uint8 *p) { } void condHaveKey(AgiGame *state, AgiEngine *vm, uint8 *p) { - state->testResult = vm->testKeypressed(); + if (!getVar(VM_VAR_KEY)) { + // Only wait for key when there is not already one set by scripts + vm->cycleInnerLoopActive(CYCLE_INNERLOOP_HAVEKEY); + do { + // Only check for events here, without updating the game cycle, + // otherwise the animations in some games are drawn too quickly + // like, for example, Manannan's lightnings in the intro of KQ3 + // and the bullets opened in the logo of PQ1, during its intro. + // Fixes bug #3600733 + vm->mainCycle(true); + } while (vm->cycleInnerLoopIsActive() && !(vm->shouldQuit() || vm->_restartGame)); + } + + state->testResult = 1; +} + +void AgiEngine::testHaveKeyCharPress(uint16 newChar) { + // pass key to scripts + setVar(VM_VAR_KEY, newChar); + + // Exit on any key press + cycleInnerLoopInactive(); + debugC(5, kDebugLevelScripts | kDebugLevelInput, "keypress = %02x", newChar); } void condSaid(AgiGame *state, AgiEngine *vm, uint8 *p) { @@ -239,29 +261,6 @@ uint8 AgiEngine::testCompareStrings(uint8 s1, uint8 s2) { return !strcmp(ms1, ms2); } -uint8 AgiEngine::testKeypressed() { - int x = _game.keypress; - - _game.keypress = 0; - if (!x) { - InputMode mode = _game.inputMode; - - _game.inputMode = INPUTMODE_NONE; - // Only check for events here, without updating the game cycle, - // otherwise the animations in some games are drawn too quickly - // like, for example, Manannan's lightnings in the intro of KQ3 - // and the bullets opened in the logo of PQ1, during its intro. - // Fixes bug #3600733 - mainCycle(true); - _game.inputMode = mode; - } - - if (x) - debugC(5, kDebugLevelScripts | kDebugLevelInput, "keypress = %02x", x); - - return x; -} - uint8 AgiEngine::testController(uint8 cont) { return (_game.controllerOccured[cont] ? true : false); } -- cgit v1.2.3