Commit 796f6eba authored by Josh McCullough's avatar Josh McCullough
Browse files

Simplified element writing (moved WriteElement(XmlTextWriter) out to

SvgDocument as Write(XmlTextWriter); allowed elements to decide whether or
not they should be written. E.g. text elements should not be written
unless they have children.
parent e4cb89ac
Showing with 68 additions and 48 deletions
+68 -48
using System;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Xml;
namespace Svg
{
......@@ -41,7 +42,7 @@ namespace Svg
private SvgUnit _x;
private SvgUnit _y;
/// <summary>
/// Gets or sets the position where the left point of the svg should start.
/// </summary>
......@@ -51,10 +52,10 @@ namespace Svg
get { return _x; }
set
{
if(_x != value)
if (_x != value)
{
_x = value;
OnAttributeChanged(new AttributeEventArgs{ Attribute = "x", Value = value });
OnAttributeChanged(new AttributeEventArgs { Attribute = "x", Value = value });
}
}
}
......@@ -68,10 +69,10 @@ namespace Svg
get { return _y; }
set
{
if(_y != value)
if (_y != value)
{
_y = value;
OnAttributeChanged(new AttributeEventArgs{ Attribute = "y", Value = value });
OnAttributeChanged(new AttributeEventArgs { Attribute = "y", Value = value });
}
}
}
......@@ -115,7 +116,7 @@ namespace Svg
get { return this.Attributes.GetAttribute<SvgViewBox>("viewBox"); }
set { this.Attributes["viewBox"] = value; }
}
/// <summary>
/// Gets or sets the aspect of the viewport.
/// </summary>
......@@ -185,29 +186,29 @@ namespace Svg
break;
}
}
/// <summary>
/// Gets the <see cref="GraphicsPath"/> for this element.
/// </summary>
/// <value></value>
public GraphicsPath Path
{
get
{
get
{
var path = new GraphicsPath();
AddPaths(this, path);
return path;
}
}
/// <summary>
/// Gets the bounds of the svg element.
/// </summary>
/// <value>The bounds.</value>
public RectangleF Bounds
{
public RectangleF Bounds
{
get
{
return this.Path.GetBounds();
......@@ -246,7 +247,7 @@ namespace Svg
}
}
if (isWidthperc)
if (isWidthperc)
{
w = (bounds.Width + bounds.X) * (Width.Value * 0.01f);
}
......@@ -254,11 +255,11 @@ namespace Svg
{
w = Width.ToDeviceValue(null, UnitRenderingType.Horizontal, this);
}
if (isHeightperc)
if (isHeightperc)
{
h = (bounds.Height + bounds.Y) * (Height.Value * 0.01f);
}
else
else
{
h = Height.ToDeviceValue(null, UnitRenderingType.Vertical, this);
}
......@@ -282,6 +283,20 @@ namespace Svg
return newObj;
}
//Override the default behavior, writing out the namespaces.
protected override void WriteStartElement(XmlTextWriter writer)
{
base.WriteStartElement(writer);
foreach (var ns in SvgAttributeAttribute.Namespaces)
{
if (string.IsNullOrEmpty(ns.Key))
writer.WriteAttributeString("xmlns", ns.Value);
else
writer.WriteAttributeString("xmlns:" + ns.Key, ns.Value);
}
writer.WriteAttributeString("version", "1.1");
}
}
}
\ No newline at end of file
......@@ -11,6 +11,8 @@ using System.Xml;
using System.Linq;
using ExCSS;
using Svg.Css;
using System.Threading;
using System.Globalization;
namespace Svg
{
......@@ -488,6 +490,18 @@ namespace Svg
//Trace.TraceInformation("End Render");
}
public override void Write(XmlTextWriter writer)
{
//Save previous culture and switch to invariant for writing
var previousCulture = Thread.CurrentThread.CurrentCulture;
Thread.CurrentThread.CurrentCulture = CultureInfo.InvariantCulture;
base.Write(writer);
//Switch culture back
Thread.CurrentThread.CurrentCulture = previousCulture;
}
public void Write(Stream stream)
{
......@@ -499,7 +513,7 @@ namespace Svg
if (!String.IsNullOrEmpty(this.ExternalCSSHref))
xmlWriter.WriteProcessingInstruction("xml-stylesheet", String.Format("type=\"text/css\" href=\"{0}\"", this.ExternalCSSHref));
this.WriteElement(xmlWriter);
this.Write(xmlWriter);
xmlWriter.Flush();
}
......
......@@ -520,16 +520,11 @@ namespace Svg
this.Render(renderer);
}
public void WriteElement(XmlTextWriter writer)
/// <summary>Derrived classes may decide that the element should not be written. For example, the text element shouldn't be written if it's empty.</summary>
public virtual bool ShouldWriteElement()
{
//Save previous culture and switch to invariant for writing
var previousCulture = Thread.CurrentThread.CurrentCulture;
Thread.CurrentThread.CurrentCulture = CultureInfo.InvariantCulture;
this.Write(writer);
//Switch culture back
Thread.CurrentThread.CurrentCulture = previousCulture;
//Write any element who has a name.
return (this.ElementName != String.Empty);
}
protected virtual void WriteStartElement(XmlTextWriter writer)
......@@ -537,18 +532,8 @@ namespace Svg
if (this.ElementName != String.Empty)
{
writer.WriteStartElement(this.ElementName);
if (this.ElementName == "svg")
{
foreach (var ns in SvgAttributeAttribute.Namespaces)
{
if (string.IsNullOrEmpty(ns.Key))
writer.WriteAttributeString("xmlns", ns.Value);
else
writer.WriteAttributeString("xmlns:" + ns.Key, ns.Value);
}
writer.WriteAttributeString("version", "1.1");
}
}
this.WriteAttributes(writer);
}
......@@ -575,7 +560,8 @@ namespace Svg
forceWrite = false;
writeStyle = (attr.Attribute.Name == "fill");
if ((attr.Attribute.Name == "fill") && (Parent != null))
if (writeStyle && (Parent != null))
{
if(propertyValue == SvgColourServer.NotSet) continue;
......@@ -676,9 +662,9 @@ namespace Svg
return resolved;
}
protected virtual void Write(XmlTextWriter writer)
public virtual void Write(XmlTextWriter writer)
{
if (this.ElementName != String.Empty)
if (ShouldWriteElement())
{
this.WriteStartElement(writer);
this.WriteChildren(writer);
......
......@@ -54,7 +54,7 @@ namespace Svg
{
using (XmlTextWriter xml = new XmlTextWriter(str))
{
elem.WriteElement(xml);
elem.Write(xml);
result = str.ToString();
}
......
......@@ -19,7 +19,7 @@ namespace Svg
protected SvgUnitCollection _dx = new SvgUnitCollection();
private string _rotate;
private List<float> _rotations = new List<float>();
/// <summary>
/// Gets or sets the text to be rendered.
/// </summary>
......@@ -143,7 +143,7 @@ namespace Svg
{
this._rotate = value;
this._rotations.Clear();
this._rotations.AddRange(from r in _rotate.Split(new char[] {',', ' ', '\r', '\n', '\t'}, StringSplitOptions.RemoveEmptyEntries) select float.Parse(r));
this._rotations.AddRange(from r in _rotate.Split(new char[] { ',', ' ', '\r', '\n', '\t' }, StringSplitOptions.RemoveEmptyEntries) select float.Parse(r));
this.IsPathDirty = true;
OnAttributeChanged(new AttributeEventArgs { Attribute = "rotate", Value = value });
}
......@@ -230,14 +230,14 @@ namespace Svg
/// <value>The bounds.</value>
public override System.Drawing.RectangleF Bounds
{
get
get
{
var path = this.Path(null);
foreach (var elem in this.Children.OfType<SvgVisualElement>())
{
path.AddPath(elem.Path(null), false);
}
return path.GetBounds();
return path.GetBounds();
}
}
......@@ -296,9 +296,9 @@ namespace Svg
public override GraphicsPath Path(ISvgRenderer renderer)
{
//if there is a TSpan inside of this text element then path should not be null (even if this text is empty!)
var nodes = GetContentNodes().Where(x => x is SvgContentNode &&
string.IsNullOrEmpty(x.Content.Trim(new[] {'\r', '\n', '\t'})));
var nodes = GetContentNodes().Where(x => x is SvgContentNode &&
string.IsNullOrEmpty(x.Content.Trim(new[] { '\r', '\n', '\t' })));
if (_path == null || IsPathDirty || nodes.Count() == 1)
{
renderer = (renderer ?? SvgRenderer.FromNull());
......@@ -913,5 +913,10 @@ namespace Svg
}
}
/// <summary>Empty text elements are not legal - only write this element if it has children.</summary>
public override bool ShouldWriteElement()
{
return (this.HasChildren() || this.Nodes.Count > 0);
}
}
}
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment