[Scummvm-git-logs] scummvm master -> aa7b3470a023bfe8bb08145c4476c3bfb2a25ed8
bluegr
bluegr at gmail.com
Sat Sep 4 12:21:16 UTC 2021
This automated email contains information about 1 new commit which have been
pushed to the 'scummvm' repo located at https://github.com/scummvm/scummvm .
Summary:
aa7b3470a0 TINSEL: Simplify font loading and handling
Commit: aa7b3470a023bfe8bb08145c4476c3bfb2a25ed8
https://github.com/scummvm/scummvm/commit/aa7b3470a023bfe8bb08145c4476c3bfb2a25ed8
Author: Filippos Karapetis (bluegr at gmail.com)
Date: 2021-09-04T15:21:07+03:00
Commit Message:
TINSEL: Simplify font loading and handling
This introduces a new helper method, GetFont(), which loads font data
using a memory stream and handles endianess reads internally. This
simplifies font loading and endianess handling considerably, and allows
for the usage of a common font struct for all engine versions
Changed paths:
engines/tinsel/font.cpp
engines/tinsel/handle.cpp
engines/tinsel/handle.h
engines/tinsel/text.cpp
engines/tinsel/text.h
diff --git a/engines/tinsel/font.cpp b/engines/tinsel/font.cpp
index d7dee32f2e..bb4f66e6b5 100644
--- a/engines/tinsel/font.cpp
+++ b/engines/tinsel/font.cpp
@@ -43,22 +43,19 @@ SCNHANDLE Font::GetTalkFontHandle() {
}
void Font::FettleFontPal(SCNHANDLE fontPal) {
- const FONT *pFont;
IMAGE *pImg;
assert(fontPal);
assert(_hTagFont); // Tag font not declared
assert(_hTalkFont); // Talk font not declared
- pFont = (const FONT *)_vm->_handle->LockMem(_hTagFont);
- pImg = (IMAGE *)_vm->_handle->LockMem(FROM_32(pFont->fontInit.hObjImg)); // get image for char 0
+ pImg = (IMAGE *)_vm->_handle->LockMem(_vm->_handle->GetFontImageHandle(_hTagFont)); // get image for char 0
if (!TinselV2)
pImg->hImgPal = TO_32(fontPal);
else
pImg->hImgPal = 0;
- pFont = (const FONT *)_vm->_handle->LockMem(_hTalkFont);
- pImg = (IMAGE *)_vm->_handle->LockMem(FROM_32(pFont->fontInit.hObjImg)); // get image for char 0
+ pImg = (IMAGE *)_vm->_handle->LockMem(_vm->_handle->GetFontImageHandle(_hTalkFont)); // get image for char 0
if (!TinselV2)
pImg->hImgPal = TO_32(fontPal);
else
diff --git a/engines/tinsel/handle.cpp b/engines/tinsel/handle.cpp
index b5c3a1b6a0..defe08a2d2 100644
--- a/engines/tinsel/handle.cpp
+++ b/engines/tinsel/handle.cpp
@@ -24,6 +24,7 @@
#define BODGE
#include "common/file.h"
+#include "common/memstream.h"
#include "common/textconsole.h"
#include "tinsel/drives.h"
@@ -297,6 +298,47 @@ void Handle::LoadFile(MEMHANDLE *pH) {
error(CANNOT_FIND_FILE, szFilename);
}
+/**
+ * Return a font specified by a SCHNHANDLE
+ * Handles endianess internally
+ * @param offset Handle and offset to data
+ * @return FONT structure
+*/
+FONT *Handle::GetFont(SCNHANDLE offset) {
+ byte *fontData = LockMem(offset);
+ const bool isBE = TinselV1Mac || TinselV1Saturn;
+ const uint32 size = (TinselV3 ? 12 * 4 : 11 * 4) + 300 * 4; // FONT struct size
+ Common::MemoryReadStreamEndian *fontStream = new Common::MemoryReadStreamEndian(fontData, size, isBE);
+
+ FONT *font = new FONT();
+ font->xSpacing = fontStream->readSint32();
+ font->ySpacing = fontStream->readSint32();
+ font->xShadow = fontStream->readSint32();
+ font->yShadow = fontStream->readSint32();
+ font->spaceSize = fontStream->readSint32();
+ font->baseColor = TinselV3 ? fontStream->readSint32() : 0;
+ font->fontInit.hObjImg = fontStream->readUint32();
+ font->fontInit.objFlags = fontStream->readSint32();
+ font->fontInit.objID = fontStream->readSint32();
+ font->fontInit.objX = fontStream->readSint32();
+ font->fontInit.objY = fontStream->readSint32();
+ font->fontInit.objZ = fontStream->readSint32();
+ for (int i = 0; i < 300; i++)
+ font->fontDef[i] = fontStream->readUint32();
+
+ delete fontStream;
+
+ return font;
+}
+
+SCNHANDLE Handle::GetFontImageHandle(SCNHANDLE offset) {
+ FONT *font = GetFont(offset);
+ SCNHANDLE handle = font->fontInit.hObjImg;
+ delete font;
+
+ return handle;
+}
+
/**
* Compute and return the address specified by a SCNHANDLE.
* @param offset Handle and offset to data
diff --git a/engines/tinsel/handle.h b/engines/tinsel/handle.h
index 55790fd361..06bbebed9e 100644
--- a/engines/tinsel/handle.h
+++ b/engines/tinsel/handle.h
@@ -33,6 +33,7 @@ class File;
namespace Tinsel {
+struct FONT;
struct MEMHANDLE;
class Handle {
@@ -45,6 +46,8 @@ public:
*/
void SetupHandleTable();
+ FONT *GetFont(SCNHANDLE offset);
+ SCNHANDLE GetFontImageHandle(SCNHANDLE offset);
byte *LockMem(SCNHANDLE offset);
void LockScene(SCNHANDLE offset);
diff --git a/engines/tinsel/text.cpp b/engines/tinsel/text.cpp
index 89e2ed594c..9cb0263482 100644
--- a/engines/tinsel/text.cpp
+++ b/engines/tinsel/text.cpp
@@ -35,24 +35,6 @@ namespace Tinsel {
/** TinselV3, base color for the text color replacement */
static uint32 g_t3fontBaseColor;
-/**
- * Returns the handle for the character image.
- * @param pFont Which font to use
- * @param c Index of the character
- */
-SCNHANDLE GetFontDef(const FONT *pFont, int c)
-{
- if (TinselV3)
- {
- const T3_FONT *pT3Font = (const T3_FONT *)pFont;
- return FROM_32(pT3Font->fontDef[c]);
- }
- else
- {
- return FROM_32(pFont->fontDef[c]);
- }
-}
-
/**
* Returns the length of one line of a string in pixels.
* @param szStr String
@@ -69,7 +51,7 @@ int StringLengthPix(char *szStr, const FONT *pFont) {
if (c & 0x80)
c = ((c & ~0x80) << 8) + *++szStr;
}
- hImg = GetFontDef(pFont, c);
+ hImg = pFont->fontDef[c];
if (hImg) {
// there is a IMAGE for this character
@@ -79,14 +61,14 @@ int StringLengthPix(char *szStr, const FONT *pFont) {
strLen += FROM_16(pChar->imgWidth);
} else
// use width of space character
- strLen += FROM_32(pFont->spaceSize);
+ strLen += pFont->spaceSize;
// finally add the inter-character spacing
- strLen += FROM_32(pFont->xSpacing);
+ strLen += pFont->xSpacing;
}
// return length of line in pixels - minus inter-char spacing for last character
- strLen -= FROM_32(pFont->xSpacing);
+ strLen -= pFont->xSpacing;
return (strLen > 0) ? strLen : 0;
}
@@ -141,15 +123,16 @@ OBJECT *ObjectTextOut(OBJECT **pList, char *szStr, int color,
assert(pList);
// get font pointer
- const FONT *pFont = (const FONT *)_vm->_handle->LockMem(hFont);
- const OBJ_INIT *pFontInit = TinselV3 ? (&((const T3_FONT *)pFont)->fontInit) : (&pFont->fontInit);
+ FONT *pFont = _vm->_handle->GetFont(hFont);
+ const OBJ_INIT *pFontInit = &pFont->fontInit;
// init head of text list
pFirst = nullptr;
// get image for capital W
- assert(GetFontDef(pFont, (int)'W'));
- pImg = (const IMAGE *)_vm->_handle->LockMem(GetFontDef(pFont, (int)'W'));
+ SCNHANDLE imgHandle = pFont->fontDef[(int)'W'];
+ assert(imgHandle);
+ pImg = (const IMAGE *)_vm->_handle->LockMem(imgHandle);
// get height of capital W for offset to next line
yOffset = FROM_16(pImg->imgHeight) & ~C16_FLAG_MASK;
@@ -164,32 +147,24 @@ OBJECT *ObjectTextOut(OBJECT **pList, char *szStr, int color,
if (c & 0x80)
c = ((c & ~0x80) << 8) + *++szStr;
}
- hImg = GetFontDef(pFont, c);
+ hImg = pFont->fontDef[c];
if (hImg == 0) {
// no image for this character
// add font spacing for a space character
- xJustify += FROM_32(pFont->spaceSize);
+ xJustify += pFont->spaceSize;
} else { // printable character
int aniX, aniY; // char image animation offsets
- OBJ_INIT oi;
- oi.hObjImg = FROM_32(pFontInit->hObjImg);
- oi.objFlags = FROM_32(pFontInit->objFlags);
- oi.objID = FROM_32(pFontInit->objID);
- oi.objX = FROM_32(pFontInit->objX);
- oi.objY = FROM_32(pFontInit->objY);
- oi.objZ = FROM_32(pFontInit->objZ);
-
// allocate and init a character object
if (pFirst == NULL)
// first time - init head of list
- pFirst = pChar = InitObject(&oi); // FIXME: endian issue using fontInit!!!
+ pFirst = pChar = InitObject(pFontInit);
else
// chain to multi-char list
- pChar = pChar->pSlave = InitObject(&oi); // FIXME: endian issue using fontInit!!!
+ pChar = pChar->pSlave = InitObject(pFontInit);
// convert image handle to pointer
pImg = (const IMAGE *)_vm->_handle->LockMem(hImg);
@@ -208,9 +183,7 @@ OBJECT *ObjectTextOut(OBJECT **pList, char *szStr, int color,
pChar->constant = color;
// set the base font color to be replaced with supplied color, only for Tinsel V3
- if (TinselV3) {
- g_t3fontBaseColor = FROM_32(((const T3_FONT*)pFont)->baseColor);
- }
+ g_t3fontBaseColor = TinselV3 ? pFont->baseColor : 0;
// get Y animation offset
GetAniOffset(hImg, pChar->flags, &aniX, &aniY);
@@ -232,8 +205,8 @@ OBJECT *ObjectTextOut(OBJECT **pList, char *szStr, int color,
CopyObject(pShad, pChar);
// add shadow offsets to characters position
- pShad->xPos += intToFrac(FROM_32(pFont->xShadow));
- pShad->yPos += intToFrac(FROM_32(pFont->yShadow));
+ pShad->xPos += intToFrac(pFont->xShadow);
+ pShad->yPos += intToFrac(pFont->yShadow);
// shadow is behind the character
pShad->zPos--;
@@ -265,14 +238,14 @@ OBJECT *ObjectTextOut(OBJECT **pList, char *szStr, int color,
}
// finally add the inter-character spacing
- xJustify += FROM_32(pFont->xSpacing);
+ xJustify += pFont->xSpacing;
// next character in string
++szStr;
}
// adjust the text y position and add the inter-line spacing
- yPos += yOffset + FROM_32(pFont->ySpacing);
+ yPos += yOffset + pFont->ySpacing;
// check for newline
if (c == LF_CHAR)
@@ -280,6 +253,8 @@ OBJECT *ObjectTextOut(OBJECT **pList, char *szStr, int color,
++szStr;
}
+ delete pFont;
+
// return head of list
return pFirst;
}
@@ -298,9 +273,11 @@ bool IsCharImage(SCNHANDLE hFont, char c) {
return false;
// get font pointer
- const FONT *pFont = (const FONT *)_vm->_handle->LockMem(hFont);
+ FONT *pFont = _vm->_handle->GetFont(hFont);
+ bool result = pFont->fontDef[c2] != 0;
+ delete pFont;
- return GetFontDef(pFont, c2) != 0;
+ return result;
}
uint32 t3GetBaseColor()
diff --git a/engines/tinsel/text.h b/engines/tinsel/text.h
index 271e28e3a0..5bea6d6e1c 100644
--- a/engines/tinsel/text.h
+++ b/engines/tinsel/text.h
@@ -45,25 +45,12 @@ enum {
#define C16_MAP 0xC000
#define C16_FLAG_MASK (C16_240 | C16_224 | C16_MAP)
-#include "common/pack-start.h" // START STRUCT PACKING
-
/**
* Text font data structure.
* @note only the pointer is used so the size of fontDef[] is not important.
* It is currently set at 300 because it suited me for debugging.
*/
struct FONT {
- int xSpacing; ///< x spacing between characters
- int ySpacing; ///< y spacing between characters
- int xShadow; ///< x shadow offset
- int yShadow; ///< y shadow offset
- int spaceSize; ///< x spacing to use for a space character
- OBJ_INIT fontInit; ///< structure used to init text objects
- SCNHANDLE fontDef[300]; ///< image handle array for all characters in the font
-} PACKED_STRUCT;
-
-
-struct T3_FONT {
int xSpacing; ///< x spacing between characters
int ySpacing; ///< y spacing between characters
int xShadow; ///< x shadow offset
@@ -72,9 +59,7 @@ struct T3_FONT {
int baseColor; ///< base color which can be replaced, specific to Tinsel 3
OBJ_INIT fontInit; ///< structure used to init text objects
SCNHANDLE fontDef[300]; ///< image handle array for all characters in the font
-} PACKED_STRUCT;
-
-#include "common/pack-end.h" // END STRUCT PACKING
+};
/** structure for passing the correct parameters to ObjectTextOut */
More information about the Scummvm-git-logs
mailing list