From e6d04b8ad61200716e376533bb075f8891739c20 Mon Sep 17 00:00:00 2001 From: Sven Hesse Date: Sun, 16 Jan 2011 22:29:49 +0000 Subject: GOB: Adding a proper shade method svn-id: r55273 --- engines/gob/draw_v2.cpp | 14 ++++++++++--- engines/gob/surface.cpp | 55 +++++++++++++++++++++++++++++++++++++++++++++++++ engines/gob/surface.h | 3 +++ 3 files changed, 69 insertions(+), 3 deletions(-) diff --git a/engines/gob/draw_v2.cpp b/engines/gob/draw_v2.cpp index 77ecd96f16..e31b1f8269 100644 --- a/engines/gob/draw_v2.cpp +++ b/engines/gob/draw_v2.cpp @@ -735,9 +735,17 @@ void Draw_v2::spriteOperation(int16 operation) { break; case DRAW_FILLRECT: - _spritesArray[_destSurface]->fillRect(destSpriteX, - _destSpriteY, _destSpriteX + _spriteRight - 1, - _destSpriteY + _spriteBottom - 1, getColor(_backColor)); + if (!(_backColor & 0xFF00) || !(_backColor & 0x0100)) { + _spritesArray[_destSurface]->fillRect(destSpriteX, + _destSpriteY, _destSpriteX + _spriteRight - 1, + _destSpriteY + _spriteBottom - 1, getColor(_backColor)); + } else { + uint8 strength = 16 - (((uint16) _backColor) >> 12); + + _spritesArray[_destSurface]->shadeRect(destSpriteX, + _destSpriteY, _destSpriteX + _spriteRight - 1, + _destSpriteY + _spriteBottom - 1, getColor(_backColor), strength); + } dirtiedRect(_destSurface, _destSpriteX, _destSpriteY, _destSpriteX + _spriteRight - 1, _destSpriteY + _spriteBottom - 1); diff --git a/engines/gob/surface.cpp b/engines/gob/surface.cpp index fa2d9cf9ab..673d8b3a19 100644 --- a/engines/gob/surface.cpp +++ b/engines/gob/surface.cpp @@ -489,6 +489,61 @@ void Surface::clear() { fill(0); } +void Surface::shadeRect(uint16 left, uint16 top, uint16 right, uint16 bottom, + uint32 color, uint8 strength) { + + if (_bpp == 1) { + // We can't properly shade in paletted mode, fill the rect instead + fillRect(left, top, right, bottom, color); + return; + } + + // Just in case those are swapped + if (left > right) + SWAP(left, right); + if (top > bottom) + SWAP(top, bottom); + + if ((left >= _width) || (top >= _height)) + // Nothing to do + return; + + // Area to actually shade + uint16 width = CLIP(right - left + 1, 0, _width - left); + uint16 height = CLIP(bottom - top + 1, 0, _height - top); + + if ((width == 0) || (height == 0)) + // Nothing to do + return; + + Graphics::PixelFormat pixelFormat = g_system->getScreenFormat(); + + uint8 cR, cG, cB; + pixelFormat.colorToRGB(color, cR, cG, cB); + + int shadeR = cR * (16 - strength); + int shadeG = cG * (16 - strength); + int shadeB = cB * (16 - strength); + + Pixel p = get(left, top); + while (height-- > 0) { + for (uint16 i = 0; i < width; i++, ++p) { + uint8 r, g, b; + + pixelFormat.colorToRGB(p.get(), r, g, b); + + r = CLIP((shadeR + strength * r) >> 4, 0, 255); + g = CLIP((shadeG + strength * g) >> 4, 0, 255); + b = CLIP((shadeB + strength * b) >> 4, 0, 255); + + p.set(pixelFormat.RGBToColor(r, g, b)); + } + + p += _width - width; + } + +} + void Surface::putPixel(uint16 x, uint16 y, uint32 color) { if ((x >= _width) || (y >= _height)) return; diff --git a/engines/gob/surface.h b/engines/gob/surface.h index b22bfb9222..89e91975a2 100644 --- a/engines/gob/surface.h +++ b/engines/gob/surface.h @@ -108,6 +108,9 @@ public: void fill(uint32 color); void clear(); + void shadeRect(uint16 left, uint16 top, uint16 right, uint16 bottom, + uint32 color, uint8 strength); + void putPixel(uint16 x, uint16 y, uint32 color); void drawLine(uint16 x0, uint16 y0, uint16 x1, uint16 y1, uint32 color); void drawCircle(uint16 x0, uint16 y0, uint16 radius, uint32 color, int16 pattern = 0); -- cgit v1.2.3