Commit b303177
Parse SVG circles
Changed files (5)
addedbirdfont-import-debug.shmodifiedlibbirdfont/CircleTool.valamodifiedlibbirdfont/Path.valamodifiedlibbirdfont/SvgParser.valamodifiedlibbirdfont/SvgStyle.vala
Diff
new file mode 100755@@ -0,0 +1,7 @@+#!/bin/sh+export LD_LIBRARY_PATH="./build/bin:$LD_LIBRARY_PATH"+PKG_PATH=$(dirname "$(readlink -f "$0")")+cd "${PKG_PATH}"++gdb ./build/bin/birdfont-import -ex "run "$@""+@@ -114,10 +114,35 @@ public class CircleTool : Tool { } } + public static Path create_circle (double x, double y,+ double r, PointType pt) { + + double px, py;+ Path path = new Path ();+ double steps = (pt == PointType.QUADRATIC) ? PI / 8 : PI / 4; + + for (double angle = 0; angle < 2 * PI; angle += steps) {+ px = r * cos (angle) + x;+ py = r * sin (angle) + y;+ path.add (px, py);+ }+ + path.init_point_type (pt);+ path.close ();+ path.recalculate_linear_handles ();++ for (int i = 0; i < 3; i++) {+ foreach (EditPoint ep in path.points) {+ ep.set_tie_handle (true);+ ep.process_tied_handle ();+ }+ }++ return path;+ }+ void press (int button, double x, double y) { Glyph glyph = MainWindow.get_current_glyph ();- double radius = 2;- double px, py, steps; Path path = new Path (); press_x = x;@@ -132,30 +157,16 @@ public class CircleTool : Tool { glyph.store_undo_state (); - steps = (DrawingTools.point_type == PointType.QUADRATIC) ? PI / 8 : PI / 4; + double px = Glyph.path_coordinate_x (x);+ double py = Glyph.path_coordinate_y (y); - for (double angle = 0; angle < 2 * PI; angle += steps) {- px = radius * cos (angle) + Glyph.path_coordinate_x (x);- py = radius * sin (angle) + Glyph.path_coordinate_y (y);- path.add (px, py);- }- - path.init_point_type ();- path.close ();- path.recalculate_linear_handles ();+ path = create_circle (px, py, 2, DrawingTools.point_type); if (StrokeTool.add_stroke) { path.stroke = StrokeTool.stroke_width; path.line_cap = StrokeTool.line_cap; }-- for (int i = 0; i < 3; i++) {- foreach (EditPoint ep in path.points) {- ep.set_tie_handle (true);- ep.process_tied_handle ();- }- }- + glyph.add_path (path); if (!PenTool.is_counter_path (circle)) {@@ -2101,10 +2101,14 @@ public class Path : GLib.Object { update_region_boundaries (); } - public void init_point_type () {+ public void init_point_type (PointType pt = PointType.NONE) { PointType type; - switch (DrawingTools.point_type) {+ if (pt == PointType.NONE) {+ pt = DrawingTools.point_type;+ }+ + switch (pt) { case PointType.QUADRATIC: type = PointType.LINE_QUADRATIC; break;@@ -190,6 +190,10 @@ public class SvgParser { if (t.get_name () == "polygon") { parse_polygon (t, pl); }+ + if (t.get_name () == "circle") {+ parse_circle (t, pl);+ } } return pl.get_all_paths ();@@ -233,6 +237,10 @@ public class SvgParser { if (t.get_name () == "rect") { parse_rect (t, pl); }++ if (t.get_name () == "circle") {+ parse_circle (t, pl);+ } } foreach (Attribute attr in tag.get_attributes ()) { @@ -419,6 +427,71 @@ public class SvgParser { return param.strip(); } + private void parse_circle (Tag tag, Layer pl) {+ Path p;+ double x, y, r;+ Glyph g;+ PathList npl;+ BezierPoints[] bezier_points;+ SvgStyle style = new SvgStyle ();+ bool hidden = false;+ + npl = new PathList ();+ + x = 0;+ y = 0;+ r = 0;+ + foreach (Attribute attr in tag.get_attributes ()) { + if (attr.get_name () == "cx") {+ x = parse_double (attr.get_content ());+ }+ + if (attr.get_name () == "cy") {+ y = -parse_double (attr.get_content ());+ }++ if (attr.get_name () == "r") {+ r = parse_double (attr.get_content ());+ }+ + if (attr.get_name () == "style") {+ style = SvgStyle.parse (attr.get_content ());+ }+ + if (attr.get_name () == "display" && attr.get_content () == "none") {+ hidden = true;+ }+ }+ + if (hidden) {+ return;+ }+ + bezier_points = new BezierPoints[1];+ bezier_points[0] = new BezierPoints ();+ bezier_points[0].type == 'L';+ bezier_points[0].x0 = x;+ bezier_points[0].y0 = y;++ g = MainWindow.get_current_glyph ();+ move_and_resize (bezier_points, 1, false, 1, g);+ + p = CircleTool.create_circle (bezier_points[0].x0,+ bezier_points[0].y0, r, PointType.CUBIC);++ npl.add (p);+ + foreach (Attribute attr in tag.get_attributes ()) {+ if (attr.get_name () == "transform") {+ transform_paths (attr.get_content (), npl);+ }+ }+ + style.apply (npl);+ pl.paths.append (npl);+ }+ private void parse_rect (Tag tag, Layer pl) { Path p; double x, y, x2, y2;@@ -541,18 +614,7 @@ public class SvgParser { } pl.paths.append (path_list);- - foreach (Path p in path_list.paths) {- if (style.has_stroke ()) {- p.stroke = style.get_stroke_width ();- } else {- p.stroke = 0;- }- - p.line_cap = style.get_line_cap ();- p.reset_stroke ();- p.update_region_boundaries (); - }+ style.apply (path_list); // assume the even odd rule is applied and convert the path // to a path using the non-zero rule@@ -83,6 +83,20 @@ public class SvgStyle { return s; }+ + public void apply (PathList path_list) {+ foreach (Path p in path_list.paths) {+ if (has_stroke ()) {+ p.stroke = get_stroke_width ();+ } else {+ p.stroke = 0;+ }+ + p.line_cap = get_line_cap ();+ p.reset_stroke ();+ p.update_region_boundaries (); + }+ } } }