diff options
-rw-r--r-- | engines/voyeur/files.cpp | 235 | ||||
-rw-r--r-- | engines/voyeur/files.h | 22 | ||||
-rw-r--r-- | engines/voyeur/graphics.cpp | 33 | ||||
-rw-r--r-- | engines/voyeur/graphics.h | 23 | ||||
-rw-r--r-- | engines/voyeur/voyeur.cpp | 4 |
5 files changed, 297 insertions, 20 deletions
diff --git a/engines/voyeur/files.cpp b/engines/voyeur/files.cpp index 74da77dda1..cfc82ddc67 100644 --- a/engines/voyeur/files.cpp +++ b/engines/voyeur/files.cpp @@ -795,10 +795,222 @@ void ViewPortResource::setupViewPort() { &GraphicsManager::restoreMCGASaveRect); } -void ViewPortResource::drawText(const Common::String &msg) { +int ViewPortResource::drawText(const Common::String &msg) { + GraphicsManager &gfxManager = _state._vm->_graphicsManager; + FontInfo &fontInfo = *gfxManager._fontPtr; + FontResource &fontData = *fontInfo._curFont; + int xShadows[9] = { 0, 1, 1, 1, 0, -1, -1, -1, 0 }; + int yShadows[9] = { 0, 1, 0, -1, -1, -1, 0, 1, 1 }; + + Common::Rect *clipPtr = gfxManager._clipPtr; + if (!(fontInfo._picFlags & 1)) + gfxManager._clipPtr = NULL; + + int minChar = fontData._minChar; + int padding = fontData._padding; + int fontHeight = fontData._fontHeight; + int totalChars = fontData._maxChar - fontData._minChar; + int msgWidth = 0; + int xp = 0, yp = 0; + + Common::Point pos = fontInfo._pos; + + _fontChar._flags = fontInfo._picFlags | 2; + _fontChar._select = fontInfo._picSelect; + _fontChar._bounds.setHeight(fontHeight); + + if (gfxManager._drawTextPermFlag || (fontInfo._fontFlags & 1) || fontInfo._justify || + (gfxManager._saveBack && fontInfo._fontSaveBack && (_flags & 0x8000))) { + msgWidth = textWidth(msg); + yp = pos.y; + xp = pos.x; + + switch (fontInfo._justify) { + case 1: + xp = pos.x + (fontInfo._justifyWidth / 2) - (msgWidth / 2); + break; + case 2: + xp = pos.x + fontInfo._justifyWidth - msgWidth; + break; + default: + break; + } + + if (!(fontInfo._fontFlags & 3)) { + _fontRect.left = xp; + _fontRect.top = yp; + _fontRect.setWidth(msgWidth); + _fontRect.setHeight(fontHeight); + } else { + _fontRect.left = pos.x; + _fontRect.top = pos.y; + _fontRect.setWidth(fontInfo._justifyWidth); + _fontRect.setHeight(fontInfo._justifyHeight); + } + + pos.x = xp; + pos.y = yp; + + if (fontInfo._fontFlags & 4) { + if (fontInfo._shadow.x <= 0) { + _fontRect.left += fontInfo._shadow.x; + _fontRect.right -= fontInfo._shadow.x * 2; + } else { + _fontRect.right += fontInfo._shadow.x; + } + + if (fontInfo._shadow.y <= 0) { + _fontRect.top += fontInfo._shadow.y; + _fontRect.bottom -= fontInfo._shadow.y * 2; + } else { + _fontRect.bottom += fontInfo._shadow.y; + } + } else if (fontInfo._fontFlags & 8) { + if (fontInfo._shadow.x <= 0) { + _fontRect.left += fontInfo._shadow.x; + _fontRect.right -= fontInfo._shadow.x * 3; + } else { + _fontRect.right += fontInfo._shadow.x * 3; + _fontRect.left -= fontInfo._shadow.x; + } + + if (fontInfo._shadow.y <= 0) { + _fontRect.top += fontInfo._shadow.y; + _fontRect.bottom -= fontInfo._shadow.y * 3; + } else { + _fontRect.bottom += fontInfo._shadow.y * 3; + _fontRect.top -= fontInfo._shadow.y; + } + } + } + + if (gfxManager._saveBack && fontInfo._fontSaveBack && (_flags & 0x8000)) { + addSaveRect(_pageIndex, _fontRect); + } + + if (fontInfo._fontFlags & 1) { + gfxManager._drawPtr->_pos = Common::Point(_fontRect.left, _fontRect.top); + gfxManager._drawPtr->_penColor = fontInfo._backColor; + sFillBox(_fontRect.width()); + } + + bool saveBack = gfxManager._saveBack; + gfxManager._saveBack = false; + + int count = 0; + if (!(fontInfo._fontFlags & 4)) + count = 1; + else if (fontInfo._fontFlags & 8) + count = 8; + + for (int i = 0; i < count; ++i) { + xp = pos.x; + yp = pos.y; + + switch (xShadows[i]) { + case -1: + xp -= fontInfo._shadow.x; + break; + case 1: + xp += fontInfo._shadow.x; + break; + default: + break; + } + + switch (yShadows[i]) { + case -1: + yp -= fontInfo._shadow.y; + break; + case 1: + yp += fontInfo._shadow.y; + break; + default: + break; + } + + if (i == 0) { + _fontChar._pick = 0; + _fontChar._onOff = fontInfo._shadowColor; + } else if (fontData.field2 == 1 || (fontInfo._fontFlags & 0x10)) { + _fontChar._pick = 0; + _fontChar._onOff = fontInfo._foreColor; + } else { + _fontChar._pick = fontInfo._picPick; + _fontChar._onOff = fontInfo._picOnOff; + _fontChar._depth = fontData.field2; + } + + // Loop to draw each character in turn + msgWidth = -padding; + const char *msgP = msg.c_str(); + char ch; + + while ((ch = *msgP++) != '\0') { + int charValue = (int)ch - minChar; + if (charValue >= totalChars || fontData._charWidth[charValue] == 0) + charValue = fontData._maxChar - minChar; + + int charWidth = fontData._charWidth[charValue]; + _fontChar._bounds.setWidth(charWidth); + + uint16 offset = READ_LE_UINT16(fontData._data1 + charValue * 2); + _fontChar._imgData = fontData._data2 + offset * 2; + + gfxManager.sDrawPic(&_fontChar, this, Common::Point(xp, yp)); + + xp += charWidth + padding; + msgWidth += charWidth + padding; + } + } + + msgWidth = MAX(msgWidth, 0); + if (fontInfo._justify == ALIGN_LEFT) + fontInfo._pos.x = xp; + + gfxManager._saveBack = saveBack; + gfxManager._clipPtr = clipPtr; + + return msgWidth; +} + +int ViewPortResource::textWidth(const Common::String &msg) { + if (msg.size() == 0) + return 0; + + const char *msgP = msg.c_str(); + FontResource &fontData = *_state._vm->_graphicsManager._fontPtr->_curFont; + int minChar = fontData._minChar; + int maxChar = fontData._maxChar; + int padding = fontData._padding; + int totalWidth = -padding; + char ch; + + // Loop through the characters + while ((ch = *msgP++) != '\0') { + int charValue = (int)ch; + if (charValue < minChar || charValue > maxChar) + charValue = maxChar; + + if (!fontData._charWidth[charValue - minChar]) + charValue = maxChar; + + totalWidth += fontData._charWidth[charValue - minChar] + padding; + } + + if (totalWidth < 0) + totalWidth = 0; + return totalWidth; +} + +void ViewPortResource::addSaveRect(int pageIndex, const Common::Rect &r) { // TODO } +void ViewPortResource::sFillBox(int width) { + +} + /*------------------------------------------------------------------------*/ ViewPortListResource::ViewPortListResource(BoltFilesState &state, const byte *src) { @@ -837,8 +1049,25 @@ ViewPortPalEntry::ViewPortPalEntry(const byte *src) { /*------------------------------------------------------------------------*/ -FontResource::FontResource(BoltFilesState &state, const byte *src) { - state._curLibPtr->resolveIt(READ_LE_UINT32(src + 0xC), &_fieldC); +FontResource::FontResource(BoltFilesState &state, byte *src) { + _minChar = src[0]; + _maxChar = src[1]; + field2 = src[2]; + _padding = src[3]; + _fontHeight = src[5]; + field6 = src[6]; + + int totalChars = _maxChar - _minChar + 1; + _charWidth = new int[totalChars]; + for (int i = 0; i < totalChars; ++i) + _charWidth[i] = READ_LE_UINT16(src + 8 + 2 * i); + + _data1 = src + 8 + totalChars * 2; + _data2 = _data1 + totalChars * 2; +} + +FontResource::~FontResource() { + delete[] _charWidth; } /*------------------------------------------------------------------------*/ diff --git a/engines/voyeur/files.h b/engines/voyeur/files.h index 4d3c2039c5..499cbb8972 100644 --- a/engines/voyeur/files.h +++ b/engines/voyeur/files.h @@ -252,12 +252,17 @@ public: ViewPortSetupPtr _setupFn; ViewPortAddPtr _addFn; ViewPortRestorePtr _restoreFn; + PictureResource _fontChar; + Common::Rect _fontRect; public: ViewPortResource(BoltFilesState &state, const byte *src); virtual ~ViewPortResource(); void setupViewPort(); - void drawText(const Common::String &msg); + int drawText(const Common::String &msg); + int textWidth(const Common::String &msg); + void addSaveRect(int pageIndex, const Common::Rect &r); + void sFillBox(int width); }; class ViewPortPalEntry { @@ -281,10 +286,17 @@ public: class FontResource { public: - byte *_fieldC; - - FontResource(BoltFilesState &state, const byte *src); - virtual ~FontResource() {} + int _minChar, _maxChar; + int field2; + int _padding; + int _fontHeight; + int field6; + int *_charWidth; + byte *_data1; + byte *_data2; + + FontResource(BoltFilesState &state, byte *src); + virtual ~FontResource(); }; class CMapResource { diff --git a/engines/voyeur/graphics.cpp b/engines/voyeur/graphics.cpp index ace4b35718..fda7c833f7 100644 --- a/engines/voyeur/graphics.cpp +++ b/engines/voyeur/graphics.cpp @@ -36,7 +36,7 @@ FontInfo::FontInfo() { _picPick = 0xff; _picOnOff = 0; _fontFlags = 0; - _justify = 0; + _justify = ALIGN_LEFT; _fontSaveBack = 0; _justifyWidth = 1; _justifyHeight = 1; @@ -47,7 +47,7 @@ FontInfo::FontInfo() { } FontInfo::FontInfo(byte picFlags, byte picSelect, byte picPick, byte picOnOff, byte fontFlags, - byte justify, int fontSaveBack, const Common::Point &pos, int justifyWidth, int justifyHeight, + FontJustify justify, int fontSaveBack, const Common::Point &pos, int justifyWidth, int justifyHeight, const Common::Point &shadow, int foreColor, int backColor, int shadowColor) { _curFont = NULL; _picSelect = picSelect; @@ -65,9 +65,20 @@ FontInfo::FontInfo(byte picFlags, byte picSelect, byte picPick, byte picOnOff, b _shadowColor = shadowColor; } +/*------------------------------------------------------------------------*/ + +DrawInfo::DrawInfo(int penColor, const Common::Point &pos, int flags) { + _penColor = penColor; + _pos = pos; + _flags = flags; +} + +/*------------------------------------------------------------------------*/ + GraphicsManager::GraphicsManager(): - _defaultFontInfo(3, 0xff, 0xff, 0, 0, 0, 0, Common::Point(), 1, 1, Common::Point(1, 1), 1, 0, 0), - _fontPtr(&_defaultFontInfo) { + _defaultFontInfo(3, 0xff, 0xff, 0, 0, ALIGN_LEFT, 0, Common::Point(), 1, 1, + Common::Point(1, 1), 1, 0, 0), _defaultDrawInfo(1, Common::Point(), 0), + _fontPtr(&_defaultFontInfo), _drawPtr(&_defaultDrawInfo) { _SVGAPage = 0; _SVGAMode = 0; _SVGAReset = 0; @@ -77,6 +88,7 @@ GraphicsManager::GraphicsManager(): _palFlag = false; _MCGAMode = false; _saveBack = true; + _drawTextPermFlag = false; _clipPtr = NULL; _viewPortListPtr = NULL; _vPort = NULL; @@ -350,11 +362,11 @@ void GraphicsManager::sDrawPic(DisplayResource *srcDisplay, DisplayResource *des error("TODO: sDrawPic"); } else { // loc_25773 - // Copy from screen to surface with transparency destP = destImgData + screenOffset; srcP = (byte *)_screenSurface.pixels + srcOffset; if (srcFlags & 2) { + // Copy from screen to surface with transparency for (int yp = 0; yp < height1; ++yp) { for (int xp = 0; xp < width2; ++xp, ++destP) { byte srcPixel = *srcP++; @@ -366,7 +378,16 @@ void GraphicsManager::sDrawPic(DisplayResource *srcDisplay, DisplayResource *des srcP += widthDiff; } } else { - error("TODO: sDrawPic"); + // Copy from screen surface without transparency + for (int yp = 0; yp < height1; ++yp) { + for (int xp = 0; xp < width2; ++xp, ++destP) { + byte srcPixel = *srcP++; + *destP = srcPixel; + } + + destP += widthDiff2; + srcP += widthDiff; + } } } } else { diff --git a/engines/voyeur/graphics.h b/engines/voyeur/graphics.h index cd1d47b6fc..9c66a32a67 100644 --- a/engines/voyeur/graphics.h +++ b/engines/voyeur/graphics.h @@ -45,6 +45,8 @@ class ViewPortListResource; class FontResource; class CMapResource; +enum FontJustify { ALIGN_LEFT = 0, ALIGN_CENTRE = 1, ALIGN_RIGHT = 2 }; + class FontInfo { public: FontResource *_curFont; @@ -53,7 +55,7 @@ public: byte _picPick; byte _picOnOff; byte _fontFlags; - byte _justify; + FontJustify _justify; int _fontSaveBack; Common::Point _pos; int _justifyWidth; @@ -64,9 +66,19 @@ public: int _shadowColor; public: FontInfo(); - FontInfo(byte picFlags, byte picSelect, byte picPick, byte picOnOff, byte fontFlags, byte justify, - int fontSaveBack, const Common::Point &pos, int justifyWidth, int justifyHeight, - const Common::Point &shadow, int foreColor, int backColor, int shadowColor); + FontInfo(byte picFlags, byte picSelect, byte picPick, byte picOnOff, byte fontFlags, + FontJustify justify, int fontSaveBack, const Common::Point &pos, int justifyWidth, + int justifyHeight, const Common::Point &shadow, int foreColor, int backColor, + int shadowColor); +}; + +class DrawInfo { +public: + int _penColor; + Common::Point _pos; + int _flags; +public: + DrawInfo(int penColor, const Common::Point &pos, int flags); }; typedef void (GraphicsManager::*GraphicMethodPtr)(); @@ -96,6 +108,9 @@ public: CMapResource *_backColors; FontInfo *_fontPtr; FontInfo _defaultFontInfo; + DrawInfo *_drawPtr; + DrawInfo _defaultDrawInfo; + bool _drawTextPermFlag; private: static void fadeIntFunc(); static void vDoCycleInt(); diff --git a/engines/voyeur/voyeur.cpp b/engines/voyeur/voyeur.cpp index 83e5d80802..9078cc9eda 100644 --- a/engines/voyeur/voyeur.cpp +++ b/engines/voyeur/voyeur.cpp @@ -257,7 +257,7 @@ bool VoyeurEngine::doLock() { // Display the last play time _graphicsManager._fontPtr->_pos = Common::Point(0, 97); - _graphicsManager._fontPtr->_justify = 1; + _graphicsManager._fontPtr->_justify = ALIGN_CENTRE; _graphicsManager._fontPtr->_justifyWidth = 384; _graphicsManager._fontPtr->_justifyHeight = 97; @@ -277,7 +277,7 @@ bool VoyeurEngine::doLock() { int x1 = READ_LE_UINT16(keyData + (((keyIndex << 2) + 1) << 1)); int x2 = READ_LE_UINT16(keyData + (((keyIndex << 2) + 3) << 1)); int y1 = READ_LE_UINT16(keyData + (((keyIndex << 2) + 2) << 1)); - int y2 = READ_LE_UINT16(keyData + (((keyIndex << 2) + 2) << 1)); + int y2 = READ_LE_UINT16(keyData + (((keyIndex << 2) + 4) << 1)); if (mousePos.x >= x1 && mousePos.x <= x2 && mousePos.y >= y1 && mousePos.y <= y2) { key = keyIndex; |