Example #1
0
		/// <summary>
		/// creates an SvgPathSegment based on the command and coords passed in
		/// </summary>
		/// <param name="command">Command.</param>
		/// <param name="segments">Segments.</param>
		/// <param name="coords">Coords.</param>
		/// <param name="isRelative">If set to <c>true</c> is relative.</param>
		static void createPathSegment( char command, List<SvgPathSegment> segments, float[] coords, bool isRelative )
		{
			switch( command )
			{
				case 'm': // relative moveto
				case 'M': // moveto
				{
					segments.Add( new SvgMoveToSegment( toAbsolute( coords[0], coords[1], segments, isRelative ) ) );

					var index = 2;
					while( index < coords.Length )
					{
						segments.Add( new SvgLineSegment( segments.lastItem().end, toAbsolute( coords[index], coords[index + 1], segments, isRelative ) ) );
						index += 2;
					}
				}
				break;

				case 'a': // relative arc
				case 'A': // arc
				{
					throw new System.NotImplementedException();
				}

				case 'l': // relative lineto
				case 'L': // lineto
				{
					var index = 0;
					while( index < coords.Length )
					{
						segments.Add( new SvgLineSegment( segments.lastItem().end, toAbsolute( coords[index], coords[index + 1], segments, isRelative ) ) );
						index += 2;
					}
				}
				break;

				case 'H': // horizontal lineto
				case 'h': // relative horizontal lineto
				{
					var index = 0;
					while( index < coords.Length )
					{
						segments.Add( new SvgLineSegment( segments.lastItem().end, toAbsolute( coords[index], segments.lastItem().end.Y, segments, isRelative, false ) ) );
						index += 1;
					}
				}
				break;

				case 'V': // vertical lineto
				case 'v': // relative vertical lineto
				{
					var index = 0;
					while( index < coords.Length )
					{
						segments.Add( new SvgLineSegment( segments.lastItem().end, toAbsolute( coords[index], segments.lastItem().end.X, segments, false, isRelative ) ) );
						index += 1;
					}
				}
				break;

				case 'Q': // curveto
				case 'q': // relative curveto
				{
					var index = 0;
					while( index < coords.Length )
					{
						var controlPoint = toAbsolute( coords[index], coords[index + 1], segments, isRelative );
						var end = toAbsolute( coords[index + 2], coords[index + 3], segments, isRelative );
						segments.Add( new SvgQuadraticCurveSegment( segments.lastItem().end, controlPoint, end ) );
						index += 4;
					}
				}
				break;

				case 'T': // shorthand/smooth curveto
				case 't': // relative shorthand/smooth curveto
				{
					var index = 0;
					while( index < coords.Length )
					{
						var lastQuadCurve = segments.lastItem() as SvgQuadraticCurveSegment;

						var controlPoint = lastQuadCurve != null
							? reflect( lastQuadCurve.controlPoint, segments.lastItem().end )
							: segments.lastItem().end;

						var end = toAbsolute( coords[index], coords[index + 1], segments, isRelative );
						segments.Add( new SvgQuadraticCurveSegment( segments.lastItem().end, controlPoint, end ) );
						index += 2;
					}
				}
				break;

				case 'C': // curveto
				case 'c': // relative curveto
				{
					var index = 0;
					while( index < coords.Length )
					{
						var firstControlPoint = toAbsolute( coords[index], coords[index + 1], segments, isRelative );
						var secondControlPoint = toAbsolute( coords[index + 2], coords[index + 3], segments, isRelative );
						var end = toAbsolute( coords[index + 4], coords[index + 5], segments, isRelative );
						segments.Add( new SvgCubicCurveSegment( segments.lastItem().end, firstControlPoint, secondControlPoint, end ) );
						index += 6;
					}
				}
				break;

				case 'S': // shorthand/smooth curveto
				case 's': // relative shorthand/smooth curveto
				{
					var index = 0;
					while( index < coords.Length )
					{
						var lastCubicCurve = segments.lastItem() as SvgCubicCurveSegment;

						var firstControlPoint = lastCubicCurve != null
								? reflect( lastCubicCurve.secondCtrlPoint, segments.lastItem().end )
							: segments.lastItem().end;

						var secondControlPoint = toAbsolute( coords[index], coords[index + 1], segments, isRelative );
						var end = toAbsolute( coords[index + 2], coords[index + 3], segments, isRelative );
						segments.Add( new SvgCubicCurveSegment( segments.lastItem().end, firstControlPoint, secondControlPoint, end ) );
						index += 4;
					}
				}
				break;

				case 'Z': // closepath
				case 'z': // relative closepath
				{
					segments.Add( new SvgClosePathSegment() );
				}
				break;
			}
		}
Example #2
0
		/// <summary>
		/// Creates point with absolute coordinates
		/// </summary>
		/// <param name="x">Raw X-coordinate value.</param>
		/// <param name="y">Raw Y-coordinate value.</param>
		/// <param name="segments">Current path segments.</param>
		/// <param name="isRelativeX"><b>true</b> if <paramref name="x"/> contains relative coordinate value, otherwise <b>false</b>.</param>
		/// <param name="isRelativeY"><b>true</b> if <paramref name="y"/> contains relative coordinate value, otherwise <b>false</b>.</param>
		/// <returns><see cref="Vector2"/> that contains absolute coordinates.</returns>
		static Vector2 toAbsolute( float x, float y, List<SvgPathSegment> segments, bool isRelativeX, bool isRelativeY )
		{
			var point = new Vector2( x, y );

			if( ( isRelativeX || isRelativeY ) && segments.Count > 0 )
			{
				var lastSegment = segments.lastItem();

				// if the last element is a SvgClosePathSegment the position of the previous element should be used because the position of SvgClosePathSegment is 0,0
				if( lastSegment is SvgClosePathSegment )
					lastSegment = ( (IList<SvgPathSegment>)segments ).Reverse().OfType<SvgMoveToSegment>().First();

				if( isRelativeX )
					point.X += lastSegment.end.X;

				if( isRelativeY )
					point.Y += lastSegment.end.Y;
			}

			return point;
		}