[Scummvm-cvs-logs] scummvm-tools master -> 505d800f83c6619c5f55cf3ef40ea676782d2b4f
lordhoto
lordhoto at gmail.com
Fri Jul 1 03:24:36 CEST 2011
This automated email contains information about 4 new commits which have been
pushed to the 'scummvm-tools' repo located at https://github.com/scummvm/scummvm-tools .
Summary:
927bd1d333 TOOLS: Cleanup create_sjisfnt tool a little.
b9db877d6c TOOLS: Move create_sjisfnt TTF code to a class.
a7fe09a023 TOOLS: Implement proper character layouting in create_sjisfnt.
505d800f83 TOOLS: Further clean up create_sjisfnt.
Commit: 927bd1d3335fda2c7256ed8ecd7efaa45b7f1ba7
https://github.com/scummvm/scummvm-tools/commit/927bd1d3335fda2c7256ed8ecd7efaa45b7f1ba7
Author: Johannes Schickel (lordhoto at scummvm.org)
Date: 2011-06-30T17:09:45-07:00
Commit Message:
TOOLS: Cleanup create_sjisfnt tool a little.
Changed paths:
A create_sjisfnt.h
create_sjisfnt.cpp
diff --git a/create_sjisfnt.cpp b/create_sjisfnt.cpp
index 63e252b..901cb46 100644
--- a/create_sjisfnt.cpp
+++ b/create_sjisfnt.cpp
@@ -18,69 +18,22 @@
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*
- * $URL$
- * $Id$
- *
*/
+#include "create_sjisfnt.h"
+
+#include "common/endian.h"
+#include "common/file.h"
+
#include <stdio.h>
#include <stdlib.h>
#include <iconv.h>
-#include <list>
#include <assert.h>
#include <errno.h>
-#include "common/endian.h"
-#include "common/file.h"
-#include "common/util.h"
-
#include <ft2build.h>
#include FT_FREETYPE_H
-namespace {
-
-bool isASCII(uint8 fB);
-
-int mapASCIItoChunk(uint8 fB);
-int mapSJIStoChunk(uint8 fB, uint8 sB);
-
-bool initSJIStoUTF32Conversion();
-void deinitSJIStoUTF32Conversion();
-uint32 convertSJIStoUTF32(uint8 fB, uint8 sB);
-
-bool initFreeType(const char *font);
-void deinitFreeType();
-
-struct Glyph {
- uint8 fB, sB;
-
- int xOffset;
- int yOffset;
- int height;
- int width;
-
- int pitch;
- uint8 *plainData;
-};
-
-bool setGlyphSize(int width, int height);
-bool checkGlyphSize(const Glyph &g, const int baseLine, const int maxW, const int maxH);
-
-bool drawGlyph(uint8 fB, uint8 sB, Glyph &glyph);
-bool drawGlyph(uint32 unicode, Glyph &glyph);
-
-void convertChar8x16(uint8 *dst, const Glyph &g);
-void convertChar16x16(uint8 *dst, const Glyph &g);
-
-typedef std::list<Glyph> GlyphList;
-void freeGlyphlist(GlyphList &list) {
- for (GlyphList::iterator i = list.begin(); i != list.end(); ++i)
- delete[] i->plainData;
- list.clear();
-}
-
-} // end of anonymous namespace
-
int main(int argc, char *argv[]) {
if (argc < 2 || argc > 3) {
printf("Usage:\n\t%s <input ttf font> [outfile]\n", argv[0]);
@@ -112,13 +65,6 @@ int main(int argc, char *argv[]) {
int chars8x16 = 0;
int chars16x16 = 0;
- // FIXME: It seems some ttf fonts will only render invalid data,
- // when FreeType2 is asked to provide 8x16 glyphs. "sazanami-mincho.ttf"
- // is such a case. When we will render them in the default 16x16 setting
- // all ASCII chars will be rendered correctly and still fit within 8x16.
- // Some fonts might require special setup as 8x16 though.
- // We should try to find some proper way of detecting and handling this.
-
// ASCII chars will be rendererd as 8x16
if (!setGlyphSize(8, 16))
return -1;
@@ -263,7 +209,11 @@ int main(int argc, char *argv[]) {
return 0;
}
-namespace {
+void freeGlyphlist(GlyphList &list) {
+ for (GlyphList::iterator i = list.begin(); i != list.end(); ++i)
+ delete[] i->plainData;
+ list.clear();
+}
bool isASCII(uint8 fB) {
return (mapASCIItoChunk(fB) != -1);
@@ -533,5 +483,3 @@ void convertChar16x16(uint8 *dst, const Glyph &g) {
}
}
-} // end of anonymous namespace
-
diff --git a/create_sjisfnt.h b/create_sjisfnt.h
new file mode 100644
index 0000000..abb85df
--- /dev/null
+++ b/create_sjisfnt.h
@@ -0,0 +1,67 @@
+/* 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 2
+ * 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, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef CREATE_SJISFNT_H
+#define CREATE_SJISFNT_H
+
+#include "common/util.h"
+
+#include <list>
+
+bool isASCII(uint8 fB);
+
+int mapASCIItoChunk(uint8 fB);
+int mapSJIStoChunk(uint8 fB, uint8 sB);
+
+bool initSJIStoUTF32Conversion();
+void deinitSJIStoUTF32Conversion();
+uint32 convertSJIStoUTF32(uint8 fB, uint8 sB);
+
+bool initFreeType(const char *font);
+void deinitFreeType();
+
+struct Glyph {
+ uint8 fB, sB;
+
+ int xOffset;
+ int yOffset;
+ int height;
+ int width;
+
+ int pitch;
+ uint8 *plainData;
+};
+
+bool setGlyphSize(int width, int height);
+bool checkGlyphSize(const Glyph &g, const int baseLine, const int maxW, const int maxH);
+
+bool drawGlyph(uint8 fB, uint8 sB, Glyph &glyph);
+bool drawGlyph(uint32 unicode, Glyph &glyph);
+
+void convertChar8x16(uint8 *dst, const Glyph &g);
+void convertChar16x16(uint8 *dst, const Glyph &g);
+
+typedef std::list<Glyph> GlyphList;
+void freeGlyphlist(GlyphList &list);
+
+#endif
+
Commit: b9db877d6c86f235adcac9940a13d163ea2a0211
https://github.com/scummvm/scummvm-tools/commit/b9db877d6c86f235adcac9940a13d163ea2a0211
Author: Johannes Schickel (lordhoto at scummvm.org)
Date: 2011-06-30T17:29:11-07:00
Commit Message:
TOOLS: Move create_sjisfnt TTF code to a class.
Changed paths:
create_sjisfnt.cpp
create_sjisfnt.h
diff --git a/create_sjisfnt.cpp b/create_sjisfnt.cpp
index 901cb46..40a64ba 100644
--- a/create_sjisfnt.cpp
+++ b/create_sjisfnt.cpp
@@ -31,9 +31,6 @@
#include <assert.h>
#include <errno.h>
-#include <ft2build.h>
-#include FT_FREETYPE_H
-
int main(int argc, char *argv[]) {
if (argc < 2 || argc > 3) {
printf("Usage:\n\t%s <input ttf font> [outfile]\n", argv[0]);
@@ -54,20 +51,22 @@ int main(int argc, char *argv[]) {
atexit(deinitSJIStoUTF32Conversion);
- if (!initFreeType(font)) {
+ TrueTypeFont *ttf = new TrueTypeFont();
+ if (!ttf->load(font)) {
+ delete ttf;
error("Could not initialize FreeType library.");
return -1;
}
- atexit(deinitFreeType);
-
GlyphList glyphs;
int chars8x16 = 0;
int chars16x16 = 0;
// ASCII chars will be rendererd as 8x16
- if (!setGlyphSize(8, 16))
+ if (!ttf->setSize(8, 16)) {
+ delete ttf;
return -1;
+ }
for (uint8 fB = 0x00; fB <= 0xDF; ++fB) {
if (mapASCIItoChunk(fB) == -1)
@@ -76,12 +75,13 @@ int main(int argc, char *argv[]) {
++chars8x16;
Glyph data;
- if (drawGlyph(fB, 0, data))
+ if (ttf->renderGlyph(fB, 0, data))
glyphs.push_back(data);
}
// The two byte SJIS chars will be rendered as 16x16
- if (!setGlyphSize(16, 16)) {
+ if (!ttf->setSize(16, 16)) {
+ delete ttf;
freeGlyphlist(glyphs);
return -1;
}
@@ -97,11 +97,14 @@ int main(int argc, char *argv[]) {
++chars16x16;
Glyph data;
- if (drawGlyph(fB, sB, data))
+ if (ttf->renderGlyph(fB, sB, data))
glyphs.push_back(data);
}
}
+ delete ttf;
+ ttf = 0;
+
// Post process all chars, so that xOffset is at least 0
int minXOffset = 0;
for (GlyphList::const_iterator i = glyphs.begin(); i != glyphs.end(); ++i)
@@ -146,10 +149,16 @@ int main(int argc, char *argv[]) {
const int sjis8x16DataSize = chars8x16 * 16;
uint8 *sjis8x16FontData = new uint8[sjis8x16DataSize];
+ if (!sjis8x16FontData) {
+ freeGlyphlist(glyphs);
+ error("Out of memory");
+ }
+
const int sjis16x16DataSize = chars16x16 * 32;
uint8 *sjis16x16FontData = new uint8[sjis16x16DataSize];
if (!sjis16x16FontData) {
+ delete[] sjis8x16FontData;
freeGlyphlist(glyphs);
error("Out of memory");
}
@@ -308,26 +317,36 @@ uint32 convertSJIStoUTF32(uint8 fB, uint8 sB) {
return ret;
}
-FT_Library ft = NULL;
-FT_Face sjisFont = NULL;
+bool checkGlyphSize(const Glyph &g, const int baseLine, const int maxW, const int maxH) {
+ if (baseLine - g.yOffset < 0 || baseLine - g.yOffset + g.height > (maxH + 1) ||
+ g.xOffset > (maxW - 1) || g.xOffset + g.width > (maxW + 1))
+ return false;
+ return true;
+}
+
+TrueTypeFont::TrueTypeFont()
+ : _library(0), _sjisFont(0) {
+}
+
+TrueTypeFont::~TrueTypeFont() {
+ FT_Done_Face(_sjisFont);
+ FT_Done_FreeType(_library);
+}
-bool initFreeType(const char *font) {
- FT_Error err = FT_Init_FreeType(&ft);
+bool TrueTypeFont::load(const char *font) {
+ FT_Error err = FT_Init_FreeType(&_library);
if (err) {
warning("Could not initialize FreeType2 library.");
return false;
}
- err = FT_New_Face(ft, font, 0, &sjisFont);
+ err = FT_New_Face(_library, font, 0, &_sjisFont);
if (err) {
warning("Could not load font '%s'", font);
return false;
}
- if (!setGlyphSize(16, 16))
- return false;
-
- err = FT_Select_Charmap(sjisFont, FT_ENCODING_UNICODE);
+ err = FT_Select_Charmap(_sjisFont, FT_ENCODING_UNICODE);
if (err) {
warning("Could not select unicode charmap.");
return false;
@@ -336,29 +355,17 @@ bool initFreeType(const char *font) {
return true;
}
-void deinitFreeType() {
- FT_Done_Face(sjisFont);
- FT_Done_FreeType(ft);
-}
-
-bool setGlyphSize(int width, int height) {
- FT_Error err = FT_Set_Pixel_Sizes(sjisFont, width, height);
+bool TrueTypeFont::setSize(int width, int height) {
+ FT_Error err = FT_Set_Pixel_Sizes(_sjisFont, width, height);
if (err) {
- warning("Could not initialize font for %dx%d outout.", width, height);
+ warning("Could not initialize font for %dx%d output.", width, height);
return false;
}
return true;
}
-bool checkGlyphSize(const Glyph &g, const int baseLine, const int maxW, const int maxH) {
- if (baseLine - g.yOffset < 0 || baseLine - g.yOffset + g.height > (maxH + 1) ||
- g.xOffset > (maxW - 1) || g.xOffset + g.width > (maxW + 1))
- return false;
- return true;
-}
-
-bool drawGlyph(uint8 fB, uint8 sB, Glyph &glyph) {
+bool TrueTypeFont::renderGlyph(uint8 fB, uint8 sB, Glyph &glyph) {
uint32 utf32 = convertSJIStoUTF32(fB, sB);
if (utf32 == (uint32)-1) {
// For now we disable that warning, since iconv will fail for all reserved,
@@ -374,7 +381,7 @@ bool drawGlyph(uint8 fB, uint8 sB, Glyph &glyph) {
glyph.fB = fB;
glyph.sB = sB;
- if (!drawGlyph(utf32, glyph)) {
+ if (!renderGlyph(utf32, glyph)) {
warning("Could not render glyph: %.2X %.2X", fB, sB);
return false;
}
@@ -382,23 +389,23 @@ bool drawGlyph(uint8 fB, uint8 sB, Glyph &glyph) {
return true;
}
-bool drawGlyph(uint32 unicode, Glyph &glyph) {
- uint32 index = FT_Get_Char_Index(sjisFont, unicode);
+bool TrueTypeFont::renderGlyph(uint32 unicode, Glyph &glyph) {
+ uint32 index = FT_Get_Char_Index(_sjisFont, unicode);
if (!index)
return false;
- FT_Error err = FT_Load_Glyph(sjisFont, index, FT_LOAD_MONOCHROME | FT_LOAD_NO_HINTING);
+ FT_Error err = FT_Load_Glyph(_sjisFont, index, FT_LOAD_MONOCHROME | FT_LOAD_NO_HINTING);
if (err)
return false;
- err = FT_Render_Glyph(sjisFont->glyph, FT_RENDER_MODE_MONO);
+ err = FT_Render_Glyph(_sjisFont->glyph, FT_RENDER_MODE_MONO);
if (err)
return false;
- const FT_Bitmap &bitmap = sjisFont->glyph->bitmap;
+ const FT_Bitmap &bitmap = _sjisFont->glyph->bitmap;
- glyph.yOffset = sjisFont->glyph->bitmap_top;
- glyph.xOffset = sjisFont->glyph->bitmap_left;
+ glyph.yOffset = _sjisFont->glyph->bitmap_top;
+ glyph.xOffset = _sjisFont->glyph->bitmap_left;
glyph.height = bitmap.rows;
glyph.width = bitmap.width;
glyph.pitch = bitmap.pitch;
diff --git a/create_sjisfnt.h b/create_sjisfnt.h
index abb85df..ca5a25c 100644
--- a/create_sjisfnt.h
+++ b/create_sjisfnt.h
@@ -27,6 +27,9 @@
#include <list>
+#include <ft2build.h>
+#include FT_FREETYPE_H
+
bool isASCII(uint8 fB);
int mapASCIItoChunk(uint8 fB);
@@ -36,9 +39,6 @@ bool initSJIStoUTF32Conversion();
void deinitSJIStoUTF32Conversion();
uint32 convertSJIStoUTF32(uint8 fB, uint8 sB);
-bool initFreeType(const char *font);
-void deinitFreeType();
-
struct Glyph {
uint8 fB, sB;
@@ -51,17 +51,30 @@ struct Glyph {
uint8 *plainData;
};
-bool setGlyphSize(int width, int height);
bool checkGlyphSize(const Glyph &g, const int baseLine, const int maxW, const int maxH);
-bool drawGlyph(uint8 fB, uint8 sB, Glyph &glyph);
-bool drawGlyph(uint32 unicode, Glyph &glyph);
-
void convertChar8x16(uint8 *dst, const Glyph &g);
void convertChar16x16(uint8 *dst, const Glyph &g);
typedef std::list<Glyph> GlyphList;
void freeGlyphlist(GlyphList &list);
+class TrueTypeFont {
+public:
+ TrueTypeFont();
+ ~TrueTypeFont();
+
+ bool load(const char *filename);
+
+ bool setSize(int width, int height);
+
+ bool renderGlyph(uint8 fb, uint8 sB, Glyph &glyph);
+private:
+ bool renderGlyph(uint32 unicode, Glyph &glyph);
+
+ FT_Library _library;
+ FT_Face _sjisFont;
+};
+
#endif
Commit: a7fe09a0235f19a935ec82dca853de04a60de676
https://github.com/scummvm/scummvm-tools/commit/a7fe09a0235f19a935ec82dca853de04a60de676
Author: Johannes Schickel (lordhoto at scummvm.org)
Date: 2011-06-30T17:54:23-07:00
Commit Message:
TOOLS: Implement proper character layouting in create_sjisfnt.
Changed paths:
create_sjisfnt.cpp
create_sjisfnt.h
diff --git a/create_sjisfnt.cpp b/create_sjisfnt.cpp
index 40a64ba..5609541 100644
--- a/create_sjisfnt.cpp
+++ b/create_sjisfnt.cpp
@@ -52,7 +52,7 @@ int main(int argc, char *argv[]) {
atexit(deinitSJIStoUTF32Conversion);
TrueTypeFont *ttf = new TrueTypeFont();
- if (!ttf->load(font)) {
+ if (!ttf->load(font, 16)) {
delete ttf;
error("Could not initialize FreeType library.");
return -1;
@@ -62,12 +62,6 @@ int main(int argc, char *argv[]) {
int chars8x16 = 0;
int chars16x16 = 0;
- // ASCII chars will be rendererd as 8x16
- if (!ttf->setSize(8, 16)) {
- delete ttf;
- return -1;
- }
-
for (uint8 fB = 0x00; fB <= 0xDF; ++fB) {
if (mapASCIItoChunk(fB) == -1)
continue;
@@ -79,13 +73,6 @@ int main(int argc, char *argv[]) {
glyphs.push_back(data);
}
- // The two byte SJIS chars will be rendered as 16x16
- if (!ttf->setSize(16, 16)) {
- delete ttf;
- freeGlyphlist(glyphs);
- return -1;
- }
-
for (uint8 fB = 0x81; fB <= 0xEF; ++fB) {
if (mapSJIStoChunk(fB, 0x40) == -1)
continue;
@@ -105,44 +92,32 @@ int main(int argc, char *argv[]) {
delete ttf;
ttf = 0;
- // Post process all chars, so that xOffset is at least 0
- int minXOffset = 0;
- for (GlyphList::const_iterator i = glyphs.begin(); i != glyphs.end(); ++i)
- minXOffset = std::min(minXOffset, i->xOffset);
-
- minXOffset = abs(minXOffset);
-
- for (GlyphList::iterator i = glyphs.begin(); i != glyphs.end(); ++i)
- i->xOffset += minXOffset;
-
- // Calculate the base line for the font. The possible range is [0, 15].
- // TODO: This logic might need some more tinkering, it's pretty hacky right now.
- int baseLine = 0;
+ // We try to find the minimum y offset here so we can substract it to make it 0 in the end.
+ // We need to do this, since otherwise the characters will take up too much vertical space.
+ int minYOffset = 16;
for (GlyphList::const_iterator i = glyphs.begin(); i != glyphs.end(); ++i) {
- int bL = 0;
-
- // Try to center the glyph vertically
- if (i->height + i->yOffset <= 16)
- bL = i->yOffset + (16 - (i->height + i->yOffset)) / 2;
-
- bL = std::min(bL, 15);
+ if (i->pitch == 0)
+ continue;
- baseLine = std::max(baseLine, bL);
+ minYOffset = std::min(minYOffset, i->yOffset);
}
// Check whether we have an character which does not fit within the boundaries6
- for (GlyphList::const_iterator i = glyphs.begin(); i != glyphs.end(); ++i) {
+ for (GlyphList::iterator i = glyphs.begin(); i != glyphs.end(); ++i) {
if (i->pitch == 0)
continue;
- if ((isASCII(i->fB) && !checkGlyphSize(*i, baseLine, 8, 16)) ||
- (!isASCII(i->fB) && !checkGlyphSize(*i, baseLine, 16, 16))) {
+ // Substract our minimum y offset
+ i->yOffset -= minYOffset;
+
+ if ((isASCII(i->fB) && !checkGlyphSize(*i, 8, 16)) ||
+ (!isASCII(i->fB) && !checkGlyphSize(*i, 16, 16))) {
for (GlyphList::iterator j = glyphs.begin(); j != glyphs.end(); ++j)
delete[] j->plainData;
- error("Could not fit glyph for %.2X %.2X top: %d bottom: %d, left: %d right: %d, xOffset: %d, yOffset: %d, width: %d, height: %d, baseLine: %d",
- i->fB, i->sB, baseLine - i->yOffset, baseLine - i->yOffset + i->height, i->xOffset, i->xOffset + i->width,
- i->xOffset, i->yOffset, i->width, i->height, baseLine);
+ error("Could not fit glyph for %.2X %.2X top: %d bottom: %d, left: %d right: %d, xOffset: %d, yOffset: %d, width: %d, height: %d",
+ i->fB, i->sB, i->yOffset, i->yOffset + i->height, i->xOffset, i->xOffset + i->width,
+ i->xOffset, i->yOffset, i->width, i->height);
}
}
@@ -172,7 +147,7 @@ int main(int argc, char *argv[]) {
if (chunk != -1) {
uint8 *dst = sjis8x16FontData + chunk * 16;
- dst += (baseLine - i->yOffset);
+ dst += i->yOffset;
convertChar8x16(dst, *i);
}
} else {
@@ -180,7 +155,7 @@ int main(int argc, char *argv[]) {
if (chunk != -1) {
uint8 *dst = sjis16x16FontData + chunk * 32;
- dst += (baseLine - i->yOffset) * 2;
+ dst += i->yOffset * 2;
convertChar16x16(dst, *i);
}
}
@@ -317,15 +292,15 @@ uint32 convertSJIStoUTF32(uint8 fB, uint8 sB) {
return ret;
}
-bool checkGlyphSize(const Glyph &g, const int baseLine, const int maxW, const int maxH) {
- if (baseLine - g.yOffset < 0 || baseLine - g.yOffset + g.height > (maxH + 1) ||
- g.xOffset > (maxW - 1) || g.xOffset + g.width > (maxW + 1))
+bool checkGlyphSize(const Glyph &g, const int maxW, const int maxH) {
+ if (g.yOffset < 0 || g.yOffset + g.height > maxH ||
+ g.xOffset > maxW || g.xOffset + g.width > maxW)
return false;
return true;
}
TrueTypeFont::TrueTypeFont()
- : _library(0), _sjisFont(0) {
+ : _library(0), _sjisFont(0), _ascent(0), _descent(0), _width(0), _height(0) {
}
TrueTypeFont::~TrueTypeFont() {
@@ -333,7 +308,15 @@ TrueTypeFont::~TrueTypeFont() {
FT_Done_FreeType(_library);
}
-bool TrueTypeFont::load(const char *font) {
+inline int ftFloor26_6(FT_Pos x) {
+ return x / 64;
+}
+
+inline int ftCeil26_6(FT_Pos x) {
+ return (x + 63) / 64;
+}
+
+bool TrueTypeFont::load(const char *font, int height) {
FT_Error err = FT_Init_FreeType(&_library);
if (err) {
warning("Could not initialize FreeType2 library.");
@@ -352,16 +335,24 @@ bool TrueTypeFont::load(const char *font) {
return false;
}
- return true;
-}
+ if (!FT_IS_SCALABLE(_sjisFont)) {
+ warning("Font '%s' is not scalable", font);
+ return false;
+ }
-bool TrueTypeFont::setSize(int width, int height) {
- FT_Error err = FT_Set_Pixel_Sizes(_sjisFont, width, height);
+ err = FT_Set_Char_Size(_sjisFont, 0, height * 64, 0, 0);
if (err) {
- warning("Could not initialize font for %dx%d output.", width, height);
+ warning("Could not initialize font for height %d", height);
return false;
}
+ FT_Fixed yScale = _sjisFont->size->metrics.y_scale;
+ _ascent = ftCeil26_6(FT_MulFix(_sjisFont->ascender, yScale));
+ _descent = ftCeil26_6(FT_MulFix(_sjisFont->descender, yScale));
+
+ _width = ftCeil26_6(FT_MulFix(_sjisFont->max_advance_width, _sjisFont->size->metrics.x_scale));
+ _height = _ascent - _descent + 1;
+
return true;
}
@@ -402,10 +393,18 @@ bool TrueTypeFont::renderGlyph(uint32 unicode, Glyph &glyph) {
if (err)
return false;
+ FT_Glyph_Metrics &metrics = _sjisFont->glyph->metrics;
+
+ glyph.xOffset = ftFloor26_6(metrics.horiBearingX);
+ glyph.yOffset = _ascent - ftFloor26_6(metrics.horiBearingY);
+
+ // In case we got a negative xMin we adjust that, this might make some
+ // characters give a odd layout though.
+ if (glyph.xOffset < 0)
+ glyph.xOffset = 0;
+
const FT_Bitmap &bitmap = _sjisFont->glyph->bitmap;
- glyph.yOffset = _sjisFont->glyph->bitmap_top;
- glyph.xOffset = _sjisFont->glyph->bitmap_left;
glyph.height = bitmap.rows;
glyph.width = bitmap.width;
glyph.pitch = bitmap.pitch;
diff --git a/create_sjisfnt.h b/create_sjisfnt.h
index ca5a25c..51ead01 100644
--- a/create_sjisfnt.h
+++ b/create_sjisfnt.h
@@ -44,6 +44,7 @@ struct Glyph {
int xOffset;
int yOffset;
+
int height;
int width;
@@ -51,7 +52,7 @@ struct Glyph {
uint8 *plainData;
};
-bool checkGlyphSize(const Glyph &g, const int baseLine, const int maxW, const int maxH);
+bool checkGlyphSize(const Glyph &g, const int maxW, const int maxH);
void convertChar8x16(uint8 *dst, const Glyph &g);
void convertChar16x16(uint8 *dst, const Glyph &g);
@@ -64,16 +65,16 @@ public:
TrueTypeFont();
~TrueTypeFont();
- bool load(const char *filename);
-
- bool setSize(int width, int height);
-
+ bool load(const char *filename, int height);
bool renderGlyph(uint8 fb, uint8 sB, Glyph &glyph);
private:
bool renderGlyph(uint32 unicode, Glyph &glyph);
FT_Library _library;
FT_Face _sjisFont;
+
+ int _ascent, _descent;
+ int _width, _height;
};
#endif
Commit: 505d800f83c6619c5f55cf3ef40ea676782d2b4f
https://github.com/scummvm/scummvm-tools/commit/505d800f83c6619c5f55cf3ef40ea676782d2b4f
Author: Johannes Schickel (lordhoto at scummvm.org)
Date: 2011-06-30T18:22:58-07:00
Commit Message:
TOOLS: Further clean up create_sjisfnt.
Changed paths:
create_sjisfnt.cpp
create_sjisfnt.h
diff --git a/create_sjisfnt.cpp b/create_sjisfnt.cpp
index 5609541..635e70a 100644
--- a/create_sjisfnt.cpp
+++ b/create_sjisfnt.cpp
@@ -110,8 +110,8 @@ int main(int argc, char *argv[]) {
// Substract our minimum y offset
i->yOffset -= minYOffset;
- if ((isASCII(i->fB) && !checkGlyphSize(*i, 8, 16)) ||
- (!isASCII(i->fB) && !checkGlyphSize(*i, 16, 16))) {
+ if ((isASCII(i->fB) && !i->checkSize(8, 16)) ||
+ (!isASCII(i->fB) && !i->checkSize(16, 16))) {
for (GlyphList::iterator j = glyphs.begin(); j != glyphs.end(); ++j)
delete[] j->plainData;
@@ -124,17 +124,14 @@ int main(int argc, char *argv[]) {
const int sjis8x16DataSize = chars8x16 * 16;
uint8 *sjis8x16FontData = new uint8[sjis8x16DataSize];
- if (!sjis8x16FontData) {
- freeGlyphlist(glyphs);
+ if (!sjis8x16FontData)
error("Out of memory");
- }
const int sjis16x16DataSize = chars16x16 * 32;
uint8 *sjis16x16FontData = new uint8[sjis16x16DataSize];
if (!sjis16x16FontData) {
delete[] sjis8x16FontData;
- freeGlyphlist(glyphs);
error("Out of memory");
}
@@ -145,24 +142,16 @@ int main(int argc, char *argv[]) {
if (isASCII(i->fB)) {
int chunk = mapASCIItoChunk(i->fB);
- if (chunk != -1) {
- uint8 *dst = sjis8x16FontData + chunk * 16;
- dst += i->yOffset;
- convertChar8x16(dst, *i);
- }
+ if (chunk != -1)
+ i->convertChar8x16(sjis8x16FontData + chunk * 16);
} else {
int chunk = mapSJIStoChunk(i->fB, i->sB);
- if (chunk != -1) {
- uint8 *dst = sjis16x16FontData + chunk * 32;
- dst += i->yOffset * 2;
- convertChar16x16(dst, *i);
- }
+ if (chunk != -1)
+ i->convertChar16x16(sjis16x16FontData + chunk * 32);
}
}
- freeGlyphlist(glyphs);
-
Common::File sjisFont(out, "wb");
if (sjisFont.isOpen()) {
// Write our magic bytes
@@ -193,12 +182,6 @@ int main(int argc, char *argv[]) {
return 0;
}
-void freeGlyphlist(GlyphList &list) {
- for (GlyphList::iterator i = list.begin(); i != list.end(); ++i)
- delete[] i->plainData;
- list.clear();
-}
-
bool isASCII(uint8 fB) {
return (mapASCIItoChunk(fB) != -1);
}
@@ -292,13 +275,6 @@ uint32 convertSJIStoUTF32(uint8 fB, uint8 sB) {
return ret;
}
-bool checkGlyphSize(const Glyph &g, const int maxW, const int maxH) {
- if (g.yOffset < 0 || g.yOffset + g.height > maxH ||
- g.xOffset > maxW || g.xOffset + g.width > maxW)
- return false;
- return true;
-}
-
TrueTypeFont::TrueTypeFont()
: _library(0), _sjisFont(0), _ascent(0), _descent(0), _width(0), _height(0) {
}
@@ -433,21 +409,58 @@ bool TrueTypeFont::renderGlyph(uint32 unicode, Glyph &glyph) {
return true;
}
-// TODO: merge these two
+Glyph::Glyph()
+ : fB(0), sB(0), xOffset(0), yOffset(0), height(0), width(0), pitch(0),
+ plainData(0) {
+}
+
+Glyph::Glyph(const Glyph &r)
+ : fB(r.fB), sB(r.sB), xOffset(r.xOffset), yOffset(r.yOffset),
+ height(r.height), width(r.width), pitch(r.pitch), plainData(0) {
+ plainData = new uint8[height * pitch];
+ memcpy(plainData, r.plainData, height * pitch);
+}
-void convertChar8x16(uint8 *dst, const Glyph &g) {
- const uint8 *src = g.plainData;
+Glyph::~Glyph() {
+ delete[] plainData;
+}
+
+Glyph &Glyph::operator=(const Glyph &r) {
+ delete[] plainData;
+
+ fB = r.fB;
+ sB = r.sB;
+ xOffset = r.xOffset;
+ yOffset = r.yOffset;
+ height = r.height;
+ width = r.width;
+ pitch = r.pitch;
+
+ plainData = new uint8[height * pitch];
+ memcpy(plainData, r.plainData, height * pitch);
+
+ return *this;
+}
+
+bool Glyph::checkSize(const int maxW, const int maxH) const {
+ if (yOffset < 0 || yOffset + height > maxH ||
+ xOffset < 0 || xOffset + width > maxW)
+ return false;
+ return true;
+}
- assert(g.width + g.xOffset <= 8);
+void Glyph::convertChar8x16(uint8 *dst) const {
+ const uint8 *src = plainData;
+ dst += yOffset;
- for (int y = 0; y < g.height; ++y) {
- uint8 mask = 1 << (7 - g.xOffset);
+ for (int y = 0; y < height; ++y) {
+ uint8 mask = 1 << (7 - xOffset);
const uint8 *curSrc = src;
uint8 line = 0;
uint8 d = 0;
- for (int x = 0; x < g.width; ++x) {
+ for (int x = 0; x < width; ++x) {
if (x == 0)
d = *curSrc++;
@@ -459,21 +472,22 @@ void convertChar8x16(uint8 *dst, const Glyph &g) {
}
*dst++ = line;
- src += g.pitch;
+ src += pitch;
}
}
-void convertChar16x16(uint8 *dst, const Glyph &g) {
- const uint8 *src = g.plainData;
+void Glyph::convertChar16x16(uint8 *dst) const {
+ const uint8 *src = plainData;
+ dst += yOffset * 2;
- for (int y = 0; y < g.height; ++y) {
- uint16 mask = 1 << (15 - g.xOffset);
+ for (int y = 0; y < height; ++y) {
+ uint16 mask = 1 << (15 - xOffset);
const uint8 *curSrc = src;
uint16 line = 0;
uint8 d = 0;
- for (int x = 0; x < g.width; ++x) {
+ for (int x = 0; x < width; ++x) {
if (x == 0 || x == 8)
d = *curSrc++;
@@ -485,7 +499,7 @@ void convertChar16x16(uint8 *dst, const Glyph &g) {
}
WRITE_BE_UINT16(dst, line); dst += 2;
- src += g.pitch;
+ src += pitch;
}
}
diff --git a/create_sjisfnt.h b/create_sjisfnt.h
index 51ead01..44088ec 100644
--- a/create_sjisfnt.h
+++ b/create_sjisfnt.h
@@ -40,6 +40,12 @@ void deinitSJIStoUTF32Conversion();
uint32 convertSJIStoUTF32(uint8 fB, uint8 sB);
struct Glyph {
+ Glyph();
+ Glyph(const Glyph &r);
+ ~Glyph();
+
+ Glyph &operator=(const Glyph &r);
+
uint8 fB, sB;
int xOffset;
@@ -50,15 +56,14 @@ struct Glyph {
int pitch;
uint8 *plainData;
-};
-bool checkGlyphSize(const Glyph &g, const int maxW, const int maxH);
+ bool checkSize(const int maxW, const int maxH) const;
-void convertChar8x16(uint8 *dst, const Glyph &g);
-void convertChar16x16(uint8 *dst, const Glyph &g);
+ void convertChar8x16(uint8 *dst) const;
+ void convertChar16x16(uint8 *dst) const;
+};
typedef std::list<Glyph> GlyphList;
-void freeGlyphlist(GlyphList &list);
class TrueTypeFont {
public:
More information about the Scummvm-git-logs
mailing list