aboutsummaryrefslogtreecommitdiff
path: root/engines/gob
diff options
context:
space:
mode:
Diffstat (limited to 'engines/gob')
-rw-r--r--engines/gob/draw.cpp18
-rw-r--r--engines/gob/draw.h4
-rw-r--r--engines/gob/draw_v2.cpp8
-rw-r--r--engines/gob/game_v2.cpp89
-rw-r--r--engines/gob/init_v2.cpp7
-rw-r--r--engines/gob/inter.cpp54
-rw-r--r--engines/gob/inter.h4
-rw-r--r--engines/gob/inter_bargon.cpp6
-rw-r--r--engines/gob/inter_v1.cpp179
-rw-r--r--engines/gob/inter_v2.cpp160
-rw-r--r--engines/gob/mult_v2.cpp6
-rw-r--r--engines/gob/util.cpp5
-rw-r--r--engines/gob/util.h2
-rw-r--r--engines/gob/video.cpp6
-rw-r--r--engines/gob/video.h4
-rw-r--r--engines/gob/video_v2.cpp9
16 files changed, 325 insertions, 236 deletions
diff --git a/engines/gob/draw.cpp b/engines/gob/draw.cpp
index b4dd65ef6f..d1d19d0179 100644
--- a/engines/gob/draw.cpp
+++ b/engines/gob/draw.cpp
@@ -129,10 +129,11 @@ Draw::Draw(GobEngine *vm) : _vm(vm) {
_cursorTimeKey = 0;
- warning("GOB2 Stub! _word_2E8E2, _word_2FC9C, _word_2FC9E, _word_2E51F, _off_2E51B, _off_2E517");
+ _scrollOffsetX = 0;
+ _scrollOffsetY = 0;
+
+ warning("GOB2 Stub! _word_2E8E2, _word_2E51F, _off_2E51B, _off_2E517");
_word_2E8E2 = 2;
- _word_2FC9C = 0;
- _word_2FC9E = 0;
_word_2E51F = 0;
_off_2E51B = 0;
_off_2E517 = 0;
@@ -157,7 +158,8 @@ void Draw::invalidateRect(int16 left, int16 top, int16 right, int16 bottom) {
bottom = temp;
}
- if (left > (_vm->_video->_surfWidth - 1) || right < 0 || top > 199 || bottom < 0)
+ if ((left > (_vm->_video->_surfWidth - 1)) || (right < 0) ||
+ (top > (_vm->_video->_surfHeight - 1)) || (bottom < 0))
return;
_noInvalidated = 0;
@@ -166,7 +168,7 @@ void Draw::invalidateRect(int16 left, int16 top, int16 right, int16 bottom) {
_invalidatedLefts[0] = 0;
_invalidatedTops[0] = 0;
_invalidatedRights[0] = _vm->_video->_surfWidth - 1;
- _invalidatedBottoms[0] = 199;
+ _invalidatedBottoms[0] = _vm->_video->_surfHeight - 1;
_invalidatedCount = 1;
return;
}
@@ -180,8 +182,8 @@ void Draw::invalidateRect(int16 left, int16 top, int16 right, int16 bottom) {
if (top < 0)
top = 0;
- if (bottom > 199)
- bottom = 199;
+ if (bottom > (_vm->_video->_surfHeight - 1))
+ bottom = _vm->_video->_surfHeight - 1;
left &= 0xfff0;
right |= 0x000f;
@@ -266,7 +268,7 @@ void Draw::blitInvalidated(void) {
clearPalette();
_vm->_video->drawSprite(_backSurface, _frontSurface, 0, 0,
- _vm->_video->_surfWidth - 1, 199, 0, 0, 0);
+ _vm->_video->_surfWidth - 1, _vm->_video->_surfHeight - 1, 0, 0, 0);
setPalette();
_invalidatedCount = 0;
_noInvalidated = 1;
diff --git a/engines/gob/draw.h b/engines/gob/draw.h
index 07a53bc073..8859b93088 100644
--- a/engines/gob/draw.h
+++ b/engines/gob/draw.h
@@ -114,8 +114,8 @@ public:
int16 _palLoadData2[4];
int16 _word_2E8E2;
- int16 _word_2FC9C;
- int16 _word_2FC9E;
+ int16 _scrollOffsetY;
+ int16 _scrollOffsetX;
int16 _word_2E51F;
Video::SurfaceDesc *_off_2E51B;
Video::SurfaceDesc *_off_2E517;
diff --git a/engines/gob/draw_v2.cpp b/engines/gob/draw_v2.cpp
index 86998c1436..77e95921b7 100644
--- a/engines/gob/draw_v2.cpp
+++ b/engines/gob/draw_v2.cpp
@@ -957,8 +957,8 @@ void Draw_v2::animateCursor(int16 cursor) {
}
void Draw_v2::initScreen(void) {
- _word_2FC9C = 0;
- _word_2FC9E = 0;
+ _scrollOffsetX = 0;
+ _scrollOffsetY = 0;
if (_word_2E51F != 0) {
_off_2E51B = new Video::SurfaceDesc;
@@ -974,7 +974,7 @@ void Draw_v2::initScreen(void) {
_off_2E517->vidPtr = _frontSurface->vidPtr +
((_frontSurface->width * _frontSurface->height ) / 4);
}
- initBigSprite(21, _vm->_video->_surfWidth, 200, 0);
+ initBigSprite(21, _vm->_video->_surfWidth, _vm->_video->_surfHeight, 0);
_backSurface = _spritesArray[21];
_vm->_video->clearSurf(_backSurface);
@@ -1002,7 +1002,7 @@ void Draw_v2::closeScreen(void) {
if (_off_2E51B != 0) {
memcpy(_frontSurface, _off_2E51B, sizeof(Video::SurfaceDesc));
_frontSurface->width = _vm->_video->_surfWidth;
- _frontSurface->height = 200;
+ _frontSurface->height = _vm->_video->_surfHeight;
delete _off_2E51B;
delete _off_2E517;
_off_2E51B = 0;
diff --git a/engines/gob/game_v2.cpp b/engines/gob/game_v2.cpp
index 1b6cd1f123..c85482fb6c 100644
--- a/engines/gob/game_v2.cpp
+++ b/engines/gob/game_v2.cpp
@@ -452,15 +452,15 @@ int16 Game_v2::checkCollisions(char handleMouse, int16 deltaTime, int16 *pResId,
&_mouseButtons, handleMouse);
// TODO: What of this is needed?
- // Scrolling?
+ // Mouse position calculation in scrollable screen?
int16 width;
int16 height;
int16 sWidth;
int16 sHeight;
int16 cursorRight;
int16 cursorBottom;
- int16 oldWord_2FC9C;
- int16 oldWord_2FC9E;
+ int16 oldOffY;
+ int16 oldOffX;
if ((_vm->_global->_videoMode == 0x14) && (handleMouse != 0)) {
width = _vm->_draw->_frontSurface->width;
height = _vm->_draw->_frontSurface->height;
@@ -470,64 +470,65 @@ int16 Game_v2::checkCollisions(char handleMouse, int16 deltaTime, int16 *pResId,
sHeight = _vm->_global->_primaryHeight;
if (_vm->_draw->_off_2E51B != 0)
sHeight -= _vm->_draw->_off_2E51B->height;
- oldWord_2FC9E = _vm->_draw->_word_2FC9E;
- oldWord_2FC9C = _vm->_draw->_word_2FC9C;
- if ((width > sWidth) && (_vm->_global->_inter_mouseX >= _vm->_draw->_word_2FC9E)) {
+ oldOffX = _vm->_draw->_scrollOffsetX;
+ oldOffY = _vm->_draw->_scrollOffsetY;
+ if ((width > sWidth) && (_vm->_global->_inter_mouseX >= _vm->_draw->_scrollOffsetX)) {
cursorRight = _vm->_global->_inter_mouseX + _vm->_draw->_cursorWidth;
- if (cursorRight > (_vm->_draw->_word_2FC9E + sWidth))
- _vm->_draw->_word_2FC9E = MIN(cursorRight - sWidth, width - sWidth);
- } else if (_vm->_global->_inter_mouseX < _vm->_draw->_word_2FC9E)
- _vm->_draw->_word_2FC9E = _vm->_global->_inter_mouseX;
+ if (cursorRight > (_vm->_draw->_scrollOffsetX + sWidth))
+ _vm->_draw->_scrollOffsetX = MIN(cursorRight - sWidth, width - sWidth);
+ } else if (_vm->_global->_inter_mouseX < _vm->_draw->_scrollOffsetX)
+ _vm->_draw->_scrollOffsetX = _vm->_global->_inter_mouseX;
height = _vm->_draw->_frontSurface->height;
- if ((height > sHeight) && (_vm->_global->_inter_mouseY >= _vm->_draw->_word_2FC9C)) {
+ if ((height > sHeight) && (_vm->_global->_inter_mouseY >= _vm->_draw->_scrollOffsetY)) {
cursorBottom = _vm->_global->_inter_mouseY + _vm->_draw->_cursorHeight;
- if (cursorBottom > (_vm->_draw->_word_2FC9C + sHeight))
- _vm->_draw->_word_2FC9C = MIN(cursorBottom - sHeight, height - sHeight);
- } else if (_vm->_global->_inter_mouseY < _vm->_draw->_word_2FC9C)
- _vm->_draw->_word_2FC9C = _vm->_global->_inter_mouseY;
- if ((oldWord_2FC9E != _vm->_draw->_word_2FC9E) ||
- (oldWord_2FC9C != _vm->_draw->_word_2FC9C)) {
+ if (cursorBottom > (_vm->_draw->_scrollOffsetY + sHeight))
+ _vm->_draw->_scrollOffsetY = MIN(cursorBottom - sHeight, height - sHeight);
+ } else if (_vm->_global->_inter_mouseY < _vm->_draw->_scrollOffsetY)
+ _vm->_draw->_scrollOffsetY = _vm->_global->_inter_mouseY;
+ if ((oldOffX != _vm->_draw->_scrollOffsetX) ||
+ (oldOffY != _vm->_draw->_scrollOffsetY)) {
if (_byte_2FC9B == 0) {
- _vm->_draw->_word_2FC9E = oldWord_2FC9E;
- _vm->_draw->_word_2FC9C = oldWord_2FC9C;
+ _vm->_draw->_scrollOffsetX = oldOffX;
+ _vm->_draw->_scrollOffsetY = oldOffY;
if ((_vm->_draw->_frontSurface->width > sWidth) &&
- (_vm->_global->_inter_mouseX >= oldWord_2FC9E)) {
+ (_vm->_global->_inter_mouseX >= oldOffX)) {
if ((_vm->_global->_inter_mouseX + _vm->_draw->_cursorWidth) >
- (_vm->_draw->_word_2FC9E + sWidth))
- _vm->_global->_inter_mouseX = _vm->_draw->_word_2FC9E +
+ (_vm->_draw->_scrollOffsetX + sWidth))
+ _vm->_global->_inter_mouseX = _vm->_draw->_scrollOffsetX +
sWidth - _vm->_draw->_cursorWidth;
- } else if (_vm->_global->_inter_mouseX < oldWord_2FC9E)
- _vm->_global->_inter_mouseX = oldWord_2FC9E;
+ } else if (_vm->_global->_inter_mouseX < oldOffX)
+ _vm->_global->_inter_mouseX = oldOffX;
if ((_vm->_draw->_frontSurface->height > sHeight) &&
- (_vm->_global->_inter_mouseY >= _vm->_draw->_word_2FC9C)) {
+ (_vm->_global->_inter_mouseY >= _vm->_draw->_scrollOffsetY)) {
if ((_vm->_global->_inter_mouseY + _vm->_draw->_cursorHeight) >
- (_vm->_draw->_word_2FC9C + sHeight))
- _vm->_global->_inter_mouseY = _vm->_draw->_word_2FC9C +
+ (_vm->_draw->_scrollOffsetY + sHeight))
+ _vm->_global->_inter_mouseY = _vm->_draw->_scrollOffsetY +
sHeight - _vm->_draw->_cursorHeight;
- } else if (_vm->_global->_inter_mouseY < oldWord_2FC9E)
- _vm->_global->_inter_mouseY = _vm->_draw->_word_2FC9C;
+ } else if (_vm->_global->_inter_mouseY < oldOffX)
+ _vm->_global->_inter_mouseY = _vm->_draw->_scrollOffsetY;
} else {
- if (oldWord_2FC9E > _vm->_draw->_word_2FC9E) {
- _vm->_global->_inter_mouseX += (oldWord_2FC9E - _vm->_draw->_word_2FC9E) / 2;
- _vm->_draw->_word_2FC9E += (oldWord_2FC9E - _vm->_draw->_word_2FC9E) / 2;
+ if (oldOffX > _vm->_draw->_scrollOffsetX) {
+ _vm->_global->_inter_mouseX += (oldOffX - _vm->_draw->_scrollOffsetX) / 2;
+ _vm->_draw->_scrollOffsetX += (oldOffX - _vm->_draw->_scrollOffsetX) / 2;
} else {
- _vm->_global->_inter_mouseX -= (_vm->_draw->_word_2FC9E - oldWord_2FC9E) / 2;
- _vm->_draw->_word_2FC9E -= (_vm->_draw->_word_2FC9E - oldWord_2FC9E) / 2;
+ _vm->_global->_inter_mouseX -= (_vm->_draw->_scrollOffsetX - oldOffX) / 2;
+ _vm->_draw->_scrollOffsetX -= (_vm->_draw->_scrollOffsetX - oldOffX) / 2;
}
- if (oldWord_2FC9C > _vm->_draw->_word_2FC9C) {
- _vm->_global->_inter_mouseY += (oldWord_2FC9C - _vm->_draw->_word_2FC9C) / 2;
- _vm->_draw->_word_2FC9C += (oldWord_2FC9C - _vm->_draw->_word_2FC9C) / 2;
- if (_vm->_draw->_word_2FC9C < 2)
- _vm->_draw->_word_2FC9C = 0;
+ if (oldOffY > _vm->_draw->_scrollOffsetY) {
+ _vm->_global->_inter_mouseY += (oldOffY - _vm->_draw->_scrollOffsetY) / 2;
+ _vm->_draw->_scrollOffsetY += (oldOffY - _vm->_draw->_scrollOffsetY) / 2;
+ if (_vm->_draw->_scrollOffsetY < 2)
+ _vm->_draw->_scrollOffsetY = 0;
} else {
- _vm->_global->_inter_mouseY -= (_vm->_draw->_word_2FC9C - oldWord_2FC9C) / 2;
- _vm->_draw->_word_2FC9C -= (_vm->_draw->_word_2FC9C - oldWord_2FC9C) / 2;
+ _vm->_global->_inter_mouseY -= (_vm->_draw->_scrollOffsetY - oldOffY) / 2;
+ _vm->_draw->_scrollOffsetY -= (_vm->_draw->_scrollOffsetY - oldOffY) / 2;
}
if (_vm->_draw->_off_2E51B == 0)
- warning("_vid_setPixelShift(_vm->_draw->_word_2FC9E, _vm->_draw->_word_2FC9C);");
+ _vm->_util->setScrollOffset();
else
- warning("_vid_setPixelShift(_vm->_draw->_word_2FC9E, _vm->_draw->_word_2FC9C + _vm->_draw->_off_2E51B->height);");
+ _vm->_util->setScrollOffset(_vm->_draw->_scrollOffsetX,
+ _vm->_draw->_scrollOffsetY + _vm->_draw->_off_2E51B->height);;
}
_vm->_util->setMousePos(_vm->_global->_inter_mouseX, _vm->_global->_inter_mouseY);
}
@@ -646,7 +647,7 @@ void Game_v2::prepareStart(void) {
_vm->_draw->initScreen();
_vm->_video->fillRect(_vm->_draw->_frontSurface, 0, 0,
- _vm->_video->_surfWidth - 1, 199, 1);
+ _vm->_video->_surfWidth - 1, _vm->_video->_surfHeight - 1, 1);
_vm->_util->setMousePos(152, 92);
diff --git a/engines/gob/init_v2.cpp b/engines/gob/init_v2.cpp
index 129f75ebd5..e8ab0283da 100644
--- a/engines/gob/init_v2.cpp
+++ b/engines/gob/init_v2.cpp
@@ -43,7 +43,8 @@ void Init_v2::soundVideo(int32 smallHeap, int16 flag) {
_vm->_global->_videoMode);
_vm->_draw->_frontSurface = &_vm->_global->_primarySurfDesc;
- _vm->_video->initSurfDesc(_vm->_global->_videoMode, _vm->_video->_surfWidth, 200, 0x80);
+ _vm->_video->initSurfDesc(_vm->_global->_videoMode, _vm->_video->_surfWidth,
+ _vm->_video->_surfHeight, 0x80);
_vm->_global->_mousePresent = 1;
@@ -61,8 +62,8 @@ void Init_v2::soundVideo(int32 smallHeap, int16 flag) {
_vm->_global->_pPaletteDesc->unused2 = _vm->_global->_unusedPalette2;
if (_vm->_global->_videoMode != 0)
- _vm->_video->initSurfDesc(_vm->_global->_videoMode, _vm->_video->_surfWidth, 200,
- PRIMARY_SURFACE);
+ _vm->_video->initSurfDesc(_vm->_global->_videoMode, _vm->_video->_surfWidth,
+ _vm->_video->_surfHeight, PRIMARY_SURFACE);
}
} // End of namespace Gob
diff --git a/engines/gob/inter.cpp b/engines/gob/inter.cpp
index ef9a34e23c..7515be82a9 100644
--- a/engines/gob/inter.cpp
+++ b/engines/gob/inter.cpp
@@ -190,60 +190,6 @@ void Inter::funcBlock(int16 retFlag) {
return;
}
-void Inter::checkSwitchTable(char **ppExec) {
- int16 i;
- int16 len;
- char found;
- int32 value;
- char notFound;
- char defFlag;
-
- found = 0;
- notFound = 1;
- *ppExec = 0;
- value = _vm->_parse->parseVarIndex();
- value = VAR_OFFSET(value);
-
- do {
- len = *(int8*)_vm->_global->_inter_execPtr++; // must be a signed char typ and char is not default signed on all platforms.
-
- if (len == -5)
- break;
-
- for (i = 0; i < len; i++) {
- evalExpr(0);
-
- if (_terminate)
- return;
-
- if (_vm->_global->_inter_resVal == value) {
- found = 1;
- notFound = 0;
- }
- }
-
- if (found != 0)
- *ppExec = _vm->_global->_inter_execPtr;
-
- _vm->_global->_inter_execPtr += READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
- found = 0;
- } while (len != -5);
-
- if (len != -5)
- _vm->_global->_inter_execPtr++;
-
- defFlag = *_vm->_global->_inter_execPtr;
- defFlag >>= 4;
- if (defFlag != 4)
- return;
- _vm->_global->_inter_execPtr++;
-
- if (notFound)
- *ppExec = _vm->_global->_inter_execPtr;
-
- _vm->_global->_inter_execPtr += READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
-}
-
void Inter::callSub(int16 retFlag) {
int16 block;
while (!_vm->_quitRequested && _vm->_global->_inter_execPtr != 0 && (char *)_vm->_global->_inter_execPtr != _vm->_game->_totFileData) {
diff --git a/engines/gob/inter.h b/engines/gob/inter.h
index ef75815e69..a6d25f53ad 100644
--- a/engines/gob/inter.h
+++ b/engines/gob/inter.h
@@ -58,11 +58,11 @@ public:
char evalExpr(int16 *pRes);
char evalBoolResult(void);
void funcBlock(int16 retFlag);
- void checkSwitchTable(char **ppExec);
void callSub(int16 retFlag);
void initControlVars(char full);
void renewTimeInVars(void);
void manipulateMap(int16 xPos, int16 yPos, int16 item);
+ virtual void checkSwitchTable(char **ppExec) = 0;
virtual int16 loadSound(int16 slot) = 0;
virtual void storeKey(int16 key) = 0;
virtual void storeMouse(void) = 0;
@@ -95,6 +95,7 @@ class Inter_v1 : public Inter {
public:
Inter_v1(GobEngine *vm);
virtual ~Inter_v1() {};
+ virtual void checkSwitchTable(char **ppExec);
virtual int16 loadSound(int16 slot);
virtual void storeKey(int16 key);
virtual void storeMouse(void);
@@ -288,6 +289,7 @@ class Inter_v2 : public Inter_v1 {
public:
Inter_v2(GobEngine *vm);
virtual ~Inter_v2() {};
+ virtual void checkSwitchTable(char **ppExec);
virtual int16 loadSound(int16 search);
virtual void storeKey(int16 key);
virtual void storeMouse(void);
diff --git a/engines/gob/inter_bargon.cpp b/engines/gob/inter_bargon.cpp
index e9f73d893e..1e3ab00e76 100644
--- a/engines/gob/inter_bargon.cpp
+++ b/engines/gob/inter_bargon.cpp
@@ -743,11 +743,11 @@ void Inter_Bargon::oBargon_intro2(int16 &extraData, int32 *retVarPtr,
_vm->_video->drawSprite(surface, _vm->_draw->_frontSurface, 0, 0, 319, 199, 0, 0, 0);
_vm->_video->drawPackedSprite("2ille4.ims", surface);
_vm->_video->drawSprite(surface, _vm->_draw->_frontSurface, 0, 0, 319, 199, 320, 0, 0);
- _vm->_util->setScrollOffset(320);
+ _vm->_util->setScrollOffset(320, 0);
_vm->_palanim->fade(_vm->_global->_pPaletteDesc, -2, 0);
_vm->_util->longDelay(1000);
for (i = 320; i >= 0; i--) {
- _vm->_util->setScrollOffset(i);
+ _vm->_util->setScrollOffset(i, 0);
if ((_vm->_game->checkKeys(&mouseX, &mouseY, &buttons, 0) == 0x11B) ||
_vm->_quitRequested) {
_vm->_palanim->fade(0, -2, 0);
@@ -760,7 +760,7 @@ void Inter_Bargon::oBargon_intro2(int16 &extraData, int32 *retVarPtr,
}
}
if (!_vm->_quitRequested)
- _vm->_util->setScrollOffset(0);
+ _vm->_util->setScrollOffset(0, 0);
_vm->_video->freeSurfDesc(surface);
if (VAR(57) == ((uint32) -1))
return;
diff --git a/engines/gob/inter_v1.cpp b/engines/gob/inter_v1.cpp
index 1e8084febb..0a2468a4c8 100644
--- a/engines/gob/inter_v1.cpp
+++ b/engines/gob/inter_v1.cpp
@@ -646,6 +646,117 @@ void Inter_v1::setupOpcodes(void) {
_opcodesGoblinV1 = opcodesGoblin;
}
+void Inter_v1::executeDrawOpcode(byte i) {
+ debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%x] (%s)", i, i, getOpcodeDrawDesc(i));
+
+ OpcodeDrawProcV1 op = _opcodesDrawV1[i].proc;
+
+ if (op == NULL)
+ warning("unimplemented opcodeDraw: %d", i);
+ else
+ (this->*op) ();
+}
+
+bool Inter_v1::executeFuncOpcode(byte i, byte j, char &cmdCount, int16 &counter, int16 &retFlag) {
+ debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%x.0x%x] (%s)", i, j, i, j, getOpcodeFuncDesc(i, j));
+
+ if ((i > 4) || (j > 15)) {
+ warning("unimplemented opcodeFunc: %d.%d", i, j);
+ return false;
+ }
+
+ OpcodeFuncProcV1 op = _opcodesFuncV1[i*16 + j].proc;
+
+ if (op == NULL)
+ warning("unimplemented opcodeFunc: %d.%d", i, j);
+ else
+ return (this->*op) (cmdCount, counter, retFlag);
+ return false;
+}
+
+void Inter_v1::executeGoblinOpcode(int i, int16 &extraData, int32 *retVarPtr, Goblin::Gob_Object *objDesc) {
+ debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%x] (%s)", i, i, getOpcodeGoblinDesc(i));
+
+ OpcodeGoblinProcV1 op = NULL;
+
+ for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
+ if (_goblinFuncLookUp[j][0] == i) {
+ op = _opcodesGoblinV1[_goblinFuncLookUp[j][1]].proc;
+ break;
+ }
+
+ if (op == NULL) {
+ warning("unimplemented opcodeGoblin: %d", i);
+ _vm->_global->_inter_execPtr -= 2;
+ int16 cmd = load16();
+ _vm->_global->_inter_execPtr += cmd * 2;
+ }
+ else
+ (this->*op) (extraData, retVarPtr, objDesc);
+}
+
+const char *Inter_v1::getOpcodeDrawDesc(byte i) {
+ return _opcodesDrawV1[i].desc;
+}
+
+const char *Inter_v1::getOpcodeFuncDesc(byte i, byte j) {
+ if ((i > 4) || (j > 15))
+ return "";
+
+ return _opcodesFuncV1[i*16 + j].desc;
+}
+
+const char *Inter_v1::getOpcodeGoblinDesc(int i) {
+ for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
+ if (_goblinFuncLookUp[j][0] == i)
+ return _opcodesGoblinV1[_goblinFuncLookUp[j][1]].desc;
+ return "";
+}
+
+void Inter_v1::checkSwitchTable(char **ppExec) {
+ int i;
+ int16 len;
+ int32 value;
+ bool found;
+ bool notFound;
+
+ found = false;
+ notFound = true;
+ *ppExec = 0;
+ value = VAR_OFFSET(_vm->_parse->parseVarIndex());
+
+ len = (int8) *_vm->_global->_inter_execPtr++;
+ while (len != -5) {
+ for (i = 0; i < len; i++) {
+ evalExpr(0);
+
+ if (_terminate)
+ return;
+
+ if (_vm->_global->_inter_resVal == value) {
+ found = true;
+ notFound = false;
+ }
+ }
+
+ if (found)
+ *ppExec = _vm->_global->_inter_execPtr;
+
+ _vm->_global->_inter_execPtr += READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ found = false;
+ len = (int8) *_vm->_global->_inter_execPtr++;
+ }
+
+ if ((*_vm->_global->_inter_execPtr >> 4) != 4)
+ return;
+
+ _vm->_global->_inter_execPtr++;
+ if (notFound)
+ *ppExec = _vm->_global->_inter_execPtr;
+
+ _vm->_global->_inter_execPtr += READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+}
+
bool Inter_v1::o1_setMousePos(char &cmdCount, int16 &counter, int16 &retFlag) {
_vm->_global->_inter_mouseX = _vm->_parse->parseValExpr();
_vm->_global->_inter_mouseY = _vm->_parse->parseValExpr();
@@ -1303,6 +1414,7 @@ bool Inter_v1::o1_loadSpriteToPos(char &cmdCount, int16 &counter, int16 &retFlag
_vm->_draw->_destSurface = 101;
_vm->_draw->_transparency &= 1;
_vm->_global->_inter_execPtr += 2;
+
_vm->_draw->spriteOperation(DRAW_LOADSPRITE);
return false;
@@ -1696,73 +1808,6 @@ void Inter_v1::o1_freeFontToSprite(void) {
_vm->_draw->_fontToSprite[i].height = -1;
}
-void Inter_v1::executeDrawOpcode(byte i) {
- debugC(1, kDebugDrawOp, "opcodeDraw %d [0x%x] (%s)", i, i, getOpcodeDrawDesc(i));
-
- OpcodeDrawProcV1 op = _opcodesDrawV1[i].proc;
-
- if (op == NULL)
- warning("unimplemented opcodeDraw: %d", i);
- else
- (this->*op) ();
-}
-
-bool Inter_v1::executeFuncOpcode(byte i, byte j, char &cmdCount, int16 &counter, int16 &retFlag) {
- debugC(1, kDebugFuncOp, "opcodeFunc %d.%d [0x%x.0x%x] (%s)", i, j, i, j, getOpcodeFuncDesc(i, j));
-
- if ((i > 4) || (j > 15)) {
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- return false;
- }
-
- OpcodeFuncProcV1 op = _opcodesFuncV1[i*16 + j].proc;
-
- if (op == NULL)
- warning("unimplemented opcodeFunc: %d.%d", i, j);
- else
- return (this->*op) (cmdCount, counter, retFlag);
- return false;
-}
-
-void Inter_v1::executeGoblinOpcode(int i, int16 &extraData, int32 *retVarPtr, Goblin::Gob_Object *objDesc) {
- debugC(1, kDebugGobOp, "opcodeGoblin %d [0x%x] (%s)", i, i, getOpcodeGoblinDesc(i));
-
- OpcodeGoblinProcV1 op = NULL;
-
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i) {
- op = _opcodesGoblinV1[_goblinFuncLookUp[j][1]].proc;
- break;
- }
-
- if (op == NULL) {
- warning("unimplemented opcodeGoblin: %d", i);
- _vm->_global->_inter_execPtr -= 2;
- int16 cmd = load16();
- _vm->_global->_inter_execPtr += cmd * 2;
- }
- else
- (this->*op) (extraData, retVarPtr, objDesc);
-}
-
-const char *Inter_v1::getOpcodeDrawDesc(byte i) {
- return _opcodesDrawV1[i].desc;
-}
-
-const char *Inter_v1::getOpcodeFuncDesc(byte i, byte j) {
- if ((i > 4) || (j > 15))
- return "";
-
- return _opcodesFuncV1[i*16 + j].desc;
-}
-
-const char *Inter_v1::getOpcodeGoblinDesc(int i) {
- for (int j = 0; j < ARRAYSIZE(_goblinFuncLookUp); j++)
- if (_goblinFuncLookUp[j][0] == i)
- return _opcodesGoblinV1[_goblinFuncLookUp[j][1]].desc;
- return "";
-}
-
bool Inter_v1::o1_callSub(char &cmdCount, int16 &counter, int16 &retFlag) {
char *storedIP = _vm->_global->_inter_execPtr;
diff --git a/engines/gob/inter_v2.cpp b/engines/gob/inter_v2.cpp
index a262680f8f..7df944c76c 100644
--- a/engines/gob/inter_v2.cpp
+++ b/engines/gob/inter_v2.cpp
@@ -715,6 +715,96 @@ const char *Inter_v2::getOpcodeGoblinDesc(int i) {
return "";
}
+void Inter_v2::checkSwitchTable(char **ppExec) {
+ int i;
+ byte cmd;
+ int16 len;
+ int32 value;
+ bool found;
+
+ found = false;
+ *ppExec = 0;
+
+ cmd = *_vm->_global->_inter_execPtr;
+
+ value = _vm->_parse->parseVarIndex();
+
+ switch (cmd) {
+ case 16:
+ case 18:
+ value = (int8) READ_VARO_UINT8(value);
+ break;
+
+ case 23:
+ case 26:
+ value = READ_VARO_UINT32(value);
+ break;
+
+ default:
+ value = READ_VARO_UINT16(value);
+ break;
+ }
+
+ if (_terminate)
+ return;
+
+ len = (int8) *_vm->_global->_inter_execPtr++;
+ while (len != -5) {
+ for (i = 0; i < len; i++) {
+ cmd = *_vm->_global->_inter_execPtr;
+
+ switch(cmd) {
+ case 19:
+ _vm->_global->_inter_execPtr++;
+ if (!found &&
+ (value == (int32) (READ_LE_UINT32(_vm->_global->_inter_execPtr))))
+ found = true;
+ _vm->_global->_inter_execPtr += 5;
+ break;
+
+ case 20:
+ _vm->_global->_inter_execPtr++;
+ if (!found &&
+ (value == (int16) (READ_LE_UINT16(_vm->_global->_inter_execPtr))))
+ found = true;
+ _vm->_global->_inter_execPtr += 3;
+ break;
+
+ case 21:
+ _vm->_global->_inter_execPtr++;
+ if (!found && (value == (int8) *_vm->_global->_inter_execPtr))
+ found = true;
+ _vm->_global->_inter_execPtr += 2;
+ break;
+
+ default:
+ if (!found) {
+ evalExpr(0);
+ if (value == _vm->_global->_inter_resVal)
+ found = true;
+ } else
+ _vm->_parse->skipExpr(99);
+ break;
+ }
+ }
+
+ if (found && (*ppExec == 0))
+ *ppExec = _vm->_global->_inter_execPtr;
+
+ _vm->_global->_inter_execPtr += READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+ len = (int8) *_vm->_global->_inter_execPtr++;
+ }
+
+ if ((*_vm->_global->_inter_execPtr >> 4) != 4)
+ return;
+
+ _vm->_global->_inter_execPtr++;
+ if (*ppExec == 0)
+ *ppExec = _vm->_global->_inter_execPtr;
+
+ _vm->_global->_inter_execPtr += READ_LE_UINT16(_vm->_global->_inter_execPtr + 2) + 2;
+}
+
void Inter_v2::o2_stub0x54(void) {
int16 index = _vm->_parse->parseValExpr();
@@ -879,7 +969,7 @@ int16 Inter_v2::loadSound(int16 search) {
} else {
if (id >= 30000) {
if (!isADL && (_vm->_game->_totFileData[0x29] >= 51)) { // loc_9763
- if (_vm->_inter->_terminate != 0)
+ if (_terminate != 0)
return slot;
soundDesc = new Snd::SoundDesc;
extData = _vm->_game->loadExtData(id, 0, 0);
@@ -1869,7 +1959,7 @@ void Inter_v2::o2_initMult(void) {
if (_vm->_mult->_objects == 0) {
_vm->_mult->_renderData2 = new Mult::Mult_Object*[_vm->_mult->_objCount];
memset(_vm->_mult->_renderData2, 0, _vm->_mult->_objCount * sizeof(Mult::Mult_Object*));
- if (_vm->_inter->_terminate)
+ if (_terminate)
return;
_vm->_mult->_orderArray = new int8[_vm->_mult->_objCount];
memset(_vm->_mult->_orderArray, 0, _vm->_mult->_objCount * sizeof(int8));
@@ -2115,15 +2205,15 @@ void Inter_v2::o2_playImd(void) {
}
void Inter_v2::o2_initScreen(void) {
- int16 start;
+ int16 offY;
int16 videoMode;
int16 width;
int16 height;
- start = load16();
+ offY = load16();
- videoMode = start & 0xFF;
- start = (start >> 8) & 0xFF;
+ videoMode = offY & 0xFF;
+ offY = (offY >> 8) & 0xFF;
width = _vm->_parse->parseValExpr();
height = _vm->_parse->parseValExpr();
@@ -2131,7 +2221,10 @@ void Inter_v2::o2_initScreen(void) {
if ((videoMode == _vm->_global->_videoMode) && (width == -1))
return;
- _vm->_video->_surfWidth = videoMode == 0x14 ? 640 : 320;
+ if (width > 0)
+ _vm->_video->_surfWidth = width;
+ if (height > 0)
+ _vm->_video->_surfHeight = height;
_vm->_draw->closeScreen();
_vm->_util->clearPalette();
@@ -2153,36 +2246,27 @@ void Inter_v2::o2_initScreen(void) {
_vm->_global->_setAllPalette = 1;
- if ((width != -1) && (_vm->_global->_videoMode == 0x14)) {
+ if ((width != -1) && (_vm->_global->_videoMode == 0x14))
_vm->_game->_byte_2FC9B = 1;
-/*
- if (width > 960)
- width = 960;
- _vm->_draw->_frontSurface->width = width;
- _vm->_draw->_frontSurface->height = height;
- warning("GOB2 Stub! _vid_setVirtRes(_vm->_draw->_frontSurface);");
- _vm->_global->_mouseMaxCol = width;
- _vm->_global->_mouseMaxRow = height;
-*/
- }
_vm->_util->setMousePos(_vm->_global->_inter_mouseX, _vm->_global->_inter_mouseY);
_vm->_util->clearPalette();
- if (start == 0)
+ // Split screen (word_2E51F ^= splitScreenHeight, off_2E51B ^= splitScreenSurf)?
+ if (offY == 0)
_vm->_draw->_word_2E51F = 0;
else
- _vm->_draw->_word_2E51F = _vm->_global->_primaryHeight - start;
+ _vm->_draw->_word_2E51F = _vm->_global->_primaryHeight - offY;
_vm->_draw->initScreen();
- if (_vm->_draw->_off_2E51B != 0) {
- _vm->_video->_scrollOffset = 0;
+ _vm->_util->setScrollOffset();
/*
- warning("_vid_setSplit(%d)", _vm->_global->_primaryHeight - start);
- warning("_vid_setPixelShift(0, %d", start);
-*/
+ if (_vm->_draw->_off_2E51B != 0) {
+ warning("_vid_setSplit(%d)", _vm->_global->_primaryHeight - offY);
+ warning("_vid_setPixelShift(0, %d", offY);
}
+*/
}
void Inter_v2::o2_setScrollOffset(void) {
@@ -2194,20 +2278,24 @@ void Inter_v2::o2_setScrollOffset(void) {
if (_vm->_game->_byte_2FC9B != 0)
_vm->_game->_byte_2FC9B = 1;
_vm->_parse->parseValExpr();
- WRITE_VAR(2, _vm->_draw->_word_2FC9E);
- WRITE_VAR(3, _vm->_draw->_word_2FC9C);
+ WRITE_VAR(2, _vm->_draw->_scrollOffsetX);
+ WRITE_VAR(3, _vm->_draw->_scrollOffsetY);
} else {
- _vm->_draw->_word_2FC9E = offset;
- _vm->_draw->_word_2FC9C = _vm->_parse->parseValExpr();
+ _vm->_draw->_scrollOffsetX = offset;
+ _vm->_draw->_scrollOffsetY = _vm->_parse->parseValExpr();
}
- _vm->_util->setScrollOffset(_vm->_draw->_word_2FC9E);
+ if (_vm->_draw->_off_2E51B != 0)
+ _vm->_util->setScrollOffset(_vm->_draw->_scrollOffsetX,
+ _vm->_draw->_scrollOffsetY + 200 - _vm->_draw->_word_2E51F);
+ else
+ _vm->_util->setScrollOffset();
_noBusyWait = true;
/*
if (_vm->_draw->_off_2E51B != 0)
- warning("_vid_setPixelShift(%d, %d)", _vm->_draw->_word_2FC9E, _vm->_draw->_word_2FC9C + 200 - _vm->_draw->_word_2E51F);
+ warning("_vid_setPixelShift(%d, %d)", _vm->_draw->_scrollOffsetX, _vm->_draw->_scrollOffsetY + 200 - _vm->_draw->_word_2E51F);
else
- warning("_vid_setPixelShift(%d, %d)", _vm->_draw->_word_2FC9E, _vm->_draw->_word_2FC9C);;
+ warning("_vid_setPixelShift(%d, %d)", _vm->_draw->_scrollOffsetX, _vm->_draw->_scrollOffsetY);;
*/
}
@@ -2228,16 +2316,14 @@ void Inter_v2::o2_scroll(void) {
stepX = _vm->_parse->parseValExpr();
stepY = _vm->_parse->parseValExpr();
- if ((stepY != 0) || (startY > 0) || (endY > 0))
- warning("GOB2 Stub! Vertical scrolling / high surfaces");
-
curX = startX;
curY = startY;
while (!_vm->_quitRequested && ((curX != endX) || (curY != endY))) {
curX = stepX > 0 ? MIN(curX + stepX, (int) endX) : MAX(curX + stepX, (int) endX);
curY = stepY > 0 ? MIN(curY + stepY, (int) endY) : MAX(curY + stepY, (int) endY);
- _vm->_draw->_word_2FC9E = curX;
- _vm->_util->setScrollOffset(_vm->_draw->_word_2FC9E);
+ _vm->_draw->_scrollOffsetX = curX;
+ _vm->_draw->_scrollOffsetY = curY;
+ _vm->_util->setScrollOffset();
}
}
diff --git a/engines/gob/mult_v2.cpp b/engines/gob/mult_v2.cpp
index 539b4fa41d..56f96f4d97 100644
--- a/engines/gob/mult_v2.cpp
+++ b/engines/gob/mult_v2.cpp
@@ -424,7 +424,7 @@ void Mult_v2::playMult(int16 startFrame, int16 endFrame, char checkEscape,
_vm->_anim->_areaTop = 0;
_vm->_anim->_areaLeft = 0;
_vm->_anim->_areaWidth = _vm->_video->_surfWidth;
- _vm->_anim->_areaHeight = 200;
+ _vm->_anim->_areaHeight = _vm->_video->_surfHeight;
_objCount = 4;
if (_objects)
@@ -478,7 +478,7 @@ void Mult_v2::playMult(int16 startFrame, int16 endFrame, char checkEscape,
_vm->_draw->_spriteLeft = 0;
_vm->_draw->_spriteTop = 0;
_vm->_draw->_spriteRight = _vm->_video->_surfWidth;
- _vm->_draw->_spriteBottom = 200;
+ _vm->_draw->_spriteBottom = _vm->_video->_surfHeight;
_vm->_draw->_transparency = 0;
_vm->_draw->spriteOperation(0);
_animDataAllocated = 1;
@@ -609,7 +609,7 @@ char Mult_v2::drawStatics(char stop) {
_vm->_draw->_spriteLeft = 0;
_vm->_draw->_spriteTop = 0;
_vm->_draw->_spriteRight = _vm->_video->_surfWidth;
- _vm->_draw->_spriteBottom = 200;
+ _vm->_draw->_spriteBottom = _vm->_video->_surfHeight;
_vm->_draw->_transparency = 0;
_vm->_draw->spriteOperation(0);
}
diff --git a/engines/gob/util.cpp b/engines/gob/util.cpp
index 7698262e26..6dfa5b4d7c 100644
--- a/engines/gob/util.cpp
+++ b/engines/gob/util.cpp
@@ -494,9 +494,10 @@ void Util::forceMouseUp(void) {
_mouseButtons = 0;
}
-void Util::setScrollOffset(int16 scrollOffset) {
+void Util::setScrollOffset(int16 x, int16 y) {
processInput();
- _vm->_video->_scrollOffset = scrollOffset;
+ _vm->_video->_scrollOffsetX = x >= 0 ? x : _vm->_draw->_scrollOffsetX;
+ _vm->_video->_scrollOffsetY = y >= 0 ? y : _vm->_draw->_scrollOffsetY;
_vm->_video->waitRetrace(_vm->_global->_videoMode);
}
diff --git a/engines/gob/util.h b/engines/gob/util.h
index 8f4d6867c6..de9e6224b9 100644
--- a/engines/gob/util.h
+++ b/engines/gob/util.h
@@ -84,7 +84,7 @@ public:
static void prepareStr(char *str);
void waitMouseRelease(char drawMouse);
void forceMouseUp(void);
- void setScrollOffset(int16 scrollOffset);
+ void setScrollOffset(int16 x = -1, int16 y = -1);
static const char trStr1[];
static const char trStr2[];
diff --git a/engines/gob/video.cpp b/engines/gob/video.cpp
index 675d7a6f23..bbe909e189 100644
--- a/engines/gob/video.cpp
+++ b/engines/gob/video.cpp
@@ -38,7 +38,9 @@ namespace Gob {
Video::Video(GobEngine *vm) : _vm(vm) {
_videoDriver = 0;
_surfWidth = 320;
- _scrollOffset = 0;
+ _surfHeight = 200;
+ _scrollOffsetX = 0;
+ _scrollOffsetY = 0;
}
char Video::initDriver(int16 vidMode) {
@@ -396,7 +398,7 @@ void Video::initPrimary(int16 mode) {
Video::initDriver(mode);
if (mode != 3) {
- initSurfDesc(mode, _surfWidth, 200, PRIMARY_SURFACE);
+ initSurfDesc(mode, _surfWidth, _vm->_video->_surfHeight, PRIMARY_SURFACE);
if (_vm->_global->_dontSetPalette)
return;
diff --git a/engines/gob/video.h b/engines/gob/video.h
index f59fa48191..99127e64bb 100644
--- a/engines/gob/video.h
+++ b/engines/gob/video.h
@@ -91,7 +91,9 @@ public:
};
int16 _surfWidth;
- int16 _scrollOffset;
+ int16 _surfHeight;
+ int16 _scrollOffsetX;
+ int16 _scrollOffsetY;
Video(class GobEngine *vm);
virtual ~Video() {};
diff --git a/engines/gob/video_v2.cpp b/engines/gob/video_v2.cpp
index 2f71412b69..d4bbd7ada8 100644
--- a/engines/gob/video_v2.cpp
+++ b/engines/gob/video_v2.cpp
@@ -45,8 +45,9 @@ void Video_v2::waitRetrace(int16, bool mouse) {
CursorMan.showMouse((_vm->_draw->_showCursor & 2) != 0);
if (_vm->_draw->_frontSurface) {
time = _vm->_util->getTimeKey();
- g_system->copyRectToScreen(_vm->_draw->_frontSurface->vidPtr + _scrollOffset,
- _surfWidth, 0, 0, 320, 200);
+ g_system->copyRectToScreen(_vm->_draw->_frontSurface->vidPtr +
+ _scrollOffsetY * _surfWidth + _scrollOffsetX, _surfWidth,
+ 0, 0, 320, 200);
g_system->updateScreen();
_vm->_util->delay(MAX(1, 10 - (int)(_vm->_util->getTimeKey() - time)));
}
@@ -136,8 +137,8 @@ Video::SurfaceDesc *Video_v2::initSurfDesc(int16 vidMode, int16 width, int16 hei
assert(descPtr);
if (descPtr->vidPtr != 0)
delete[] descPtr->vidPtr;
- vidMem = new byte[_surfWidth * 200];
- memset(vidMem, 0, _surfWidth * 200);
+ vidMem = new byte[_surfWidth * _surfHeight];
+ memset(vidMem, 0, _surfWidth * _surfHeight);
} else {
if (flags & DISABLE_SPR_ALLOC) {
descPtr = new SurfaceDesc;