Hosted by
|
with Readers; use Readers;
with Token_Readers; use Token_Readers;
with Writers; use Writers;
with Indent_Writers; use Indent_Writers;
with Real_Vectors; use Real_Vectors;
with Integer_Strings; use Integer_Strings;
with Messages; use Messages;
with Lines; use Lines;
package body Outlines.SVG is
SVG_Error : exception;
function Read
(XML : access XML_Reader)
return Outline_Access
is
XS, YS : Real;
X1, Y1 : Real;
X2, Y2 : Real;
X3, Y3 : Real;
XE, YE : Real;
Result : Outline_Access := Create;
begin
Skip_Whitespace(XML);
Assert_Char(XML, 'M');
Skip_Whitespace(XML);
XS := Read_Real(XML);
YS := Read_Real(XML);
XE := XS;
YE := YS;
loop
if End_Of_File(XML) then
Error(XML, "unexpected end of file");
raise SVG_Error;
end if;
if Found_Char(XML, 'Z') or Found_Char(XML, 'M') then
if XS /= XE or YS /= YE then
Error(XML, "previous outline not closed");
raise SVG_Error;
end if;
exit;
end if;
if Found_Char(XML, 'L') then
Get(XML); Skip_Whitespace(XML);
X1 := Read_Real(XML); Y1 := Read_Real(XML);
Add_Straight(Result, (X1, Y1));
XE := X1; YE := Y1;
elsif Found_Char(XML, 'C') then
Get(XML); Skip_Whitespace(XML);
X1 := Read_Real(XML); Y1 := Read_Real(XML);
X2 := Read_Real(XML); Y2 := Read_Real(XML);
X3 := Read_Real(XML); Y3 := Read_Real(XML);
Add_Cubic(Result, (X1, Y1), (X2, Y2), (X3, Y3));
XE := X3; YE := Y3;
else
Expect_Error(XML, "" & Get_Char(XML),
"Z" / "M" / "L" / "C");
end if;
end loop;
return Result;
end Read;
procedure Write
(XML : access XML_Writer;
This : access Outline;
Tolerance : in Real)
is
use Outlines.Line_Lists;
begin
Put_Line(XML, "M " & To_String(Last(This).To, Tolerance));
Reset(This);
while Line_Lists.Next(This) loop
Put_Line(XML, To_SVG(Current(This), Tolerance));
end loop;
end Write;
end Outlines.SVG;
|