aboutsummaryrefslogtreecommitdiff
path: root/scumm
diff options
context:
space:
mode:
Diffstat (limited to 'scumm')
-rw-r--r--scumm/charset.cpp13
-rw-r--r--scumm/charset.h2
-rw-r--r--scumm/gfx.cpp107
-rw-r--r--scumm/gfx.h11
-rw-r--r--scumm/saveload.cpp18
-rw-r--r--scumm/scumm.cpp29
-rw-r--r--scumm/scumm.h2
7 files changed, 91 insertions, 91 deletions
diff --git a/scumm/charset.cpp b/scumm/charset.cpp
index 458de41a13..9f1ddbc3c0 100644
--- a/scumm/charset.cpp
+++ b/scumm/charset.cpp
@@ -202,10 +202,21 @@ CharsetRenderer::CharsetRenderer(ScummEngine *vm) {
_blitAlso = false;
_firstChar = false;
_disableOffsX = false;
- _textSurface.pixels = 0;
_vm = vm;
_curId = 0;
+
+ const int size = _vm->_screenWidth * _vm->_screenHeight;
+ _textSurface.pixels = malloc(size);
+ memset(_textSurface.pixels, CHARSET_MASK_TRANSPARENCY, size);
+ _textSurface.w = _vm->_screenWidth;
+ _textSurface.h = _vm->_screenHeight;
+ _textSurface.pitch = _vm->_screenWidth;
+ _textSurface.bytesPerPixel = 1;
+}
+
+CharsetRenderer::~CharsetRenderer() {
+ free(_textSurface.pixels);
}
void CharsetRendererCommon::setCurID(byte id) {
diff --git a/scumm/charset.h b/scumm/charset.h
index c41f1051e6..a9be1dd231 100644
--- a/scumm/charset.h
+++ b/scumm/charset.h
@@ -88,7 +88,7 @@ protected:
public:
CharsetRenderer(ScummEngine *vm);
- virtual ~CharsetRenderer() {}
+ virtual ~CharsetRenderer();
void restoreCharsetBg();
void clearCharsetMask();
diff --git a/scumm/gfx.cpp b/scumm/gfx.cpp
index 6ad0d3a753..4c4bfe9989 100644
--- a/scumm/gfx.cpp
+++ b/scumm/gfx.cpp
@@ -189,21 +189,66 @@ static const TransitionEffect transitionEffects[6] = {
};
#endif
-#pragma mark -
-#pragma mark --- Virtual Screens ---
-#pragma mark -
-
-
-#define CHARSET_MASK_TRANSPARENCY 253
Gdi::Gdi(ScummEngine *vm) {
memset(this, 0, sizeof(*this));
_vm = vm;
_roomPalette = vm->_roomPalette;
+ _roomStrips = 0;
if ((vm->_features & GF_AMIGA) && (vm->_version >= 4))
_roomPalette += 16;
}
+Gdi::~Gdi() {
+ free(_roomStrips);
+}
+
+void Gdi::init() {
+ _numStrips = _vm->_screenWidth / 8;
+
+ // Increase the number of screen strips by one; needed for smooth scrolling
+ if (_vm->_version >= 7) {
+ // We now have mostly working smooth scrolling code in place for V7+ games
+ // (i.e. The Dig, Full Throttle and COMI). It seems to work very well so far.
+ // One area which still may need some work are the AKOS codecs (except for
+ // codec 1, which I already updated): their masking code may need adjustments,
+ // similar to the treatment codec 1 received.
+ //
+ // To understand how we achieve smooth scrolling, first note that with it, the
+ // virtual screen strips don't match the display screen strips anymore. To
+ // overcome that problem, we simply use a screen pitch that is 8 pixel wider
+ // than the actual screen width, and always draw one strip more than needed to
+ // the backbuf (of course we have to treat the right border seperately). This
+ _numStrips += 1;
+ }
+}
+
+void Gdi::roomChanged(byte *roomptr, uint32 IM00_offs) {
+ if (_vm->_version == 1) {
+ if (_vm->_features & GF_NES) {
+ decodeNESGfx(roomptr);
+ } else {
+ for (int i = 0; i < 4; i++){
+ _C64.colors[i] = roomptr[6 + i];
+ }
+ decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 10), _C64.charMap, 2048);
+ decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 12), _C64.picMap, roomptr[4] * roomptr[5]);
+ decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 14), _C64.colorMap, roomptr[4] * roomptr[5]);
+ decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 16), _C64.maskMap, roomptr[4] * roomptr[5]);
+ decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 18) + 2, _C64.maskChar, READ_LE_UINT16(roomptr + READ_LE_UINT16(roomptr + 18)));
+ _objectMode = true;
+ }
+ } else if (_vm->_version == 2) {
+ _roomStrips = generateStripTable(roomptr + IM00_offs, _vm->_roomWidth, _vm->_roomHeight, _roomStrips);
+ }
+}
+
+
+#pragma mark -
+#pragma mark --- Virtual Screens ---
+#pragma mark -
+
+
void ScummEngine::initScreens(int b, int h) {
int i;
int adj = 0;
@@ -239,46 +284,6 @@ void ScummEngine::initScreens(int b, int h) {
_screenH = h;
gdi.init();
-
- const int size = _screenWidth * _screenHeight;
- free(_compositeBuf);
- free(_charset->_textSurface.pixels);
- free(_herculesBuf);
- _compositeBuf = (byte *)malloc(size);
- _charset->_textSurface.pixels = malloc(size);
- memset(_compositeBuf, CHARSET_MASK_TRANSPARENCY, size);
- memset(_charset->_textSurface.pixels, CHARSET_MASK_TRANSPARENCY, size);
-
- if (_renderMode == Common::kRenderHercA || _renderMode == Common::kRenderHercG) {
- _herculesBuf = (byte *)malloc(Common::kHercW * Common::kHercH);
- memset(_herculesBuf, CHARSET_MASK_TRANSPARENCY, Common::kHercW * Common::kHercH);
- }
-
- _charset->_textSurface.w = _screenWidth;
- _charset->_textSurface.h = _screenHeight;
- _charset->_textSurface.pitch = _screenWidth;
- _charset->_textSurface.bytesPerPixel = 1;
-
-}
-
-void Gdi::init() {
- _numStrips = _vm->_screenWidth / 8;
-
- // Increase the number of screen strips by one; needed for smooth scrolling
- if (_vm->_version >= 7) {
- // We now have mostly working smooth scrolling code in place for V7+ games
- // (i.e. The Dig, Full Throttle and COMI). It seems to work very well so far.
- // One area which still may need some work are the AKOS codecs (except for
- // codec 1, which I already updated): their masking code may need adjustments,
- // similar to the treatment codec 1 received.
- //
- // To understand how we achieve smooth scrolling, first note that with it, the
- // virtual screen strips don't match the display screen strips anymore. To
- // overcome that problem, we simply use a screen pitch that is 8 pixel wider
- // than the actual screen width, and always draw one strip more than needed to
- // the backbuf (of course we have to treat the right border seperately). This
- _numStrips += 1;
- }
}
void ScummEngine::initVirtScreen(VirtScreenNumber slot, int number, int top, int width, int height, bool twobufs,
@@ -812,7 +817,7 @@ void ScummEngine::redrawBGStrip(int start, int num) {
gdi._objectMode = false;
gdi.drawBitmap(room + _IM00_offs,
- &virtscr[0], s, 0, _roomWidth, virtscr[0].h, s, num, 0, _roomStrips);
+ &virtscr[0], s, 0, _roomWidth, virtscr[0].h, s, num, 0);
}
void ScummEngine::restoreBG(Common::Rect rect, byte backColor) {
@@ -1137,8 +1142,8 @@ void ScummEngine::setShake(int mode) {
#pragma mark -
-void Gdi::drawBitmapV2Helper(const byte *ptr, VirtScreen *vs, int x, int y, const int width, const int height, int stripnr, int numstrip, StripTable *table) {
-
+void Gdi::drawBitmapV2Helper(const byte *ptr, VirtScreen *vs, int x, int y, const int width, const int height, int stripnr, int numstrip) {
+ StripTable *table = (_objectMode ? 0 : _roomStrips);
const int left = (stripnr * 8);
const int right = left + (numstrip * 8);
byte *dst;
@@ -1318,7 +1323,7 @@ int Gdi::getZPlanes(const byte *ptr, const byte *zplane_list[9], bool bmapImage)
* and objects, used throughout all SCUMM versions.
*/
void Gdi::drawBitmap(const byte *ptr, VirtScreen *vs, int x, int y, const int width, const int height,
- int stripnr, int numstrip, byte flag, StripTable *table) {
+ int stripnr, int numstrip, byte flag) {
assert(ptr);
assert(height > 0);
byte *dstPtr;
@@ -1365,7 +1370,7 @@ void Gdi::drawBitmap(const byte *ptr, VirtScreen *vs, int x, int y, const int wi
// differently from all other (newer) graphic formats for this reason.
//
if (_vm->_version == 2)
- drawBitmapV2Helper(ptr, vs, x, y, width, height, stripnr, numstrip, table);
+ drawBitmapV2Helper(ptr, vs, x, y, width, height, stripnr, numstrip);
sx = x - vs->xstart / 8;
if (sx < 0) {
diff --git a/scumm/gfx.h b/scumm/gfx.h
index c1e70c005d..cde49b1ab1 100644
--- a/scumm/gfx.h
+++ b/scumm/gfx.h
@@ -199,6 +199,8 @@ struct BompDrawData {
struct StripTable;
+#define CHARSET_MASK_TRANSPARENCY 253
+
class Gdi {
friend class ScummEngine; // Mostly for the code in saveload.cpp ...
ScummEngine *_vm;
@@ -210,6 +212,7 @@ public:
int32 _numStrips;
Gdi(ScummEngine *vm);
+ ~Gdi();
protected:
byte *_roomPalette;
@@ -236,6 +239,9 @@ protected:
int _NESObj_x;
bool _NEShasmask;
+ /** For V2 games, we cache offsets into the room graphics, to speed up things. */
+ StripTable *_roomStrips;
+
/* Bitmap decompressors */
bool decompressBitmap(byte *dst, int dstPitch, const byte *src, int numLinesToProcess);
@@ -272,13 +278,14 @@ protected:
int getZPlanes(const byte *smap_ptr, const byte *zplane_list[9], bool bmapImage) const;
void drawBitmapV2Helper(const byte *ptr, VirtScreen *vs, int x, int y, const int width, const int height,
- int stripnr, int numstrip, StripTable *table);
+ int stripnr, int numstrip);
public:
void init();
+ void roomChanged(byte *roomptr, uint32 IM00_offs);
void drawBitmap(const byte *ptr, VirtScreen *vs, int x, int y, const int width, const int height,
- int stripnr, int numstrip, byte flag, StripTable *table = 0);
+ int stripnr, int numstrip, byte flag);
StripTable *generateStripTable(const byte *src, int width, int height, StripTable *table) const;
void decodeC64Gfx(const byte *src, byte *dst, int size) const;
diff --git a/scumm/saveload.cpp b/scumm/saveload.cpp
index 5d0a5daccb..de39f67cb6 100644
--- a/scumm/saveload.cpp
+++ b/scumm/saveload.cpp
@@ -284,22 +284,8 @@ bool ScummEngine::loadState(int slot, bool compat) {
setupV1ActorTalkColor();
// Regenerate strip table (for V1/V2 games)
- if (_version == 1) {
- roomptr = getResourceAddress(rtRoom, _roomResource);
- _IM00_offs = 0;
- for (i = 0; i < 4; i++){
- gdi._C64.colors[i] = roomptr[6 + i];
- }
- gdi.decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 10), gdi._C64.charMap, 2048);
- gdi.decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 12), gdi._C64.picMap, roomptr[4] * roomptr[5]);
- gdi.decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 14), gdi._C64.colorMap, roomptr[4] * roomptr[5]);
- gdi.decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 16), gdi._C64.maskMap, roomptr[4] * roomptr[5]);
- gdi.decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 18) + 2, gdi._C64.maskChar, READ_LE_UINT16(roomptr + READ_LE_UINT16(roomptr + 18)));
- gdi._objectMode = true;
- } else if (_version == 2) {
- _roomStrips = gdi.generateStripTable(getResourceAddress(rtRoom, _roomResource) + _IM00_offs,
- _roomWidth, _roomHeight, _roomStrips);
- }
+ roomptr = getResourceAddress(rtRoom, _roomResource);
+ gdi.roomChanged(roomptr, _IM00_offs);
if (!(_features & GF_NEW_CAMERA)) {
camera._last.x = camera._cur.x;
diff --git a/scumm/scumm.cpp b/scumm/scumm.cpp
index 28a8dc466d..308c627984 100644
--- a/scumm/scumm.cpp
+++ b/scumm/scumm.cpp
@@ -806,7 +806,6 @@ ScummEngine::ScummEngine(GameDetector *detector, OSystem *syst, const ScummGameS
_doEffect = false;
memset(&_flashlight, 0, sizeof(_flashlight));
- _roomStrips = 0;
_compositeBuf = 0;
_herculesBuf = 0;
_bompActorPalettePtr = NULL;
@@ -1127,6 +1126,12 @@ ScummEngine::ScummEngine(GameDetector *detector, OSystem *syst, const ScummGameS
_screenHeight = 200;
}
+ _compositeBuf = (byte *)malloc(_screenWidth * _screenHeight);
+
+ if (_renderMode == Common::kRenderHercA || _renderMode == Common::kRenderHercG) {
+ _herculesBuf = (byte *)malloc(Common::kHercW * Common::kHercH);
+ }
+
_midi = gs.midi;
}
@@ -1169,9 +1174,11 @@ ScummEngine::~ScummEngine() {
free(_classData);
free(_arraySlot);
- free(_roomStrips);
free(_languageIndex);
+ free(_compositeBuf);
+ free(_herculesBuf);
+
delete _debugger;
}
@@ -2304,24 +2311,9 @@ void ScummEngine::initRoomSubBlocks() {
// Find the room image data
//
if (_version == 1) {
- if (_features & GF_NES) {
- gdi.decodeNESGfx(roomptr);
- } else {
- _IM00_offs = 0;
- for (i = 0; i < 4; i++){
- gdi._C64.colors[i] = roomptr[6 + i];
- }
- gdi.decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 10), gdi._C64.charMap, 2048);
- gdi.decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 12), gdi._C64.picMap, roomptr[4] * roomptr[5]);
- gdi.decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 14), gdi._C64.colorMap, roomptr[4] * roomptr[5]);
- gdi.decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 16), gdi._C64.maskMap, roomptr[4] * roomptr[5]);
- gdi.decodeC64Gfx(roomptr + READ_LE_UINT16(roomptr + 18) + 2, gdi._C64.maskChar, READ_LE_UINT16(roomptr + READ_LE_UINT16(roomptr + 18)));
- gdi._objectMode = true;
- }
+ _IM00_offs = 0;
} else if (_features & GF_OLD_BUNDLE) {
_IM00_offs = READ_LE_UINT16(roomptr + 0x0A);
- if (_version == 2)
- _roomStrips = gdi.generateStripTable(roomptr + _IM00_offs, _roomWidth, _roomHeight, _roomStrips);
} else if (_version == 8) {
_IM00_offs = getObjectImage(roomptr, 1) - roomptr;
} else if (_features & GF_SMALL_HEADER) {
@@ -2332,6 +2324,7 @@ void ScummEngine::initRoomSubBlocks() {
} else {
_IM00_offs = findResource(MKID('IM00'), findResource(MKID('RMIM'), roomptr)) - roomptr;
}
+ gdi.roomChanged(roomptr, _IM00_offs);
//
// Look for an exit script
diff --git a/scumm/scumm.h b/scumm/scumm.h
index 7b324e3df7..69611abed4 100644
--- a/scumm/scumm.h
+++ b/scumm/scumm.h
@@ -891,8 +891,6 @@ protected:
uint32 _CLUT_offs, _EPAL_offs;
uint32 _IM00_offs, _PALS_offs;
- StripTable *_roomStrips;
-
//ender: fullscreen
bool _fullRedraw, _bgNeedsRedraw;
bool _screenEffectFlag, _completeScreenRedraw;