[Scummvm-git-logs] scummvm master -> 0fdd48416c6cd1a743fbaabddc829a1d7d17952a

neuromancer noreply at scummvm.org
Tue Oct 1 21:26:40 UTC 2024


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:
0fdd48416c FREESCAPE: big refactoring of font handling to use the common font code


Commit: 0fdd48416c6cd1a743fbaabddc829a1d7d17952a
    https://github.com/scummvm/scummvm/commit/0fdd48416c6cd1a743fbaabddc829a1d7d17952a
Author: neuromancer (gustavo.grieco at gmail.com)
Date: 2024-10-01T23:25:12+02:00

Commit Message:
FREESCAPE: big refactoring of font handling to use the common font code

Changed paths:
  A engines/freescape/font.cpp
  A engines/freescape/font.h
    engines/freescape/freescape.cpp
    engines/freescape/freescape.h
    engines/freescape/games/castle/castle.cpp
    engines/freescape/games/castle/castle.h
    engines/freescape/games/castle/dos.cpp
    engines/freescape/games/castle/zx.cpp
    engines/freescape/games/dark/amiga.cpp
    engines/freescape/games/dark/atari.cpp
    engines/freescape/games/dark/cpc.cpp
    engines/freescape/games/dark/dos.cpp
    engines/freescape/games/dark/zx.cpp
    engines/freescape/games/driller/amiga.cpp
    engines/freescape/games/driller/atari.cpp
    engines/freescape/games/driller/cpc.cpp
    engines/freescape/games/driller/dos.cpp
    engines/freescape/games/driller/zx.cpp
    engines/freescape/games/eclipse/cpc.cpp
    engines/freescape/games/eclipse/dos.cpp
    engines/freescape/games/eclipse/zx.cpp
    engines/freescape/loaders/8bitBinaryLoader.cpp
    engines/freescape/module.mk


diff --git a/engines/freescape/font.cpp b/engines/freescape/font.cpp
new file mode 100644
index 00000000000..8db79102e51
--- /dev/null
+++ b/engines/freescape/font.cpp
@@ -0,0 +1,180 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+#include "engines/freescape/freescape.h"
+#include "engines/freescape/font.h"
+
+namespace Freescape {
+
+Font::Font() {
+    _backgroundColor = 0;
+    _secondaryColor = 0;
+    _kerningOffset = 0;
+    _chars.clear();
+}
+
+Font::Font(Common::Array<Graphics::ManagedSurface *> &chars) {
+    _chars = chars;
+    _backgroundColor = 0;
+    _secondaryColor = 0;
+    _kerningOffset = 0;
+}
+
+Font::~Font() {
+    /*for (Graphics::ManagedSurface *surface : _chars) {
+        surface->free();
+        delete surface;
+    }*/
+}
+
+int Font::getCharWidth(uint32 chr) const {
+    return 8;
+}
+
+int Font::getMaxCharWidth() const {
+    return getCharWidth(0);
+}
+
+int Font::getFontHeight() const {
+    return _chars[0]->h + 1;
+}
+
+void Font::setSecondaryColor(uint32 color) {
+    _secondaryColor = color;
+}
+
+void Font::setBackground(uint32 color) {
+    _backgroundColor = color;
+}
+
+void Font::drawChar(Graphics::Surface *dst, uint32 chr, int x, int y, uint32 color) const {
+    assert(chr >= 32);
+    chr -= 32;
+
+    Graphics::ManagedSurface surface = Graphics::ManagedSurface();
+    surface.copyFrom(*_chars[chr]);
+
+    uint8 rb, gb, bb;
+    uint8 rp, gp, bp;
+    uint8 rs, gs, bs;
+
+    dst->format.colorToRGB(color, rp, gp, bp);
+    dst->format.colorToRGB(_secondaryColor, rs, gs, bs);
+    dst->format.colorToRGB(_backgroundColor, rb, gb, bb);
+
+    byte palette[3][3] = {
+        { rb, gb, bb },
+        { rp, gp, bp },
+        { rs, gs, bs },
+    };
+
+    surface.convertToInPlace(dst->format, (byte *)palette, 3);
+    dst->copyRectToSurfaceWithKey(surface, x, y, Common::Rect(0, 0, 8, surface.h), surface.getTransparentColor());
+    surface.free();
+}
+
+Common::Array<Graphics::ManagedSurface *> FreescapeEngine::getChars(Common::SeekableReadStream *file, int offset, int charsNumber) {
+	byte *fontBuffer = (byte *)malloc(6 * charsNumber);
+	file->seek(offset);
+	file->read(fontBuffer, 6 * charsNumber);
+
+	Common::BitArray font;
+	font.set_size(48 * charsNumber);
+	font.set_bits(fontBuffer);
+
+	Common::Array<Graphics::ManagedSurface *> chars;
+
+	int sizeX = 8;
+	int sizeY = 6;
+	int additional = isEclipse() ? 0 : 1;
+
+	for (int c = 0; c < charsNumber - 1; c++) {
+		int position = sizeX * sizeY * c;
+
+		Graphics::ManagedSurface *surface = new Graphics::ManagedSurface();
+		surface->create(sizeX, sizeY, Graphics::PixelFormat::createFormatCLUT8());
+		for (int j = 0; j < sizeY; j++) {
+			for (int i = 0; i < sizeX; i++) {
+				if (font.get(position + additional + j * 8 + i))
+					surface->setPixel(7 - i, j, 1);
+				else
+					surface->setPixel(7 - i, j, 0);
+			}
+		}
+		chars.push_back(surface);
+	}
+	return chars;
+}
+
+Common::Array<Graphics::ManagedSurface *> FreescapeEngine::getCharsAmigaAtari(Common::SeekableReadStream *file, int offset, int charsNumber) {
+
+	file->seek(offset);
+	int fontSize = 4654;
+	byte *fontBuffer = (byte *)malloc(fontSize);
+	file->read(fontBuffer, fontSize);
+
+	Common::BitArray font;
+	font.set_size(8 * fontSize);
+	font.set_bits(fontBuffer);
+
+	Common::Array<Graphics::ManagedSurface *> chars;
+
+	int sizeX = 8;
+	int sizeY = 8;
+	int additional = isEclipse() ? 0 : 1;
+	int m1 = isDriller() ? 33 : 16;
+	int m2 = isDriller() ? 32 : 16;
+
+	for (int c = 0; c < charsNumber - 1; c++) {
+		int position = 8 * (m1*c + 1);
+		Graphics::ManagedSurface *surface = new Graphics::ManagedSurface();
+		surface->create(sizeX, sizeY, Graphics::PixelFormat::createFormatCLUT8());
+		for (int j = 0; j < sizeY; j++) {
+			for (int i = 0; i < sizeX; i++) {
+				if (font.get(position + additional + j * m2 + i + 7))
+					surface->setPixel(7 - i, j, 2);
+				else if (font.get(position + j * m2 + i)) {
+					surface->setPixel(7 - i, j, 1);
+				} else
+					surface->setPixel(7 - i, j, 0);
+			}
+		}
+		chars.push_back(surface);
+	}
+	return chars;
+}
+
+void FreescapeEngine::drawStringInSurface(const Common::String &str, int x, int y, uint32 fontColor, uint32 backColor, Graphics::Surface *surface, int offset) {
+	Common::String ustr = str;
+	ustr.toUppercase();
+	_font.setBackground(backColor);
+	_font.drawString(surface, ustr, x, y, _screenW, fontColor);
+}
+
+void FreescapeEngine::drawStringInSurface(const Common::String &str, int x, int y, uint32 primaryColor, uint32 secondaryColor, uint32 backColor, Graphics::Surface *surface, int offset) {
+	Common::String ustr = str;
+	ustr.toUppercase();
+	_font.setSecondaryColor(secondaryColor);
+	_font.drawString(surface, ustr, x, y, _screenW, primaryColor);
+}
+
+
+} // End of namespace Freescape
diff --git a/engines/freescape/font.h b/engines/freescape/font.h
new file mode 100644
index 00000000000..8582707737e
--- /dev/null
+++ b/engines/freescape/font.h
@@ -0,0 +1,58 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef FREESCAPE_FONT_H
+#define FREESCAPE_FONT_H
+
+#include "common/array.h"
+#include "common/stream.h"
+
+#include "graphics/font.h"
+#include "graphics/managed_surface.h"
+
+namespace Freescape {
+
+class Font : public Graphics::Font {
+public:
+	Font();
+	Font(Common::Array<Graphics::ManagedSurface *> &chars);
+	~Font() override;
+
+	void setBackground(uint32 color);
+	void setSecondaryColor(uint32 color);
+	int getFontHeight() const override;
+	int getMaxCharWidth() const override;
+	int getCharWidth(uint32 chr) const override;
+	int getKerningOffset(uint32 left, uint32 right) const override { return _kerningOffset; }
+	void setKernelingOffset(int offset) { _kerningOffset = offset; }
+
+	void drawChar(Graphics::Surface *dst, uint32 chr, int x, int y, uint32 color) const override;
+
+	//const Graphics::ManagedSurface &getImageSurface() const { return _image; }
+private:
+    Common::Array<Graphics::ManagedSurface *> _chars;
+	uint32 _backgroundColor;
+	uint32 _secondaryColor;
+	int _kerningOffset;
+};
+
+} // End of namespace Freescape
+
+#endif // FREESCAPE_FONT_H
diff --git a/engines/freescape/freescape.cpp b/engines/freescape/freescape.cpp
index 0c32900502a..397ddd2089a 100644
--- a/engines/freescape/freescape.cpp
+++ b/engines/freescape/freescape.cpp
@@ -964,58 +964,6 @@ bool FreescapeEngine::hasFeature(EngineFeature f) const {
 		   (f == kSupportsArbitraryResolutions && !softRenderer);
 }
 
-void FreescapeEngine::drawStringInSurface(const Common::String &str, int x, int y, uint32 fontColor, uint32 backColor, Graphics::Surface *surface, int offset) {
-	if (!_fontLoaded)
-		return;
-	Common::String ustr = str;
-	uint32 transparent = _gfx->_texturePixelFormat.ARGBToColor(0, 0, 0, 0);
-	ustr.toUppercase();
-
-	int sizeX = 8;
-	int sizeY = isCastle() ? 8 : 6;
-	int sep = isCastle() ? 9 : 8;
-	int additional = isCastle() || isEclipse() ? 0 : 1;
-
-	for (uint32 c = 0; c < ustr.size(); c++) {
-		assert(ustr[c] >= 32);
-		int position = sizeX * sizeY * (offset + ustr[c] - 32);
-		for (int j = 0; j < sizeY; j++) {
-			for (int i = 0; i < sizeX; i++) {
-				if (_font.get(position + additional + j * 8 + i) && fontColor != transparent)
-					surface->setPixel(x + 8 - i + sep * c, y + j, fontColor);
-				else if (backColor != transparent)
-					surface->setPixel(x + 8 - i + sep * c, y + j, backColor);
-			}
-		}
-	}
-}
-
-void FreescapeEngine::drawStringInSurface(const Common::String &str, int x, int y, uint32 primaryColor, uint32 secondaryColor, uint32 backColor, Graphics::Surface *surface, int offset) {
-	if (!_fontLoaded)
-		return;
-	Common::String ustr = str;
-	ustr.toUppercase();
-
-	int multiplier1 = isDriller() ? 33 : 16;
-	int multiplier2 = isDriller() ? 32 : 16;
-
-	for (uint32 c = 0; c < ustr.size(); c++) {
-		assert(ustr[c] >= 32);
-		int position = 8 * (multiplier1*(offset + ustr[c] - 32) + 1);
-		for (int j = 0; j < 8; j++) {
-			for (int i = 0; i < 8; i++) {
-				if (_font.get(position + j * multiplier2 + i + 8)) {
-					surface->setPixel(x + 8 - i + 8 * c, y + j, secondaryColor);
-				} else if (_font.get(position + j * multiplier2 + i)) {
-					surface->setPixel(x + 8 - i + 8 * c, y + j, primaryColor);
-				} else {
-					surface->setPixel(x + 8 - i + 8 * c, y + j, backColor);
-				}
-			}
-		}
-	}
-}
-
 Common::Error FreescapeEngine::loadGameStream(Common::SeekableReadStream *stream) {
 
 	uint16 areaID = stream->readUint16LE();
diff --git a/engines/freescape/freescape.h b/engines/freescape/freescape.h
index 2836746f8b3..fdc3cb652a3 100644
--- a/engines/freescape/freescape.h
+++ b/engines/freescape/freescape.h
@@ -34,6 +34,7 @@
 #include "graphics/framelimiter.h"
 
 #include "freescape/area.h"
+#include "freescape/font.h"
 #include "freescape/gfx.h"
 #include "freescape/objects/entrance.h"
 #include "freescape/objects/geometricobject.h"
@@ -504,11 +505,13 @@ public:
 	void drawFullscreenMessage(Common::String message, uint32 front, Graphics::Surface *surface);
 
 	// Font loading and rendering
-	void loadFonts(Common::SeekableReadStream *file, int offset, Common::BitArray &font);
+	void loadFonts(Common::SeekableReadStream *file, int offset);
 	void loadFonts(byte *font, int charNumber);
+	Common::Array<Graphics::ManagedSurface *> getChars(Common::SeekableReadStream *file, int offset, int charsNumber);
+	Common::Array<Graphics::ManagedSurface *> getCharsAmigaAtari(Common::SeekableReadStream *file, int offset, int charsNumber);
 	Common::StringArray _currentAreaMessages;
 	Common::StringArray _currentEphymeralMessages;
-	Common::BitArray _font;
+	Font _font;
 	bool _fontLoaded;
 	virtual void drawStringInSurface(const Common::String &str, int x, int y, uint32 fontColor, uint32 backColor, Graphics::Surface *surface, int offset = 0);
 	virtual void drawStringInSurface(const Common::String &str, int x, int y, uint32 primaryFontColor, uint32 secondaryFontColor, uint32 backColor, Graphics::Surface *surface, int offset = 0);
diff --git a/engines/freescape/games/castle/castle.cpp b/engines/freescape/games/castle/castle.cpp
index 4e3830ce964..ec4e97f408f 100644
--- a/engines/freescape/games/castle/castle.cpp
+++ b/engines/freescape/games/castle/castle.cpp
@@ -822,7 +822,7 @@ void CastleEngine::drawRiddle(uint16 riddle, uint32 front, uint32 back, Graphics
 	drawFullscreenSurface(surface);
 }
 
-void CastleEngine::drawStringInSurface(const Common::String &str, int x, int y, uint32 fontColor, uint32 backColor, Graphics::Surface *surface, int offset) {
+/*void CastleEngine::drawStringInSurface(const Common::String &str, int x, int y, uint32 fontColor, uint32 backColor, Graphics::Surface *surface, int offset) {
 	if (isSpectrum() || isCPC()) {
 		FreescapeEngine::drawStringInSurface(str, x, y, fontColor, backColor, surface, offset);
 		return;
@@ -841,7 +841,7 @@ void CastleEngine::drawStringInSurface(const Common::String &str, int x, int y,
 	_font = Common::BitArray();
 	//_font = _fontPlane3;
 	//FreescapeEngine::drawStringInSurface(str, x, y, transparent, green, surface, offset);
-}
+}*/
 
 void CastleEngine::drawEnergyMeter(Graphics::Surface *surface, Common::Point origin) {
 	if (!_strenghtBackgroundFrame)
diff --git a/engines/freescape/games/castle/castle.h b/engines/freescape/games/castle/castle.h
index 5324c6747d4..c831708adb1 100644
--- a/engines/freescape/games/castle/castle.h
+++ b/engines/freescape/games/castle/castle.h
@@ -89,7 +89,7 @@ public:
 	Common::BitArray _fontPlane2;
 	Common::BitArray _fontPlane3;
 
-	void drawStringInSurface(const Common::String &str, int x, int y, uint32 fontColor, uint32 backColor, Graphics::Surface *surface, int offset = 0) override;
+	//void drawStringInSurface(const Common::String &str, int x, int y, uint32 fontColor, uint32 backColor, Graphics::Surface *surface, int offset = 0) override;
 	//void drawStringInSurface(const Common::String &str, int x, int y, uint32 primaryFontColor, uint32 secondaryFontColor, uint32 backColor, Graphics::Surface *surface, int offset = 0) override;
 	Graphics::ManagedSurface *loadFrameWithHeaderDOS(Common::SeekableReadStream *file);
 	Common::Array <Graphics::ManagedSurface *>loadFramesWithHeaderDOS(Common::SeekableReadStream *file, int numFrames);
diff --git a/engines/freescape/games/castle/dos.cpp b/engines/freescape/games/castle/dos.cpp
index 2e671c71be9..f9d9256b50f 100644
--- a/engines/freescape/games/castle/dos.cpp
+++ b/engines/freescape/games/castle/dos.cpp
@@ -53,7 +53,7 @@ extern byte kEGADefaultPalette[16][3];
 extern Common::MemoryReadStream *unpackEXE(Common::File &ms);
 
 void CastleEngine::loadDOSFonts(Common::SeekableReadStream *file, int pos) {
-	file->seek(pos);
+	/*file->seek(pos);
 	byte *bufferPlane1 = (byte *)malloc(sizeof(byte) * 59 * 8);
 	byte *bufferPlane2 = (byte *)malloc(sizeof(byte) * 59 * 8);
 	byte *bufferPlane3 = (byte *)malloc(sizeof(byte) * 59 * 8);
@@ -85,7 +85,7 @@ void CastleEngine::loadDOSFonts(Common::SeekableReadStream *file, int pos) {
 	_fontLoaded = true;
 	free(bufferPlane1);
 	free(bufferPlane2);
-	free(bufferPlane3);
+	free(bufferPlane3);*/
 }
 
 Graphics::ManagedSurface *CastleEngine::loadFrameFromPlanes(Common::SeekableReadStream *file, int widthInBytes, int height) {
@@ -241,6 +241,14 @@ void CastleEngine::loadAssetsDOSFullGame() {
 			_thunderFrame = loadFrameFromPlanes(stream, 16, 128);
 			_thunderFrame->convertToInPlace(_gfx->_texturePixelFormat, (byte *)&kEGADefaultPalette, 16);
 
+			stream->seek(0x29696);
+			Common::Array<Graphics::ManagedSurface *> chars;
+			for (int i = 0; i < 90; i++) {
+				chars.push_back(loadFrameFromPlanes(stream, 8, 8));
+				chars[i]->convertToInPlace(_gfx->_texturePixelFormat, (byte *)&kEGADefaultPalette, 16);
+			}
+			_font = Font(chars);
+
 			// No header
 			// Another thunder frame?
 		}
diff --git a/engines/freescape/games/castle/zx.cpp b/engines/freescape/games/castle/zx.cpp
index d1cf3a61b3b..c77c226a2d6 100644
--- a/engines/freescape/games/castle/zx.cpp
+++ b/engines/freescape/games/castle/zx.cpp
@@ -91,6 +91,7 @@ Graphics::ManagedSurface *CastleEngine::loadFrame(Common::SeekableReadStream *fi
 void CastleEngine::loadAssetsZXFullGame() {
 	Common::File file;
 	uint8 r, g, b;
+	Common::Array<Graphics::ManagedSurface *> chars;
 
 	file.open("castlemaster.zx.title");
 	if (file.isOpen()) {
@@ -117,13 +118,31 @@ void CastleEngine::loadAssetsZXFullGame() {
 			loadMessagesVariableSize(&file, 0xf3d, 71);
 			load8bitBinary(&file, 0x6aab - 2, 16);
 			loadSpeakerFxZX(&file, 0xca0, 0xcdc);
-			loadFonts(&file, 0x1218 + 16, _font);
+			//loadFonts(&file, 0x1218 + 16);
+
+			file.seek(0x1218 + 16);
+			for (int i = 0; i < 90; i++) {
+				Graphics::ManagedSurface *surface = new Graphics::ManagedSurface();
+				surface->create(8, 8, Graphics::PixelFormat::createFormatCLUT8());
+				chars.push_back(loadFrame(&file, surface, 1, 8, 1));
+			}
+			_font = Font(chars);
+
 			break;
 		case Common::EN_ANY:
 			loadRiddles(&file, 0x145c - 2 - 9 * 2, 9);
 			load8bitBinary(&file, 0x6a3b, 16);
 			loadSpeakerFxZX(&file, 0xc91, 0xccd);
-			loadFonts(&file, 0x1219, _font);
+			//loadFonts(&file, 0x1219);
+
+			file.seek(0x1219);
+			for (int i = 0; i < 90; i++) {
+				Graphics::ManagedSurface *surface = new Graphics::ManagedSurface();
+				surface->create(8, 8, Graphics::PixelFormat::createFormatCLUT8());
+				chars.push_back(loadFrame(&file, surface, 1, 8, 1));
+			}
+			_font = Font(chars);
+
 			break;
 		default:
 			error("Language not supported");
diff --git a/engines/freescape/games/dark/amiga.cpp b/engines/freescape/games/dark/amiga.cpp
index 7591ce0a24b..52212a0a05e 100644
--- a/engines/freescape/games/dark/amiga.cpp
+++ b/engines/freescape/games/dark/amiga.cpp
@@ -99,7 +99,7 @@ void DarkEngine::initAmigaAtari() {
 void DarkEngine::drawString(const DarkFontSize size, const Common::String &str, int x, int y, uint32 primaryColor, uint32 secondaryColor, uint32 backColor, Graphics::Surface *surface) {
 	if (!_fontLoaded)
 		return;
-	Common::String ustr = str;
+	/*Common::String ustr = str;
 	ustr.toUppercase();
 
 	int multiplier1 = 0;
@@ -145,14 +145,14 @@ void DarkEngine::drawString(const DarkFontSize size, const Common::String &str,
 			for (int i = 0; i < sizeX; i++) {
 				if (_font.get(position + j * multiplier2 + i)) {
 					surface->setPixel(x + 8 - i + sep * c, y + j, primaryColor);
-				} /*else if (_font.get(position + j * multiplier2 + i)) {
+				}*/ /*else if (_font.get(position + j * multiplier2 + i)) {
 					surface->setPixel(x + 8 - i + 8 * c, y + j, primaryColor);
-				}*/ else {
+				}*/ /*else {
 					surface->setPixel(x + 8 - i + sep * c, y + j, backColor);
 				}
 			}
 		}
-	}
+	}*/
 }
 
 } // End of namespace Freescape
diff --git a/engines/freescape/games/dark/atari.cpp b/engines/freescape/games/dark/atari.cpp
index bfcf38c8617..50c0eba5c52 100644
--- a/engines/freescape/games/dark/atari.cpp
+++ b/engines/freescape/games/dark/atari.cpp
@@ -53,9 +53,9 @@ void DarkEngine::loadAssetsAtariFullGame() {
 	parseAmigaAtariHeader(stream);
 
 	_border = loadAndConvertNeoImage(stream, 0xd710);
-	loadFonts(stream, 0xd06b, _fontBig);
+	/*loadFonts(stream, 0xd06b, _fontBig);
 	loadFonts(stream, 0xd49a, _fontMedium);
-	loadFonts(stream, 0xd49b, _fontSmall);
+	loadFonts(stream, 0xd49b, _fontSmall);*/
 
 	load8bitBinary(stream, 0x20918, 16);
 	loadMessagesVariableSize(stream, 0x3f6f, 66);
diff --git a/engines/freescape/games/dark/cpc.cpp b/engines/freescape/games/dark/cpc.cpp
index c5dc8880fc2..d910283ec3f 100644
--- a/engines/freescape/games/dark/cpc.cpp
+++ b/engines/freescape/games/dark/cpc.cpp
@@ -62,7 +62,7 @@ void DarkEngine::loadAssetsCPCFullGame() {
 		error("Failed to open DARKCODE.BIN");
 
 	loadMessagesFixedSize(&file, 0x5d9, 16, 27);
-	loadFonts(&file, 0x60f3, _font);
+	loadFonts(&file, 0x60f3);
 	loadGlobalObjects(&file, 0x9a, 23);
 	load8bitBinary(&file, 0x6255, 16);
 	_indicators.push_back(loadBundledImage("dark_fallen_indicator"));
diff --git a/engines/freescape/games/dark/dos.cpp b/engines/freescape/games/dark/dos.cpp
index 6aa28fff15b..046aa2649df 100644
--- a/engines/freescape/games/dark/dos.cpp
+++ b/engines/freescape/games/dark/dos.cpp
@@ -108,7 +108,7 @@ void DarkEngine::loadAssetsDOSDemo() {
 		loadSpeakerFxDOS(&file, 0x4837 + 0x200, 0x46e8 + 0x200);
 		loadMessagesFixedSize(&file, 0x4525, 16, 27);
 		loadMessagesFixedSize(&file, 0x993f - 2, 308, 5);
-		loadFonts(&file, 0xa598, _font);
+		loadFonts(&file, 0xa598);
 		loadGlobalObjects(&file, 0x3d04, 23);
 		load8bitBinary(&file, 0xa700, 16);
 		_border = load8bitBinImage(&file, 0x210);
@@ -135,7 +135,7 @@ void DarkEngine::loadAssetsDOSDemo() {
 			error("Failed to open DSIDEC.EXE");
 
 		loadSpeakerFxDOS(&file, 0x3077 + 0x200, 0x2f28 + 0x200);
-		loadFonts(&file, 0x8907, _font);
+		loadFonts(&file, 0x8907);
 		loadMessagesFixedSize(&file, 0x2d65, 16, 27);
 		loadMessagesFixedSize(&file, 0x7c3a, 308, 5);
 		loadGlobalObjects(&file, 0x2554, 23);
@@ -163,7 +163,7 @@ void DarkEngine::loadAssetsDOSFullGame() {
 			error("Failed to open DSIDEE.EXE");
 
 		loadSpeakerFxDOS(&file, 0x4837 + 0x200, 0x46e8 + 0x200);
-		loadFonts(&file, 0xa113, _font);
+		loadFonts(&file, 0xa113);
 		loadMessagesFixedSize(&file, 0x4525, 16, 27);
 		loadGlobalObjects(&file, 0x3d04, 23);
 		load8bitBinary(&file, 0xa280, 16);
@@ -191,7 +191,7 @@ void DarkEngine::loadAssetsDOSFullGame() {
 			error("Failed to open DSIDEC.EXE");
 
 		loadSpeakerFxDOS(&file, 0x3077 + 0x200, 0x2f28 + 0x200);
-		loadFonts(&file, 0x8496, _font);
+		loadFonts(&file, 0x8496);
 		loadMessagesFixedSize(&file, 0x2d65, 16, 27);
 		loadGlobalObjects(&file, 0x2554, 23);
 		load8bitBinary(&file, 0x8600, 16);
diff --git a/engines/freescape/games/dark/zx.cpp b/engines/freescape/games/dark/zx.cpp
index ba7e8b78a35..ec2b0bbc0b2 100644
--- a/engines/freescape/games/dark/zx.cpp
+++ b/engines/freescape/games/dark/zx.cpp
@@ -73,7 +73,7 @@ void DarkEngine::loadAssetsZXFullGame() {
 
 	loadMessagesFixedSize(&file, 0x56b - 6, 16, 27);
 
-	loadFonts(&file, 0x5d60 - 6, _font);
+	loadFonts(&file, 0x5d60 - 6);
 	loadGlobalObjects(&file, 0x1a, 23);
 	load8bitBinary(&file, 0x5ec0 - 4, 4);
 	loadSpeakerFxZX(&file, 0x9c1, 0xa55);
@@ -112,7 +112,7 @@ void DarkEngine::loadAssetsZXDemo() {
 	loadMessagesFixedSize(&file, 0x5761, 264, 5);
 	loadSpeakerFxZX(&file, 0x9c7, 0xa5b);
 
-	loadFonts(&file, 0x6164, _font);
+	loadFonts(&file, 0x6164);
 	loadGlobalObjects(&file, 0x20, 23);
 	load8bitBinary(&file, 0x62c6, 4);
 	_indicators.push_back(loadBundledImage("dark_fallen_indicator"));
diff --git a/engines/freescape/games/driller/amiga.cpp b/engines/freescape/games/driller/amiga.cpp
index 634be9cf66d..881c7d1fa76 100644
--- a/engines/freescape/games/driller/amiga.cpp
+++ b/engines/freescape/games/driller/amiga.cpp
@@ -43,7 +43,7 @@ void DrillerEngine::loadAssetsAmigaFullGame() {
 		}
 		_title = loadAndConvertNeoImage(&file, 0x10, palette);
 
-		loadFonts(&file, 0x8940, _font);
+		loadFonts(&file, 0x8940);
 		loadMessagesFixedSize(&file, 0xc66e, 14, 20);
 		loadGlobalObjects(&file, 0xbd62, 8);
 		load8bitBinary(&file, 0x29c16, 16);
@@ -68,7 +68,7 @@ void DrillerEngine::loadAssetsAmigaFullGame() {
 		if (!file.isOpen())
 			error("Failed to open 'driller' executable for Amiga");
 
-		loadFonts(&file, 0xa62, _font);
+		loadFonts(&file, 0xa62);
 		loadMessagesFixedSize(&file, 0x499a, 14, 20);
 		loadGlobalObjects(&file, 0x4098, 8);
 		load8bitBinary(&file, 0x21a3e, 16);
@@ -120,12 +120,12 @@ void DrillerEngine::loadAssetsAmigaDemo() {
 		error("Failed to open 'driller' file");
 
 	if (_variant & GF_AMIGA_MAGAZINE_DEMO) {
-		loadFonts(&file, 0xa62, _font);
+		loadFonts(&file, 0xa62);
 		loadMessagesFixedSize(&file, 0x3df0, 14, 20);
 		loadGlobalObjects(&file, 0x3ba6, 8);
 		_demoMode = false;
 	} else {
-		loadFonts(&file, 0xa30, _font);
+		loadFonts(&file, 0xa30);
 		loadMessagesFixedSize(&file, 0x3960, 14, 20);
 		loadGlobalObjects(&file, 0x3716, 8);
 	}
diff --git a/engines/freescape/games/driller/atari.cpp b/engines/freescape/games/driller/atari.cpp
index f5a3bdd76a8..c4bad291d8d 100644
--- a/engines/freescape/games/driller/atari.cpp
+++ b/engines/freescape/games/driller/atari.cpp
@@ -68,7 +68,7 @@ void DrillerEngine::loadAssetsAtariFullGame() {
 		_border = loadAndConvertNeoImage(stream, 0x14b96);
 		_title = loadAndConvertNeoImage(stream, 0x1c916);
 
-		loadFonts(stream, 0x8a92, _font);
+		loadFonts(stream, 0x8a92);
 		loadMessagesFixedSize(stream, 0xda22, 14, 20);
 		loadGlobalObjects(stream, 0xd116, 8);
 		load8bitBinary(stream, 0x2afb8, 16);
@@ -91,7 +91,7 @@ void DrillerEngine::loadAssetsAtariFullGame() {
 			}
 			_title = loadAndConvertNeoImage(&file, 0x10, palette);
 
-			loadFonts(&file, 0x8a32 - 0x1d6, _font);
+			loadFonts(&file, 0x8a32 - 0x1d6);
 			loadMessagesFixedSize(&file, 0xc5d8 - 0x1da, 14, 20);
 			loadGlobalObjects(&file, 0xbccc - 0x1da, 8);
 			load8bitBinary(&file, 0x29b3c - 0x1d6, 16);
@@ -107,7 +107,7 @@ void DrillerEngine::loadAssetsAtariFullGame() {
 			}
 			_title = loadAndConvertNeoImage(&file, 0x10, palette);
 
-			loadFonts(&file, 0x8a32, _font);
+			loadFonts(&file, 0x8a32);
 			loadMessagesFixedSize(&file, 0xc5d8, 14, 20);
 			loadGlobalObjects(&file, 0xbccc, 8);
 			load8bitBinary(&file, 0x29b3c, 16);
@@ -161,11 +161,11 @@ void DrillerEngine::loadAssetsAtariDemo() {
 	}
 
 	if (_variant & GF_ATARI_MAGAZINE_DEMO) {
-		loadFonts(&file, 0x7ee, _font);
+		loadFonts(&file, 0x7ee);
 		loadMessagesFixedSize(&file, 0x40d2, 14, 20);
 		loadGlobalObjects(&file, 0x3e88, 8);
 	} else {
-		loadFonts(&file, 0x7bc, _font);
+		loadFonts(&file, 0x7bc);
 		loadMessagesFixedSize(&file, 0x3b90, 14, 20);
 		loadGlobalObjects(&file, 0x3946, 8);
 	}
diff --git a/engines/freescape/games/driller/cpc.cpp b/engines/freescape/games/driller/cpc.cpp
index 308f8053853..04cb7f3484d 100644
--- a/engines/freescape/games/driller/cpc.cpp
+++ b/engines/freescape/games/driller/cpc.cpp
@@ -150,7 +150,7 @@ void DrillerEngine::loadAssetsCPCFullGame() {
 		error("Failed to open DRILL.BIN");
 
 	loadMessagesFixedSize(&file, 0x214c, 14, 20);
-	loadFonts(&file, 0x5b69, _font);
+	loadFonts(&file, 0x5b69);
 	loadGlobalObjects(&file, 0x1d07, 8);
 	load8bitBinary(&file, 0x5ccb, 16);
 }
diff --git a/engines/freescape/games/driller/dos.cpp b/engines/freescape/games/driller/dos.cpp
index 996f96a4c13..a50802daccf 100644
--- a/engines/freescape/games/driller/dos.cpp
+++ b/engines/freescape/games/driller/dos.cpp
@@ -321,7 +321,7 @@ void DrillerEngine::loadAssetsDOSFullGame() {
 
 		loadSpeakerFxDOS(&file, 0x4397 + 0x200, 0x4324 + 0x200);
 		loadMessagesFixedSize(&file, 0x4135, 14, 20);
-		loadFonts(&file, 0x99dd, _font);
+		loadFonts(&file, 0x99dd);
 		loadGlobalObjects(&file, 0x3b42, 8);
 		load8bitBinary(&file, 0x9b40, 16);
 		_border = load8bitBinImage(&file, 0x210);
@@ -346,7 +346,7 @@ void DrillerEngine::loadAssetsDOSFullGame() {
 
 		loadSpeakerFxDOS(&file, 0x27e7 + 0x200, 0x2774 + 0x200);
 
-		loadFonts(&file, 0x07a4a, _font);
+		loadFonts(&file, 0x07a4a);
 		loadMessagesFixedSize(&file, 0x2585, 14, 20);
 		load8bitBinary(&file, 0x7bb0, 4);
 		loadGlobalObjects(&file, 0x1fa2, 8);
@@ -367,7 +367,7 @@ void DrillerEngine::loadAssetsDOSFullGame() {
 
 		//loadSpeakerFxDOS(&file, 0x27e7 + 0x200, 0x2774 + 0x200);
 
-		//loadFonts(&file, 0x07a4a, _font);
+		loadFonts(&file, 0x8871);
 		loadMessagesFixedSize(&file, 0x3411, 14, 20);
 		load8bitBinary(&file, 0x89e0, 4);
 		loadGlobalObjects(&file, 0x2d02, 8);
@@ -402,7 +402,7 @@ void DrillerEngine::loadAssetsDOSDemo() {
 	if (!file.isOpen())
 		error("Failed to open 'd2' file");
 
-	loadFonts(&file, 0x4eb0, _font);
+	loadFonts(&file, 0x4eb0);
 	loadMessagesFixedSize(&file, 0x636, 14, 20);
 	load8bitBinary(&file, 0x55b0, 4);
 	loadGlobalObjects(&file, 0x8c, 5);
@@ -423,10 +423,7 @@ void DrillerEngine::loadAssetsDOSDemo() {
 }
 
 void DrillerEngine::drawDOSUI(Graphics::Surface *surface) {
-
-	if (_renderMode == Common::kRenderHercG)
-		return;
-	uint32 color = _renderMode == Common::kRenderCGA ? 1 : 14;
+	uint32 color = _renderMode == Common::kRenderCGA || _renderMode == Common::kRenderHercG ? 1 : 14;
 	uint8 r, g, b;
 
 	_gfx->readFromPalette(color, r, g, b);
@@ -496,12 +493,14 @@ void DrillerEngine::drawDOSUI(Graphics::Surface *surface) {
 		surface->fillRect(shieldBar, front);
 	}
 
-	if (!_flyMode)
-		surface->copyRectToSurface(*_indicators[0], 132, 128, Common::Rect(_indicators[0]->w, _indicators[0]->h));
-	else
-		surface->copyRectToSurface(*_indicators[1], 132, 128, Common::Rect(_indicators[1]->w, _indicators[1]->h));
+	if (_indicators.size() >= 2) {
+		if (!_flyMode)
+			surface->copyRectToSurface(*_indicators[0], 132, 128, Common::Rect(_indicators[0]->w, _indicators[0]->h));
+		else
+			surface->copyRectToSurface(*_indicators[1], 132, 128, Common::Rect(_indicators[1]->w, _indicators[1]->h));
+	}
 
-	color = 2;
+	color = _renderMode == Common::kRenderHercG ? 1 : 2;
 	_gfx->readFromPalette(color, r, g, b);
 	uint32 other = _gfx->_texturePixelFormat.ARGBToColor(0xFF, r, g, b);
 
diff --git a/engines/freescape/games/driller/zx.cpp b/engines/freescape/games/driller/zx.cpp
index 4de92def650..636343fdd47 100644
--- a/engines/freescape/games/driller/zx.cpp
+++ b/engines/freescape/games/driller/zx.cpp
@@ -59,11 +59,11 @@ void DrillerEngine::loadAssetsZXFullGame() {
 		loadMessagesFixedSize(&file, 0x20e4, 14, 20);
 
 	if (_variant & GF_ZX_RETAIL)
-		loadFonts(&file, 0x62ca, _font);
+		loadFonts(&file, 0x62ca);
 	else if (_variant & GF_ZX_BUDGET)
-		loadFonts(&file, 0x5aa8, _font);
+		loadFonts(&file, 0x5aa8);
 	else if (_variant & GF_ZX_DISC)
-		loadFonts(&file, 0x63f0, _font);
+		loadFonts(&file, 0x63f0);
 
 	if (_variant & GF_ZX_DISC)
 		loadGlobalObjects(&file, 0x1d13, 8);
diff --git a/engines/freescape/games/eclipse/cpc.cpp b/engines/freescape/games/eclipse/cpc.cpp
index 557ee43b917..e6a79e47f6a 100644
--- a/engines/freescape/games/eclipse/cpc.cpp
+++ b/engines/freescape/games/eclipse/cpc.cpp
@@ -73,11 +73,11 @@ void EclipseEngine::loadAssetsCPCFullGame() {
 		error("Failed to open TECODE.BIN/TE2.BI2");
 
 	if (isEclipse2()) {
-		loadFonts(&file, 0x60bc, _font);
+		loadFonts(&file, 0x60bc);
 		loadMessagesFixedSize(&file, 0x326, 16, 30);
 		load8bitBinary(&file, 0x62b4, 16);
 	} else {
-		loadFonts(&file, 0x6076, _font);
+		loadFonts(&file, 0x6076);
 		loadMessagesFixedSize(&file, 0x326, 16, 30);
 		load8bitBinary(&file, 0x626e, 16);
 	}
@@ -119,7 +119,7 @@ void EclipseEngine::loadAssetsCPCDemo() {
 	if (!file.isOpen())
 		error("Failed to open TEPROG.BIN");
 
-	loadFonts(&file, 0x63ce, _font);
+	loadFonts(&file, 0x63ce);
 	loadMessagesFixedSize(&file, 0x362, 16, 23);
 	loadMessagesFixedSize(&file, 0x570b, 264, 5);
 	load8bitBinary(&file, 0x65c6, 16);
diff --git a/engines/freescape/games/eclipse/dos.cpp b/engines/freescape/games/eclipse/dos.cpp
index c2a1c6890e4..bc3125e381b 100644
--- a/engines/freescape/games/eclipse/dos.cpp
+++ b/engines/freescape/games/eclipse/dos.cpp
@@ -93,7 +93,7 @@ void EclipseEngine::loadAssetsDOSFullGame() {
 		loadMessagesFixedSize(&file, 0x710f, 16, 20);
 		loadSoundsFx(&file, 0xd670, 1);
 		loadSpeakerFxDOS(&file, 0x7396 + 0x200, 0x72a1 + 0x200);
-		loadFonts(&file, 0xd403, _font);
+		loadFonts(&file, 0xd403);
 		load8bitBinary(&file, 0x3ce0, 16);
 		for (auto &it : _areaMap) {
 			it._value->addStructure(_areaMap[255]);
@@ -122,7 +122,7 @@ void EclipseEngine::loadAssetsDOSFullGame() {
 
 		loadMessagesFixedSize(&file, 0x594f, 16, 20);
 		load1bPCM(&file, 0xd038 - 4);
-		loadFonts(&file, 0xb785, _font);
+		loadFonts(&file, 0xb785);
 		load8bitBinary(&file, 0x2530, 4);
 		for (auto &it : _areaMap) {
 			it._value->addStructure(_areaMap[255]);
diff --git a/engines/freescape/games/eclipse/zx.cpp b/engines/freescape/games/eclipse/zx.cpp
index 41b62c48e82..640c95f8674 100644
--- a/engines/freescape/games/eclipse/zx.cpp
+++ b/engines/freescape/games/eclipse/zx.cpp
@@ -75,12 +75,12 @@ void EclipseEngine::loadAssetsZXFullGame() {
 
 	if (isEclipse2()) {
 		loadMessagesFixedSize(&file, 0x2ac, 16, 30);
-		loadFonts(&file, 0x61c3, _font);
+		loadFonts(&file, 0x61c3);
 		loadSpeakerFxZX(&file, 0x8c6, 0x91a);
 		load8bitBinary(&file, 0x63bb, 4);
 	} else {
 		loadMessagesFixedSize(&file, 0x2ac, 16, 23);
-		loadFonts(&file, 0x6163, _font);
+		loadFonts(&file, 0x6163);
 		loadSpeakerFxZX(&file, 0x816, 0x86a);
 		load8bitBinary(&file, 0x635b, 4);
 
@@ -133,13 +133,13 @@ void EclipseEngine::loadAssetsZXDemo() {
 		loadSpeakerFxZX(&file, 0x798, 0x7ec);
 		loadMessagesFixedSize(&file, 0x2ac, 16, 23);
 		loadMessagesFixedSize(&file, 0x56e6, 264, 1);
-		loadFonts(&file, 0x5f7b, _font);
+		loadFonts(&file, 0x5f7b);
 		load8bitBinary(&file, 0x6173, 4);
 	} else if (_variant & GF_ZX_DEMO_CRASH) {
 		loadSpeakerFxZX(&file, 0x65c, 0x6b0);
 		loadMessagesFixedSize(&file, 0x364, 16, 9);
 		loadMessagesFixedSize(&file, 0x5901, 264, 5);
-		loadFonts(&file, 0x6589, _font);
+		loadFonts(&file, 0x6589);
 		load8bitBinary(&file, 0x6781, 4);
 	} else
 		error("Unknown ZX Spectrum demo variant");
diff --git a/engines/freescape/loaders/8bitBinaryLoader.cpp b/engines/freescape/loaders/8bitBinaryLoader.cpp
index 23a3dedc9c9..825d9cb6bf1 100644
--- a/engines/freescape/loaders/8bitBinaryLoader.cpp
+++ b/engines/freescape/loaders/8bitBinaryLoader.cpp
@@ -942,38 +942,21 @@ void FreescapeEngine::load8bitBinary(Common::SeekableReadStream *file, int offse
 	_binaryBits = 8;
 }
 
-void FreescapeEngine::loadFonts(byte *font, int charNumber) {
-	if (isDOS() || isSpectrum() || isCPC() || isC64()) {
-		_font.set_size(64 * charNumber);
-		_font.set_bits(font);
-	} else if (isAmiga() || isAtariST()) {
-		error("Not implemented yet");
-	}
-	_fontLoaded = true;
-}
+void FreescapeEngine::loadFonts(Common::SeekableReadStream *file, int offset) {
+	Common::Array<Graphics::ManagedSurface *> chars;
+
+	if (isAmiga() || isAtariST())
+		chars = getCharsAmigaAtari(file, offset, 85);
+	else
+		chars = getChars(file, offset, 85);
+
+	_font = Font(chars);
+	if (isCastle())
+		_font.setKernelingOffset(4);
+	else
+		_font.setKernelingOffset(0);
 
-void FreescapeEngine::loadFonts(Common::SeekableReadStream *file, int offset, Common::BitArray &font) {
-	file->seek(offset);
-	int charNumber = 85;
-	byte *fontBuffer = nullptr;
-	if (isDOS() || isSpectrum() || isCPC() || isC64()) {
-		fontBuffer = (byte *)malloc(6 * charNumber);
-		file->read(fontBuffer, 6 * charNumber);
-
-		font.set_size(48 * charNumber);
-		font.set_bits(fontBuffer);
-	} else if (isAmiga() || isAtariST()) {
-		int fontSize = 4654; // Driller
-		fontBuffer = (byte *)malloc(fontSize);
-		file->read(fontBuffer, fontSize);
-
-		font.set_size(fontSize * 8);
-		font.set_bits(fontBuffer);
-	} else {
-		_fontLoaded = false;
-	}
 	_fontLoaded = true;
-	free(fontBuffer);
 }
 
 void FreescapeEngine::loadMessagesFixedSize(Common::SeekableReadStream *file, int offset, int size, int number) {
diff --git a/engines/freescape/module.mk b/engines/freescape/module.mk
index 72f4c10e3fe..c88ba77771d 100644
--- a/engines/freescape/module.mk
+++ b/engines/freescape/module.mk
@@ -3,6 +3,7 @@ MODULE := engines/freescape
 MODULE_OBJS := \
 	area.o \
 	assets.o \
+	font.o \
 	events.o \
 	demo.o \
 	freescape.o \




More information about the Scummvm-git-logs mailing list