diff options
Diffstat (limited to 'saga')
-rw-r--r-- | saga/actionmap.h | 7 | ||||
-rw-r--r-- | saga/actor.cpp | 135 | ||||
-rw-r--r-- | saga/actor.h | 32 | ||||
-rw-r--r-- | saga/input.cpp | 3 | ||||
-rw-r--r-- | saga/interface.cpp | 9 | ||||
-rw-r--r-- | saga/interface.h | 6 | ||||
-rw-r--r-- | saga/objectmap.h | 13 | ||||
-rw-r--r-- | saga/saga.h | 12 | ||||
-rw-r--r-- | saga/scene.cpp | 20 | ||||
-rw-r--r-- | saga/scene.h | 6 | ||||
-rw-r--r-- | saga/script.cpp | 147 | ||||
-rw-r--r-- | saga/script.h | 14 |
12 files changed, 344 insertions, 60 deletions
diff --git a/saga/actionmap.h b/saga/actionmap.h index 9684a68975..3329d47b59 100644 --- a/saga/actionmap.h +++ b/saga/actionmap.h @@ -47,7 +47,12 @@ class ActionMap { int getExitSceneNumber(int index) const; int hitTest(const Point &testPoint); int draw(SURFACE *ds, int color); - + const HitZone * getHitZone(int index) const { + if ((index < 0) || (index >= _stepZoneListCount)) { + error("ActionMap::getHitZone wrong index 0x%X", index); + } + return _stepZoneList[index]; + } void cmdInfo(); private: diff --git a/saga/actor.cpp b/saga/actor.cpp index 8f4d450800..3d9b681bb9 100644 --- a/saga/actor.cpp +++ b/saga/actor.cpp @@ -39,6 +39,7 @@ #include "saga/actordata.h" #include "saga/stream.h" #include "saga/interface.h" +#include "saga/events.h" #include "common/config-manager.h" namespace Saga { @@ -149,8 +150,8 @@ Actor::Actor(SagaEngine *vm) : _vm(vm) { _pathNodeList = _newPathNodeList = NULL; _pathList = NULL; - _pathListAlloced = _pathNodeListAlloced = 0; - _pathListIndex = _pathNodeListIndex = -1; + _pathListAlloced = _pathNodeListAlloced = _newPathNodeListAlloced = 0; + _pathListIndex = _pathNodeListIndex = _newPathNodeListIndex = -1; _centerActor = _protagonist = NULL; @@ -202,6 +203,7 @@ Actor::Actor(SagaEngine *vm) : _vm(vm) { actor->frameNumber = 0; actor->targetObject = ID_NOTHING; actor->actorFlags = 0; + actor->lastZone = NULL; actor->location.x = ITE_ActorTable[i].x; actor->location.y = ITE_ActorTable[i].y; @@ -310,6 +312,57 @@ bool Actor::loadActorResources(ActorData *actor) { return true; } +void Actor::takeExit(uint16 actorId, const HitZone *hitZone) { + ActorData *actor; + actor = getActor(actorId); + actor->lastZone = NULL; + + _vm->_scene->changeScene(hitZone->getSceneNumber(), hitZone->getActorsEntrance()); + _vm->_script->setNoPendingVerb(); +} + +void Actor::stepZoneAction(ActorData *actor, const HitZone *hitZone, bool exit, bool stopped) { + EVENT event; + + if (actor != _protagonist) { + return; + } + if (((hitZone->getFlags() & kHitZoneTerminus) && !stopped) || (!(hitZone->getFlags() & kHitZoneTerminus) && stopped)) { + return; + } + + if (!exit) { + if (hitZone->getFlags() & kHitZoneAutoWalk) { + actor->currentAction = kActionWalkDir; + actor->actionDirection = actor->facingDirection = hitZone->getDirection(); + actor->walkFrameSequence = kFrameWalk; + return; + } + } else { + if (!(hitZone->getFlags() & kHitZoneAutoWalk)) { + return; + } + } + if (hitZone->getFlags() & kHitZoneExit) { + takeExit(actor->actorId, hitZone); + } else { + if (hitZone->getScriptNumber() > 0) { + event.type = ONESHOT_EVENT; + event.code = SCRIPT_EVENT; + event.op = EVENT_EXEC_NONBLOCKING; + event.time = 0; + event.param = hitZone->getScriptNumber(); + event.param2 = kVerbEnter; // Action + event.param3 = ID_NOTHING; // Object + event.param4 = ID_NOTHING; // With Object + event.param5 = ID_PROTAG; // Actor + + _vm->_events->queue(&event); + } + } + +} + void Actor::realLocation(Location &location, uint16 objectId, uint16 walkFlags) { int angle; int distance; @@ -408,7 +461,7 @@ bool Actor::validFollowerLocation(const Location &location) { return (_vm->_scene->canWalk(point)); } -void Actor::updateActorsScene() { +void Actor::updateActorsScene(int actorsEntrance) { int i, j; int followerDirection; ActorData *actor; @@ -638,6 +691,9 @@ void Actor::handleActions(int msec, bool setup) { int speed; Location delta; Location addDelta; + int hitZoneIndex; + const HitZone *hitZone; + Point hitPoint; for (i = 0; i < _actorsCount; i++) { actor = _actors[i]; @@ -873,6 +929,28 @@ void Actor::handleActions(int msec, bool setup) { //todo: do it break; } + + if ((actor->currentAction >= kActionWalkToPoint) && (actor->currentAction <= kActionWalkDir)) { + hitZone = NULL; + // tiled stuff + if (_vm->_scene->getFlags() & kSceneFlagISO) { + //todo: it + } else { + actor->location.toScreenPointXY(hitPoint); + hitZoneIndex = _vm->_scene->_actionMap->hitTest(hitPoint); + if (hitZoneIndex != -1) { + hitZone = _vm->_scene->_actionMap->getHitZone(hitZoneIndex); + } + } + + if (hitZone != actor->lastZone) { + if (actor->lastZone) + stepZoneAction( actor, actor->lastZone, true, false); + actor->lastZone = hitZone; + if (hitZone) + stepZoneAction( actor, hitZone, false, false); + } + } } } @@ -1106,6 +1184,8 @@ bool Actor::followProtagonist(ActorData *actor) { bool Actor::actorEndWalk(uint16 actorId, bool recurse) { bool walkMore = false; ActorData *actor; + const HitZone *hitZone; + int hitZoneIndex; actor = getActor(actorId); actor->actorFlags &= ~kActorBackwards; @@ -1127,7 +1207,19 @@ bool Actor::actorEndWalk(uint16 actorId, bool recurse) { if (actor == _protagonist) { _vm->_script->wakeUpActorThread(kWaitTypeWalk, actor); - //todo: it + if (_vm->_script->_pendingVerb == kVerbWalkTo) { + hitZoneIndex = _vm->_scene->_actionMap->hitTest(actor->screenPosition); + if (hitZoneIndex != -1) { + hitZone = _vm->_scene->_actionMap->getHitZone(hitZoneIndex); + stepZoneAction(actor, hitZone, false, true); + } else { + _vm->_script->setNoPendingVerb(); + } + } else { + if (_vm->_script->_pendingVerb != kVerbNone) { + _vm->_script->doVerb(); + } + } } else { if (recurse && (actor->flags & kFollower)) @@ -1826,7 +1918,6 @@ void Actor::condenseNodeList() { void Actor::removePathPoints() { int i, j, k, l; PathNode *node; - int newPathNodeIndex; int start; int end; Point point1, point2; @@ -1835,13 +1926,12 @@ void Actor::removePathPoints() { if (_pathNodeListIndex < 2) return; - _newPathNodeList = (PathNode*)realloc(_newPathNodeList, _pathNodeListAlloced); - _newPathNodeList[0] = _pathNodeList[0]; - newPathNodeIndex = 0; - + + _newPathNodeListIndex = -1; + addNewPathNodeListPoint(_pathNodeList[0].point, _pathNodeList[0].link); + for (i = 1, node = _pathNodeList + 1; i < _pathNodeListIndex; i++, node++) { - newPathNodeIndex++; - _newPathNodeList[newPathNodeIndex] = *node; + addNewPathNodeListPoint(node->point, node->link); for (j = 5; j > 0; j--) { start = node->link - j; @@ -1859,17 +1949,17 @@ void Actor::removePathPoints() { if (scanPathLine(point1, point2)) { - for (l = 1; l <= newPathNodeIndex; l++) { + for (l = 1; l <= _newPathNodeListIndex; l++) { if (start <= _newPathNodeList[l].link) { - newPathNodeIndex = l; - _newPathNodeList[newPathNodeIndex].point = point1; - _newPathNodeList[newPathNodeIndex].link = start; - newPathNodeIndex++; + _newPathNodeListIndex = l; + _newPathNodeList[_newPathNodeListIndex].point = point1; + _newPathNodeList[_newPathNodeListIndex].link = start; + incrementNewPathNodeListIndex(); break; } } - _newPathNodeList[newPathNodeIndex].point = point2; - _newPathNodeList[newPathNodeIndex].link = end; + _newPathNodeList[_newPathNodeListIndex].point = point2; + _newPathNodeList[_newPathNodeListIndex].link = end; for (k = start + 1; k < end; k++) { _pathList[k].x = PATH_NODE_EMPTY; @@ -1878,12 +1968,11 @@ void Actor::removePathPoints() { } } } + + addNewPathNodeListPoint(_pathNodeList[_pathNodeListIndex].point, _pathNodeList[_pathNodeListIndex].link); - newPathNodeIndex++; - _newPathNodeList[newPathNodeIndex] = _pathNodeList[_pathNodeListIndex]; - - for (i = 0, j = 0; i <= newPathNodeIndex; i++) { - if (newPathNodeIndex == i || (_newPathNodeList[i].point != _newPathNodeList[i+1].point)) { + for (i = 0, j = 0; i <= _newPathNodeListIndex; i++) { + if (_newPathNodeListIndex == i || (_newPathNodeList[i].point != _newPathNodeList[i+1].point)) { _pathNodeList[j++] = _newPathNodeList[i]; } } diff --git a/saga/actor.h b/saga/actor.h index 8430c45643..07009bedfd 100644 --- a/saga/actor.h +++ b/saga/actor.h @@ -33,6 +33,8 @@ namespace Saga { +class HitZone; + #define ACTOR_DEBUG #define ACTOR_BARRIERS_MAX 16 @@ -191,7 +193,8 @@ struct ActorData { int actionDirection; int actionCycle; int frameNumber; // current actor frame number - uint16 targetObject; + uint16 targetObject; + const HitZone *lastZone; int cycleFrameSequence; uint8 cycleDelay; @@ -263,6 +266,8 @@ struct SpeechData { } }; + + class Actor { public: ActorData *_centerActor; @@ -279,11 +284,12 @@ public: int direct(int msec); int drawActors(); - void updateActorsScene(); // calls from scene loading to update Actors info + void updateActorsScene(int actorsEntrance); // calls from scene loading to update Actors info void drawPathTest(); uint16 testHit(const Point& mousePointer){ return ID_NOTHING;}; //TODO: do it + void takeExit(uint16 actorId, const HitZone *hitZone); const char * getActorName(uint16 actorId); bool actorEndWalk(uint16 actorId, bool recurse); bool actorWalkTo(uint16 actorId, const Location &toLocation); @@ -309,7 +315,8 @@ public: private: bool loadActorResources(ActorData *actor); - + void stepZoneAction(ActorData *actor, const HitZone *hitZone, bool exit, bool stopped); + void createDrawOrderList(); void calcActorScreenPosition(ActorData *actor); bool followProtagonist(ActorData *actor); @@ -376,7 +383,6 @@ private: int _pathNodeListIndex; int _pathNodeListAlloced; PathNode *_pathNodeList; - PathNode *_newPathNodeList; void addPathNodeListPoint(const Point &point) { ++_pathNodeListIndex; if (_pathNodeListIndex >= _pathNodeListAlloced) { @@ -386,6 +392,24 @@ private: } _pathNodeList[_pathNodeListIndex].point = point; } + + int _newPathNodeListIndex; + int _newPathNodeListAlloced; + PathNode *_newPathNodeList; + void incrementNewPathNodeListIndex() { + ++_newPathNodeListIndex; + if (_newPathNodeListIndex >= _newPathNodeListAlloced) { + _newPathNodeListAlloced += 100; + _newPathNodeList = (PathNode*) realloc(_newPathNodeList, _newPathNodeListAlloced * sizeof(*_newPathNodeList)); + + } + } + void addNewPathNodeListPoint(const Point &point, int link) { + incrementNewPathNodeListIndex(); + _newPathNodeList[_newPathNodeListIndex].point = point; + _newPathNodeList[_newPathNodeListIndex].link = link; + } + public: #ifdef ACTOR_DEBUG //path debug - use with care diff --git a/saga/input.cpp b/saga/input.cpp index cfc3d48363..39f952b919 100644 --- a/saga/input.cpp +++ b/saga/input.cpp @@ -88,10 +88,11 @@ int SagaEngine::processInput() { } break; case OSystem::EVENT_LBUTTONDOWN: + case OSystem::EVENT_RBUTTONDOWN: _mousePos.x = event.mouse.x; _mousePos.y = event.mouse.y; imousePt = _mousePos; - _interface->update(imousePt, UPDATE_MOUSECLICK); + _interface->update(imousePt, (event.type == OSystem::EVENT_LBUTTONDOWN) ? UPDATE_LEFTBUTTONCLICK : UPDATE_RIGHTBUTTONCLICK); break; case OSystem::EVENT_MOUSEMOVE: _mousePos.x = event.mouse.x; diff --git a/saga/interface.cpp b/saga/interface.cpp index d64c1a2aa4..8012b2d9f3 100644 --- a/saga/interface.cpp +++ b/saga/interface.cpp @@ -350,7 +350,6 @@ int Interface::draw() { int Interface::update(const Point& mousePoint, int updateFlag) { SURFACE *backBuffer; - if (_vm->_scene->isInDemo() || _panelMode == kPanelFade) return SUCCESS; @@ -359,7 +358,7 @@ int Interface::update(const Point& mousePoint, int updateFlag) { if (_panelMode == kPanelMain) { - if (updateFlag == UPDATE_MOUSEMOVE) { + if (updateFlag & UPDATE_MOUSEMOVE) { if (mousePoint.y < _vm->getSceneHeight()) { //handlePlayfieldUpdate(backBuffer, imousePointer); @@ -373,9 +372,11 @@ int Interface::update(const Point& mousePoint, int updateFlag) { } else { - if (updateFlag == UPDATE_MOUSECLICK) { + if (updateFlag & UPDATE_MOUSECLICK) { if (mousePoint.y < _vm->getSceneHeight()) { - handlePlayfieldClick(backBuffer, mousePoint); + //handlePlayfieldClick(backBuffer, mousePoint); + _vm->_script->playfieldClick(mousePoint, (updateFlag & UPDATE_LEFTBUTTONCLICK) != 0); + } else { handleCommandClick(backBuffer, mousePoint); } diff --git a/saga/interface.h b/saga/interface.h index d9030c3bd7..fa0558e134 100644 --- a/saga/interface.h +++ b/saga/interface.h @@ -31,9 +31,11 @@ namespace Saga { -enum INTERFACE_UPDATE_FLAGS { +enum InterfaceUpdateFlags { UPDATE_MOUSEMOVE = 1, - UPDATE_MOUSECLICK + UPDATE_LEFTBUTTONCLICK = 2, + UPDATE_RIGHTBUTTONCLICK = 4, + UPDATE_MOUSECLICK = UPDATE_LEFTBUTTONCLICK | UPDATE_RIGHTBUTTONCLICK }; #define ITE_INVENTORY_SIZE 24 diff --git a/saga/objectmap.h b/saga/objectmap.h index ffe3cbbf9a..3a856161c4 100644 --- a/saga/objectmap.h +++ b/saga/objectmap.h @@ -45,14 +45,21 @@ public: int getSceneNumber() const { return _nameNumber; } - - int getEntranceNumber() const { + int getActorsEntrance() const { + return _scriptNumber; + } + int getScriptNumber() const { return _scriptNumber; } int getRightButtonVerb() const { return _rightButtonVerb; } - + int getFlags() const { + return _flags; + } + int getDirection() const { + return ((_flags >> 4) & 0xF); + } void draw(SURFACE *ds, int color); bool hitTest(const Point &testPoint); private: diff --git a/saga/saga.h b/saga/saga.h index 02922eb709..bde42bc1d7 100644 --- a/saga/saga.h +++ b/saga/saga.h @@ -122,11 +122,21 @@ enum HitZoneFlags { // in the specified direction, and the actual specified effect of // the zone will be delayed until the actor leaves the zone. kHitZoneAutoWalk = (1 << 2), + + // When set on a hit zone, this causes the character not to walk + // to the object (but they will look at it). + kHitZoneNoWalk = (1 << 2), // zone activates only when character stops walking - kHitZoneTerminus = (1 << 3) + kHitZoneTerminus = (1 << 3), + + // Hit zones only - when the zone is clicked on it projects the + // click point downwards from the middle of the zone until it + // reaches the lowest point in the zone. + kHitZoneProject = (1 << 3) }; + enum PanelButtonType { kPanelButtonVerb = 0, kPanelButtonArrow = 1 diff --git a/saga/scene.cpp b/saga/scene.cpp index c5ff11199b..44598cfeb8 100644 --- a/saga/scene.cpp +++ b/saga/scene.cpp @@ -191,7 +191,7 @@ int Scene::startScene() { scene_qdat = queueIterator.operator->(); assert(scene_qdat != NULL); - loadScene(scene_qdat->scene_n, scene_qdat->load_flag, scene_qdat->scene_proc, scene_qdat->sceneDescription, scene_qdat->fadeType); + loadScene(scene_qdat->scene_n, scene_qdat->load_flag, scene_qdat->scene_proc, scene_qdat->sceneDescription, scene_qdat->fadeType, 0); return SUCCESS; } @@ -230,7 +230,7 @@ int Scene::nextScene() { scene_qdat = queueIterator.operator->(); assert(scene_qdat != NULL); - loadScene(scene_qdat->scene_n, scene_qdat->load_flag, scene_qdat->scene_proc, scene_qdat->sceneDescription, scene_qdat->fadeType); + loadScene(scene_qdat->scene_n, scene_qdat->load_flag, scene_qdat->scene_proc, scene_qdat->sceneDescription, scene_qdat->fadeType, 0); return SUCCESS; } @@ -277,14 +277,14 @@ int Scene::skipScene() { _sceneQueue.erase(_sceneQueue.begin(), queueIterator); endScene(); - loadScene(skip_qdat->scene_n, skip_qdat->load_flag, skip_qdat->scene_proc, skip_qdat->sceneDescription, skip_qdat->fadeType); + loadScene(skip_qdat->scene_n, skip_qdat->load_flag, skip_qdat->scene_proc, skip_qdat->sceneDescription, skip_qdat->fadeType, 0); } // Search for a scene to skip to return SUCCESS; } -int Scene::changeScene(int scene_num) { +int Scene::changeScene(int sceneNumber, int actorsEntrance) { assert(_initialized); if (!_sceneLoaded) { @@ -292,18 +292,18 @@ int Scene::changeScene(int scene_num) { return FAILURE; } - if ((scene_num < 0) || (scene_num > _sceneMax)) { + if ((sceneNumber < 0) || (sceneNumber > _sceneMax)) { warning("Scene::changeScene(): Error: Can't change scene. Invalid scene number"); return FAILURE; } - if (_sceneLUT[scene_num] == 0) { + if (_sceneLUT[sceneNumber] == 0) { warning("Scene::changeScene(): Error: Can't change scene; invalid scene descriptor resource number (0)"); return FAILURE; } endScene(); - loadScene(scene_num, BY_SCENE, SC_defaultScene, NULL, false); + loadScene(sceneNumber, BY_SCENE, SC_defaultScene, NULL, SCENE_NOFADE, actorsEntrance); return SUCCESS; } @@ -504,7 +504,7 @@ int Scene::getSceneLUT(int scene_num) { return _sceneLUT[scene_num]; } -int Scene::loadScene(int scene_num, int load_flag, SCENE_PROC scene_proc, SceneDescription *scene_desc_param, int fadeType) { +int Scene::loadScene(int scene_num, int load_flag, SCENE_PROC scene_proc, SceneDescription *scene_desc_param, int fadeType, int actorsEntrance) { SCENE_INFO scene_info; uint32 res_number = 0; int result; @@ -670,7 +670,7 @@ int Scene::loadScene(int scene_num, int load_flag, SCENE_PROC scene_proc, SceneD _sceneProc(SCENE_BEGIN, &scene_info, this); - _vm->_actor->updateActorsScene(); + _vm->_actor->updateActorsScene(actorsEntrance); if (_desc.flags & kSceneFlagShowCursor) _vm->_interface->activate(); @@ -985,7 +985,7 @@ void Scene::cmdSceneChange(int argc, const char **argv) { clearSceneQueue(); - if (changeScene(scene_num) == SUCCESS) { + if (changeScene(scene_num, 0) == SUCCESS) { _vm->_console->DebugPrintf("Scene changed.\n"); } else { _vm->_console->DebugPrintf("Couldn't change scene!\n"); diff --git a/saga/scene.h b/saga/scene.h index 4f95a1082d..95889c73bc 100644 --- a/saga/scene.h +++ b/saga/scene.h @@ -131,7 +131,7 @@ struct SCENE_ANIMINFO { typedef SortedList<SCENE_ANIMINFO> SceneAnimInfoList; -enum SCENE_FADE_TYPES { +enum SceneTransitionType { SCENE_NOFADE = 0, SCENE_FADE = 1, SCENE_FADE_NO_INTERFACE = 2 @@ -224,7 +224,7 @@ class Scene { void getSlopes(int &beginSlope, int &endSlope); int clearSceneQueue(void); - int changeScene(int scene_num); + int changeScene(int sceneNumber, int actorsEntrance); bool initialized() { return _initialized; } @@ -233,7 +233,7 @@ class Scene { int currentSceneNumber() { return _sceneNumber; } private: - int loadScene(int scene, int load_flag, SCENE_PROC scene_proc, SceneDescription *, int fadeIn); + int loadScene(int scene, int load_flag, SCENE_PROC scene_proc, SceneDescription *, int fadeIn, int actorsEntrance); int loadSceneDescriptor(uint32 res_number); int loadSceneResourceList(uint32 res_number); int processSceneResources(); diff --git a/saga/script.cpp b/saga/script.cpp index 3fa26f5128..f404c3abe3 100644 --- a/saga/script.cpp +++ b/saga/script.cpp @@ -731,7 +731,144 @@ void Script::setPointerVerb() { } } -void Script::whichObject(const Point& mousePointer) { +void Script::hitObject(bool leftButton) { + int verb; + verb = leftButton ? _leftButtonVerb : _rightButtonVerb; + + if (verb > kVerbNone) { + if (_firstObjectSet) { + if (_secondObjectNeeded) { + _pendingObject[0] = _currentObject[0]; + _pendingObject[1] = _currentObject[1]; + _pendingVerb = verb; + + _leftButtonVerb = verb; + if (_pendingVerb > kVerbNone) { + // statusColor = BRIGHT_WHITE; + } + showVerb(); + /*statusColor = GREEN_BA;*/ + + _secondObjectNeeded = false; + _firstObjectSet = false; + return; + } + } else { + if (verb == kVerbGive) { + _secondObjectNeeded = true; + } else { + if (verb == kVerbUse) { + + if (_currentObjectFlags[0] & kObjUseWith) { + _secondObjectNeeded = true; + } + } + } + + if (!_secondObjectNeeded) { + _pendingObject[0] = _currentObject[0]; + _pendingObject[1] = ID_NOTHING; + _pendingVerb = verb; + + _secondObjectNeeded = false; + _firstObjectSet = false; + } else { + _firstObjectSet = true; + } + } + + _leftButtonVerb = verb; + if (_pendingVerb > kVerbNone) { + // statusColor = BRIGHT_WHITE; + } + showVerb(); + //statusColor = GREEN_BA; + } + +} + +void Script::playfieldClick(const Point& mousePoint, bool leftButton) { + Location pickLocation; + const HitZone *hitZone; + + _vm->_actor->abortSpeech(); + + if ((_vm->_actor->_protagonist->currentAction != kActionWait) && + (_vm->_actor->_protagonist->currentAction != kActionFreeze) && + (_vm->_actor->_protagonist->currentAction != kActionWalkToLink) && + (_vm->_actor->_protagonist->currentAction != kActionWalkToPoint)) { + return; + } + if (_pendingVerb > kVerbNone) { + setLeftButtonVerb(kVerbWalkTo); + } + + if (_pointerObject != ID_NOTHING) { + hitObject( leftButton ); + } else { + _pendingObject[0] = ID_NOTHING; + _pendingObject[1] = ID_NOTHING; + _pendingVerb = kVerbWalkTo; + } + + + // tiled stuff + if (_vm->_scene->getFlags() & kSceneFlagISO) { + //todo: it + } else { + pickLocation.fromScreenPoint(mousePoint); + } + + + hitZone = NULL; + + if (objectIdType(_pendingObject[0]) == kGameObjectHitZone) { + // hitZone = _vm->_scene->_objectMap _pendingObject[0]; //TODO: + } else { + if ((_pendingVerb == kVerbUse) && (objectIdType(_pendingObject[1]) == kGameObjectHitZone)) { + // hitZone = _vm->_scene->_objectMap _pendingObject[1]; //TODO: + } + } + + if (hitZone != NULL) { + if (hitZone->getFlags() & kHitZoneNoWalk) { + _vm->_actor->actorFaceTowardsPoint(ID_PROTAG, pickLocation); + doVerb(); + return; + } + + if (hitZone->getFlags() & kHitZoneProject) { + //TODO: do it + } + } + + switch (_pendingVerb) { + case kVerbWalkTo: + case kVerbPickUp: + case kVerbOpen: + case kVerbClose: + case kVerbUse: + _vm->_actor->actorWalkTo(ID_PROTAG, pickLocation); + break; + + case kVerbLookAt: + if (objectIdType(_pendingObject[0]) != kGameObjectActor ) { + _vm->_actor->actorWalkTo(ID_PROTAG, pickLocation); + } else { + doVerb(); + } + break; + + case kVerbTalkTo: + case kVerbGive: + doVerb(); + break; + } + + +} + +void Script::whichObject(const Point& mousePoint) { uint16 objectId; int16 objectFlags; int newRightButtonVerb; @@ -748,7 +885,7 @@ void Script::whichObject(const Point& mousePointer) { if (_vm->_actor->_protagonist->currentAction == kActionWalkDir) { } else { - newObjectId = _vm->_actor->testHit(mousePointer); + newObjectId = _vm->_actor->testHit(mousePoint); if (newObjectId != ID_NOTHING) { if (objectIdType(newObjectId) == kGameObjectObject) { @@ -785,12 +922,12 @@ void Script::whichObject(const Point& mousePointer) { if (_vm->_scene->getFlags() & kSceneFlagISO) { //todo: it } else { - pickLocation.x = mousePointer.x; - pickLocation.y = mousePointer.y; + pickLocation.x = mousePoint.x; + pickLocation.y = mousePoint.y; pickLocation.z = 0; } - hitZoneId = _vm->_scene->_objectMap->hitTest(mousePointer); + hitZoneId = _vm->_scene->_objectMap->hitTest(mousePoint); if ((hitZoneId != -1) && 0) { //TODO: do it //hitZone = _vm->_scene->_objectMap->getZone(hitZoneId); diff --git a/saga/script.h b/saga/script.h index 9236a7e131..3f195f6df7 100644 --- a/saga/script.h +++ b/saga/script.h @@ -255,7 +255,9 @@ public: void setVerb(int verb); int getCurrentVerb() const { return _currentVerb; } void setPointerVerb(); - void whichObject(const Point& mousePointer); + void whichObject(const Point& mousePoint); + void hitObject(bool leftButton); + void playfieldClick(const Point& mousePoint, bool leftButton); void setLeftButtonVerb(int verb); int getLeftButtonVerb() const { return _leftButtonVerb; } @@ -266,6 +268,11 @@ public: _pointerObject = ID_NOTHING; _currentObject[_firstObjectSet ? 1 : 0] = ID_NOTHING; } + void setNoPendingVerb() { + _pendingVerb = kVerbNone; + _currentObject[0] = _currentObject[0] = ID_NOTHING; + setPointerVerb(); + } void scriptInfo(); void scriptExec(int argc, const char **argv); @@ -287,13 +294,14 @@ protected: bool _secondObjectNeeded; uint16 _currentObject[2]; int16 _currentObjectFlags[2]; - uint16 _pendingObject[2]; int _currentVerb; int _stickyVerb; int _leftButtonVerb; int _rightButtonVerb; - int _pendingVerb; +public: + uint16 _pendingObject[2]; + int _pendingVerb; uint16 _pointerObject; public: |