diff options
Diffstat (limited to 'engines/fullpipe/scenes/scene09.cpp')
-rw-r--r-- | engines/fullpipe/scenes/scene09.cpp | 519 |
1 files changed, 519 insertions, 0 deletions
diff --git a/engines/fullpipe/scenes/scene09.cpp b/engines/fullpipe/scenes/scene09.cpp new file mode 100644 index 0000000000..44f817f1b6 --- /dev/null +++ b/engines/fullpipe/scenes/scene09.cpp @@ -0,0 +1,519 @@ +/* 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 "fullpipe/fullpipe.h" + +#include "fullpipe/objectnames.h" +#include "fullpipe/constants.h" + +#include "fullpipe/gameloader.h" +#include "fullpipe/motion.h" +#include "fullpipe/scenes.h" +#include "fullpipe/statics.h" + +#include "fullpipe/interaction.h" +#include "fullpipe/behavior.h" + + +namespace Fullpipe { + +struct Hanger { + StaticANIObject *ani; + int field_4; + int field_8; + int phase; +}; + +void scene09_setupGrit(Scene *sc) { + if (g_vars->scene09_grit->_statics->_staticsId == ST_GRT9_GRIT) { + if (!getGameLoaderInventory()->getCountItemsWithId(ANI_INV_COIN)) { + if (g_fp->getObjectState(sO_CoinSlot_1) == g_fp->getObjectEnumState(sO_CoinSlot_1, sO_Empty) + && (g_vars->swallowedEgg1->_value.intValue == ANI_INV_EGGBOOT || g_vars->swallowedEgg2->_value.intValue == ANI_INV_EGGBOOT || g_vars->swallowedEgg3->_value.intValue == ANI_INV_EGGBOOT)) { + Scene *oldsc = g_fp->_currentScene; + g_fp->_currentScene = sc; + g_vars->scene09_grit->changeStatics2(ST_GRT9_NORM); + g_fp->_currentScene = oldsc; + } + } + } +} + +void scene09_initScene(Scene *sc) { + g_vars->scene09_flyingBall = 0; + g_vars->scene09_var05 = 0; + g_vars->scene09_glotatel = sc->getStaticANIObject1ById(ANI_GLOTATEL, -1); + g_vars->scene09_spitter = sc->getStaticANIObject1ById(ANI_PLEVATEL, -1); + g_vars->scene09_grit = sc->getStaticANIObject1ById(ANI_GRIT_9, -1); + g_vars->scene09_var08 = 1; + g_vars->scene09_var09 = 0; + g_vars->scene09_var10 = -1; + g_vars->scene09_var11 = -1; + g_vars->scene09_var12 = -1000; + + g_vars->scene09_balls.cPlexLen = 10; + g_vars->scene09_var07.cPlexLen = 10; + + while (g_vars->scene09_balls.numBalls) { + Ball *b = g_vars->scene09_balls.pHead->p0; + + g_vars->scene09_balls.pHead = g_vars->scene09_balls.pHead->p0; + + if (g_vars->scene09_balls.pHead) + g_vars->scene09_balls.pHead->p0->p1 = 0; + else + g_vars->scene09_balls.field_8 = 0; + + g_vars->scene09_balls.init(&b); + } + + g_vars->scene09_var13 = 3; + + g_vars->scene09_hangers.clear(); + g_vars->scene09_var15 = 4; + g_vars->scene09_numMovingHangers = 4; + + StaticANIObject *hanger = sc->getStaticANIObject1ById(ANI_VISUNCHIK, -1); + Hanger *hng = new Hanger; + + hng->ani = hanger; + hng->phase = 0; + hng->field_4 = 0; + hng->field_8 = 0; + + g_vars->scene09_hangers.push_back(hng); + + int x = 75; + + for (int i = 1; x < 300; i++, x += 75) { + StaticANIObject *ani = new StaticANIObject(hanger); + + ani->show1(x + hanger->_ox, hanger->_oy, MV_VSN_CYCLE2, 0); + sc->addStaticANIObject(hanger, 1); + + hng = new Hanger; + + hng->ani = ani; + hng->phase = 0; + hng->field_4 = 0; + hng->field_8 = 0; + + g_vars->scene09_hangers.push_back(hng); + } + + while (g_vars->scene09_var07.numBalls) { + Ball *ohead = g_vars->scene09_var07.pHead; + + g_vars->scene09_var07.pHead = g_vars->scene09_var07.pHead->p0; + + if (g_vars->scene09_var07.pHead) + ohead->p0->p1 = 0; + else + g_vars->scene09_var07.field_8 = 0; + + ohead->p0 = g_vars->scene09_var07.pTail; + + g_vars->scene09_var07.pTail = ohead; + + g_vars->scene09_var07.numBalls--; + } + + g_vars->scene09_var07.reset(); + + Ball *b9 = g_vars->scene09_var07.sub04(g_vars->scene09_var07.field_8, 0); + b9->ani = sc->getStaticANIObject1ById(ANI_BALL9, -1); + b9->ani->setAlpha(0xc8); + + if (g_vars->scene09_var07.field_8) { + g_vars->scene09_var07.field_8->p0 = b9; + g_vars->scene09_var07.field_8 = b9; + } else { + g_vars->scene09_var07.pHead = b9; + g_vars->scene09_var07.field_8 = b9; + } + + for (int i = 0; i < 4; i++) { + StaticANIObject *newball = new StaticANIObject(b9->ani); + + newball->setAlpha(0xc8); + + Ball *runPtr = g_vars->scene09_var07.pTail; + Ball *lastP = g_vars->scene09_var07.field_8; + + if (!g_vars->scene09_var07.pTail) { + g_vars->scene09_var07.cPlex = (byte *)calloc(g_vars->scene09_var07.cPlexLen, sizeof(Ball)); + + byte *p1 = g_vars->scene09_var07.cPlex + (g_vars->scene09_var07.cPlexLen - 1) * sizeof(Ball); + + if (g_vars->scene09_var07.cPlexLen - 1 < 0) { + runPtr = g_vars->scene09_var07.pTail; + } else { + runPtr = g_vars->scene09_var07.pTail; + + for (int j = 0; j < g_vars->scene09_var07.cPlexLen; j++) { + ((Ball *)p1)->p1 = runPtr; + runPtr = (Ball *)p1; + + p1 -= sizeof(Ball); + } + + g_vars->scene09_var07.pTail = runPtr; + } + } + + g_vars->scene09_var07.pTail = runPtr->p0; + runPtr->p1 = lastP; + runPtr->p0 = 0; + runPtr->ani = newball; + + g_vars->scene09_var07.numBalls++; + + if (g_vars->scene09_var07.field_8) + g_vars->scene09_var07.field_8->p0 = runPtr; + else + g_vars->scene09_var07.pHead = runPtr; + + g_vars->scene09_var07.field_8 = runPtr; + + sc->addStaticANIObject(newball, 1); + } + + g_fp->setObjectState(sO_RightStairs_9, g_fp->getObjectEnumState(sO_RightStairs_9, sO_IsClosed)); + + GameVar *eggvar = g_fp->getGameLoaderGameVar()->getSubVarByName("OBJSTATES")->getSubVarByName(sO_GulpedEggs); + + g_vars->swallowedEgg1 = eggvar->getSubVarByName(sO_Egg1); + g_vars->swallowedEgg2 = eggvar->getSubVarByName(sO_Egg2); + g_vars->swallowedEgg3 = eggvar->getSubVarByName(sO_Egg3); + + scene09_setupGrit(sc); + + g_fp->initArcadeKeys("SC_9"); + + g_fp->lift_setButton(sO_Level1, ST_LBN_1N); + + g_fp->setArcadeOverlay(PIC_CSR_ARCADE4); +} + +int sceneHandler09_updateScreenCallback() { + int res = g_fp->drawArcadeOverlay(g_fp->_objectIdAtCursor == ANI_VISUNCHIK || g_vars->scene09_var10 >= 0); + + if (!res) + g_fp->_updateScreenCallback = 0; + + return res; +} + +int scene09_updateCursor() { + g_fp->updateCursorCommon(); + + if (g_vars->scene09_var10 < 0) { + if (g_fp->_objectIdAtCursor == ANI_VISUNCHIK) { + if (g_fp->_cursorId == PIC_CSR_ITN) + g_fp->_updateScreenCallback = sceneHandler09_updateScreenCallback; + } else { + if (g_fp->_objectIdAtCursor == PIC_SC9_LADDER_R && g_fp->_cursorId == PIC_CSR_ITN) + g_fp->_cursorId = (g_vars->scene09_var02 < 350) ? PIC_CSR_GOD : PIC_CSR_GOU; + } + } else { + g_fp->_cursorId = PIC_CSR_ITN; + } + + return g_fp->_cursorId; +} + +void sceneHandler09_winArcade() { + if (g_vars->scene09_glotatel->_flags & 4) { + g_vars->scene09_glotatel->changeStatics2(ST_GLT_SIT); + g_vars->scene09_glotatel->startAnim(MV_GLT_FLYAWAY, 0, -1); + + g_fp->setObjectState(sO_Jug, g_fp->getObjectEnumState(sO_Jug, sO_Unblocked)); + g_fp->setObjectState(sO_RightStairs_9, g_fp->getObjectEnumState(sO_RightStairs_9, sO_IsOpened)); + + g_vars->scene09_var08 = 0; + } +} + +void sceneHandler09_startAuntie() { + MessageQueue *mq = new MessageQueue(g_fp->_currentScene->getMessageQueueById(QU_TTA9_GOL), 0, 1); + + mq->getExCommandByIndex(0)->_x = g_fp->_sceneRect.right + 30; + mq->chain(0); +} + +void sceneHandler09_spitterClick() { + if (g_vars->scene09_spitter->_flags & 4) { + PicAniInfo info; + + g_vars->scene09_spitter->getPicAniInfo(&info); + g_vars->scene09_spitter->_messageQueueId = 0; + g_vars->scene09_spitter->changeStatics2(ST_PLV_SIT); + + int x = g_vars->scene09_spitter->_ox - 10; + int y = g_vars->scene09_spitter->_oy + 145; + + g_vars->scene09_spitter->setPicAniInfo(&info); + + if (ABS(x - g_fp->_aniMan->_ox) > 1 || ABS(y - g_fp->_aniMan->_oy) > 1) { + MessageQueue *mq = getCurrSceneSc2MotionController()->method34(g_fp->_aniMan, x, y, 1, ST_MAN_UP); + + if (mq) { + ExCommand *ex = new ExCommand(0, 17, MSG_SC9_PLVCLICK, 0, 0, 0, 1, 0, 0, 0); + ex->_excFlags = 2; + mq->addExCommandToEnd(ex); + + postExCommand(g_fp->_aniMan->_id, 2, x, y, 0, -1); + } + } else { + if (!g_fp->_aniMan->_movement) { + g_vars->scene09_spitter->changeStatics2(ST_PLV_SIT); + g_vars->scene09_spitter->hide(); + + g_fp->_aniMan->startAnim(MV_MAN9_SHOOT, 0, -1); + + g_fp->stopAllSoundInstances(SND_9_006); + } + + g_fp->_aniMan2 = 0; + + if (g_fp->_sceneRect.left < 800) + g_fp->_currentScene->_x = 800 - g_fp->_sceneRect.left; + } + } +} + +void sceneHandler09_eatBall() { + warning("STUB: sceneHandler09_eatBall()"); +} + +void sceneHandler09_showBall() { + warning("STUB: sceneHandler09_showBall()"); +} + +void sceneHandler09_cycleHangers() { + warning("STUB: sceneHandler09_cycleHangers()"); +} + +void sceneHandler09_limitHangerPhase() { + warning("STUB: sceneHandler09_limitHangerPhase()"); +} + +void sceneHandler09_collideBall(Ball *ball) { + if (g_vars->scene09_var08) { + g_vars->scene09_flyingBall = ball->ani; + + if (g_vars->scene09_glotatel) { + g_vars->scene09_glotatel->changeStatics2(ST_GLT_SIT); + + MessageQueue *mq = new MessageQueue(g_fp->_currentScene->getMessageQueueById(QU_SC9_EATBALL), 0, 0); + + mq->setFlags(mq->getFlags() | 1); + + if (!mq->chain(g_vars->scene09_glotatel)) + delete mq; + } + } +} + +void sceneHandler09_checkHangerCollide() { + warning("STUB: sceneHandler09_checkHangerCollide()"); +} + +void sceneHandler09_hangerStartCycle() { + StaticANIObject *ani = g_vars->scene09_hangers[g_vars->scene09_var10]->ani; + + if (ani->_movement) { + ani->startAnim(MV_VSN_CYCLE2, 0, -1); + g_vars->scene09_hangers[g_vars->scene09_var10]->field_8 = 0; + g_vars->scene09_hangers[g_vars->scene09_var10]->phase = g_vars->scene09_var11 + (g_fp->_mouseScreenPos.y - g_vars->scene09_var19) / 2; + + if (g_vars->scene09_var12 != -1000 && g_vars->scene09_hangers[g_vars->scene09_var10]->phase != g_vars->scene09_var12) { + ExCommand *ex = new ExCommand(0, 35, SND_9_019, 0, 0, 0, 1, 0, 0, 0); + + ex->_field_14 = 1; + ex->_excFlags |= 2; + ex->postMessage(); + + g_vars->scene09_var12 = -1000; + } + } else { + g_vars->scene09_var10 = -1; + } +} + +int sceneHandler09(ExCommand *cmd) { + if (cmd->_messageKind != 17) + return 0; + + switch (cmd->_messageNum) { + case MSG_CMN_WINARCADE: + sceneHandler09_winArcade(); + break; + + case MSG_SC9_STARTTIOTIA: + sceneHandler09_startAuntie(); + break; + + case MSG_SC9_FROMLADDER: + getCurrSceneSc2MotionController()->setEnabled(); + getGameLoaderInteractionController()->enableFlag24(); + + g_vars->scene09_var09 = 0; + break; + + case MSG_SC9_TOLADDER: + getCurrSceneSc2MotionController()->clearEnabled(); + getGameLoaderInteractionController()->disableFlag24(); + + g_vars->scene09_var09 = 1; + break; + + case MSG_SC9_PLVCLICK: + sceneHandler09_spitterClick(); + break; + + case MSG_SC9_FLOWN: + g_vars->scene09_var08 = 0; + break; + + case MSG_SC9_EATBALL: + sceneHandler09_eatBall(); + break; + + case MSG_SC9_SHOWBALL: + sceneHandler09_showBall(); + break; + + case 33: + { + int res = 0; + + if (g_fp->_aniMan2) { + int x = g_fp->_aniMan2->_ox; + + g_vars->scene09_var02 = g_fp->_aniMan2->_oy; + + if (x < g_fp->_sceneRect.left + 200) + g_fp->_currentScene->_x = x - g_fp->_sceneRect.left - 300; + + if (x > g_fp->_sceneRect.right - 200) + g_fp->_currentScene->_x = x - g_fp->_sceneRect.right + 300; + + res = 1; + } else { + if (g_fp->_aniMan->_movement && g_fp->_aniMan->_movement->_id != MV_MAN9_SHOOT) + g_fp->_aniMan2 = g_fp->_aniMan; + } + + sceneHandler09_cycleHangers(); + sceneHandler09_limitHangerPhase(); + sceneHandler09_checkHangerCollide(); + + if (g_vars->scene09_var10 >= 0) + sceneHandler09_hangerStartCycle(); + + if (!g_vars->scene09_var17) + g_fp->_behaviorManager->updateBehaviors(); + + g_fp->startSceneTrack(); + + return res; + } + + case 30: + if (g_vars->scene09_var10 >= 0) { + if (ABS(g_vars->scene09_hangers[g_vars->scene09_var10]->phase) < 15) { + g_vars->scene09_hangers[g_vars->scene09_var10]->ani->_callback2 = 0; + g_vars->scene09_hangers[g_vars->scene09_var10]->ani->changeStatics2(ST_VSN_NORMAL); + } + } + + g_vars->scene09_var10 = -1; + + break; + + case 29: + { + StaticANIObject *ani = g_fp->_currentScene->getStaticANIObjectAtPos(g_fp->_sceneRect.left + cmd->_x, g_fp->_sceneRect.top + cmd->_y); + + if (ani) { + if (ani->_id == ANI_PLEVATEL) { + sceneHandler09_spitterClick(); + break; + } + + if (ani->_id == ANI_VISUNCHIK) { + if (g_vars->scene09_numMovingHangers > 0) { + int hng = 0; + + while (g_vars->scene09_hangers[hng]->ani != ani) { + ++hng; + + if (hng >= g_vars->scene09_numMovingHangers) + break; + } + + g_vars->scene09_var10 = hng; + g_vars->scene09_var11 = g_vars->scene09_hangers[hng]->phase; + g_vars->scene09_var12 = g_vars->scene09_hangers[hng]->phase; + + g_vars->scene09_var19 = cmd->_y; + + if (!g_vars->scene09_hangers[hng]->ani->_movement || g_vars->scene09_hangers[hng]->ani->_movement->_id != MV_VSN_CYCLE2) { + g_vars->scene09_hangers[hng]->ani->changeStatics2(ST_VSN_NORMAL); + g_vars->scene09_hangers[hng]->ani->startAnim(MV_VSN_CYCLE2, 0, -1); + g_vars->scene09_hangers[hng]->ani->_callback2 = 0; + } + + ExCommand *ex = new ExCommand(0, 35, SND_9_018, 0, 0, 0, 1, 0, 0, 0); + + ex->_field_14 = 1; + ex->_excFlags |= 2; + ex->postMessage(); + } + + break; + } + } + + if (g_vars->scene09_var09 && g_fp->_currentScene->getPictureObjectIdAtPos(cmd->_sceneClickX, cmd->_sceneClickY) == PIC_SC9_LADDER_R + && !cmd->_keyCode && !g_fp->_aniMan->_movement) { + handleObjectInteraction(g_fp->_aniMan, g_fp->_currentScene->getPictureObjectById(PIC_SC9_LADDER_R, 0), 0); + } + + if (!ani || !canInteractAny(g_fp->_aniMan, ani, cmd->_keyCode)) { + int picId = g_fp->_currentScene->getPictureObjectIdAtPos(cmd->_sceneClickX, cmd->_sceneClickY); + PictureObject *pic = g_fp->_currentScene->getPictureObjectById(picId, 0); + + if (!pic || !canInteractAny(g_fp->_aniMan, pic, cmd->_keyCode)) { + if ((g_fp->_sceneRect.right - cmd->_sceneClickX < 47 && g_fp->_sceneRect.right < g_fp->_sceneWidth - 1) || (cmd->_sceneClickX - g_fp->_sceneRect.left < 47 && g_fp->_sceneRect.left > 0)) + g_fp->processArcade(cmd); + } + } + + break; + } + } + + return 0; +} + +} // End of namespace Fullpipe |