diff --git a/engines/prince/graphics.cpp b/engines/prince/graphics.cpp index 49cc88c8ae17..298337673fba 100644 --- a/engines/prince/graphics.cpp +++ b/engines/prince/graphics.cpp @@ -24,6 +24,8 @@ #include "prince/prince.h" +#include "prince/mhwanh.h" + #include "graphics/palette.h" #include "common/memstream.h" @@ -89,6 +91,29 @@ void GraphicsMan::drawTransparentSurface(int32 posX, int32 posY, const Graphics: change(); } +void GraphicsMan::drawTransparentWithBlend(int32 posX, int32 posY, const Graphics::Surface *s, int transColor) { + _blendTable = new byte[256]; + for (int i = 0; i < 256; i++) { + _blendTable[i] = 255; + } + for (int y = 0; y < s->h; y++) { + for (int x = 0; x < s->w; x++) { + byte pixel = *((byte*)s->getBasePtr(x, y)); + if (pixel != transColor) { + if (x + posX < _frontScreen->w && x + posX >= 0) { + if (y + posY < _frontScreen->h && y + posY >= 0) { + byte backgroundPixel = *((byte*)_frontScreen->getBasePtr(x + posX, y + posY)); + byte blendPixel = getBlendTableColor(pixel, backgroundPixel); + *((byte*)_frontScreen->getBasePtr(x + posX, y + posY)) = blendPixel; + } + } + } + } + } + delete _blendTable; + change(); +} + void GraphicsMan::drawTransparent(Graphics::Surface *frontScreen, DrawNode *drawNode) { for (int y = 0; y < drawNode->s->h; y++) { for (int x = 0; x < drawNode->s->w; x++) { @@ -147,6 +172,103 @@ void GraphicsMan::drawAsShadow(Graphics::Surface *frontScreen, DrawNode *drawNod } } +byte GraphicsMan::getBlendTableColor(byte pixelColor, byte backgroundPixelColor) { + int32 redFirstOrg, greenFirstOrg, blueFirstOrg; + int32 redFirstBack, greenFirstBack, blueFirstBack; + int32 redSecondOrg, greenSecondOrg, blueSecondOrg; + int32 redNew, greenNew, blueNew; + + int32 sumOfColorValues; + int32 bigValue; + int32 currColor; + + if (_blendTable[pixelColor] != 255) { + currColor = _blendTable[pixelColor]; + } else { + const byte *originalPalette = _vm->_roomBmp->getPalette(); //? + const byte *suitcasePalette = _vm->_suitcaseBmp->getPalette(); //? + + //debug("backgroundPixelColor: %d", backgroundPixelColor); + //debug("orgpalette: %d", pixelColor); + //debug("mst_shadow: %d", _vm->_mst_shadow); + + redFirstOrg = originalPalette[pixelColor * 4] * _vm->_mst_shadow / 256; + if (redFirstOrg >= 256) { + redFirstOrg = 255; + } + if (_vm->_mst_shadow <= 256) { + redFirstBack = suitcasePalette[backgroundPixelColor * 4] * (256 - _vm->_mst_shadow) / 256; + if (redFirstBack >= 256) { + redFirstBack = 255; + } + redFirstOrg += redFirstBack; + if (redFirstOrg >= 256) { + redFirstOrg = 255; + } + } + + greenFirstOrg = originalPalette[pixelColor * 4 + 1] * _vm->_mst_shadow / 256; + if (greenFirstOrg >= 256) { + greenFirstOrg = 255; + } + if (_vm->_mst_shadow <= 256) { + greenFirstBack = suitcasePalette[backgroundPixelColor * 4 + 1] * (256 - _vm->_mst_shadow) / 256; + if (greenFirstBack >= 256) { + greenFirstBack = 255; + } + greenFirstOrg += greenFirstBack; + if (greenFirstOrg >= 256) { + greenFirstOrg = 255; + } + } + + blueFirstOrg = originalPalette[pixelColor * 4 + 2] * _vm->_mst_shadow / 256; + if (blueFirstOrg >= 256) { + blueFirstOrg = 255; + } + if (_vm->_mst_shadow <= 256) { + blueFirstBack = suitcasePalette[backgroundPixelColor * 4 + 2] * (256 - _vm->_mst_shadow) / 256; + if (blueFirstBack >= 256) { + blueFirstBack = 255; + } + blueFirstOrg += blueFirstBack; + if (blueFirstOrg >= 256) { + blueFirstOrg = 255; + } + } + + currColor = 0; + bigValue = 999999999; // infinity + for (int j = 0; j < 256; j++) { + redSecondOrg = originalPalette[3 * j]; + redNew = redFirstOrg - redSecondOrg; + redNew = redNew * redNew; + + greenSecondOrg = originalPalette[3 * j + 1]; + greenNew = greenFirstOrg - greenSecondOrg; + greenNew = greenNew * greenNew; + + blueSecondOrg = originalPalette[3 * j + 2]; + blueNew = blueFirstOrg - blueSecondOrg; + blueNew = blueNew * blueNew; + + sumOfColorValues = redNew + greenNew + blueNew; + + if (sumOfColorValues < bigValue) { + bigValue = sumOfColorValues; + currColor = j; + } + + if (sumOfColorValues == 0) { + break; + } + } + _blendTable[pixelColor] = currColor; + } + //debug("currColor: %d", currColor); + return currColor; +} + void GraphicsMan::makeShadowTable(int brightness, byte *shadowPalette) { int32 redFirstOrg, greenFirstOrg, blueFirstOrg; int32 redSecondOrg, greenSecondOrg, blueSecondOrg; diff --git a/engines/prince/graphics.h b/engines/prince/graphics.h index cd3d8b4f354d..7651dae7a196 100644 --- a/engines/prince/graphics.h +++ b/engines/prince/graphics.h @@ -30,6 +30,7 @@ namespace Prince { class PrinceEngine; struct DrawNode; +class MhwanhDecoder; class GraphicsMan { @@ -46,11 +47,14 @@ class GraphicsMan void draw(uint16 x, uint16 y, const Graphics::Surface *s); void drawTransparentSurface(int32 posX, int32 poxY, const Graphics::Surface *s, int transColor); + void drawTransparentWithBlend(int32 posX, int32 poxY, const Graphics::Surface *s, int transColor); static void drawTransparent(Graphics::Surface *frontScreen, DrawNode *drawNode); static void drawAsShadow(Graphics::Surface *frontScreen, DrawNode *drawNode); static void drawMask(Graphics::Surface *frontScreen, DrawNode *drawNode); + byte getBlendTableColor(byte pixelColor, byte backgroundPixelColor); + Graphics::Surface *_frontScreen; Graphics::Surface *_backScreen; const Graphics::Surface *_roomBackground; @@ -60,6 +64,8 @@ class GraphicsMan static const byte kShadowColor = 191; + byte *_blendTable; + private: PrinceEngine *_vm; diff --git a/engines/prince/prince.cpp b/engines/prince/prince.cpp index 7a716fd98a7c..a0405c76db36 100644 --- a/engines/prince/prince.cpp +++ b/engines/prince/prince.cpp @@ -1398,9 +1398,10 @@ void PrinceEngine::drawInvItems() { drawY += (_maxInvH - itemSurface->h) / 2; } if (!_mst_shadow) { - _graph->drawTransparentSurface(drawX, drawY, itemSurface, 0); //TODO - ShowSprite0 + _graph->drawTransparentSurface(drawX, drawY, itemSurface, 0); } else { - _graph->drawTransparentSurface(drawX, drawY, itemSurface, 0); //TODO - ShowSprite01 + _mst_shadow = _mst_shadow2; + _graph->drawTransparentWithBlend(drawX, drawY, itemSurface, 0); //TODO - ShowSprite01 } } else { // candle item: @@ -1418,11 +1419,8 @@ void PrinceEngine::displayInventory() { // temp: _mainHero->_inventory.clear(); _mainHero->_inventory.push_back(0); - _mainHero->_inventory.push_back(1); _mainHero->_inventory.push_back(2); - _mainHero->_inventory.push_back(3); - _mainHero->_inventory.push_back(4); - _mainHero->_inventory.push_back(5); + _mainHero->_inventory.push_back(1); prepareInventoryToView(); diff --git a/engines/prince/prince.h b/engines/prince/prince.h index 1694286f5407..71512f0d8ade 100644 --- a/engines/prince/prince.h +++ b/engines/prince/prince.h @@ -254,6 +254,7 @@ class PrinceEngine : public Engine { int32 _picWindowX; int32 _picWindowY; Image::BitmapDecoder *_roomBmp; + MhwanhDecoder *_suitcaseBmp; Common::Array _animList; Common::Array _backAnimList; @@ -330,7 +331,6 @@ class PrinceEngine : public Engine { Common::RandomSource *_rnd; Cursor *_cursor1; Cursor *_cursor2; - MhwanhDecoder *_suitcaseBmp; Debugger *_debugger; GraphicsMan *_graph; Script *_script;