diff options
author | johndoe123 | 2015-12-08 21:37:06 +0100 |
---|---|---|
committer | Eugene Sandulenko | 2018-07-20 06:43:33 +0000 |
commit | c0c25691e0d388e30d4ca1a5acdb31ef0aabfb8d (patch) | |
tree | d09cf284e028f8212173cf075658262be92a17b4 /engines/illusions/bbdou | |
parent | c6f2c6ba4eb013119597399e04b58435fe70bfab (diff) | |
download | scummvm-rg350-c0c25691e0d388e30d4ca1a5acdb31ef0aabfb8d.tar.gz scummvm-rg350-c0c25691e0d388e30d4ca1a5acdb31ef0aabfb8d.tar.bz2 scummvm-rg350-c0c25691e0d388e30d4ca1a5acdb31ef0aabfb8d.zip |
ILLUSIONS: BBDOU: Implement missing script opcodes and special opcodes; fix ActorType bugs and more
Diffstat (limited to 'engines/illusions/bbdou')
-rw-r--r-- | engines/illusions/bbdou/bbdou_specialcode.cpp | 64 | ||||
-rw-r--r-- | engines/illusions/bbdou/bbdou_specialcode.h | 9 | ||||
-rw-r--r-- | engines/illusions/bbdou/illusions_bbdou.cpp | 7 | ||||
-rw-r--r-- | engines/illusions/bbdou/illusions_bbdou.h | 2 | ||||
-rw-r--r-- | engines/illusions/bbdou/scriptopcodes_bbdou.cpp | 103 | ||||
-rw-r--r-- | engines/illusions/bbdou/scriptopcodes_bbdou.h | 10 |
6 files changed, 191 insertions, 4 deletions
diff --git a/engines/illusions/bbdou/bbdou_specialcode.cpp b/engines/illusions/bbdou/bbdou_specialcode.cpp index db03cb8eb4..d7ba8ceb41 100644 --- a/engines/illusions/bbdou/bbdou_specialcode.cpp +++ b/engines/illusions/bbdou/bbdou_specialcode.cpp @@ -148,6 +148,7 @@ void BbdouSpecialCode::init() { SPECIAL(0x00160037, spcIsCursorHoldingObjectId); SPECIAL(0x00160038, spcInitRadarMicrophone); SPECIAL(0x0016003A, spcSaladCtl); + SPECIAL(0x0016003B, spcRunCause); } void BbdouSpecialCode::run(uint32 specialCodeId, OpCall &opCall) { @@ -329,6 +330,16 @@ void BbdouSpecialCode::spcSaladCtl(OpCall &opCall) { } } +void BbdouSpecialCode::spcRunCause(OpCall &opCall) { + ARG_UINT32(cursorObjectId); + ARG_UINT32(verbId); + ARG_UINT32(objectId1); + ARG_UINT32(objectId2); + Control *cursorControl = _vm->getObjectControl(cursorObjectId); + debug("runCause(%08X, %08X, %08X)", verbId, objectId1, objectId2); + runCause(cursorControl, _cursor->_data, verbId, objectId1, objectId2, 0); +} + void BbdouSpecialCode::playSoundEffect(int soundIndex) { static const uint32 kSoundEffectIds[] = { 0, 1, @@ -595,7 +606,60 @@ void BbdouSpecialCode::cursorInteractControlRoutine(Control *cursorControl, uint } void BbdouSpecialCode::cursorControlRoutine2(Control *cursorControl, uint32 deltaTime) { + + static const struct ShooterAnim { + uint32 objectId; + uint32 sequenceIds1[8]; + uint32 sequenceIds2[8]; + } kShooterAnims[] = { + {0x401C4, + {0x60637, 0x60638, 0x60639, 0x6063A, 0x6063B, 0x6063C, 0x6063D, 0x6063E}, + {0x6063F, 0x60640, 0x60641, 0x60642, 0x60643, 0x60644, 0x60645, 0x60646}}, + {0x401C3, + {0x6064A, 0x6064B, 0x6064C, 0x6064D, 0x6064E, 0x6064F, 0x60650, 0x60651}, + {0x60652, 0x60653, 0x60654, 0x60655, 0x60656, 0x60657, 0x60658, 0x60659}} + }; + + Actor *actor = cursorControl->_actor; + CursorData &cursorData = _cursor->_data; + // TODO + //debug("BbdouSpecialCode::cursorControlRoutine2()"); + + if (cursorData._visibleCtr <= 0) { + if (cursorData._currOverlappedObjectId || cursorData._mode == 3) { + if (cursorData._mode == 3) + _cursor->restoreInfo(); + cursorControl->setActorIndexTo1(); + } + cursorData._currOverlappedObjectId = 0; + return; + } + + Common::Point cursorPos = _vm->_input->getCursorPosition(); + + if (cursorPos != actor->_position) { + actor->_position = cursorPos; + int16 gridX = 8 * cursorPos.x / 640; + if (gridX >= 8) + gridX = 4; + + for (uint i = 0; i < 2; ++i) { + const ShooterAnim &anim = kShooterAnims[i]; + Control *control2 = _vm->getObjectControl(anim.objectId); + if (control2 && control2->_actor) { + if (_shooterStatus[i].gridX != gridX && (!_shooterStatus[i].flag || !control2->_actor->_seqCodeIp)) { + _shooterStatus[i].gridX = gridX; + control2->_actor->_seqCodeIp = 0; + control2->startSequenceActor(anim.sequenceIds1[gridX], 2, 0); + } + } + } + + } + + // TODO A lot of stuff + } bool BbdouSpecialCode::testVerbId(uint32 verbId, uint32 holdingObjectId, uint32 overlappedObjectId) { diff --git a/engines/illusions/bbdou/bbdou_specialcode.h b/engines/illusions/bbdou/bbdou_specialcode.h index 762aff1de0..22fdd12cbc 100644 --- a/engines/illusions/bbdou/bbdou_specialcode.h +++ b/engines/illusions/bbdou/bbdou_specialcode.h @@ -82,6 +82,11 @@ public: RadarMicrophoneZone _zones[8]; }; +struct ShooterStatus { + int gridX; + bool flag; +}; + class BbdouSpecialCode : public SpecialCode { public: BbdouSpecialCode(IllusionsEngine_BBDOU *vm); @@ -101,6 +106,9 @@ public: uint _saladCount; uint32 _saladObjectIds[12]; + // Shooter + ShooterStatus _shooterStatus[2]; + // Special code interface functions void spcInitCursor(OpCall &opCall); void spcEnableCursor(OpCall &opCall); @@ -125,6 +133,7 @@ public: void spcIsCursorHoldingObjectId(OpCall &opCall); void spcInitRadarMicrophone(OpCall &opCall); void spcSaladCtl(OpCall &opCall); + void spcRunCause(OpCall &opCall); void playSoundEffect(int soundIndex); void resetItem10(uint32 objectId, Item10 *item10); diff --git a/engines/illusions/bbdou/illusions_bbdou.cpp b/engines/illusions/bbdou/illusions_bbdou.cpp index 95be82f2cf..8466780ab0 100644 --- a/engines/illusions/bbdou/illusions_bbdou.cpp +++ b/engines/illusions/bbdou/illusions_bbdou.cpp @@ -196,7 +196,14 @@ Common::Error IllusionsEngine_BBDOU::run() { startScriptThread(0x00020004, 0, 0, 0, 0); _doScriptThreadInit = true; + _walkthroughStarted = false; + while (!shouldQuit()) { + if (_walkthroughStarted) { + //enterScene(0x10003, 0); + startScriptThread(0x00020404, 0, 0, 0, 0); + _walkthroughStarted = false; + } runUpdateFunctions(); _system->updateScreen(); updateEvents(); diff --git a/engines/illusions/bbdou/illusions_bbdou.h b/engines/illusions/bbdou/illusions_bbdou.h index 3b190ea7db..65d9e2630d 100644 --- a/engines/illusions/bbdou/illusions_bbdou.h +++ b/engines/illusions/bbdou/illusions_bbdou.h @@ -72,6 +72,8 @@ public: uint32 _theThreadId; uint32 _globalSceneId; + bool _walkthroughStarted; + void initInput(); void initUpdateFunctions(); diff --git a/engines/illusions/bbdou/scriptopcodes_bbdou.cpp b/engines/illusions/bbdou/scriptopcodes_bbdou.cpp index 945892f82f..6004f44160 100644 --- a/engines/illusions/bbdou/scriptopcodes_bbdou.cpp +++ b/engines/illusions/bbdou/scriptopcodes_bbdou.cpp @@ -62,37 +62,56 @@ void ScriptOpcodes_BBDOU::initOpcodes() { OPCODE(4, opTerminate); OPCODE(5, opJump); OPCODE(6, opStartScriptThread); + // 7 unused OPCODE(8, opStartTempScriptThread); OPCODE(9, opStartTimerThread); + // 10-11 unused OPCODE(12, opNotifyThreadId); + // 13 unused OPCODE(14, opSetThreadSceneId); OPCODE(15, opEndTalkThreads); OPCODE(16, opLoadResource); OPCODE(17, opUnloadResource); + // TODO OPCODE(18, opPauseText); + // TODO OPCODE(19, opResumeText); OPCODE(20, opEnterScene); + OPCODE(21, opLeaveScene); + // TODO OPCODE(22, opEnterPause); + // TODO OPCODE(23, opLeavePause); + OPCODE(24, opUnloadActiveScenes); OPCODE(25, opChangeScene); OPCODE(26, opStartModalScene); OPCODE(27, opExitModalScene); + // 28-29 unused OPCODE(30, opEnterCloseUpScene); OPCODE(31, opExitCloseUpScene); OPCODE(32, opPanCenterObject); + // 33 unused OPCODE(34, opPanToObject); OPCODE(35, opPanToNamedPoint); OPCODE(36, opPanToPoint); OPCODE(37, opPanStop); OPCODE(39, opSetDisplay); + OPCODE(40, opSetCameraBounds); + OPCODE(41, opSetCameraBoundsToMasterBg); OPCODE(42, opIncBlockCounter); OPCODE(43, opClearBlockCounter); + // 44 unused OPCODE(45, opSetProperty); OPCODE(46, opPlaceActor); OPCODE(47, opFaceActor); OPCODE(48, opFaceActorToObject); OPCODE(49, opStartSequenceActor); + // 50 unused OPCODE(51, opStartMoveActor); + // 52 unused OPCODE(53, opSetActorToNamedPoint); + // TODO OPCODE(54, opSetActorPosition); + // 55 unused OPCODE(56, opStartTalkThread); OPCODE(57, opAppearActor); OPCODE(58, opDisappearActor); + OPCODE(59, opIsActorVisible); OPCODE(60, opActivateObject); OPCODE(61, opDeactivateObject); OPCODE(62, opSetDefaultSequence); @@ -101,18 +120,31 @@ void ScriptOpcodes_BBDOU::initOpcodes() { OPCODE(65, opSetDenySfx); OPCODE(66, opSetAdjustUpSfx); OPCODE(67, opSetAdjustDnSfx); + // 68 unused + // TODO OPCODE(69, opPause); + // TODO OPCODE(70, opResume); OPCODE(71, opStartSound); + // TODO OPCODE(72, opStartSoundAtNamedPoint); + // TODO OPCODE(73, opStartSoundAtActor); OPCODE(74, opStopSound); OPCODE(75, opStartMusic); OPCODE(76, opStopMusic); + // 77 unused OPCODE(78, opStackPushRandom); OPCODE(79, opIfLte); OPCODE(80, opAddMenuChoice); OPCODE(81, opDisplayMenu); OPCODE(82, opSwitchMenuChoice); + // TODO OPCODE(83, opQuitGame); OPCODE(84, opResetGame); + // TODO OPCODE(85, opSaveGame); + // TODO OPCODE(86, opRestoreGame); OPCODE(87, opDeactivateButton); OPCODE(88, opActivateButton); + // TODO 89 NOP + // 90 unused + // TODO 91 NOP + // 92-102 unused OPCODE(103, opJumpIf); OPCODE(104, opIsPrevSceneId); OPCODE(105, opIsCurrentSceneId); @@ -123,11 +155,14 @@ void ScriptOpcodes_BBDOU::initOpcodes() { OPCODE(110, opGetProperty); OPCODE(111, opCompareBlockCounter); OPCODE(126, opDebug126); + OPCODE(127, opDebug127); OPCODE(144, opPlayVideo); OPCODE(146, opStackPop); OPCODE(147, opStackDup); OPCODE(148, opLoadSpecialCodeModule); OPCODE(150, opRunSpecialCode); + OPCODE(152, opLinkObjectToObject); + OPCODE(153, opUnlinkObject); OPCODE(160, opStopActor); OPCODE(161, opSetActorUsePan); OPCODE(168, opStartAbortableThread); @@ -185,7 +220,7 @@ void ScriptOpcodes_BBDOU::opStartTimerThread(ScriptThread *scriptThread, OpCall if (maxDuration) duration += _vm->getRandom(maxDuration); -duration = 1;//DEBUG Speeds up things +//duration = 1;//DEBUG Speeds up things if (isAbortable) _vm->startAbortableTimerThread(duration, opCall._threadId); @@ -237,6 +272,16 @@ void ScriptOpcodes_BBDOU::opEnterScene(ScriptThread *scriptThread, OpCall &opCal opCall._result = kTSTerminate; } +void ScriptOpcodes_BBDOU::opLeaveScene(ScriptThread *scriptThread, OpCall &opCall) { + _vm->exitScene(opCall._callerThreadId); +} + +void ScriptOpcodes_BBDOU::opUnloadActiveScenes(ScriptThread *scriptThread, OpCall &opCall) { + ARG_SKIP(2); + ARG_UINT32(sceneId); + _vm->dumpActiveScenes(sceneId, opCall._callerThreadId); +} + //DEBUG Scenes //uint32 dsceneId = 0x00010031, dthreadId = 0x00020036;//MAP //uint32 dsceneId = 0x00010028, dthreadId = 0x000202A1; @@ -249,7 +294,8 @@ void ScriptOpcodes_BBDOU::opEnterScene(ScriptThread *scriptThread, OpCall &opCal //uint32 dsceneId = 0x00010067, dthreadId = 0x0002022A; //uint32 dsceneId = 0x0001000C, dthreadId = 0x00020011;//Cafeteria //uint32 dsceneId = 0x0001000B, dthreadId = 0x00020010; -uint32 dsceneId = 0x0001001A, dthreadId = 0x0002001F; +//uint32 dsceneId = 0x0001001A, dthreadId = 0x0002001F; +uint32 dsceneId = 0x00010047, dthreadId = 0x0002005F; void ScriptOpcodes_BBDOU::opChangeScene(ScriptThread *scriptThread, OpCall &opCall) { ARG_SKIP(2); @@ -257,6 +303,12 @@ void ScriptOpcodes_BBDOU::opChangeScene(ScriptThread *scriptThread, OpCall &opCa ARG_UINT32(threadId); if (dsceneId) { +//#define RUN_WALKTHROUGH +#ifdef RUN_WALKTHROUGH + _vm->_walkthroughStarted = true; + dsceneId = 0; + return; +#endif sceneId = dsceneId; threadId = dthreadId; dsceneId = 0; @@ -346,6 +398,20 @@ void ScriptOpcodes_BBDOU::opSetDisplay(ScriptThread *scriptThread, OpCall &opCal _vm->_screen->setDisplayOn(flag != 0); } +void ScriptOpcodes_BBDOU::opSetCameraBounds(ScriptThread *scriptThread, OpCall &opCall) { + ARG_SKIP(2); + ARG_INT16(x1); + ARG_INT16(y1); + ARG_INT16(x2); + ARG_INT16(y2); + _vm->_camera->setBounds(Common::Point(x1, y1), Common::Point(x2, y2)); +} + +void ScriptOpcodes_BBDOU::opSetCameraBoundsToMasterBg(ScriptThread *scriptThread, OpCall &opCall) { + WidthHeight bgDimensions = _vm->_backgroundInstances->getMasterBgDimensions(); + _vm->_camera->setBoundsToDimensions(bgDimensions); +} + void ScriptOpcodes_BBDOU::opIncBlockCounter(ScriptThread *scriptThread, OpCall &opCall) { ARG_INT16(index); byte value = _vm->_scriptResource->_blockCounters.get(index) + 1; @@ -410,6 +476,8 @@ void ScriptOpcodes_BBDOU::opStartMoveActor(ScriptThread *scriptThread, OpCall &o ARG_UINT32(namedPointId); // NOTE Skipped checking for stalled sequence, not sure if needed Control *control = _vm->_dict->getObjectControl(objectId); + //if (!control) { opCall._deltaOfs = 0; return; }// TODO CHECKME + if (!control) { return; }// TODO CHECKME Common::Point pos = _vm->getNamedPointPosition(namedPointId); control->startMoveActor(sequenceId, pos, opCall._callerThreadId, opCall._threadId); } @@ -454,6 +522,14 @@ void ScriptOpcodes_BBDOU::opDisappearActor(ScriptThread *scriptThread, OpCall &o control->disappearActor(); } +void ScriptOpcodes_BBDOU::opIsActorVisible(ScriptThread *scriptThread, OpCall &opCall) { + ARG_SKIP(2); + ARG_UINT32(objectId); + Control *control = _vm->_dict->getObjectControl(objectId); + const bool visible = control && control->isActorVisible(); + _vm->_stack->push(visible ? 1 : 0); +} + void ScriptOpcodes_BBDOU::opActivateObject(ScriptThread *scriptThread, OpCall &opCall) { ARG_SKIP(2); ARG_UINT32(objectId); @@ -675,7 +751,12 @@ void ScriptOpcodes_BBDOU::opCompareBlockCounter(ScriptThread *scriptThread, OpCa void ScriptOpcodes_BBDOU::opDebug126(ScriptThread *scriptThread, OpCall &opCall) { // NOTE Prints some debug text - debug(1, "[DBG] %s", (char*)opCall._code); + debug(1, "[DBG126] %s", (char*)opCall._code); +} + +void ScriptOpcodes_BBDOU::opDebug127(ScriptThread *scriptThread, OpCall &opCall) { + // NOTE Prints some debug text + debug(1, "[DBG127] %s", (char*)opCall._code); } void ScriptOpcodes_BBDOU::opPlayVideo(ScriptThread *scriptThread, OpCall &opCall) { @@ -711,6 +792,22 @@ void ScriptOpcodes_BBDOU::opRunSpecialCode(ScriptThread *scriptThread, OpCall &o _vm->_specialCode->run(specialCodeId, opCall); } +void ScriptOpcodes_BBDOU::opLinkObjectToObject(ScriptThread *scriptThread, OpCall &opCall) { + ARG_SKIP(2); + ARG_UINT32(objectId); + ARG_UINT32(parentObjectId); + ARG_UINT32(linkedObjectValue); + Control *control = _vm->_dict->getObjectControl(objectId); + control->linkToObject(parentObjectId, linkedObjectValue); +} + +void ScriptOpcodes_BBDOU::opUnlinkObject(ScriptThread *scriptThread, OpCall &opCall) { + ARG_SKIP(2); + ARG_UINT32(objectId); + Control *control = _vm->_dict->getObjectControl(objectId); + control->unlinkObject(); +} + void ScriptOpcodes_BBDOU::opStopActor(ScriptThread *scriptThread, OpCall &opCall) { ARG_SKIP(2); ARG_UINT32(objectId); diff --git a/engines/illusions/bbdou/scriptopcodes_bbdou.h b/engines/illusions/bbdou/scriptopcodes_bbdou.h index 89f73dc227..20b6aff72e 100644 --- a/engines/illusions/bbdou/scriptopcodes_bbdou.h +++ b/engines/illusions/bbdou/scriptopcodes_bbdou.h @@ -54,6 +54,8 @@ protected: void opLoadResource(ScriptThread *scriptThread, OpCall &opCall); void opUnloadResource(ScriptThread *scriptThread, OpCall &opCall); void opEnterScene(ScriptThread *scriptThread, OpCall &opCall); + void opLeaveScene(ScriptThread *scriptThread, OpCall &opCall); + void opUnloadActiveScenes(ScriptThread *scriptThread, OpCall &opCall); void opChangeScene(ScriptThread *scriptThread, OpCall &opCall); void opStartModalScene(ScriptThread *scriptThread, OpCall &opCall); void opExitModalScene(ScriptThread *scriptThread, OpCall &opCall); @@ -64,7 +66,9 @@ protected: void opPanToNamedPoint(ScriptThread *scriptThread, OpCall &opCall); void opPanToPoint(ScriptThread *scriptThread, OpCall &opCall); void opPanStop(ScriptThread *scriptThread, OpCall &opCall); - void opSetDisplay(ScriptThread *scriptThread, OpCall &opCall); + void opSetDisplay(ScriptThread *scriptThread, OpCall &opCall); + void opSetCameraBounds(ScriptThread *scriptThread, OpCall &opCall); + void opSetCameraBoundsToMasterBg(ScriptThread *scriptThread, OpCall &opCall); void opIncBlockCounter(ScriptThread *scriptThread, OpCall &opCall); void opClearBlockCounter(ScriptThread *scriptThread, OpCall &opCall); void opSetProperty(ScriptThread *scriptThread, OpCall &opCall); @@ -77,6 +81,7 @@ protected: void opStartTalkThread(ScriptThread *scriptThread, OpCall &opCall); void opAppearActor(ScriptThread *scriptThread, OpCall &opCall); void opDisappearActor(ScriptThread *scriptThread, OpCall &opCall); + void opIsActorVisible(ScriptThread *scriptThread, OpCall &opCall); void opActivateObject(ScriptThread *scriptThread, OpCall &opCall); void opDeactivateObject(ScriptThread *scriptThread, OpCall &opCall); void opSetDefaultSequence(ScriptThread *scriptThread, OpCall &opCall); @@ -107,11 +112,14 @@ protected: void opGetProperty(ScriptThread *scriptThread, OpCall &opCall); void opCompareBlockCounter(ScriptThread *scriptThread, OpCall &opCall); void opDebug126(ScriptThread *scriptThread, OpCall &opCall); + void opDebug127(ScriptThread *scriptThread, OpCall &opCall); void opPlayVideo(ScriptThread *scriptThread, OpCall &opCall); void opStackPop(ScriptThread *scriptThread, OpCall &opCall); void opStackDup(ScriptThread *scriptThread, OpCall &opCall); void opLoadSpecialCodeModule(ScriptThread *scriptThread, OpCall &opCall); void opRunSpecialCode(ScriptThread *scriptThread, OpCall &opCall); + void opLinkObjectToObject(ScriptThread *scriptThread, OpCall &opCall); + void opUnlinkObject(ScriptThread *scriptThread, OpCall &opCall); void opStopActor(ScriptThread *scriptThread, OpCall &opCall); void opSetActorUsePan(ScriptThread *scriptThread, OpCall &opCall); void opStartAbortableThread(ScriptThread *scriptThread, OpCall &opCall); |