我们一直无法找到减少字体使用的内存的方法。
我们通过使用 ImageMagick 和 perl 脚本为我们正在使用的所有可能的大小和字形生成 png 文件,成功地解决了这个问题。
png 文件放置在具有字体名称和磅值的目录结构中。每个字形都有自己的 png 命名,以十六进制 Unicode 代码点命名。
然后将所有 png 文件放入 Xcode 项目中,并以这种方式结束在包中。
在运行时,我们不使用字体[UIImage imageNamed:]
渲染,而是执行 a 并渲染它。
该解决方案性能良好,并且在小部件中使用了有限的内存量。
有几个缺点:
- 小部件和主应用程序包变得臃肿:添加了 1000 多个 png 文件(磁盘上 575 KB = 4.7 MB)。我们还不知道这会增加多少应用程序的分布大小。
- 我们失去了原始方法的灵活性。新的设备类型或对动态类型的更好支持可能会导致需要更多尺寸,然后我们需要生成更多 png。
- 更大的错误风险
生成 png 的脚本是:
#!/usr/bin/perl
use File::Path qw(make_path);
$fontName = "SSSymboliconsBlock";
@sizes = (10, 11, 13, 16, 18);
foreach $size (@sizes) {
$path = "fontCache/$fontName/$size";
make_path($path);
@glyphs = ("1f50d", "1f512", "1f511");
foreach $glyphNo (@glyphs) {
$glyph = chr(hex($glyphNo));
system("convert -background none -fill black -font $fontName.ttf -pointsize $size label:\"$glyph\" $path/$glyphNo.png");
}
}
要加载图像,它是这样的:
- (UIImage *)loadImageForGlyph:(NSString *)glyph
fontName:(NSString *)fontName
fontSize:(CGFloat)fontSize
{
// NSDictionary that translates from a glyph to a string with the hex
// value of the code point.
// e.g. glyph = @"", codePoint = @"1f50d"
NSString * codePoint = self.codePointByGlyph[glyph];
NSString * path
= [[[[@"fontCache" stringByAppendingPathComponent:fontName]
stringByAppendingPathComponent:[@(fontSize) stringValue]]
stringByAppendingPathComponent:codePoint]
stringByAppendingPathExtension:@"png"];
UIImage * img = [UIImage imageNamed:path];
return img;
}