我编写了一个简单的代码来检查给定的自定义字体文件(.ttf或.otf)中是否有可用的字形,为此我正在使用:
Font.canDisplay()
当我在Windows上测试我的代码时工作正常,但是在mac上它总是返回true,即使该字形不可用,我猜在mac中默认为字体替换选项,任何建议如何关闭它?
Environment:
VM Version 1.6.0_26
Mac OS X 10.7.2
字体文件(truetype):http://www.fontsc.com/font/depth-charge(您可以在此网站上查看字符映射字符在CAP中不可用)
答案 0 :(得分:1)
在NativeEnvironment中注册的Native OS和Font之间存在差异,
需要检查本机操作系统中的Font is there registred
Font font = Font.createFont(int fontFormat, File fontFile)
/(int fontFormat, InputStream fontStream)
GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
ge.registerFont(font);
if (font.canDisplay()/canDisplayUpTo()){
//your code with font.....
}
canDisplay()/canDisplayUpTo()
可以是createGlyphVector ,则答案 1 :(得分:0)
更新: Oracle接受了我的错误报告: https://bugs.java.com/bugdatabase/view_bug.do?bug_id=JDK-8223834
您将在下面找到可能的解决方法:
这似乎是Mac OS的Font2D类实现中的错误。
我能够使用反射解决该问题。这是在Mac上产生正确结果的代码。它在Kotlin中,但是在必要时将其直接翻译为Java应该很简单。
// Mac OS workaround for incorrectly implemented canDisplayUpTo method
fun Font.macCanDisplayUpTo(str: String): Int {
val getFontMethod = Font::class.java.getDeclaredMethod("getFont2D")
getFontMethod.isAccessible = true
val font2d = getFontMethod.invoke(this)
val getMapperMethod = font2d.javaClass.getDeclaredMethod("getMapper")
getMapperMethod.isAccessible = true
val mapper = getMapperMethod.invoke(font2d)
val charToGlyphMethod = mapper.javaClass.getDeclaredMethod("charToGlyph", Char::class.java)
val len = str.length
var i = 0
while (i < len) {
val c = str[i]
val glyph = charToGlyphMethod.invoke(mapper, c) as Int
if (glyph >= 0) {
i++
continue
}
if (!Character.isHighSurrogate(c)
|| (charToGlyphMethod.invoke(mapper, str.codePointAt(i)) as Int) < 0) {
return i
}
i += 2
}
return -1
}
如果您使用的是Java 9或更高版本,则需要将以下命令args传递给VM,以使代码正常工作:
--add-opens java.desktop/java.awt=your.module.name
--add-opens java.desktop/sun.font=your.module.name
此代码在Windows上不起作用(将产生不正确的结果)。仅适用于MacOS。