[Scummvm-cvs-logs] SF.net SVN: scummvm:[33900] scummvm/trunk/engines/parallaction
peres001 at users.sourceforge.net
peres001 at users.sourceforge.net
Fri Aug 15 16:25:44 CEST 2008
Revision: 33900
http://scummvm.svn.sourceforge.net/scummvm/?rev=33900&view=rev
Author: peres001
Date: 2008-08-15 14:25:43 +0000 (Fri, 15 Aug 2008)
Log Message:
-----------
Added routines to load and handle item masks: animation are now correctly hidden when they are behind any object. The masks of items that are not explicitly activated (even if visible) still are handled (e.g. the crown in the museum is not visible in the foreground).
Modified Paths:
--------------
scummvm/trunk/engines/parallaction/disk.h
scummvm/trunk/engines/parallaction/disk_br.cpp
scummvm/trunk/engines/parallaction/exec_ns.cpp
scummvm/trunk/engines/parallaction/graphics.h
scummvm/trunk/engines/parallaction/objects.h
scummvm/trunk/engines/parallaction/parser.h
scummvm/trunk/engines/parallaction/parser_br.cpp
Modified: scummvm/trunk/engines/parallaction/disk.h
===================================================================
--- scummvm/trunk/engines/parallaction/disk.h 2008-08-15 13:50:08 UTC (rev 33899)
+++ scummvm/trunk/engines/parallaction/disk.h 2008-08-15 14:25:43 UTC (rev 33900)
@@ -69,6 +69,7 @@
virtual Table* loadTable(const char* name) = 0;
virtual Common::SeekableReadStream* loadMusic(const char* name) = 0;
virtual Common::ReadStream* loadSound(const char* name) = 0;
+ virtual void loadMask(const char *name, MaskBuffer &buffer) { }
};
@@ -248,6 +249,7 @@
Table* loadTable(const char* name);
Common::SeekableReadStream* loadMusic(const char* name);
Common::ReadStream* loadSound(const char* name);
+ void loadMask(const char *name, MaskBuffer &buffer);
};
class DosDemo_br : public DosDisk_br {
Modified: scummvm/trunk/engines/parallaction/disk_br.cpp
===================================================================
--- scummvm/trunk/engines/parallaction/disk_br.cpp 2008-08-15 13:50:08 UTC (rev 33899)
+++ scummvm/trunk/engines/parallaction/disk_br.cpp 2008-08-15 14:25:43 UTC (rev 33900)
@@ -357,6 +357,29 @@
return;
}
+void DosDisk_br::loadMask(const char *name, MaskBuffer &buffer) {
+ if (!name) {
+ return;
+ }
+
+ Common::String filepath;
+ FilesystemNode node;
+ Common::File stream;
+
+ filepath = Common::String(name) + ".msk";
+ node = _mskDir.getChild(filepath);
+ if (!node.exists()) {
+ errorFileNotFound(_mskDir, filepath);
+ }
+ stream.open(node);
+
+ // NOTE: info.width and info.height are only valid if the background graphics
+ // have already been loaded
+ buffer.bigEndian = false;
+ stream.read(buffer.data, buffer.size);
+ stream.close();
+}
+
void DosDisk_br::loadScenery(BackgroundInfo& info, const char *name, const char *mask, const char* path) {
debugC(5, kDebugDisk, "DosDisk_br::loadScenery");
Modified: scummvm/trunk/engines/parallaction/exec_ns.cpp
===================================================================
--- scummvm/trunk/engines/parallaction/exec_ns.cpp 2008-08-15 13:50:08 UTC (rev 33899)
+++ scummvm/trunk/engines/parallaction/exec_ns.cpp 2008-08-15 14:25:43 UTC (rev 33900)
@@ -261,8 +261,13 @@
if ((z->_type & 0xFFFF) == kZoneGet) {
_gfx->showGfxObj(z->u.get->gfxobj, visible);
+
+ GetData *data = z->u.get;
+ if (data->hasMask && _gfx->_backgroundInfo->hasMask) {
+ int frame = visible ? 0 : 1;
+ _gfx->_backgroundInfo->mask.blt(data->gfxobj->x, data->gfxobj->y, data->_mask[frame], 0, 0, data->_mask->w, data->_mask->h);
+ }
}
-
}
DECLARE_COMMAND_OPCODE(on) {
Modified: scummvm/trunk/engines/parallaction/graphics.h
===================================================================
--- scummvm/trunk/engines/parallaction/graphics.h 2008-08-15 13:50:08 UTC (rev 33899)
+++ scummvm/trunk/engines/parallaction/graphics.h 2008-08-15 14:25:43 UTC (rev 33900)
@@ -209,6 +209,32 @@
return (m >> n) & 3;
}
+ inline byte* getPtr(uint16 x, uint16 y) const {
+ return data + (x >> 2) + y * internalWidth;
+ }
+
+ void blt(uint16 dx, uint16 dy, const MaskBuffer &src, uint16 sx, uint16 sy, uint width, uint height) {
+ assert((width <= w) && (width <= src.w) && (height <= h) && (height <= src.h));
+
+ byte *s = src.getPtr(sx, sy);
+ byte *d = getPtr(dx, dy);
+
+ uint diffs = 0;
+
+ // this code assumes buffers are aligned on 4-pixels boundaries, as the original does
+ uint16 linewidth = width >> 2;
+ for (uint16 i = 0; i < height; i++) {
+ for (uint16 j = 0; j < linewidth; j++) {
+ if (*s) diffs++;
+ *d++ |= *s++;
+ }
+ d += internalWidth - linewidth;
+ s += src.internalWidth - linewidth;
+ }
+
+ printf("MaskBuffer::blt() diffs = %i\n", diffs);
+ }
+
};
@@ -419,7 +445,9 @@
int layers[4];
PaletteFxRange ranges[6];
- BackgroundInfo() : x(0), y(0), width(0), height(0) {
+ bool hasMask;
+
+ BackgroundInfo() : x(0), y(0), width(0), height(0), hasMask(false) {
layers[0] = layers[1] = layers[2] = layers[3] = 0;
memset(ranges, 0, sizeof(ranges));
}
Modified: scummvm/trunk/engines/parallaction/objects.h
===================================================================
--- scummvm/trunk/engines/parallaction/objects.h 2008-08-15 13:50:08 UTC (rev 33899)
+++ scummvm/trunk/engines/parallaction/objects.h 2008-08-15 14:25:43 UTC (rev 33900)
@@ -198,11 +198,14 @@
byte *_backup;
uint16 field_14; // unused
uint16 field_16; // unused
+ MaskBuffer _mask[2];
+ bool hasMask;
GetData() {
_icon = 0;
_backup = NULL;
gfxobj = NULL;
+ hasMask = false;
}
};
struct SpeakData { // size = 36
Modified: scummvm/trunk/engines/parallaction/parser.h
===================================================================
--- scummvm/trunk/engines/parallaction/parser.h 2008-08-15 13:50:08 UTC (rev 33899)
+++ scummvm/trunk/engines/parallaction/parser.h 2008-08-15 14:25:43 UTC (rev 33900)
@@ -131,9 +131,6 @@
// BRA specific
int numZones;
BackgroundInfo *info;
- char *bgName;
- char *maskName;
- char *pathName;
char *characterName;
} ctxt;
@@ -306,6 +303,7 @@
virtual void parseZoneTypeBlock(ZonePtr z);
void parsePathData(ZonePtr z);
+ void parseGetData(ZonePtr z);
public:
LocationParser_br(Parallaction_br *vm) : LocationParser_ns((Parallaction_ns*)vm), _vm(vm) {
Modified: scummvm/trunk/engines/parallaction/parser_br.cpp
===================================================================
--- scummvm/trunk/engines/parallaction/parser_br.cpp 2008-08-15 13:50:08 UTC (rev 33899)
+++ scummvm/trunk/engines/parallaction/parser_br.cpp 2008-08-15 14:25:43 UTC (rev 33900)
@@ -316,7 +316,6 @@
debugC(7, kDebugParser, "LOCATION_PARSER(location) ");
strcpy(_vm->_location._name, _tokens[1]);
- ctxt.bgName = strdup(_tokens[1]);
bool flip = false;
int nextToken;
@@ -340,6 +339,8 @@
if (_tokens[nextToken][0] != '\0') {
_vm->_char._ani->setF(atoi(_tokens[nextToken]));
}
+
+ _vm->_disk->loadScenery(*ctxt.info, _tokens[1], 0, 0);
}
@@ -465,18 +466,20 @@
DECLARE_LOCATION_PARSER(mask) {
debugC(7, kDebugParser, "LOCATION_PARSER(mask) ");
- ctxt.maskName = strdup(_tokens[1]);
ctxt.info->layers[0] = 0;
ctxt.info->layers[1] = atoi(_tokens[2]);
ctxt.info->layers[2] = atoi(_tokens[3]);
ctxt.info->layers[3] = atoi(_tokens[4]);
+
+ _vm->_disk->loadScenery(*ctxt.info, 0, _tokens[1], 0);
+ ctxt.info->hasMask = true;
}
DECLARE_LOCATION_PARSER(path) {
debugC(7, kDebugParser, "LOCATION_PARSER(path) ");
- ctxt.pathName = strdup(_tokens[1]);
+ _vm->_disk->loadScenery(*ctxt.info, 0, 0, _tokens[1]);
}
@@ -768,6 +771,54 @@
z->u.path = data;
}
+void LocationParser_br::parseGetData(ZonePtr z) {
+
+ GetData *data = new GetData;
+
+ do {
+
+ if (!scumm_stricmp(_tokens[0], "file")) {
+
+ GfxObj *obj = _vm->_gfx->loadGet(_tokens[1]);
+ obj->frame = 0;
+ obj->x = z->getX();
+ obj->y = z->getY();
+ data->gfxobj = obj;
+ }
+
+ if (!scumm_stricmp(_tokens[0], "mask")) {
+ if (ctxt.info->hasMask) {
+ Common::Rect rect;
+ data->gfxobj->getRect(0, rect);
+ data->_mask[0].create(rect.width(), rect.height());
+ _vm->_disk->loadMask(_tokens[1], data->_mask[0]);
+ data->_mask[1].create(rect.width(), rect.height());
+ data->_mask[1].blt(0, 0, ctxt.info->mask, data->gfxobj->x, data->gfxobj->y, data->_mask->w, data->_mask->h);
+ data->hasMask = true;
+ } else {
+ warning("Mask for zone '%s' ignored, since background doesn't have one", z->_name);
+ }
+ }
+
+ if (!scumm_stricmp(_tokens[0], "path")) {
+
+ }
+
+ if (!scumm_stricmp(_tokens[0], "icon")) {
+ data->_icon = 4 + _vm->_objectsNames->lookup(_tokens[1]);
+ }
+
+ _script->readLineToken(true);
+ } while (scumm_stricmp(_tokens[0], "endzone"));
+
+ z->u.get = data;
+
+ // FIXME: right now showZone doesn't work properly when called during location
+ // parsing. In fact, the main backgroundInfo is not properly set yet.
+ bool visible = (z->_flags & kFlagsRemove) == 0;
+ _vm->showZone(z, visible);
+}
+
void LocationParser_br::parseZoneTypeBlock(ZonePtr z) {
debugC(7, kDebugParser, "parseZoneTypeBlock(name: %s, type: %x)", z->_name, z->_type);
@@ -1192,15 +1243,11 @@
Script *script2 = new Script(getStream(list), true);
ctxt.numZones = 0;
- ctxt.bgName = 0;
- ctxt.maskName = 0;
- ctxt.pathName = 0;
ctxt.characterName = 0;
ctxt.info = new BackgroundInfo;
LocationParser_ns::parse(script2);
- _vm->_disk->loadScenery(*ctxt.info, ctxt.bgName, ctxt.maskName, ctxt.pathName);
_vm->_gfx->setBackground(kBackgroundLocation, ctxt.info);
_vm->_pathBuffer = &ctxt.info->path;
@@ -1209,9 +1256,6 @@
_vm->changeCharacter(ctxt.characterName);
}
- free(ctxt.bgName);
- free(ctxt.maskName);
- free(ctxt.pathName);
free(ctxt.characterName);
delete script2;
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
More information about the Scummvm-git-logs
mailing list