aboutsummaryrefslogtreecommitdiff
path: root/engines/scumm/gfx.cpp
diff options
context:
space:
mode:
authorEugene Sandulenko2007-07-10 00:39:12 +0000
committerEugene Sandulenko2007-07-10 00:39:12 +0000
commit1db83059b0a33f910c1d2f78630dccde2dd167b9 (patch)
tree174f1a8e6527c70bd968cd8165b04ae491375248 /engines/scumm/gfx.cpp
parentaaa987201ee15fcb48ad349911e9e41655a001dc (diff)
downloadscummvm-rg350-1db83059b0a33f910c1d2f78630dccde2dd167b9.tar.gz
scummvm-rg350-1db83059b0a33f910c1d2f78630dccde2dd167b9.tar.bz2
scummvm-rg350-1db83059b0a33f910c1d2f78630dccde2dd167b9.zip
Preliminary (and buggy) Kanji support.
svn-id: r27998
Diffstat (limited to 'engines/scumm/gfx.cpp')
-rw-r--r--engines/scumm/gfx.cpp135
1 files changed, 112 insertions, 23 deletions
diff --git a/engines/scumm/gfx.cpp b/engines/scumm/gfx.cpp
index c70a0e9351..3c6f57be1a 100644
--- a/engines/scumm/gfx.cpp
+++ b/engines/scumm/gfx.cpp
@@ -561,8 +561,25 @@ void ScummEngine::drawStripToScreen(VirtScreen *vs, int x, int width, int top, i
return;
const byte *src = vs->getPixels(x, top);
+ int m = _textSurfaceMultiplier;
+ byte *dst;
+ int vsPitch;
int pitch = vs->pitch;
+ if (_useCJKMode && _textSurfaceMultiplier == 2) {
+ dst = _fmtownsBuf;
+
+ scale2x(dst, _screenWidth * m, src, vs->pitch, width, height);
+ src = dst;
+
+ vsPitch = _screenWidth * m - width * m;
+
+ } else {
+ vsPitch = vs->pitch - width;
+ }
+
+ dst = _compositeBuf;
+
if (_game.version < 7) {
// For The Dig, FT and COMI, we just blit everything to the screen at once.
// For older games, things are more complicated. First off, we need to
@@ -572,7 +589,7 @@ void ScummEngine::drawStripToScreen(VirtScreen *vs, int x, int width, int top, i
// Compute pointer to the text surface
assert(_compositeBuf);
- const byte *text = (byte *)_textSurface.getBasePtr(x, y);
+ const byte *text = (byte *)_textSurface.getBasePtr(x * m, y * m);
// The values x, width, etc. are all multiples of 8 at this point,
// so loop unrolloing might be a good idea...
@@ -594,19 +611,18 @@ void ScummEngine::drawStripToScreen(VirtScreen *vs, int x, int width, int top, i
// but also more complicated to implement, and incurs a bigger overhead when
// writing to the text surface.
#ifdef __DS__
- DS::asmDrawStripToScreen(height, width, text, src, _compositeBuf, vs->pitch, width, _textSurface.pitch);
+ DS::asmDrawStripToScreen(height, width, text, src, dst, vs->pitch, width, _textSurface.pitch);
#else
- byte *dst = _compositeBuf;
- for (int h = 0; h < height; ++h) {
- for (int w = 0; w < width; ++w) {
+ for (int h = 0; h < height * m; ++h) {
+ for (int w = 0; w < width * m; ++w) {
byte tmp = *text++;
if (tmp == CHARSET_MASK_TRANSPARENCY)
tmp = *src;
*dst++ = tmp;
src++;
}
- src += vs->pitch - width;
- text += _textSurface.pitch - width;
+ src += vsPitch;
+ text += _textSurface.pitch - width * m;
}
#endif
@@ -621,6 +637,12 @@ void ScummEngine::drawStripToScreen(VirtScreen *vs, int x, int width, int top, i
// center image on the screen
x += (Common::kHercW - _screenWidth * 2) / 2; // (720 - 320*2)/2 = 40
+ } else if (_useCJKMode && m == 2) {
+ pitch *= m;
+ x *= m;
+ y *= m;
+ width *= m;
+ height *= m;
} else {
if (_renderMode == Common::kRenderCGA)
ditherCGA(_compositeBuf, width, x, y, width, height);
@@ -721,6 +743,25 @@ void ditherHerc(byte *src, byte *hercbuf, int srcPitch, int *x, int *y, int *wid
*height = dsty - *y;
}
+void ScummEngine::scale2x(byte *dst, int dstPitch, const byte *src, int srcPitch, int w, int h) {
+ byte *dstL1 = dst;
+ byte *dstL2 = dst + dstPitch;
+
+ int dstAdd = dstPitch * 2 - w * 2;
+ int srcAdd = srcPitch - w;
+
+ while (h--) {
+ for (int x = 0; x < w; ++x, dstL1 += 2, dstL2 += 2) {
+ uint16 col = *src++;
+ col |= col << 8;
+ *(uint16*)(dstL1) = col;
+ *(uint16*)(dstL2) = col;
+ }
+ dstL1 += dstAdd; dstL2 += dstAdd;
+ src += srcAdd;
+ }
+}
+
#pragma mark -
#pragma mark --- Background buffers & charset mask ---
@@ -1117,8 +1158,8 @@ void ScummEngine::drawBox(int x, int y, int x2, int y2, int color) {
error("can only copy bg to main window");
blit(backbuff, vs->pitch, bgbuff, vs->pitch, width, height);
if (_charset->_hasMask) {
- byte *mask = (byte *)_textSurface.getBasePtr(x, y - _screenTop);
- fill(mask, _textSurface.pitch, CHARSET_MASK_TRANSPARENCY, width, height);
+ byte *mask = (byte *)_textSurface.getBasePtr(x * _textSurfaceMultiplier, (y - _screenTop) * _textSurfaceMultiplier);
+ fill(mask, _textSurface.pitch, CHARSET_MASK_TRANSPARENCY, width * _textSurfaceMultiplier, height * _textSurfaceMultiplier);
}
} else if (_game.heversion >= 71) {
// Flags are used for different methods in HE games
@@ -3362,7 +3403,17 @@ void ScummEngine::dissolveEffect(int width, int height) {
for (i = 0; i < w * h; i++) {
x = offsets[i] % vs->pitch;
y = offsets[i] / vs->pitch;
- _system->copyRectToScreen(vs->getPixels(x, y), vs->pitch, x, y + vs->topline, width, height);
+
+ if (_useCJKMode && _textSurfaceMultiplier == 2) {
+ int m = _textSurfaceMultiplier;
+ byte *dst = _fmtownsBuf + x * m + y * m * _screenWidth * m;
+ scale2x(dst, _screenWidth * m, vs->getPixels(x, y), vs->pitch, width, height);
+
+ _system->copyRectToScreen(dst, _screenWidth * m, x * m, (y + vs->topline) * m, width * m, height * m);
+ } else {
+ _system->copyRectToScreen(vs->getPixels(x, y), vs->pitch, x, y + vs->topline, width, height);
+ }
+
if (++blits >= blits_before_refresh) {
blits = 0;
@@ -3391,16 +3442,30 @@ void ScummEngine::scrollEffect(int dir) {
step = (step * delay) / kScrolltime;
+ byte *src;
+ int m = _textSurfaceMultiplier;
+ int vsPitch = vs->pitch;
+
switch (dir) {
case 0:
//up
y = 1 + step;
while (y < vs->h) {
moveScreen(0, -step, vs->h);
- _system->copyRectToScreen(vs->getPixels(0, y - step),
- vs->pitch,
- 0, vs->h - step,
- vs->w, step);
+
+ src = vs->getPixels(0, y - step);
+ if (_useCJKMode && m == 2) {
+ int x1 = 0, y1 = vs->h - step;
+ byte *dst = _fmtownsBuf + x1 * m + y1 * m * _screenWidth * m;
+ scale2x(dst, _screenWidth * m, src, vs->pitch, vs->w, step);
+ src = dst;
+ vsPitch = _screenWidth * 2;
+ }
+
+ _system->copyRectToScreen(src,
+ vsPitch,
+ 0 * m, (vs->h - step) * m,
+ vs->w * m, step * m);
_system->updateScreen();
waitForTimer(delay);
@@ -3412,10 +3477,18 @@ void ScummEngine::scrollEffect(int dir) {
y = 1 + step;
while (y < vs->h) {
moveScreen(0, step, vs->h);
- _system->copyRectToScreen(vs->getPixels(0, vs->h - y),
- vs->pitch,
+ src = vs->getPixels(0, vs->h - y);
+ if (_useCJKMode && m == 2) {
+ int x1 = 0, y1 = 0;
+ byte *dst = _fmtownsBuf + x1 * m + y1 * m * _screenWidth * m;
+ scale2x(dst, _screenWidth * m, src, vs->pitch, vs->w, step);
+ src = dst;
+ vsPitch = _screenWidth * 2;
+ }
+ _system->copyRectToScreen(src,
+ vsPitch,
0, 0,
- vs->w, step);
+ vs->w * m, step * m);
_system->updateScreen();
waitForTimer(delay);
@@ -3427,10 +3500,18 @@ void ScummEngine::scrollEffect(int dir) {
x = 1 + step;
while (x < vs->w) {
moveScreen(-step, 0, vs->h);
- _system->copyRectToScreen(vs->getPixels(x - step, 0),
- vs->pitch,
- vs->w - step, 0,
- step, vs->h);
+ src = vs->getPixels(x - step, 0);
+ if (_useCJKMode && m == 2) {
+ int x1 = vs->w - step, y1 = 0;
+ byte *dst = _fmtownsBuf + x1 * m + y1 * m * _screenWidth * m;
+ scale2x(dst, _screenWidth * m, src, vs->pitch, step, vs->h);
+ src = dst;
+ vsPitch = _screenWidth * 2;
+ }
+ _system->copyRectToScreen(src,
+ vsPitch,
+ (vs->w - step) * m, 0,
+ step * m, vs->h * m);
_system->updateScreen();
waitForTimer(delay);
@@ -3442,8 +3523,16 @@ void ScummEngine::scrollEffect(int dir) {
x = 1 + step;
while (x < vs->w) {
moveScreen(step, 0, vs->h);
- _system->copyRectToScreen(vs->getPixels(vs->w - x, 0),
- vs->pitch,
+ src = vs->getPixels(vs->w - x, 0);
+ if (_useCJKMode && m == 2) {
+ int x1 = 0, y1 = 0;
+ byte *dst = _fmtownsBuf + x1 * m + y1 * m * _screenWidth * m;
+ scale2x(dst, _screenWidth * m, src, vs->pitch, step, vs->h);
+ src = dst;
+ vsPitch = _screenWidth * 2;
+ }
+ _system->copyRectToScreen(src,
+ vsPitch,
0, 0,
step, vs->h);
_system->updateScreen();