aboutsummaryrefslogtreecommitdiff
path: root/engines
diff options
context:
space:
mode:
authorPaul Gilbert2014-08-18 00:29:01 -0400
committerPaul Gilbert2014-08-18 00:29:01 -0400
commit17315a4dd71d4f9151724166bb5ddd7fdc0074f7 (patch)
tree41fd398f69023782a82dee20bbba13118f6be2b3 /engines
parentd570da065ec422132b4dd409b9b4ecf9cea92fc8 (diff)
downloadscummvm-rg350-17315a4dd71d4f9151724166bb5ddd7fdc0074f7.tar.gz
scummvm-rg350-17315a4dd71d4f9151724166bb5ddd7fdc0074f7.tar.bz2
scummvm-rg350-17315a4dd71d4f9151724166bb5ddd7fdc0074f7.zip
ACCESS: Implemented wall checks for pathfinding
Diffstat (limited to 'engines')
-rw-r--r--engines/access/player.cpp20
-rw-r--r--engines/access/player.h3
-rw-r--r--engines/access/room.cpp135
-rw-r--r--engines/access/room.h12
4 files changed, 154 insertions, 16 deletions
diff --git a/engines/access/player.cpp b/engines/access/player.cpp
index cde1a74de2..0733e80c7d 100644
--- a/engines/access/player.cpp
+++ b/engines/access/player.cpp
@@ -249,7 +249,7 @@ void Player::walkUp() {
_rawYTemp = _rawPlayer.y - _vm->_screen->_scaleTable1[walkOff];
_rawXTemp = _rawPlayer.x;
- if (codeWalls()) {
+ if (_vm->_room->codeWalls()) {
plotCom2();
} else {
_rawPlayer.y = _rawYTemp;
@@ -277,7 +277,7 @@ void Player::walkDown() {
_rawYTemp = _rawPlayer.y - _vm->_screen->_scaleTable1[walkOff];
_rawXTemp = _rawPlayer.x;
- if (codeWalls()) {
+ if (_vm->_room->codeWalls()) {
plotCom2();
} else {
_rawPlayer.y = _rawYTemp;
@@ -316,7 +316,7 @@ void Player::walkLeft() {
}
_rawYTemp = _rawPlayer.y;
- if (codeWalls()) {
+ if (_vm->_room->codeWalls()) {
plotCom2();
} else {
_rawPlayer.x = _rawXTemp;
@@ -355,7 +355,7 @@ void Player::walkRight() {
}
_rawYTemp = _rawPlayer.y;
- if (codeWalls()) {
+ if (_vm->_room->codeWalls()) {
plotCom2();
} else {
_rawPlayer.x = _rawXTemp;
@@ -398,7 +398,7 @@ void Player::walkUpLeft() {
_rawYTempL = _rawPlayerLow.y - _vm->_screen->_scaleTable2[walkOffset];
_rawYTemp = _rawPlayer.y - _vm->_screen->_scaleTable1[walkOffset];
- if (codeWalls()) {
+ if (_vm->_room->codeWalls()) {
plotCom2();
} else {
_rawPlayer.x = _rawXTemp;
@@ -445,7 +445,7 @@ void Player::walkDownLeft() {
_rawYTempL = _rawPlayerLow.y - _vm->_screen->_scaleTable2[walkOffset];
_rawYTemp = _rawPlayer.y - _vm->_screen->_scaleTable1[walkOffset];
- if (codeWalls()) {
+ if (_vm->_room->codeWalls()) {
plotCom2();
} else {
_rawPlayer.x = _rawXTemp;
@@ -492,7 +492,7 @@ void Player::walkUpRight() {
_rawYTempL = _rawPlayerLow.y - _vm->_screen->_scaleTable2[walkOffset];
_rawYTemp = _rawPlayer.y - _vm->_screen->_scaleTable1[walkOffset];
- if (codeWalls()) {
+ if (_vm->_room->codeWalls()) {
plotCom2();
} else {
_rawPlayer.x = _rawXTemp;
@@ -540,7 +540,7 @@ void Player::walkDownRight() {
_rawYTempL = _rawPlayerLow.y - _vm->_screen->_scaleTable2[walkOffset];
_rawYTemp = _rawPlayer.y - _vm->_screen->_scaleTable1[walkOffset];
- if (codeWalls()) {
+ if (_vm->_room->codeWalls()) {
plotCom2();
} else {
_rawPlayer.x = _rawXTemp;
@@ -658,10 +658,6 @@ void Player::plotCom3() {
plotCom2();
}
-bool Player::codeWalls() {
- error("TODO codeWalls");
-}
-
void Player::checkScroll() {
_scrollFlag = false;
if (_playerDirection == NONE)
diff --git a/engines/access/player.h b/engines/access/player.h
index b11cc4a826..876c0e5ea4 100644
--- a/engines/access/player.h
+++ b/engines/access/player.h
@@ -48,7 +48,6 @@ private:
int _diagUpWalkMin, _diagUpWalkMax;
int _diagDownWalkMin, _diagDownWalkMax;
Common::Point _guard;
- bool _collideFlag;
Direction _move;
int _xFlag, _yFlag;
SpriteResource *_playerSprites1;
@@ -56,7 +55,6 @@ private:
int _scrollEnd;
int _inactiveYOff;
- bool codeWalls();
void checkMove();
void plotCom(int v1);
void plotCom1();
@@ -103,6 +101,7 @@ public:
bool _playerOff;
bool _playerMove;
Common::Point _moveTo;
+ bool _collideFlag;
bool _scrollFlag;
int _scrollThreshold;
int _scrollAmount;
diff --git a/engines/access/room.cpp b/engines/access/room.cpp
index 0405e7c4ac..9c2bd01650 100644
--- a/engines/access/room.cpp
+++ b/engines/access/room.cpp
@@ -584,6 +584,141 @@ int Room::validateBox(int boxId) {
return _vm->_scripts->executeScript();
}
+void Room::swapOrg() {
+ SWAP<int>(_vm->_screen->_orgX1, _vm->_screen->_orgX2);
+ SWAP<int>(_vm->_screen->_orgY1, _vm->_screen->_orgY2);
+}
+
+int Room::calcLR(int yp) {
+ const Screen &screen = *_vm->_screen;
+
+ int yv = (yp - screen._orgY1) * (screen._orgX2 - screen._orgX1);
+ int yd = screen._orgY2 - screen._orgY1;
+
+ int rem = (yv % yd) << 1;
+ yv /= yd;
+ if (rem >= yd)
+ ++yv;
+
+ return yv + screen._orgX1;
+}
+
+int Room::calcUD(int xp) {
+ const Screen &screen = *_vm->_screen;
+
+ int xv = (xp - screen._orgX1) * (screen._orgY2 - screen._orgY1);
+ int xd = screen._orgX2 - screen._orgX1;
+
+ int rem = (xv % xd) << 1;
+ xv /= xd;
+ if (rem >= xd)
+ ++xv;
+
+ return xv + screen._orgY1;
+}
+
+bool Room::codeWalls() {
+ Screen &screen = *_vm->_screen;
+ Player &player = *_vm->_player;
+
+ if (_plotter._walls.size() == 0)
+ return false;
+
+ for (uint i = 0; i < _plotter._walls.size(); ++i) {
+ Common::Rect &r = _plotter._walls[i];
+ JetFrame &jf = _jetFrame[i];
+
+ jf._wallCode = 0;
+ jf._wallCode1 = 0;
+ screen._orgX1 = r.left;
+ screen._orgY1 = r.top;
+ screen._orgX2 = r.right;
+ screen._orgY2 = r.bottom;
+
+ if (screen._orgY2 != screen._orgY1) {
+ if (screen._orgY2 < screen._orgY1)
+ swapOrg();
+
+ if ((player._rawYTemp >= screen._orgY1) &&
+ (player._rawYTemp <= screen._orgY2)) {
+ jf._wallCode |= (calcLR(player._rawYTemp) - player._rawXTemp) < 0 ? 2 : 1;
+ jf._wallCode1 |= (calcLR(player._rawYTemp) - player._playerOffset.x) < 0 ? 2 : 1;
+ }
+ }
+
+ if (screen._orgX2 != screen._orgX1) {
+ if (screen._orgX2 < screen._orgX1)
+ swapOrg();
+
+ if ((player._rawXTemp >= screen._orgX1) &&
+ (player._rawXTemp <= screen._orgX2)) {
+ int y = screen._orgY2;
+ if (y == screen._orgY1)
+ y = calcUD(player._rawXTemp);
+
+ jf._wallCode |= (player._rawYTemp - y) < 0 ? 4 : 8;
+ }
+
+ int x = player._rawXTemp + player._playerOffset.x;
+ if ((x >= screen._orgX1) && (x <= screen._orgX2)) {
+ int y = screen._orgY2;
+ if (screen._orgY2 != screen._orgY1)
+ y = calcUD(player._rawXTemp + player._playerOffset.x);
+
+ jf._wallCode1 |= (player._rawYTemp - y) < 0 ? 4 : 8;
+ }
+ }
+ }
+
+ for (uint i = 0; i < _jetFrame.size(); ++i) {
+ JetFrame &jf = _jetFrame[i];
+ if (checkCode(jf._wallCode, jf._wallCodeOld) ||
+ checkCode(jf._wallCode1, jf._wallCode1Old))
+ return true;
+ }
+
+ // Copy the current wall calculations to the old properties
+ for (uint i = 0; i < _jetFrame.size(); ++i) {
+ JetFrame &jf = _jetFrame[i];
+ jf._wallCodeOld = jf._wallCode;
+ jf._wallCode1Old = jf._wallCode1;
+ }
+
+ return false;
+}
+
+bool Room::checkCode(int v1, int v2) {
+ Player &p = *_vm->_player;
+
+ if (!v1) {
+ p._collideFlag = true;
+ return true;
+ } if (!v2 || (v1 == v2)) {
+ } else if (v1 & 1) {
+ if (v2 & 2) {
+ p._collideFlag = true;
+ return true;
+ }
+ } else if (v1 & 2) {
+ if (v2 & 1) {
+ p._collideFlag = true;
+ return true;
+ }
+ } else if (v1 & 4) {
+ if (v2 & 8) {
+ p._collideFlag = true;
+ return true;
+ }
+ } else if (v1 & 8) {
+ if (v2 & 4) {
+ p._collideFlag = true;
+ return true;
+ }
+ }
+
+ return false;
+}
+
/*------------------------------------------------------------------------*/
RoomInfo::RoomInfo(const byte *data) {
diff --git a/engines/access/room.h b/engines/access/room.h
index a90c6e400e..c76bd7021b 100644
--- a/engines/access/room.h
+++ b/engines/access/room.h
@@ -65,6 +65,12 @@ private:
void loadPlayField(int fileNum, int subfile);
void commandOff();
+
+ void swapOrg();
+ int calcLR(int yp);
+ int calcUD(int xp);
+
+ bool checkCode(int v1, int v2);
protected:
void loadRoomData(const byte *roomData);
void setupRoom();
@@ -109,8 +115,6 @@ protected:
virtual void mainAreaClick() = 0;
public:
- void setWallCodes();
-
virtual void setIconPalette() {}
public:
Plotter _plotter;
@@ -142,6 +146,10 @@ public:
void buildRow(int playY, int screenY);
void init4Quads();
+
+ void setWallCodes();
+
+ bool codeWalls();
};
class RoomInfo {