Hosted by
|
with Readers; use Readers;
with Token_Readers; use Token_Readers;
with XML_Readers; use XML_Readers;
with Writers; use Writers;
with Indent_Writers; use Indent_Writers;
with XML_Writers; use XML_Writers;
with Real_Vectors; use Real_Vectors;
with Real_Strings; use Real_Strings;
with Integer_Strings; use Integer_Strings;
with Messages; use Messages;
with Glyphs; use Glyphs;
with Glyphs.SVG; use Glyphs.SVG;
package body Choices.SVG is
procedure Read_SVG_Header
(XML : access XML_Reader) is
begin
Assert_Tag_Name(XML, "?xml");
Assert_Attribute_Name(XML, "version");
Assert_Attribute_Value(XML, "1.0");
Assert_Attribute_Name(XML, "standalone");
Assert_Attribute_Value(XML, "no");
Exit_Tag(XML);
Assert_Tag_Name(XML, "!DOCTYPE");
Assert_Attribute_Name(XML, "svg");
Assert_Attribute_Name(XML, "PUBLIC");
Assert_Attribute_Name(XML, "-//W3C//DTD SVG 1.1//EN");
Assert_Attribute_Name(XML, "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd");
Exit_Tag(XML);
end Read_SVG_Header;
procedure Write_SVG_Header
(XML : access XML_Writer)
is
begin
Start_Tag(XML, "?xml");
Write_Attribute(XML, "version", "1.0");
Write_Attribute(XML, "standalone", "no");
Close_Tag(XML, "?");
New_Line(XML);
Start_Tag(XML, "!DOCTYPE");
Put(XML, ' '); Write_Word(XML, "svg");
Put(XML, ' '); Write_Word(XML, "PUBLIC");
Put(XML, ' '); Write_String(XML, "-//W3C//DTD SVG 1.1//EN");
Put(XML, ' '); Write_String(XML, "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd");
Close_Tag(XML);
New_Line(XML);
end Write_SVG_Header;
procedure Read_SVG_Start_Tag
(XML : access XML_Reader;
This : access Choice)
is
Width, Height : Real;
begin
Assert_Tag_name(XML, "svg");
while not End_Of_Tag(XML) loop
Read_Attribute_Name(XML);
if Found(XML, "width") then
Read_Attribute_Value(XML);
Width := To_Number(Get_Token(XML));
elsif Found(XML, "height") then
Read_Attribute_Value(XML);
Height := To_Number(Get_Token(XML));
elsif Found(XML, "version") then
Assert_Attribute_Value(XML, "1.1");
elsif Found(XML, "xmlns") then
Assert_Attribute_Value(XML, "http://www.w3.org/2000/svg");
elsif Found(XML, "xmlns:roemer") then
Assert_Attribute_Value(XML, "http://roemer.sourceforge.net/xmlns");
else
XML_Expect_Error(XML, "", "width" / "height");
end if;
end loop;
Exit_Tag(XML);
end Read_SVG_Start_Tag;
procedure Write_SVG_Start_Tag
(XML : access XML_Writer;
This : access Choice;
Tolerance : in Real;
Width : in Real;
Height : in Real) is
begin
Start_Tag(XML, "svg");
Write_Attribute(XML, "width", To_String(Width, Tolerance));
Write_Attribute(XML, "height", To_String(Height, Tolerance));
Write_Attribute(XML, "version", "1.1");
Write_Attribute(XML, "xmlns", "http://www.w3.org/2000/svg");
Write_Attribute(XML, "xmlns:roemer", "http://roemer.sourceforge.net/xmlns");
Close_Tag(XML);
New_Line(XML);
Indent(XML);
end Write_SVG_Start_Tag;
function Read
(XML : access XML_Reader)
return Choice_Access
is
Result : Choice_Access := Create;
begin
Read_SVG_Header(XML);
Read_SVG_Start_Tag(XML, Result);
while Descend(XML) loop
if not Context_Is(XML, "path") then
XML_Expect_Error(XML, "/svg", "path");
end if;
Add_Regular(Result, Read(XML));
end loop;
return Result;
end Read;
procedure Layout
(This : access Choice;
Glyphs_Per_Row : out Positive;
Rows : out Positive;
Glyph_Width : out Real;
Glyph_Height : out Real)
is
Layout_Space : constant := 8;
Layout_Factor : constant := 4;
Count : Natural := This.Regular_Count + This.Special_Count;
begin
Glyph_Width := 0.0;
Glyph_Height := 0.0;
for Index in 1 .. This.Regular_Count loop
if Get_Height(Get_Regular(This, Index)) > Glyph_Height then
Glyph_Height := Get_Height(Get_Regular(This, Index));
end if;
if Get_Width(Get_Regular(This, Index)) > Glyph_Width then
Glyph_Width := Get_Width(Get_Regular(This, Index));
end if;
end loop;
for Index in 1 .. This.Special_Count loop
if Get_Height(Get_Special(This, Index)) > Glyph_Height then
Glyph_Height := Get_Height(Get_Special(This, Index));
end if;
if Get_Width(Get_Special(This, Index)) > Glyph_Width then
Glyph_Width := Get_Width(Get_Special(This, Index));
end if;
end loop;
Glyph_Width := Glyph_Width + Real(Layout_Space * Layout_Factor);
Glyph_Height := Glyph_Height + Real(Layout_Space * Layout_Factor);
Glyphs_Per_Row := 480 * Layout_Factor / Positive(Glyph_Width);
Rows := (Count + Glyphs_Per_Row - 1) / Glyphs_Per_Row;
if Rows = 1 then
Glyphs_Per_Row := Count;
end if;
end Layout;
procedure Write
(XML : access XML_Writer;
This : access Choice;
Tolerance : in Real)
is
Glyph_Width : Real;
Glyph_Height : Real;
Glyphs_Per_Row : Positive;
Rows : Positive;
X, Y : Natural := 0;
|