aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--engines/hugo/display.cpp11
-rw-r--r--engines/hugo/display.h2
-rw-r--r--engines/hugo/hugo.cpp29
-rw-r--r--engines/hugo/hugo.h1
-rw-r--r--engines/hugo/mouse.cpp65
-rw-r--r--engines/hugo/mouse.h10
-rw-r--r--engines/hugo/object.cpp13
-rw-r--r--engines/hugo/route.cpp27
-rw-r--r--engines/hugo/route.h6
9 files changed, 91 insertions, 73 deletions
diff --git a/engines/hugo/display.cpp b/engines/hugo/display.cpp
index 37b3e6e97b..a2902e3b9d 100644
--- a/engines/hugo/display.cpp
+++ b/engines/hugo/display.cpp
@@ -40,6 +40,7 @@
#include "hugo/inventory.h"
#include "hugo/util.h"
#include "hugo/object.h"
+#include "hugo/mouse.h"
namespace Hugo {
/**
@@ -658,20 +659,16 @@ bool Screen::isOverlapping(const rect_t *rectA, const rect_t *rectB) const {
}
/**
- * Display exit hotspots in God Mode ('PPG')
+ * Display active boundaries in God Mode ('PPG')
* Light Red = Exit hotspots
* Light Green = Visible objects
* White = Fixed objects, parts of background
*/
-void Screen::drawHotspots() {
+void Screen::drawBoundaries() {
if (!_vm->getGameStatus().godModeFl)
return;
- for (int i = 0; _vm->_hotspots[i].screenIndex >= 0; i++) {
- hotspot_t *hotspot = &_vm->_hotspots[i];
- if (hotspot->screenIndex == _vm->_hero->screenIndex)
- drawRectangle(false, hotspot->x1, hotspot->y1, hotspot->x2, hotspot->y2, _TLIGHTRED);
- }
+ _vm->_mouse->drawHotspots();
for (int i = 0; i < _vm->_object->_numObj; i++) {
object_t *obj = &_vm->_object->_objects[i]; // Get pointer to object
diff --git a/engines/hugo/display.h b/engines/hugo/display.h
index 575d47c37b..21e9fe2e9c 100644
--- a/engines/hugo/display.h
+++ b/engines/hugo/display.h
@@ -61,7 +61,7 @@ public:
void displayFrame(const int sx, const int sy, seq_t *seq, const bool foreFl);
void displayList(dupdate_t update, ...);
void displayRect(const int16 x, const int16 y, const int16 dx, const int16 dy);
- void drawHotspots();
+ void drawBoundaries();
void drawRectangle(const bool filledFl, const int16 x1, const int16 y1, const int16 x2, const int16 y2, const int color);
void drawShape(const int x, const int y, const int color1, const int color2);
void drawStatusText();
diff --git a/engines/hugo/hugo.cpp b/engines/hugo/hugo.cpp
index 97fe82c615..4a8b74fc1c 100644
--- a/engines/hugo/hugo.cpp
+++ b/engines/hugo/hugo.cpp
@@ -54,7 +54,7 @@ maze_t _maze; // Default to not in maze
hugo_boot_t _boot; // Boot info structure file
HugoEngine::HugoEngine(OSystem *syst, const HugoGameDescription *gd) : Engine(syst), _gameDescription(gd),
- _arrayReqs(0), _hotspots(0), _invent(0), _uses(0), _catchallList(0), _backgroundObjects(0), _points(0), _cmdList(0),
+ _arrayReqs(0), _invent(0), _uses(0), _catchallList(0), _backgroundObjects(0), _points(0), _cmdList(0),
_screenActs(0), _hero(0), _heroImage(0), _defltTunes(0), _introX(0), _introY(0), _maxInvent(0), _numBonuses(0),
_numScreens(0), _tunesNbr(0), _soundSilence(0), _soundTest(0), _screenStates(0), _score(0), _maxscore(0),
_backgroundObjectsSize(0), _screenActsSize(0), _usesSize(0), _lastTime(0), _curTime(0)
@@ -90,7 +90,7 @@ HugoEngine::~HugoEngine() {
free(_arrayReqs);
}
- free(_hotspots);
+ _mouse->freeHotspots();
free(_invent);
if (_uses) {
@@ -249,7 +249,7 @@ Common::Error HugoEngine::run() {
_status.doQuitFl = false;
while (!_status.doQuitFl) {
- _screen->drawHotspots();
+ _screen->drawBoundaries();
g_system->updateScreen();
runMachine();
@@ -413,28 +413,7 @@ bool HugoEngine::loadHugoDat() {
// Read _arrayReqs
_arrayReqs = loadLongArray(in);
- // Read _hotspots
- for (int varnt = 0; varnt < _numVariant; varnt++) {
- int numRows = in.readUint16BE();
- hotspot_t *wrkHotspots = (hotspot_t *)malloc(sizeof(hotspot_t) * numRows);
-
- for (int i = 0; i < numRows; i++) {
- wrkHotspots[i].screenIndex = in.readSint16BE();
- wrkHotspots[i].x1 = in.readSint16BE();
- wrkHotspots[i].y1 = in.readSint16BE();
- wrkHotspots[i].x2 = in.readSint16BE();
- wrkHotspots[i].y2 = in.readSint16BE();
- wrkHotspots[i].actIndex = in.readUint16BE();
- wrkHotspots[i].viewx = in.readSint16BE();
- wrkHotspots[i].viewy = in.readSint16BE();
- wrkHotspots[i].direction = in.readSint16BE();
- }
-
- if (varnt == _gameVariant)
- _hotspots = wrkHotspots;
- else
- free(wrkHotspots);
- }
+ _mouse->loadHotspots(in);
int numElem, numSubElem;
//Read _invent
diff --git a/engines/hugo/hugo.h b/engines/hugo/hugo.h
index 720e97e7bd..b73b24eccf 100644
--- a/engines/hugo/hugo.h
+++ b/engines/hugo/hugo.h
@@ -251,7 +251,6 @@ public:
command_t _line; // Line of user text input
config_t _config; // User's config
uint16 **_arrayReqs;
- hotspot_t *_hotspots;
int16 *_invent;
uses_t *_uses;
uint16 _usesSize;
diff --git a/engines/hugo/mouse.cpp b/engines/hugo/mouse.cpp
index 73ba915192..9bbc60f04b 100644
--- a/engines/hugo/mouse.cpp
+++ b/engines/hugo/mouse.cpp
@@ -84,13 +84,12 @@ void MouseHandler::cursorText(const char *buffer, const int16 cx, const int16 cy
* Find the exit hotspot containing cx, cy.
* Return hotspot index or -1 if not found.
*/
-int16 MouseHandler::findExit(const int16 cx, const int16 cy) {
- debugC(2, kDebugMouse, "findExit(%d, %d)", cx, cy);
+int16 MouseHandler::findExit(const int16 cx, const int16 cy, byte screenId) {
+ debugC(2, kDebugMouse, "findExit(%d, %d, %d)", cx, cy, screenId);
- int i = 0;
- for (hotspot_t *hotspot = _vm->_hotspots; hotspot->screenIndex >= 0; i++, hotspot++) {
- if (hotspot->screenIndex == *_vm->_screen_p) {
- if (cx >= hotspot->x1 && cx <= hotspot->x2 && cy >= hotspot->y1 && cy <= hotspot->y2)
+ for (int i = 0; _hotspots[i].screenIndex >= 0; i++) {
+ if (_hotspots[i].screenIndex == screenId) {
+ if (cx >= _hotspots[i].x1 && cx <= _hotspots[i].x2 && cy >= _hotspots[i].y1 && cy <= _hotspots[i].y2)
return i;
}
}
@@ -174,20 +173,20 @@ void MouseHandler::processLeftClick(const int16 objId, const int16 cx, const int
_vm->_screen->displayList(kDisplayAdd, 0, kDibOffY, kXPix, kInvDy);
break;
case kExitHotspot: // Walk to exit hotspot
- i = findExit(cx, cy);
- x = _vm->_hotspots[i].viewx;
- y = _vm->_hotspots[i].viewy;
+ i = findExit(cx, cy, *_vm->_screen_p);
+ x = _hotspots[i].viewx;
+ y = _hotspots[i].viewy;
if (x >= 0) { // Hotspot refers to an exit
// Special case of immediate exit
if (_jumpExitFl) {
// Get rid of iconbar if necessary
if (_vm->_inventory->getInventoryState() != kInventoryOff)
_vm->_inventory->setInventoryState(kInventoryUp);
- _vm->_scheduler->insertActionList(_vm->_hotspots[i].actIndex);
+ _vm->_scheduler->insertActionList(_hotspots[i].actIndex);
} else { // Set up route to exit spot
- if (_vm->_hotspots[i].direction == Common::KEYCODE_RIGHT)
+ if (_hotspots[i].direction == Common::KEYCODE_RIGHT)
x -= kHeroMaxWidth;
- else if (_vm->_hotspots[i].direction == Common::KEYCODE_LEFT)
+ else if (_hotspots[i].direction == Common::KEYCODE_LEFT)
x += kHeroMaxWidth;
if (!_vm->_route->startRoute(kRouteExit, i, x, y))
Utils::Box(kBoxAny, "%s", _vm->_text->getTextMouse(kMsNoWayText)); // Can't get there
@@ -278,8 +277,8 @@ void MouseHandler::mouseHandler() {
// Process cursor over an exit hotspot
if (objId == -1) {
- int i = findExit(cx, cy);
- if (i != -1 && _vm->_hotspots[i].viewx >= 0) {
+ int i = findExit(cx, cy, *_vm->_screen_p);
+ if (i != -1 && _hotspots[i].viewx >= 0) {
objId = kExitHotspot;
cursorText(_vm->_text->getTextMouse(kMsExit), cx, cy, U_FONT8, _TBRIGHTWHITE);
}
@@ -294,4 +293,42 @@ void MouseHandler::mouseHandler() {
resetRightButton();
}
+/**
+ * Load hotspots data from hugo.dat
+ */
+void MouseHandler::loadHotspots(Common::ReadStream &in) {
+ // Read _hotspots
+ for (int varnt = 0; varnt < _vm->_numVariant; varnt++) {
+ int numRows = in.readUint16BE();
+ hotspot_t *wrkHotspots = (hotspot_t *)malloc(sizeof(hotspot_t) * numRows);
+
+ for (int i = 0; i < numRows; i++) {
+ wrkHotspots[i].screenIndex = in.readSint16BE();
+ wrkHotspots[i].x1 = in.readSint16BE();
+ wrkHotspots[i].y1 = in.readSint16BE();
+ wrkHotspots[i].x2 = in.readSint16BE();
+ wrkHotspots[i].y2 = in.readSint16BE();
+ wrkHotspots[i].actIndex = in.readUint16BE();
+ wrkHotspots[i].viewx = in.readSint16BE();
+ wrkHotspots[i].viewy = in.readSint16BE();
+ wrkHotspots[i].direction = in.readSint16BE();
+ }
+
+ if (varnt == _vm->_gameVariant)
+ _hotspots = wrkHotspots;
+ else
+ free(wrkHotspots);
+ }
+}
+
+/**
+ * Display hotspot boundaries for the current screen
+ */
+void MouseHandler::drawHotspots() const {
+ for (int i = 0; _hotspots[i].screenIndex >= 0; i++) {
+ hotspot_t *hotspot = &_hotspots[i];
+ if (hotspot->screenIndex == _vm->_hero->screenIndex)
+ _vm->_screen->drawRectangle(false, hotspot->x1, hotspot->y1, hotspot->x2, hotspot->y2, _TLIGHTRED);
+ }
+}
} // End of namespace Hugo
diff --git a/engines/hugo/mouse.h b/engines/hugo/mouse.h
index a335233ab7..eae13b48fb 100644
--- a/engines/hugo/mouse.h
+++ b/engines/hugo/mouse.h
@@ -46,11 +46,19 @@ public:
void setJumpExitFl(bool fl) { _jumpExitFl = fl; }
void setMouseX(int x) { _mouseX = x; }
void setMouseY(int y) { _mouseY = y; }
+ void freeHotspots() { free(_hotspots); }
bool getJumpExitFl() const { return _jumpExitFl; }
int getMouseX() const { return _mouseX; }
int getMouseY() const { return _mouseY; }
+ int16 getDirection(const int16 hotspotId) const { return _hotspots[hotspotId].direction; }
+ int16 getHotspotActIndex(const int16 hotspotId) const { return _hotspots[hotspotId].actIndex; }
+
+ void drawHotspots() const;
+ int16 findExit(const int16 cx, const int16 cy, byte screenId);
+ void loadHotspots(Common::ReadStream &in);
+
private:
HugoEngine *_vm;
@@ -65,6 +73,7 @@ private:
kMsExit = 1
};
+ hotspot_t *_hotspots;
bool _leftButtonFl; // Left mouse button pressed
bool _rightButtonFl; // Right button pressed
int _mouseX;
@@ -72,7 +81,6 @@ private:
bool _jumpExitFl; // Allowed to jump to a screen exit
void cursorText(const char *buffer, const int16 cx, const int16 cy, const uif_t fontId, const int16 color);
- int16 findExit(const int16 cx, const int16 cy);
void processRightClick(const int16 objId, const int16 cx, const int16 cy);
void processLeftClick(const int16 objId, const int16 cx, const int16 cy);
};
diff --git a/engines/hugo/object.cpp b/engines/hugo/object.cpp
index 1fa5293992..b909df45bb 100644
--- a/engines/hugo/object.cpp
+++ b/engines/hugo/object.cpp
@@ -44,6 +44,7 @@
#include "hugo/schedule.h"
#include "hugo/text.h"
#include "hugo/inventory.h"
+#include "hugo/mouse.h"
namespace Hugo {
@@ -746,14 +747,10 @@ void ObjectHandler::boundaryCollision(object_t *obj) {
x = obj->x + obj->currImagePtr->x1;
int y = obj->y + obj->currImagePtr->y2;
- for (int i = 0; _vm->_hotspots[i].screenIndex >= 0; i++) {
- hotspot_t *hotspot = &_vm->_hotspots[i];
- if (hotspot->screenIndex == obj->screenIndex)
- if ((x >= hotspot->x1) && (x <= hotspot->x2) && (y >= hotspot->y1) && (y <= hotspot->y2)) {
- _vm->_scheduler->insertActionList(hotspot->actIndex);
- break;
- }
- }
+ int16 index = _vm->_mouse->findExit(x, y, obj->screenIndex);
+ if (index >= 0)
+ _vm->_scheduler->insertActionList(_vm->_mouse->getHotspotActIndex(index));
+
} else {
// Check whether an object collided with HERO
int dx = _vm->_hero->x + _vm->_hero->currImagePtr->x1 - obj->x - obj->currImagePtr->x1;
diff --git a/engines/hugo/route.cpp b/engines/hugo/route.cpp
index fd7bb84a9d..c122439c70 100644
--- a/engines/hugo/route.cpp
+++ b/engines/hugo/route.cpp
@@ -39,13 +39,14 @@
#include "hugo/route.h"
#include "hugo/object.h"
#include "hugo/inventory.h"
+#include "hugo/mouse.h"
namespace Hugo {
Route::Route(HugoEngine *vm) : _vm(vm) {
_oldWalkDirection = 0;
_routeIndex = -1; // Hero not following a route
- _go_for = kRouteSpace; // Hero walking to space
- _go_id = -1; // Hero not walking to anything
+ _routeType = kRouteSpace; // Hero walking to space
+ _routeObjId = -1; // Hero not walking to anything
}
/**
@@ -442,26 +443,26 @@ void Route::processRoute() {
// Arrived at final node?
if (--_routeIndex < 0) {
// See why we walked here
- switch (_go_for) {
+ switch (_routeType) {
case kRouteExit: // Walked to an exit, proceed into it
- setWalk(_vm->_hotspots[_go_id].direction);
+ setWalk(_vm->_mouse->getDirection(_routeObjId));
break;
case kRouteLook: // Look at an object
if (turnedFl) {
- _vm->_object->lookObject(&_vm->_object->_objects[_go_id]);
+ _vm->_object->lookObject(&_vm->_object->_objects[_routeObjId]);
turnedFl = false;
} else {
- setDirection(_vm->_object->_objects[_go_id].direction);
+ setDirection(_vm->_object->_objects[_routeObjId].direction);
_routeIndex++; // Come round again
turnedFl = true;
}
break;
case kRouteGet: // Get (or use) an object
if (turnedFl) {
- _vm->_object->useObject(_go_id);
+ _vm->_object->useObject(_routeObjId);
turnedFl = false;
} else {
- setDirection(_vm->_object->_objects[_go_id].direction);
+ setDirection(_vm->_object->_objects[_routeObjId].direction);
_routeIndex++; // Come round again
turnedFl = true;
}
@@ -493,8 +494,8 @@ void Route::processRoute() {
* go_for is the purpose, id indexes the exit or object to walk to
* Returns FALSE if route not found
*/
-bool Route::startRoute(const go_t go_for, const int16 id, int16 cx, int16 cy) {
- debugC(1, kDebugRoute, "startRoute(%d, %d, %d, %d)", go_for, id, cx, cy);
+bool Route::startRoute(const go_t routeType, const int16 objId, int16 cx, int16 cy) {
+ debugC(1, kDebugRoute, "startRoute(%d, %d, %d, %d)", routeType, objId, cx, cy);
// Don't attempt to walk if user does not have control
if (_vm->_hero->pathType != kPathUser)
@@ -504,11 +505,11 @@ bool Route::startRoute(const go_t go_for, const int16 id, int16 cx, int16 cy) {
if (_vm->_inventory->getInventoryState() != kInventoryOff)
_vm->_inventory->setInventoryState(kInventoryUp);
- _go_for = go_for; // Purpose of trip
- _go_id = id; // Index of exit/object
+ _routeType = routeType; // Purpose of trip
+ _routeObjId = objId; // Index of exit/object
// Adjust destination to center hero if walking to cursor
- if (_go_for == kRouteSpace)
+ if (_routeType == kRouteSpace)
cx -= kHeroMinWidth / 2;
bool foundFl = false; // TRUE if route found ok
diff --git a/engines/hugo/route.h b/engines/hugo/route.h
index 5b1eb9bff4..727c7d77eb 100644
--- a/engines/hugo/route.h
+++ b/engines/hugo/route.h
@@ -58,7 +58,7 @@ public:
int16 getRouteIndex() const {return _routeIndex; }
void processRoute();
- bool startRoute(const go_t go_for, const int16 id, int16 cx, int16 cy);
+ bool startRoute(const go_t routeType, const int16 objId, int16 cx, int16 cy);
void setDirection(const uint16 keyCode);
void setWalk(const uint16 direction);
@@ -73,8 +73,8 @@ private:
uint16 _oldWalkDirection; // Last direction char
int16 _routeIndex; // Index into route list, or -1
- go_t _go_for; // Purpose of an automatic route
- int16 _go_id; // Index of exit of object walking to
+ go_t _routeType; // Purpose of an automatic route
+ int16 _routeObjId; // Index of exit of object walking to
byte _boundaryMap[kYPix][kXPix]; // Boundary byte map
segment_t _segment[kMaxSeg]; // List of points in fill-path