core :: Text :: parse_bmfont
self
as an XML BMFont description fileReports only basic XML format errors, other errors may be ignored or cause a crash.
var desc = """
<font>
<info face="arial" size="72" bold="0" italic="0" charset=""
unicode="1" stretchH="100" smooth="1" aa="1" padding="2,2,2,2"
spacing="0,0" outline="0"/>
<common lineHeight="80" base="65" scaleW="4030" scaleH="231"
pages="1" packed="0"/>
<pages>
<page id="0" file="arial.png"/>
</pages>
<chars count="3">
<char id="65" x="2519" y="10" width="55" height="59" xoffset="0"
yoffset="13" xadvance="48" page="0" chnl="15"/>
<char id="66" x="2600" y="10" width="46" height="58" xoffset="5"
yoffset="13" xadvance="48" page="0" chnl="15"/>
<char id="67" x="2673" y="9" width="52" height="60" xoffset="4"
yoffset="12" xadvance="52" page="0" chnl="15"/>
</chars>
<kernings count="1">
<kerning first="65" second="67" amount="-1"/>
</kernings>
</font>
"""
var fnt = desc.parse_bmfont("dir_in_assets").value
assert fnt.to_s == "<BMFont arial at 72.0 pt, 1 pages, 3 chars>"
assert fnt.line_height == 80.0
assert fnt.kernings['A', 'C'] == -1.0
assert fnt.chars['A'].page.as(TextureAsset).path == "dir_in_assets/arial.png"
# Parse `self` as an XML BMFont description file
#
# Reports only basic XML format errors, other errors may be ignored or
# cause a crash.
#
# ~~~
# var desc = """
# <font>
# <info face="arial" size="72" bold="0" italic="0" charset=""
# unicode="1" stretchH="100" smooth="1" aa="1" padding="2,2,2,2"
# spacing="0,0" outline="0"/>
# <common lineHeight="80" base="65" scaleW="4030" scaleH="231"
# pages="1" packed="0"/>
# <pages>
# <page id="0" file="arial.png"/>
# </pages>
# <chars count="3">
# <char id="65" x="2519" y="10" width="55" height="59" xoffset="0"
# yoffset="13" xadvance="48" page="0" chnl="15"/>
# <char id="66" x="2600" y="10" width="46" height="58" xoffset="5"
# yoffset="13" xadvance="48" page="0" chnl="15"/>
# <char id="67" x="2673" y="9" width="52" height="60" xoffset="4"
# yoffset="12" xadvance="52" page="0" chnl="15"/>
# </chars>
# <kernings count="1">
# <kerning first="65" second="67" amount="-1"/>
# </kernings>
# </font>
# """
#
# var fnt = desc.parse_bmfont("dir_in_assets").value
# assert fnt.to_s == "<BMFont arial at 72.0 pt, 1 pages, 3 chars>"
# assert fnt.line_height == 80.0
# assert fnt.kernings['A', 'C'] == -1.0
# assert fnt.chars['A'].page.as(TextureAsset).path == "dir_in_assets/arial.png"
# ~~~
fun parse_bmfont(dir: String): MaybeError[BMFont, Error]
do
# Parse XML
var xml = to_xml
if xml isa XMLError then
var msg = "XML Parse Error: {xml.message}:{xml.location or else 0}"
return new MaybeError[BMFont, Error](maybe_error=new Error(msg))
end
# Basic sanity check
var roots = xml["font"]
if roots.is_empty then
var msg = "Error: the XML document doesn't declare the expected `font` root"
return new MaybeError[BMFont, Error](maybe_error=new Error(msg))
end
# Expect the rest of the document to be well formatted
var root = roots.first
var info = root["info"].first
assert info isa XMLAttrTag
var info_map = info.attributes_to_map
var common = root["common"].first
assert common isa XMLAttrTag
var common_map = common.attributes_to_map
var fnt = new BMFont(
info_map["face"],
info_map["size"].to_f,
info_map["bold"] == "1",
info_map["italic"] == "1",
info_map["unicode"] == "1",
info_map["padding"],
info_map["spacing"],
common_map["lineHeight"].to_f,
common_map["base"].to_f,
common_map["scaleW"].to_f,
common_map["scaleH"].to_f
)
# Pages / pixel data files
var xml_pages = root["pages"].first
for page in xml_pages["page"] do
if not page isa XMLAttrTag then continue
var attributes = page.attributes_to_map
var file = dir / attributes["file"]
fnt.pages[attributes["id"]] = new TextureAsset(file)
end
# Char description
for item in root["chars"].first["char"] do
if not item isa XMLAttrTag then continue
var attributes = item.attributes_to_map
var id = attributes["id"].to_i.code_point
var c = new BMFontChar(
attributes["x"].to_f, attributes["y"].to_f,
attributes["width"].to_f, attributes["height"].to_f,
attributes["xoffset"].to_f, attributes["yoffset"].to_f,
attributes["xadvance"].to_f,
fnt.pages[attributes["page"]])
fnt.chars[id] = c
end
# Kerning between two characters
var kernings = root["kernings"]
if kernings.not_empty then
for item in kernings.first["kerning"] do
if not item isa XMLAttrTag then continue
var attributes = item.attributes_to_map
var first = attributes["first"].to_i.code_point
var second = attributes["second"].to_i.code_point
var amount = attributes["amount"].to_f
fnt.kernings[first, second] = amount
end
end
return new MaybeError[BMFont, Error](fnt)
end
lib/gamnit/bmfont.nit:156,2--275,4