/* 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 "startrek/room.h" #define OBJECT_MUDD 8 #define OBJECT_9 9 #define OBJECT_ALIEN_IMAGE 10 #define OBJECT_ALIENDV 11 #define OBJECT_NORTH_DOOR 12 #define OBJECT_REPAIR_TOOL 13 #define HOTSPOT_SCREEN 0x20 #define HOTSPOT_SPHERE 0x21 #define HOTSPOT_NORTH_DOOR 0x22 #define HOTSPOT_EAST_DOOR 0x23 namespace StarTrek { // BUG-ish: trying to scan the sphere while someone is behind it causes it to scan that // object instead. void Room::mudd3Tick1() { playVoc("MUD3LOOP"); _awayMission->crewDirectionsAfterWalk[OBJECT_REDSHIRT] = DIR_W; if (_awayMission->mudd.databaseDestroyed) { loadActorAnim(OBJECT_9, "s4lbpb", 0xa2, 0x9f); // FIXME: is this supposed to be in this if statement? if (!_awayMission->mudd.tookRepairTool) loadActorAnim(OBJECT_REPAIR_TOOL, "s4lbdv", 0xb7, 0xa8); } _awayMission->mudd.muddInDatabaseRoom = false; if (!_awayMission->mudd.muddVisitedDatabaseRoom && _awayMission->mudd.translatedAlienLanguage && !_awayMission->mudd.muddUnavailable) { _awayMission->mudd.muddVisitedDatabaseRoom = true; loadActorAnim(OBJECT_MUDD, "s4lbhs", 0xa2, 0x9f); playMidiMusicTracks(3); _awayMission->mudd.muddInDatabaseRoom = true; _awayMission->timers[2] = 10; } } void Room::mudd3UseCommunicator() { showText(TX_SPEAKER_KIRK, 3, true); showText(TX_SPEAKER_UHURA, TX_STATICU1); } void Room::mudd3LookAtScreen() { // BUGFIX: the condition was flipped in the original; the more "vague" description // should be shown before the alien language is understood. if (_awayMission->mudd.translatedAlienLanguage) showText(TX_SPEAKER_SPOCK, 38, true); else showDescription(17, true); } void Room::mudd3UseSTricorderOnScreen() { if (_roomVar.mudd.tricordersUnavailable) showText(TX_SPEAKER_SPOCK, 39, true); else spockScan(DIR_S, 17, false, true); } // BUGFIX: Event was actually "use screen on kirk", which makes no sense. void Room::mudd3UseKirkOnScreen() { if (!_awayMission->mudd.translatedAlienLanguage) { showDescription(11, true); showText(TX_SPEAKER_SPOCK, 37, true); } } void Room::mudd3UseSpockOnSphere() { _awayMission->crewDirectionsAfterWalk[OBJECT_SPOCK] = DIR_S; loadActorStandAnim(OBJECT_SPOCK); if (_awayMission->mudd.computerDataErasedOrDestroyed) { if (!_awayMission->mudd.databaseDestroyed) { showDescription(0, true); showText(TX_SPEAKER_SPOCK, 52, true); showText(TX_SPEAKER_KIRK, 12, true); showText(TX_SPEAKER_MCCOY, 24, true); } showText(TX_SPEAKER_KIRK, 6, true); showText(TX_SPEAKER_SPOCK, 48, true); showText(TX_SPEAKER_KIRK, 8, true); showText(TX_SPEAKER_SPOCK, 51, true); } else if (_awayMission->mudd.translatedAlienLanguage) { if (_awayMission->mudd.accessedAlienDatabase) showText(TX_SPEAKER_SPOCK, 35, true); else { _awayMission->mudd.accessedAlienDatabase = true; showText(TX_SPEAKER_SPOCK, 54, true); showText(TX_SPEAKER_MCCOY, 32, true); showText(TX_SPEAKER_SPOCK, 50, true); showText(TX_SPEAKER_SPOCK, 49, true); showText(TX_SPEAKER_SPOCK, 46, true); showText(TX_SPEAKER_KIRK, 7, true); _awayMission->mudd.missionScore++; playVoc("LSHAIANS"); loadActorAnim(OBJECT_ALIEN_IMAGE, "s4lbap", 0x32, 0x64); _awayMission->crewDirectionsAfterWalk[OBJECT_KIRK] = DIR_W; _awayMission->crewDirectionsAfterWalk[OBJECT_SPOCK] = DIR_W; _awayMission->crewDirectionsAfterWalk[OBJECT_MCCOY] = DIR_W; _awayMission->crewDirectionsAfterWalk[OBJECT_REDSHIRT] = DIR_W; loadActorStandAnim(OBJECT_KIRK); loadActorStandAnim(OBJECT_SPOCK); loadActorStandAnim(OBJECT_MCCOY); loadActorStandAnim(OBJECT_REDSHIRT); _awayMission->disableInput = true; _awayMission->timers[3] = 40; } } else if (_awayMission->mudd.discoveredBase3System) { showText(TX_SPEAKER_SPOCK, 43, true); showText(TX_SPEAKER_MCCOY, 22, true); showText(TX_SPEAKER_SPOCK, 56, true); showText(TX_SPEAKER_KIRK, 15, true); showText(TX_SPEAKER_SPOCK, 47, true); _roomVar.mudd.suggestedUsingTricorders = true; } else { showText(TX_SPEAKER_SPOCK, 44, true); _awayMission->crewDirectionsAfterWalk[OBJECT_SPOCK] = DIR_W; walkCrewman(OBJECT_SPOCK, 0xcd, 0x87); } } // Finished looking at alien image void Room::mudd3Timer3Expired() { _awayMission->disableInput = false; showText(TX_SPEAKER_MCCOY, 27, true); showText(TX_SPEAKER_SPOCK, 53, true); showText(TX_SPEAKER_MCCOY, 28, true); showText(TX_SPEAKER_MCCOY, 26, true); } void Room::mudd3UseMccoyOnSphere() { // ENHANCEMENT: Turn to face south _awayMission->crewDirectionsAfterWalk[OBJECT_MCCOY] = DIR_S; loadActorStandAnim(OBJECT_MCCOY); showText(TX_SPEAKER_MCCOY, 21, true); _awayMission->crewDirectionsAfterWalk[OBJECT_MCCOY] = DIR_W; walkCrewman(OBJECT_MCCOY, 0xec, 0x84); } void Room::mudd3UseRedshirtOnSphere() { // ENHANCEMENT: Turn to face south _awayMission->crewDirectionsAfterWalk[OBJECT_REDSHIRT] = DIR_S; loadActorStandAnim(OBJECT_REDSHIRT); showText(TX_SPEAKER_BUCHERT, 68, true); // BUGFIX: original played McCoy's audio by mistake _awayMission->crewDirectionsAfterWalk[OBJECT_REDSHIRT] = DIR_W; walkCrewman(OBJECT_REDSHIRT, 0xec, 0x84); } void Room::mudd3UseMTricorderOnSphere() { if (_roomVar.mudd.tricordersUnavailable) showText(TX_SPEAKER_SPOCK, 39, true); // BUGFIX: speaker is Spock else { _awayMission->crewDirectionsAfterWalk[OBJECT_MCCOY] = DIR_S; loadActorStandAnim(OBJECT_MCCOY); if (!_awayMission->mudd.translatedAlienLanguage && _roomVar.mudd.suggestedUsingTricorders && _awayMission->mudd.discoveredBase3System) { _awayMission->disableInput = true; _awayMission->crewDirectionsAfterWalk[OBJECT_MCCOY] = DIR_S; walkCrewman(OBJECT_MCCOY, 0xac, 0x88); _awayMission->crewDirectionsAfterWalk[OBJECT_SPOCK] = DIR_S; walkCrewmanC(OBJECT_SPOCK, 0xa5, 0x8c, &Room::mudd3ReadyToHookUpTricorders); } else { showText(TX_SPEAKER_MCCOY, 21, true); _awayMission->crewDirectionsAfterWalk[OBJECT_MCCOY] = DIR_W; walkCrewman(OBJECT_MCCOY, 0xec, 0x84); } } } void Room::mudd3UseSTricorderOnSphere() { _awayMission->crewDirectionsAfterWalk[OBJECT_SPOCK] = DIR_S; loadActorStandAnim(OBJECT_SPOCK); if (_roomVar.mudd.tricordersUnavailable) showText(TX_SPEAKER_SPOCK, 39, true); // BUGFIX: speaker is Spock else if (_awayMission->mudd.translatedAlienLanguage || (_awayMission->mudd.discoveredBase3System && !_roomVar.mudd.suggestedUsingTricorders)) { showText(TX_SPEAKER_SPOCK, 41, true); _awayMission->crewDirectionsAfterWalk[OBJECT_SPOCK] = DIR_W; walkCrewman(OBJECT_SPOCK, 0xcd, 0x87); } else if (_awayMission->mudd.discoveredBase3System && _roomVar.mudd.suggestedUsingTricorders) { // Hooking up tricorders _awayMission->disableInput = true; _awayMission->crewDirectionsAfterWalk[OBJECT_MCCOY] = DIR_S; walkCrewmanC(OBJECT_MCCOY, 0xca, 0x88, &Room::mudd3ReadyToHookUpTricorders); } else { // No idea how to access it showText(TX_SPEAKER_SPOCK, 42, true); walkCrewman(OBJECT_SPOCK, 0xcd, 0x87); } } void Room::mudd3ReadyToHookUpTricorders() { showText(TX_SPEAKER_SPOCK, 18, true); _roomVar.mudd.tricordersUnavailable = true; _awayMission->timers[1] = 50; loadActorAnim2(OBJECT_SPOCK, "sscans"); playSoundEffectIndex(SND_TRICORDER); } void Room::mudd3Timer1Expired() { // Tricorders ready for use again showText(TX_SPEAKER_SPOCK, 40, true); showText(TX_SPEAKER_SPOCK, 34, true); _awayMission->disableInput = false; _roomVar.mudd.tricordersUnavailable = false; _roomVar.mudd.suggestedUsingTricorders = false; _awayMission->mudd.translatedAlienLanguage = true; _awayMission->mudd.missionScore++; _awayMission->crewDirectionsAfterWalk[OBJECT_SPOCK] = DIR_W; _awayMission->crewDirectionsAfterWalk[OBJECT_MCCOY] = DIR_W; walkCrewman(OBJECT_SPOCK, 0xcd, 0x87); walkCrewman(OBJECT_MCCOY, 0xec, 0x84); } // Harry Mudd stumbled into the room void Room::mudd3Timer2Expired() { const TextRef choices[] = { TX_SPEAKER_KIRK, 10, 9, TX_BLANK }; _awayMission->mudd.computerDataErasedOrDestroyed = true; showText(TX_SPEAKER_MUDD, 65, true); int choice = showMultipleTexts(choices, true); if (choice == 0) { // Allow him to access the database (he ends up erasing it) showText(TX_SPEAKER_MUDD, 66, true); _awayMission->mudd.muddErasedDatabase = true; // ENHANCEMENT: Add a few lines to make it clear that Mudd erased the databanks. // Otherwise, the end of the mission when you confront Mudd doesn't make sense // unless the player happened to try accessing the database again. Also, if you // talk to the crew, they berate him for no apparent reason if this isn't clear. showDescription(0, true); showText(TX_SPEAKER_MCCOY, 31, true); } else { // Don't allow it (he destroys it by accident) showText(TX_SPEAKER_MUDD, 64, true); _awayMission->timers[4] = 98; _awayMission->disableInput = 2; playMidiMusicTracks(26); loadActorAnim(OBJECT_MUDD, "s4lbhb", 0xa2, 0x9f); } } void Room::mudd3Timer4Expired() { _awayMission->mudd.databaseDestroyed = true; showText(TX_SPEAKER_MUDD, 63, true); showText(TX_SPEAKER_MCCOY, 31, true); _awayMission->disableInput = false; } void Room::mudd3UseMemoryDiskOnSphere() { // ENHANCEMENT: Turn to face south _awayMission->crewDirectionsAfterWalk[OBJECT_KIRK] = DIR_S; loadActorStandAnim(OBJECT_KIRK); if (_awayMission->mudd.databaseDestroyed) showDescription(14, true); else if (_awayMission->mudd.translatedAlienLanguage && !_awayMission->mudd.muddErasedDatabase) { showDescription(20, true); if (!_awayMission->mudd.gotPointsForDownloadingData) { _awayMission->mudd.missionScore += 3; _awayMission->mudd.gotPointsForDownloadingData = true; } } else showDescription(19, true); } void Room::mudd3GetRepairTool() { if (_awayMission->mudd.tookRepairTool) showDescription(18, true); // NOTE: unused, since the object disappears, can't be selected again else { _awayMission->disableInput = true; _awayMission->crewDirectionsAfterWalk[OBJECT_KIRK] = DIR_N; walkCrewmanC(OBJECT_KIRK, 0xba, 0xc1, &Room::mudd3ReachedRepairTool); } } void Room::mudd3ReachedRepairTool() { _awayMission->crewDirectionsAfterWalk[OBJECT_KIRK] = DIR_N; loadActorAnimC(OBJECT_KIRK, "kusemn", -1, -1, &Room::mudd3PickedUpRepairTool); } void Room::mudd3PickedUpRepairTool() { _awayMission->disableInput = false; loadActorStandAnim(OBJECT_REPAIR_TOOL); _awayMission->mudd.tookRepairTool = true; _awayMission->mudd.missionScore++; giveItem(OBJECT_IDOOVER); } void Room::mudd3LookAtSphere() { // ENHANCEMENT: Turn to face south _awayMission->crewDirectionsAfterWalk[OBJECT_KIRK] = DIR_S; loadActorStandAnim(OBJECT_KIRK); showDescription(15, true); } void Room::mudd3WalkToNorthDoor() { _roomVar.mudd.walkingToDoor = true; _awayMission->disableInput = true; walkCrewman(OBJECT_KIRK, 0xb8, 0x70); } void Room::mudd3TouchedHotspot0() { // Triggers north door if (_roomVar.mudd.walkingToDoor) { playVoc("SMADOOR3"); loadActorAnim(OBJECT_NORTH_DOOR, "s4lbdo", 0xba, 0x6f); } } void Room::mudd3WalkToEastDoor() { _roomVar.mudd.walkingToDoor = true; _awayMission->disableInput = true; walkCrewman(OBJECT_KIRK, 0x121, 0x81); } void Room::mudd3TouchedHotspot1() { if (_roomVar.mudd.walkingToDoor) { playVoc("SMADOOR3"); } } void Room::mudd3LookAtKirk() { if (!_awayMission->mudd.muddInDatabaseRoom) showDescription(5, true); else showDescription(4, true); } void Room::mudd3LookAtSpock() { if (!_awayMission->mudd.muddInDatabaseRoom) showDescription(12, true); else showDescription( 2, true); } void Room::mudd3LookAtMccoy() { if (!_awayMission->mudd.muddInDatabaseRoom) showDescription(10, true); else showDescription( 9, true); } void Room::mudd3LookAtRedshirt() { if (!_awayMission->mudd.muddInDatabaseRoom) showDescription(7, true); else showDescription(6, true); } void Room::mudd3LookAtMudd() { showDescription(3, true); } void Room::mudd3TalkToKirk() { if (!_awayMission->mudd.muddInDatabaseRoom) { showText(TX_SPEAKER_KIRK, 14, true); showText(TX_SPEAKER_SPOCK, 57, true); showText(TX_SPEAKER_MCCOY, 25, true); } else showText(TX_SPEAKER_KIRK, 2, true); } void Room::mudd3TalkToSpock() { if (!_awayMission->mudd.muddInDatabaseRoom) { showText(TX_SPEAKER_SPOCK, 55, true); showText(TX_SPEAKER_MCCOY, 33, true); showText(TX_SPEAKER_KIRK, 11, true); } else showText(TX_SPEAKER_SPOCK, 19, true); } void Room::mudd3TalkToMccoy() { if (!_awayMission->mudd.muddInDatabaseRoom) showText(TX_SPEAKER_MCCOY, 23, true); else { showText(TX_SPEAKER_MCCOY, 30, true); showText(TX_SPEAKER_MUDD, 62, true); } } void Room::mudd3TalkToRedshirt() { if (!_awayMission->mudd.muddInDatabaseRoom) { showText(TX_SPEAKER_BUCHERT, 70, true); showText(TX_SPEAKER_KIRK, 16, true); showText(TX_SPEAKER_BUCHERT, 71, true); } else showText(TX_SPEAKER_BUCHERT, 67, true); } void Room::mudd3TalkToMudd() { // ENHANCEMENT: the 2nd part of the if condition is new; whether he physically // destroys the database or does through software, he should give this reaction. if (_awayMission->mudd.databaseDestroyed || _awayMission->mudd.muddErasedDatabase) { showText(TX_SPEAKER_MUDD, 60, true); showText(TX_SPEAKER_MCCOY, 29, true); showText(TX_SPEAKER_MUDD, 61, true); showText(TX_SPEAKER_KIRK, 13, true); showText(TX_SPEAKER_MUDD, 58, true); showText(TX_SPEAKER_SPOCK, TX_DEM0N009); showText(TX_SPEAKER_BUCHERT, 69, true); showText(TX_SPEAKER_MUDD, 59, true); showText(TX_SPEAKER_KIRK, 5, true); } } void Room::mudd3UseMedkit() { showText(TX_SPEAKER_MCCOY, 20, true); } }