public override void Render(WpfDrawingRenderer renderer)
        {
            if (_drawGroup != null)
            {
                Geometry clipGeom = this.ClipGeometry;
                if (clipGeom != null)
                {
                    _drawGroup.ClipGeometry = clipGeom;
                }

                Transform transform = this.Transform;
                if (transform != null)
                {
                    _drawGroup.Transform = transform;
                }

                float opacityValue = -1;

                SvgGElement element = (SvgGElement)_svgElement;
                string      opacity = element.GetAttribute("opacity");
                if (opacity != null && opacity.Length > 0)
                {
                    opacityValue = (float)SvgNumber.ParseNumber(opacity);
                    opacityValue = Math.Min(opacityValue, 1);
                    opacityValue = Math.Max(opacityValue, 0);
                }

                if (opacityValue >= 0)
                {
                    _drawGroup.Opacity = opacityValue;
                }
            }

            base.Render(renderer);
        }
        private GradientStopCollection GetGradientStops(XmlNodeList stops)
        {
            int itemCount = stops.Count;
            GradientStopCollection gradientStops = new GradientStopCollection(itemCount);

            double lastOffset = 0;

            for (int i = 0; i < itemCount; i++)
            {
                SvgStopElement stop  = (SvgStopElement)stops.Item(i);
                string         prop  = stop.GetAttribute("stop-color");
                string         style = stop.GetAttribute("style");
                Color          color = Colors.Transparent; // no auto-inherited...
                if (!String.IsNullOrEmpty(prop) || !String.IsNullOrEmpty(style))
                {
                    WpfSvgColor svgColor = new WpfSvgColor(stop, "stop-color");
                    color = svgColor.Color;
                }
                else
                {
                    color = Colors.Black; // the default color...
                    double alpha = 255;
                    string opacity;

                    opacity = stop.GetAttribute("stop-opacity"); // no auto-inherit
                    if (opacity == "inherit")                    // if explicitly defined...
                    {
                        opacity = stop.GetPropertyValue("stop-opacity");
                    }
                    if (opacity != null && opacity.Length > 0)
                    {
                        alpha *= SvgNumber.ParseNumber(opacity);
                    }

                    alpha = Math.Min(alpha, 255);
                    alpha = Math.Max(alpha, 0);

                    color = Color.FromArgb((byte)Convert.ToInt32(alpha),
                                           color.R, color.G, color.B);
                }

                double offset = stop.Offset.AnimVal;

                offset /= 100;
                offset  = Math.Max(lastOffset, offset);

                gradientStops.Add(new GradientStop(color, offset));
                lastOffset = offset;
            }

            if (itemCount == 0)
            {
                gradientStops.Add(new GradientStop(Colors.Black, 0));
                gradientStops.Add(new GradientStop(Colors.Black, 1));
            }

            return(gradientStops);
        }
Example #3
0
        public static GradientStopCollection ToGradientStops(System.Xml.XmlNodeList stops)
        {
            int itemCount = stops.Count;
            GradientStopCollection gradientStops = new GradientStopCollection(itemCount);

            double lastOffset = 0;

            for (int i = 0; i < itemCount; i++)
            {
                SvgStopElement stop  = (SvgStopElement)stops.Item(i);
                string         prop  = stop.GetAttribute("stop-color");
                string         style = stop.GetAttribute("style");
                Color          color = Colors.Transparent; // no auto-inherited...
                if (!string.IsNullOrWhiteSpace(prop) || !string.IsNullOrWhiteSpace(style))
                {
                    SvgColor svgColor = new SvgColor(stop.GetComputedStyle(string.Empty).GetPropertyValue("stop-color"));
                    if (svgColor.ColorType == SvgColorType.CurrentColor)
                    {
                        string sCurColor = stop.GetComputedStyle(string.Empty).GetPropertyValue(CssConstants.PropColor);
                        svgColor = new SvgColor(sCurColor);
                    }
                    TryConvertColor(svgColor.RgbColor, out color);
                }
                else
                {
                    color = Colors.Black; // the default color...
                }

                double alpha = 255;
                string opacity;

                opacity = stop.GetAttribute("stop-opacity"); // no auto-inherit
                if (opacity == "inherit")                    // if explicitly defined...
                {
                    opacity = stop.GetPropertyValue("stop-opacity");
                }
                if (!string.IsNullOrWhiteSpace(opacity))
                {
                    alpha *= SvgNumber.ParseNumber(opacity);
                }

                alpha = Math.Min(alpha, 255);
                alpha = Math.Max(alpha, 0);

                color = Color.FromArgb((byte)Convert.ToInt32(alpha),
                                       color.R, color.G, color.B);

                double offset = stop.Offset.AnimVal;

                offset /= 100;
                offset  = Math.Max(lastOffset, offset);

                gradientStops.Add(new GradientStop(color, offset));
                lastOffset = offset;
            }

            return(gradientStops);
        }
Example #4
0
        private void RenderTSpanPath(SvgTSpanElement element, WpfPathTextBuilder pathBuilder, ref Point ctp)
        {
            WpfTextPlacement placement = WpfTextPlacement.Create(element, ctp, true);

            ctp = placement.Location;
            double rotate = placement.Rotation;

            if (!placement.HasPositions)
            {
                placement = null; // Render it useless.
            }

            string sBaselineShift = element.GetPropertyValue("baseline-shift").Trim();
            double shiftBy        = 0;

            var comparer = StringComparison.OrdinalIgnoreCase;

            if (sBaselineShift.Length > 0)
            {
                SvgTextBaseElement textElement = (SvgTextBaseElement)element.SelectSingleNode("ancestor::svg:text",
                                                                                              element.OwnerDocument.NamespaceManager);

                double textFontSize = GetComputedFontSize(textElement);
                if (sBaselineShift.EndsWith("%", comparer))
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift.Substring(0,
                                                                             sBaselineShift.Length - 1)) / 100f * textFontSize;
                }
                else if (string.Equals(sBaselineShift, "sub", comparer))
                {
                    shiftBy = -0.6F * textFontSize;
                }
                else if (string.Equals(sBaselineShift, "super", comparer))
                {
                    shiftBy = 0.6F * textFontSize;
                }
                else if (string.Equals(sBaselineShift, "baseline", comparer))
                {
                    shiftBy = 0;
                }
                else
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift);
                }
            }

            foreach (XmlNode child in element.ChildNodes)
            {
                if (child.NodeType == XmlNodeType.Text)
                {
                    ctp.Y -= shiftBy;
                    RenderTextPath(element, pathBuilder, GetText(element, child),
                                   new Point(ctp.X, ctp.Y), rotate, placement);
                    ctp.Y += shiftBy;
                }
            }
        }
Example #5
0
        private void RenderTSpanPath(SvgTSpanElement element, WpfTextOnPathDrawing pathDrawing,
                                     ref Point ctp)
        {
            WpfTextPlacement placement = GetCurrentTextPosition(element, ctp);

            ctp = placement.Location;
            double rotate = placement.Rotation;

            if (!placement.HasPositions)
            {
                placement = null; // Render it useless.
            }

            string sBaselineShift = element.GetPropertyValue("baseline-shift").Trim();
            double shiftBy        = 0;

            if (sBaselineShift.Length > 0)
            {
                SvgTextElement textElement = (SvgTextElement)element.SelectSingleNode("ancestor::svg:text",
                                                                                      element.OwnerDocument.NamespaceManager);

                double textFontSize = GetComputedFontSize(textElement);
                if (sBaselineShift.EndsWith("%"))
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift.Substring(0,
                                                                             sBaselineShift.Length - 1)) / 100f * textFontSize;
                }
                else if (sBaselineShift == "sub")
                {
                    shiftBy = -0.6F * textFontSize;
                }
                else if (sBaselineShift == "super")
                {
                    shiftBy = 0.6F * textFontSize;
                }
                else if (sBaselineShift == "baseline")
                {
                    shiftBy = 0;
                }
                else
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift);
                }
            }

            foreach (XmlNode child in element.ChildNodes)
            {
                if (child.NodeType == XmlNodeType.Text)
                {
                    ctp.Y -= shiftBy;
                    RenderTextPath(element, pathDrawing, GetText(element, child),
                                   new Point(ctp.X, ctp.Y), rotate, placement);
                    ctp.Y += shiftBy;
                }
            }
        }
Example #6
0
        private Color?GetNodeColor(ISvgElement targetNode, string property)
        {
            //StyleColor fillColor = new StyleColor();
            //fillColor.FillType = ColorFillType.Solid;
            string szRGB         = null;
            string szOpacity     = null;
            string szNodeopacity = null;


            if (targetNode.RenderingHint == SvgRenderingHint.Text || targetNode.RenderingHint == SvgRenderingHint.Shape)
            {
                szRGB         = (targetNode as SvgElement).GetComputedStyle("").GetPropertyValue(property);
                szOpacity     = (targetNode as SvgElement).GetComputedStyle("").GetPropertyValue(property + @"-opacity");
                szNodeopacity = (targetNode as SvgElement).GetComputedStyle("").GetPropertyValue("opacity");

                if (string.IsNullOrEmpty(szRGB))
                {
                    return(null);
                }
            }

            //Get RGB Color
            SvgPaint paint = new SvgPaint(szRGB);

            if (paint.RgbColor == null)
            {
                return(null);
            }
            Color?solidColor = WpfConvert.ToColor(paint.RgbColor);

            if (solidColor == null)
            {
                return(null);
            }

            //Get Aplha
            Color result = solidColor.Value;

            if (szNodeopacity != null || szOpacity != null)
            {
                double opacityValue = 1;
                if (szNodeopacity != null && szNodeopacity.Length > 0)
                {
                    opacityValue *= SvgNumber.ParseNumber(szNodeopacity);
                }
                else if (szOpacity != null && szOpacity.Length > 0)
                {
                    opacityValue *= SvgNumber.ParseNumber(szOpacity);
                }
                opacityValue = Math.Min(opacityValue, 1);
                opacityValue = Math.Max(opacityValue, 0);
                result.A     = Convert.ToByte(opacityValue * 255);
            }
            return(result);
        }
        public override void Render(WpfDrawingRenderer renderer)
        {
            if (_drawGroup != null)
            {
                Geometry clipGeom = this.ClipGeometry;
                if (clipGeom != null)
                {
                    _drawGroup.ClipGeometry = clipGeom;
                }

                Transform transform = this.Transform;
                if (transform != null)
                {
                    _drawGroup.Transform = transform;
                }

                float opacityValue = -1;

                SvgGElement element = (SvgGElement)_svgElement;
                string      opacity = element.GetAttribute("opacity");
                if (string.IsNullOrWhiteSpace(opacity))
                {
                    opacity = element.GetPropertyValue("opacity");
                }
                if (!string.IsNullOrWhiteSpace(opacity))
                {
                    opacityValue = (float)SvgNumber.ParseNumber(opacity);
                    opacityValue = Math.Min(opacityValue, 1);
                    opacityValue = Math.Max(opacityValue, 0);
                }

                if (opacityValue >= 0 && opacityValue < 1)
                {
                    _drawGroup.Opacity = opacityValue;
                }

                string sVisibility = element.GetPropertyValue("visibility");
                string sDisplay    = element.GetPropertyValue("display");
                if (string.Equals(sVisibility, "hidden") || string.Equals(sDisplay, "none"))
                {
                    _drawGroup.Opacity = 0;
                }
            }

            // Register this drawing with the Drawing-Document...
            this.Rendered(_drawGroup);

            base.Render(renderer);
        }
Example #8
0
        private double GetMiterLimit(double strokeWidth)
        {
            // Use this to prevent the default value of "4" being used...
            string miterLimitAttr = _element.GetAttribute("stroke-miterlimit");

            if (String.IsNullOrEmpty(miterLimitAttr))
            {
                string strokeLinecap = _element.GetAttribute("stroke-linecap");
                if (String.Equals(strokeLinecap, "round", StringComparison.OrdinalIgnoreCase))
                {
                    return(1.0d);
                }
                return(-1.0d);
            }

            string miterLimitStr = _element.GetPropertyValue("stroke-miterlimit");

            if (String.IsNullOrEmpty(miterLimitStr) || (float)(strokeWidth) <= 0)
            {
                return(-1.0d);
            }

            double miterLimit = SvgNumber.ParseNumber(miterLimitStr);

            if (miterLimit < 1)
            {
                throw new SvgException(SvgExceptionType.SvgInvalidValueErr,
                                       "stroke-miterlimit can not be less then 1");
            }

            //if (miterLimit < 1.0d)
            //{
            //    return -1.0d;
            //}

            double ratioLimit = miterLimit / strokeWidth;

            if (ratioLimit >= 1.8d)
            {
                return(miterLimit);
            }
            else
            {
                return(1.0d);
            }
        }
        private void AddTSpanElementPath(SvgTSpanElement element, ref PointF ctp)
        {
            ctp = GetCurrentTextPosition(element, ctp);
            string sBaselineShift = element.GetPropertyValue("baseline-shift").Trim();
            double shiftBy        = 0;

            if (sBaselineShift.Length > 0)
            {
                SvgTextBaseElement textElement = (SvgTextBaseElement)element.SelectSingleNode("ancestor::svg:text",
                                                                                              element.OwnerDocument.NamespaceManager);

                float textFontSize = GetComputedFontSize(textElement);
                if (sBaselineShift.EndsWith("%", StringComparison.OrdinalIgnoreCase))
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift.Substring(0,
                                                                             sBaselineShift.Length - 1)) / 100 * textFontSize;
                }
                else if (sBaselineShift == "sub")
                {
                    shiftBy = -0.6F * textFontSize;
                }
                else if (sBaselineShift == "super")
                {
                    shiftBy = 0.6F * textFontSize;
                }
                else if (sBaselineShift == "baseline")
                {
                    shiftBy = 0;
                }
                else
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift);
                }
            }

            foreach (XmlNode child in element.ChildNodes)
            {
                if (child.NodeType == XmlNodeType.Text)
                {
                    ctp.Y -= (float)shiftBy;
                    AddGraphicsPath(element, ref ctp, GetText(element, child));
                    ctp.Y += (float)shiftBy;
                }
            }
        }
        private float GetMiterLimit()
        {
            string miterLimitStr = _element.GetPropertyValue("stroke-miterlimit");

            if (miterLimitStr.Length == 0)
            {
                miterLimitStr = "4";
            }

            float miterLimit = (float)SvgNumber.ParseNumber(miterLimitStr);

            if (miterLimit < 1)
            {
                throw new SvgException(SvgExceptionType.SvgInvalidValueErr, "stroke-miterlimit can not be less then 1");
            }

            return(miterLimit);
        }
        private int GetOpacity(string fillOrStroke)
        {
            double alpha = 255;
            string opacity;

            opacity = _element.GetPropertyValue(fillOrStroke + "-opacity");
            if (opacity.Length > 0)
            {
                alpha *= SvgNumber.ParseNumber(opacity);
            }

            opacity = _element.GetPropertyValue("opacity");
            if (opacity.Length > 0)
            {
                alpha *= SvgNumber.ParseNumber(opacity);
            }

            alpha = Math.Min(alpha, 255);
            alpha = Math.Max(alpha, 0);

            return(Convert.ToInt32(alpha));
        }
Example #12
0
        public static double GetOpacity(SvgStyleableElement element, string fillOrStroke)
        {
            double opacityValue = 1;

            string opacity = element.GetPropertyValue(fillOrStroke + "-opacity");

            if (opacity != null && opacity.Length > 0)
            {
                opacityValue *= SvgNumber.ParseNumber(opacity);
            }

            opacity = element.GetPropertyValue("opacity");
            if (opacity != null && opacity.Length > 0)
            {
                opacityValue *= SvgNumber.ParseNumber(opacity);
            }

            opacityValue = Math.Min(opacityValue, 1);
            opacityValue = Math.Max(opacityValue, 0);

            return(opacityValue);
        }
Example #13
0
        private double GetOpacity(string fillOrStroke)
        {
            double opacityValue = 1;

            string opacity = _element.GetPropertyValue(fillOrStroke + "-opacity");

            if (opacity != null && opacity.Length > 0)
            {
                opacityValue *= SvgNumber.ParseNumber(opacity);
            }

            opacity = _element.GetPropertyValue("opacity");
            if (opacity != null && opacity.Length > 0)
            {
                opacityValue *= SvgNumber.ParseNumber(opacity);
            }

            opacityValue = Math.Min(opacityValue, 1);
            opacityValue = Math.Max(opacityValue, 0);

            return(opacityValue);
        }
Example #14
0
        private double GetOpacity(string fillOrStroke)
        {
            double opacityValue = 1;

            string opacity = _element.GetPropertyValue(fillOrStroke + "-opacity");

            if (!string.IsNullOrWhiteSpace(opacity))
            {
                opacityValue *= SvgNumber.ParseNumber(opacity);
            }

            opacity = _element.GetPropertyValue("opacity");
            if (!string.IsNullOrWhiteSpace(opacity))
            {
                opacityValue *= SvgNumber.ParseNumber(opacity);
            }

            opacityValue = Math.Min(opacityValue, 1);
            opacityValue = Math.Max(opacityValue, 0);

            return(opacityValue);
        }
Example #15
0
        public static bool TryGetMiterLimit(SvgStyleableElement element, double strokeWidth, out double miterLimit)
        {
            string miterLimitAttr = element.GetAttribute("stroke-miterlimit");

            if (string.IsNullOrWhiteSpace(miterLimitAttr))
            {
                string strokeLinecap = element.GetAttribute("stroke-linecap");
                if (string.Equals(strokeLinecap, "round", StringComparison.OrdinalIgnoreCase))
                {
                    miterLimit = 1.0d;
                    return(true);
                }
                miterLimit = -1.0d;
                return(false);
            }

            string miterLimitStr = element.GetPropertyValue("stroke-miterlimit");

            if (string.IsNullOrWhiteSpace(miterLimitStr) || strokeWidth <= 0)
            {
                miterLimit = -1.0d;
                return(false);
            }

            miterLimit = SvgNumber.ParseNumber(miterLimitStr);
            if (miterLimit < 1)
            {
                return(false);
            }

            double ratioLimit = miterLimit / strokeWidth;

            if (ratioLimit < 1.8d)
            {
                miterLimit = 1.0d;
            }
            return(true);
        }
        public override void Render(WpfDrawingRenderer renderer)
        {
            Geometry  clipGeom  = this.ClipGeometry;
            Transform transform = this.Transform;

            WpfDrawingContext context = renderer.Context;

            SvgSwitchElement switchElement = (SvgSwitchElement)_svgElement;

            string elementId = this.GetElementName();

            float opacityValue = -1;

            string opacity = switchElement.GetAttribute("opacity");

            if (string.IsNullOrWhiteSpace(opacity))
            {
                opacity = switchElement.GetPropertyValue("opacity");
            }
            if (!string.IsNullOrWhiteSpace(opacity))
            {
                opacityValue = (float)SvgNumber.ParseNumber(opacity);
                opacityValue = Math.Min(opacityValue, 1);
                opacityValue = Math.Max(opacityValue, 0);
            }

            if (clipGeom != null || transform != null || (opacityValue >= 0 && opacityValue < 1) ||
                (!string.IsNullOrWhiteSpace(elementId) && !context.IsRegisteredId(elementId)))
            {
                _drawGroup = new DrawingGroup();

                DrawingGroup currentGroup = context.Peek();

                if (currentGroup == null)
                {
                    throw new InvalidOperationException("An existing group is expected.");
                }

                currentGroup.Children.Add(_drawGroup);
                context.Push(_drawGroup);

                if (clipGeom != null)
                {
                    _drawGroup.ClipGeometry = clipGeom;
                }

                if (transform != null)
                {
                    _drawGroup.Transform = transform;
                }

                if (opacityValue >= 0 && opacityValue < 1)
                {
                    _drawGroup.Opacity = opacityValue;
                }

                if (!string.IsNullOrWhiteSpace(elementId) && !context.IsRegisteredId(elementId))
                {
                    SvgObject.SetName(_drawGroup, elementId);

                    context.RegisterId(elementId);

                    if (context.IncludeRuntime)
                    {
                        SvgObject.SetId(_drawGroup, elementId);
                    }
                }
            }

            base.Render(renderer);
        }
Example #17
0
        public override void Render(WpfDrawingRenderer renderer)
        {
            WpfDrawingContext context      = renderer.Context;
            SvgImageElement   imageElement = (SvgImageElement)_svgElement;

            double width  = imageElement.Width.AnimVal.Value;
            double height = imageElement.Height.AnimVal.Value;

            Rect destRect = new Rect(imageElement.X.AnimVal.Value, imageElement.Y.AnimVal.Value,
                                     width, height);

            ImageSource imageSource = null;

            if (imageElement.IsSvgImage)
            {
                SvgWindow wnd = GetSvgWindow();
                //_embeddedRenderer.BackColor = Color.Empty;
                _embeddedRenderer.Render(wnd.Document);

                DrawingGroup imageGroup = _embeddedRenderer.Drawing as DrawingGroup;
                if (imageGroup != null &&
                    (imageGroup.Children != null && imageGroup.Children.Count == 1))
                {
                    DrawingGroup drawImage = imageGroup.Children[0] as DrawingGroup;
                    if (drawImage != null)
                    {
                        if (drawImage.ClipGeometry != null)
                        {
                            drawImage.ClipGeometry = null;
                        }

                        imageSource = new DrawingImage(drawImage);
                    }
                    else
                    {
                        if (imageGroup.ClipGeometry != null)
                        {
                            imageGroup.ClipGeometry = null;
                        }

                        imageSource = new DrawingImage(imageGroup);
                    }
                }
                else
                {
                    imageSource = new DrawingImage(_embeddedRenderer.Drawing);
                }

                if (_embeddedRenderer != null)
                {
                    _embeddedRenderer.Dispose();
                    _embeddedRenderer = null;
                }
            }
            else
            {
                imageSource = GetBitmapSource(imageElement, context);
            }

            if (imageSource == null)
            {
                return;
            }

            //TODO--PAUL: Set the DecodePixelWidth/DecodePixelHeight?

            // Freeze the DrawingImage for performance benefits.
            imageSource.Freeze();

            DrawingGroup drawGroup = null;

            ISvgAnimatedPreserveAspectRatio animatedAspectRatio = imageElement.PreserveAspectRatio;

            if (animatedAspectRatio != null && animatedAspectRatio.AnimVal != null)
            {
                SvgPreserveAspectRatio     aspectRatio     = animatedAspectRatio.AnimVal as SvgPreserveAspectRatio;
                SvgPreserveAspectRatioType aspectRatioType =
                    (aspectRatio != null) ? aspectRatio.Align : SvgPreserveAspectRatioType.Unknown;
                if (aspectRatio != null && aspectRatioType != SvgPreserveAspectRatioType.None &&
                    aspectRatioType != SvgPreserveAspectRatioType.Unknown)
                {
                    double imageWidth  = imageSource.Width;
                    double imageHeight = imageSource.Height;

                    double viewWidth  = destRect.Width;
                    double viewHeight = destRect.Height;

                    SvgMeetOrSlice meetOrSlice = aspectRatio.MeetOrSlice;
                    if (meetOrSlice == SvgMeetOrSlice.Meet)
                    {
                        if (imageWidth <= viewWidth && imageHeight <= viewHeight)
                        {
                            destRect = this.GetBounds(destRect,
                                                      new Size(imageWidth, imageHeight), aspectRatioType);
                        }
                        else
                        {
                            Transform viewTransform = this.GetAspectRatioTransform(aspectRatio,
                                                                                   new SvgRect(0, 0, imageWidth, imageHeight),
                                                                                   new SvgRect(destRect.X, destRect.Y, destRect.Width, destRect.Height));
                            //Transform scaleTransform = this.FitToViewbox(aspectRatio,
                            //  new SvgRect(destRect.X, destRect.Y, imageWidth, imageHeight),
                            //  new SvgRect(destRect.X, destRect.Y, destRect.Width, destRect.Height));

                            if (viewTransform != null)
                            {
                                drawGroup           = new DrawingGroup();
                                drawGroup.Transform = viewTransform;

                                DrawingGroup lastGroup = context.Peek();
                                Debug.Assert(lastGroup != null);

                                if (lastGroup != null)
                                {
                                    lastGroup.Children.Add(drawGroup);
                                }

                                destRect = this.GetBounds(destRect,
                                                          new Size(imageWidth, imageHeight), aspectRatioType);

                                // The origin is already handled by the view transform...
                                destRect.X = 0;
                                destRect.Y = 0;
                            }
                        }
                    }
                    else if (meetOrSlice == SvgMeetOrSlice.Slice)
                    {
                    }
                }
            }

            ImageDrawing drawing = new ImageDrawing(imageSource, destRect);

            float opacityValue = -1;

            string opacity = imageElement.GetAttribute("opacity");

            if (opacity != null && opacity.Length > 0)
            {
                opacityValue = (float)SvgNumber.ParseNumber(opacity);
                opacityValue = Math.Min(opacityValue, 1);
                opacityValue = Math.Max(opacityValue, 0);
            }

            Geometry  clipGeom  = this.ClipGeometry;
            Transform transform = this.Transform;

            if (drawGroup == null)
            {
                drawGroup = context.Peek();
            }
            Debug.Assert(drawGroup != null);
            if (drawGroup != null)
            {
                if (opacityValue >= 0 || (clipGeom != null && !clipGeom.IsEmpty()) ||
                    (transform != null && !transform.Value.IsIdentity))
                {
                    DrawingGroup clipGroup = new DrawingGroup();
                    if (opacityValue >= 0)
                    {
                        clipGroup.Opacity = opacityValue;
                    }
                    if (clipGeom != null)
                    {
                        SvgUnitType clipUnits = this.ClipUnits;
                        if (clipUnits == SvgUnitType.ObjectBoundingBox)
                        {
                            Rect drawingBounds = drawing.Bounds;

                            TransformGroup transformGroup = new TransformGroup();

                            // Scale the clip region (at (0, 0)) and translate to the top-left corner of the target.
                            transformGroup.Children.Add(
                                new ScaleTransform(drawingBounds.Width, drawingBounds.Height));
                            transformGroup.Children.Add(
                                new TranslateTransform(drawingBounds.X, drawingBounds.Y));

                            clipGeom.Transform = transformGroup;
                        }

                        clipGroup.ClipGeometry = clipGeom;
                    }
                    if (transform != null)
                    {
                        clipGroup.Transform = transform;
                    }

                    clipGroup.Children.Add(drawing);
                    drawGroup.Children.Add(clipGroup);
                }
                else
                {
                    drawGroup.Children.Add(drawing);
                }
            }
        }
        public override void Render(WpfDrawingRenderer renderer)
        {
            if (_drawGroup == null || _drawContext == null)
            {
                return;
            }

            Point ctp = new Point(0, 0); // current text position

            WpfTextPlacement placement = WpfTextRenderer.GetCurrentTextPosition(_textElement, ctp);

            ctp = placement.Location;
            double rotate = placement.Rotation;

            if (!placement.HasPositions)
            {
                placement = null; // render it useless
            }
            string sBaselineShift = _textElement.GetPropertyValue("baseline-shift").Trim();
            double shiftBy        = 0;

            if (sBaselineShift.Length > 0)
            {
                double textFontSize = WpfTextRenderer.GetComputedFontSize(_textElement);
                if (sBaselineShift.EndsWith("%", StringComparison.OrdinalIgnoreCase))
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift.Substring(0,
                                                                             sBaselineShift.Length - 1)) / 100 * textFontSize;
                }
                else if (sBaselineShift == "sub")
                {
                    shiftBy = -0.6F * textFontSize;
                }
                else if (sBaselineShift == "super")
                {
                    shiftBy = 0.6F * textFontSize;
                }
                else if (sBaselineShift == "baseline")
                {
                    shiftBy = 0;
                }
                else
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift);
                }
            }

            XmlNodeType nodeType = XmlNodeType.None;

            bool   isVertical  = false;
            string writingMode = _textElement.GetPropertyValue("writing-mode");

            if (!string.IsNullOrWhiteSpace(writingMode) &&
                string.Equals(writingMode, "tb", StringComparison.OrdinalIgnoreCase))
            {
                isVertical = true;
            }

            if (_svgElement.ChildNodes.Count == 1)
            {
                XmlNode child = _svgElement.ChildNodes[0];
                nodeType = child.NodeType;
                if (nodeType == XmlNodeType.Text || nodeType == XmlNodeType.CDATA)
                {
                    if (isVertical)
                    {
                        ctp.X -= shiftBy;
                        RenderSingleLineTextV(_textElement, ref ctp,
                                              WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                        ctp.X += shiftBy;
                    }
                    else
                    {
                        ctp.Y -= shiftBy;
                        RenderSingleLineTextH(_textElement, ref ctp,
                                              WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                        ctp.Y += shiftBy;
                    }
                }
                else if (nodeType == XmlNodeType.Element)
                {
                    string nodeName = child.Name;
                    if (string.Equals(nodeName, "tref"))
                    {
                        AddTRefElementRun((SvgTRefElement)child, ref ctp, isVertical, true);
                    }
                    else if (string.Equals(nodeName, "tspan"))
                    {
                        AddTSpanElementRun((SvgTSpanElement)child, ref ctp, isVertical, true);
                    }
                    else if (string.Equals(nodeName, "textPath"))
                    {
                        RenderTextPath((SvgTextPathElement)child, ref ctp, rotate, placement);
                    }
                }
                else if (nodeType == XmlNodeType.Whitespace)
                {
                    if (isVertical)
                    {
                        ctp.X -= shiftBy;
                        RenderSingleLineTextV(_textElement, ref ctp,
                                              WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                        ctp.X += shiftBy;
                    }
                    else
                    {
                        ctp.Y -= shiftBy;
                        RenderSingleLineTextH(_textElement, ref ctp,
                                              WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                        ctp.Y += shiftBy;
                    }
                }
            }
            else
            {
                string textAnchor = _textElement.GetPropertyValue("text-anchor");

                WpfTextAnchor anchor = WpfTextAnchor.None;

                if (textAnchor == "middle")
                {
                    anchor = WpfTextAnchor.Middle;
                }
                else if (textAnchor == "end")
                {
                    anchor = WpfTextAnchor.End;
                }

                XmlNodeList nodeList = _svgElement.ChildNodes;
                // This is a very simply hack to change centered text to left align, since for
                // text containing spans, different font weights may be applied to the spans...
                if (anchor == WpfTextAnchor.Middle)
                {
                    // Suspend the rendering...
                    _isMeasuring = true;

                    foreach (XmlNode child in nodeList)
                    {
                        nodeType = child.NodeType;
                        if (nodeType == XmlNodeType.Text)
                        {
                            if (isVertical)
                            {
                                ctp.X -= shiftBy;
                                RenderTextRunV(_textElement, ref ctp,
                                               WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                                ctp.X += shiftBy;
                            }
                            else
                            {
                                ctp.Y -= shiftBy;
                                RenderTextRunH(_textElement, ref ctp,
                                               WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                                ctp.Y += shiftBy;
                            }
                        }
                        else if (nodeType == XmlNodeType.Element)
                        {
                            string nodeName = child.Name;
                            if (string.Equals(nodeName, "tref"))
                            {
                                AddTRefElementRun((SvgTRefElement)child, ref ctp, isVertical, false);
                            }
                            else if (string.Equals(nodeName, "tspan"))
                            {
                                AddTSpanElementRun((SvgTSpanElement)child, ref ctp, isVertical, false);
                            }
                            else if (string.Equals(nodeName, "textPath"))
                            {
                                RenderTextPath((SvgTextPathElement)child, ref ctp, rotate, placement);
                            }
                        }
                        else if (nodeType == XmlNodeType.Whitespace)
                        {
                            if (isVertical)
                            {
                                ctp.X -= shiftBy;
                                //RenderTextRunV(_textElement, ref ctp, GetText(_textElement, child));
                                RenderTextRunV(_textElement, ref ctp, Whitespace, rotate, placement);
                                ctp.X += shiftBy;
                            }
                            else
                            {
                                ctp.Y -= shiftBy;
                                //RenderTextRunH(_textElement, ref ctp, GetText(_textElement, child));
                                RenderTextRunH(_textElement, ref ctp, Whitespace, rotate, placement);
                                ctp.Y += shiftBy;
                            }
                        }
                    }

                    ctp.X -= (_textWidth / 2d);

                    // Resume the rendering...
                    _isMeasuring = false;
                }

                bool textRendered = false;

                for (int i = 0; i < nodeList.Count; i++)
                {
                    XmlNode child = nodeList[i];
                    nodeType = child.NodeType;
                    if (nodeType == XmlNodeType.Text)
                    {
                        if (isVertical)
                        {
                            ctp.X -= shiftBy;
                            RenderTextRunV(_textElement, ref ctp,
                                           WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                            ctp.X += shiftBy;
                        }
                        else
                        {
                            ctp.Y -= shiftBy;
                            RenderTextRunH(_textElement, ref ctp,
                                           WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                            ctp.Y += shiftBy;
                        }

                        textRendered = true;
                    }
                    else if (nodeType == XmlNodeType.Element)
                    {
                        string nodeName = child.Name;
                        if (string.Equals(nodeName, "tref"))
                        {
                            AddTRefElementRun((SvgTRefElement)child, ref ctp, isVertical, false);

                            textRendered = true;
                        }
                        else if (string.Equals(nodeName, "tspan"))
                        {
                            AddTSpanElementRun((SvgTSpanElement)child, ref ctp, isVertical, false);

                            textRendered = true;
                        }
                        else if (string.Equals(nodeName, "textPath"))
                        {
                            RenderTextPath((SvgTextPathElement)child, ref ctp, rotate, placement);

                            textRendered = false;
                        }
                    }
                    else if (nodeType == XmlNodeType.Whitespace)
                    {
                        if (textRendered)
                        {
                            if (isVertical)
                            {
                                ctp.X -= shiftBy;
                                //RenderTextRunV(_textElement, ref ctp, GetText(_textElement, child));
                                RenderTextRunV(_textElement, ref ctp, Whitespace, rotate, placement);
                                ctp.X += shiftBy;
                            }
                            else
                            {
                                ctp.Y -= shiftBy;
                                //RenderTextRunH(_textElement, ref ctp, GetText(_textElement, child));
                                RenderTextRunH(_textElement, ref ctp, Whitespace, rotate, placement);
                                ctp.Y += shiftBy;
                            }

                            textRendered = false;
                        }
                    }
                }
            }
        }
        private void AddTSpanElementRun(SvgTSpanElement element, ref Point ctp,
                                        bool isVertical, bool isSingleLine)
        {
            WpfTextPlacement placement = WpfTextRenderer.GetCurrentTextPosition(element, ctp);

            ctp = placement.Location;
            double rotate = placement.Rotation;

            if (!placement.HasPositions)
            {
                placement = null; // render it useless
            }

            string sBaselineShift = element.GetPropertyValue("baseline-shift").Trim();
            double shiftBy        = 0;

            if (sBaselineShift.Length > 0)
            {
                double textFontSize = WpfTextRenderer.GetComputedFontSize(_textElement);
                if (sBaselineShift.EndsWith("%", StringComparison.OrdinalIgnoreCase))
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift.Substring(0,
                                                                             sBaselineShift.Length - 1)) / 100f * textFontSize;
                }
                else if (sBaselineShift == "sub")
                {
                    shiftBy = -0.6F * textFontSize;
                }
                else if (sBaselineShift == "super")
                {
                    shiftBy = 0.6F * textFontSize;
                }
                else if (sBaselineShift == "baseline")
                {
                    shiftBy = 0;
                }
                else
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift);
                }
            }

            foreach (XmlNode child in element.ChildNodes)
            {
                if (child.NodeType == XmlNodeType.Text)
                {
                    if (isVertical)
                    {
                        ctp.X += shiftBy;
                        if (isSingleLine)
                        {
                            RenderSingleLineTextV(element, ref ctp,
                                                  WpfTextRenderer.GetText(element, child), rotate, placement);
                        }
                        else
                        {
                            RenderTextRunV(element, ref ctp,
                                           WpfTextRenderer.GetText(element, child), rotate, placement);
                        }
                        ctp.X -= shiftBy;
                    }
                    else
                    {
                        ctp.Y -= shiftBy;
                        if (isSingleLine)
                        {
                            RenderSingleLineTextH(element, ref ctp,
                                                  WpfTextRenderer.GetText(element, child), rotate, placement);
                        }
                        else
                        {
                            RenderTextRunH(element, ref ctp,
                                           WpfTextRenderer.GetText(element, child), rotate, placement);
                        }
                        ctp.Y += shiftBy;
                    }
                }
            }
        }
        public override void Render(WpfDrawingRenderer renderer)
        {
            if (_drawGroup == null || _drawContext == null)
            {
                return;
            }

            var comparer = StringComparison.OrdinalIgnoreCase;

            Point ctp = new Point(0, 0); // current text position

            WpfTextPlacement placement = WpfTextPlacement.Create(_textElement, ctp, _textContext.IsTextPath);

            ctp = placement.Location;
            double rotate = placement.Rotation;

            if (!placement.HasPositions)
            {
                placement = null; // render it useless
            }
            string sBaselineShift = _textElement.GetPropertyValue("baseline-shift").Trim();
            double shiftBy        = 0;

            if (sBaselineShift.Length > 0)
            {
                double textFontSize = WpfTextRenderer.GetComputedFontSize(_textElement);
                if (sBaselineShift.EndsWith("%", comparer))
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift.Substring(0,
                                                                             sBaselineShift.Length - 1)) / 100 * textFontSize;
                }
                else if (string.Equals(sBaselineShift, "sub", comparer))
                {
                    shiftBy = -0.6F * textFontSize;
                }
                else if (string.Equals(sBaselineShift, "super", comparer))
                {
                    shiftBy = 0.6F * textFontSize;
                }
                else if (string.Equals(sBaselineShift, "baseline", comparer))
                {
                    shiftBy = 0;
                }
                else
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift);
                }
            }

            // For for fonts loading in the background...
            var svgDoc = _svgElement.OwnerDocument;

            if (svgDoc.IsFontsLoaded == false)
            {
                //TODO: Use of SpinUntil is known to CPU heavy, but will work for now...
                //SpinWait.SpinUntil(() => svgDoc.IsFontsLoaded == true);

                var svgWnd = svgDoc.Window as SvgWindow;
                if (svgWnd != null)
                {
                    svgWnd.AwaitTasks("SvgDocument");
                }
            }

            XmlNodeType nodeType = XmlNodeType.None;

            bool   isVertical  = false;
            string writingMode = _textElement.GetPropertyValue("writing-mode");

            if (!string.IsNullOrWhiteSpace(writingMode) && string.Equals(writingMode, "tb", comparer))
            {
                isVertical = true;
            }

            if (_svgElement.ChildNodes.Count == 1)
            {
                XmlNode child = _svgElement.ChildNodes[0];
                nodeType = child.NodeType;
                if (nodeType == XmlNodeType.Text || nodeType == XmlNodeType.CDATA)
                {
                    if (isVertical)
                    {
                        ctp.X -= shiftBy;
                        RenderVertText(_textElement, ref ctp,
                                       WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                        ctp.X += shiftBy;
                    }
                    else
                    {
                        ctp.Y -= shiftBy;
                        RenderHorzText(_textElement, ref ctp,
                                       WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                        ctp.Y += shiftBy;
                    }
                }
                else if (nodeType == XmlNodeType.Element)
                {
                    string nodeName = child.Name;
                    if (string.Equals(nodeName, "tref", comparer))
                    {
                        AddTRefElementRun((SvgTRefElement)child, ref ctp, isVertical, true);
                    }
                    else if (string.Equals(nodeName, "tspan", comparer))
                    {
                        AddTSpanElementRun((SvgTSpanElement)child, ref ctp, isVertical, true);
                    }
                    else if (string.Equals(nodeName, "textPath", comparer))
                    {
                        RenderTextPath((SvgTextPathElement)child, ref ctp, rotate, placement);
                    }
                    else if (string.Equals(nodeName, "altGlyph", comparer))
                    {
                        AddAltGlyphElementRun((SvgAltGlyphElement)child, ref ctp, isVertical, true);
                    }
                }
                else if (nodeType == XmlNodeType.Whitespace)
                {
                    if (isVertical)
                    {
                        ctp.X -= shiftBy;
                        RenderVertText(_textElement, ref ctp,
                                       WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                        ctp.X += shiftBy;
                    }
                    else
                    {
                        ctp.Y -= shiftBy;
                        RenderHorzText(_textElement, ref ctp,
                                       WpfTextRenderer.GetText(_textElement, child), rotate, placement);
                        ctp.Y += shiftBy;
                    }
                }
            }
            else
            {
                string textAnchor = _textElement.GetPropertyValue("text-anchor");

                WpfTextAnchor anchor = WpfTextAnchor.None;

                if (string.Equals(textAnchor, "middle", comparer))
                {
                    anchor = WpfTextAnchor.Middle;
                }
                else if (string.Equals(textAnchor, "end", comparer))
                {
                    anchor = WpfTextAnchor.End;
                }

                XmlNodeList nodeList  = _svgElement.ChildNodes;
                int         nodeCount = nodeList.Count;
                // This is a very simply hack to change centered text to left align, since for
                // text containing spans, different font weights may be applied to the spans...
                if (anchor == WpfTextAnchor.Middle)
                {
                    // Suspend the rendering...
                    _isMeasuring = true;
                    Point savedPt = new Point(ctp.X, ctp.Y);

                    _textContext.BeginMeasure(nodeCount);

                    for (int i = 0; i < nodeCount; i++)
                    {
                        XmlNode child = nodeList[i];
                        nodeType = child.NodeType;
                        //if (i == 0 && nodeType == XmlNodeType.Whitespace)
                        //{
                        //    continue;
                        //}
                        if (nodeType == XmlNodeType.Text)
                        {
                            var nodeText = WpfTextRenderer.GetText(_textElement, child);
                            if (i == (nodeCount - 1))
                            {
                                // No need to render the last white space...
                                nodeText = nodeText.TrimEnd();
                            }
                            else if (i == 0)
                            {
                                nodeText = nodeText.Trim();
                            }

                            if (isVertical)
                            {
                                ctp.X -= shiftBy;
                                RenderVertTextRun(_textElement, ref ctp, nodeText, rotate, placement);
                                ctp.X += shiftBy;
                            }
                            else
                            {
                                ctp.Y -= shiftBy;
                                RenderHorzTextRun(_textElement, ref ctp, nodeText, rotate, placement);
                                ctp.Y += shiftBy;
                            }
                        }
                        else if (nodeType == XmlNodeType.Element)
                        {
                            string nodeName = child.Name;
                            if (string.Equals(nodeName, "tref", comparer))
                            {
                                AddTRefElementRun((SvgTRefElement)child, ref ctp, isVertical, false);
                            }
                            else if (string.Equals(nodeName, "tspan", comparer))
                            {
                                bool isAdded = false;
                                if ((i + 1) < nodeCount - 1)
                                {
                                    XmlNode nextChild = nodeList[i + 1];
                                    if (nextChild.NodeType == XmlNodeType.Whitespace)
                                    {
                                        isAdded = true;
                                        AddTSpanElementRun((SvgTSpanElement)child, ref ctp, isVertical, false, nextChild);
                                        i++;
                                    }
                                }
                                if (!isAdded)
                                {
                                    AddTSpanElementRun((SvgTSpanElement)child, ref ctp, isVertical, false);
                                }
                            }
                            else if (string.Equals(nodeName, "textPath", comparer))
                            {
                                RenderTextPath((SvgTextPathElement)child, ref ctp, rotate, placement);
                            }
                            else if (string.Equals(nodeName, "altGlyph", comparer))
                            {
                                AddAltGlyphElementRun((SvgAltGlyphElement)child, ref ctp, isVertical, false);
                            }
                        }
                        else if (nodeType == XmlNodeType.Whitespace)
                        {
                            if (isVertical)
                            {
                                ctp.X -= shiftBy;
                                RenderVertTextRun(_textElement, ref ctp, Whitespace, rotate, placement, true);
                                ctp.X += shiftBy;
                            }
                            else
                            {
                                ctp.Y -= shiftBy;
                                RenderHorzTextRun(_textElement, ref ctp, Whitespace, rotate, placement, true);
                                ctp.Y += shiftBy;
                            }
                        }
                    }

                    _textContext.EndMeasure();

                    ctp = savedPt;

                    ctp.X -= (_textWidth / 2d);

                    // Resume the rendering...
                    _isMeasuring = false;
                }

                bool textRendered = false;

                for (int i = 0; i < nodeCount; i++)
                {
                    XmlNode child = nodeList[i];
                    nodeType = child.NodeType;
                    //if (i == 0 && nodeType == XmlNodeType.Whitespace)
                    //{
                    //    continue;
                    //}

                    if (nodeType == XmlNodeType.Text)
                    {
                        var nodeText = WpfTextRenderer.GetText(_textElement, child);
                        if (i == (nodeCount - 1))
                        {
                            // No need to render the last white space...
                            nodeText = nodeText.TrimEnd();
                        }
                        else if (i == 0)
                        {
                            nodeText = nodeText.Trim();
                        }

                        if (isVertical)
                        {
                            ctp.X -= shiftBy;
                            RenderVertTextRun(_textElement, ref ctp, nodeText, rotate, placement);
                            ctp.X += shiftBy;
                        }
                        else
                        {
                            ctp.Y -= shiftBy;
                            RenderHorzTextRun(_textElement, ref ctp, nodeText, rotate, placement);
                            ctp.Y += shiftBy;
                        }

                        textRendered = true;
                    }
                    else if (nodeType == XmlNodeType.Element)
                    {
                        string nodeName = child.Name;
                        if (string.Equals(nodeName, "tref", comparer))
                        {
                            AddTRefElementRun((SvgTRefElement)child, ref ctp, isVertical, false);

                            textRendered = true;
                        }
                        else if (string.Equals(nodeName, "tspan", comparer))
                        {
                            bool isAdded = false;
                            if ((i + 1) < nodeCount - 1)
                            {
                                XmlNode nextChild = nodeList[i + 1];
                                if (nextChild.NodeType == XmlNodeType.Whitespace)
                                {
                                    isAdded = true;
                                    AddTSpanElementRun((SvgTSpanElement)child, ref ctp, isVertical, false, nextChild);
                                    i++;
                                }
                            }
                            if (!isAdded)
                            {
                                AddTSpanElementRun((SvgTSpanElement)child, ref ctp, isVertical, false);
                            }

                            textRendered = true;
                        }
                        else if (string.Equals(nodeName, "textPath", comparer))
                        {
                            RenderTextPath((SvgTextPathElement)child, ref ctp, rotate, placement);

                            textRendered = false;
                        }
                        else if (string.Equals(nodeName, "altGlyph", comparer))
                        {
                            AddAltGlyphElementRun((SvgAltGlyphElement)child, ref ctp, isVertical, false);
                        }
                    }
                    else if (nodeType == XmlNodeType.Whitespace)
                    {
                        if (textRendered)
                        {
                            if (isVertical)
                            {
                                ctp.X -= shiftBy;
                                RenderVertTextRun(_textElement, ref ctp, Whitespace, rotate, placement, true);
                                ctp.X += shiftBy;
                            }
                            else
                            {
                                ctp.Y -= shiftBy;
                                RenderHorzTextRun(_textElement, ref ctp, Whitespace, rotate, placement, true);
                                ctp.Y += shiftBy;
                            }

                            textRendered = false;
                        }
                    }
                }
            }

            // Register this drawing with the Drawing-Document...
            if (_drawGroup != null)
            {
                this.Rendered(_drawGroup);
            }
        }
Example #21
0
        private void AddTSpanElementRun(SvgTSpanElement element, ref Point ctp,
                                        bool isVertical, bool isSingleLine, XmlNode spaceNode = null)
        {
            var nodeList  = element.ChildNodes;
            int nodeCount = nodeList.Count;

            if (nodeCount == 0)
            {
                return;
            }

            _textContext.PositioningElement = element;
            _textContext.PositioningStart   = new Point(ctp.X, ctp.Y);

            WpfTextPlacement placement = WpfTextPlacement.Create(element, ctp);

            ctp = placement.Location;
            double rotate = placement.Rotation;

            if (!placement.HasPositions)
            {
                placement = null; // render it useless
            }

            _textContext.PositioningEnd = new Point(ctp.X, ctp.Y);

            var comparer = StringComparison.OrdinalIgnoreCase;

            string sBaselineShift = element.GetPropertyValue("baseline-shift").Trim();
            double shiftBy        = 0;

            if (sBaselineShift.Length > 0)
            {
                double textFontSize = WpfTextRenderer.GetComputedFontSize(_textElement);
                if (sBaselineShift.EndsWith("%", comparer))
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift.Substring(0,
                                                                             sBaselineShift.Length - 1)) / 100f * textFontSize;
                }
                else if (string.Equals(sBaselineShift, "sub", comparer))
                {
                    shiftBy = -0.6F * textFontSize;
                }
                else if (string.Equals(sBaselineShift, "super", comparer))
                {
                    shiftBy = 0.6F * textFontSize;
                }
                else if (string.Equals(sBaselineShift, "baseline", comparer))
                {
                    shiftBy = 0;
                }
                else
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift);
                }
            }

            for (int i = 0; i < nodeCount; i++)
            {
                XmlNode child = nodeList[i];
                if (child.NodeType == XmlNodeType.Text)
                {
                    if (isVertical)
                    {
                        ctp.X += shiftBy;
                        if (isSingleLine)
                        {
                            if (i == (nodeCount - 1) && spaceNode != null)
                            {
                                RenderSingleLineTextV(element, ref ctp,
                                                      WpfTextRenderer.GetText(element, child, spaceNode), rotate, placement);
                            }
                            else
                            {
                                RenderSingleLineTextV(element, ref ctp,
                                                      WpfTextRenderer.GetText(element, child), rotate, placement);
                            }
                        }
                        else
                        {
                            if (i == (nodeCount - 1) && spaceNode != null)
                            {
                                RenderTextRunV(element, ref ctp,
                                               WpfTextRenderer.GetText(element, child, spaceNode), rotate, placement);
                            }
                            else
                            {
                                RenderTextRunV(element, ref ctp,
                                               WpfTextRenderer.GetText(element, child), rotate, placement);
                            }
                        }
                        ctp.X -= shiftBy;
                    }
                    else
                    {
                        ctp.Y -= shiftBy;
                        if (isSingleLine)
                        {
                            if (i == (nodeCount - 1) && spaceNode != null)
                            {
                                RenderSingleLineTextH(element, ref ctp,
                                                      WpfTextRenderer.GetText(element, child, spaceNode), rotate, placement);
                            }
                            else
                            {
                                RenderSingleLineTextH(element, ref ctp,
                                                      WpfTextRenderer.GetText(element, child), rotate, placement);
                            }
                        }
                        else
                        {
                            if (i == (nodeCount - 1) && spaceNode != null)
                            {
                                RenderTextRunH(element, ref ctp,
                                               WpfTextRenderer.GetText(element, child, spaceNode), rotate, placement);
                            }
                            else
                            {
                                RenderTextRunH(element, ref ctp,
                                               WpfTextRenderer.GetText(element, child), rotate, placement);
                            }
                        }
                        ctp.Y += shiftBy;
                    }
                }
            }
        }
        public override void Render(GdiGraphicsRenderer renderer)
        {
            _graphics = renderer.GdiGraphics;

            //SvgRenderingHint hint = _svgElement.RenderingHint;
            //if (hint == SvgRenderingHint.Clipping)
            //{
            //    return;
            //}
            //if (_svgElement.ParentNode is SvgClipPathElement)
            //{
            //    return;
            //}

            SvgTextBaseElement textElement = _svgElement as SvgTextBaseElement;

            if (textElement == null)
            {
                return;
            }

            string sVisibility = textElement.GetPropertyValue("visibility");
            string sDisplay    = textElement.GetPropertyValue("display");

            if (string.Equals(sVisibility, "hidden") || string.Equals(sDisplay, "none"))
            {
                return;
            }

            if (_textMode != GdiTextMode.Outlining)
            {
                SetClip(_graphics);
            }

            PointF ctp = new PointF(0, 0); // current text position

            ctp = GetCurrentTextPosition(textElement, ctp);
            string sBaselineShift = textElement.GetPropertyValue("baseline-shift").Trim();
            double shiftBy        = 0;

            if (sBaselineShift.Length > 0)
            {
                float textFontSize = GetComputedFontSize(textElement);
                if (sBaselineShift.EndsWith("%", StringComparison.OrdinalIgnoreCase))
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift.Substring(0,
                                                                             sBaselineShift.Length - 1)) / 100 * textFontSize;
                }
                else if (sBaselineShift == "sub")
                {
                    shiftBy = -0.6F * textFontSize;
                }
                else if (sBaselineShift == "super")
                {
                    shiftBy = 0.6F * textFontSize;
                }
                else if (sBaselineShift == "baseline")
                {
                    shiftBy = 0;
                }
                else
                {
                    shiftBy = SvgNumber.ParseNumber(sBaselineShift);
                }
            }

            // For for fonts loading in the background...
            var svgDoc = _svgElement.OwnerDocument;

            if (svgDoc.IsFontsLoaded == false)
            {
                //TODO: Use of SpinUntil is known to CPU heavy, but will work for now...
                SpinWait.SpinUntil(() => svgDoc.IsFontsLoaded == true);
            }

            XmlNodeType nodeType = XmlNodeType.None;

            foreach (XmlNode child in _svgElement.ChildNodes)
            {
                SvgStyleableElement stylable = child as SvgStyleableElement;
                if (stylable != null)
                {
                    sVisibility = stylable.GetPropertyValue("visibility");
                    sDisplay    = stylable.GetPropertyValue("display");
                    if (string.Equals(sVisibility, "hidden") || string.Equals(sDisplay, "none"))
                    {
                        continue;
                    }
                }

                nodeType = child.NodeType;
                if (nodeType == XmlNodeType.Text)
                {
                    ctp.Y -= (float)shiftBy;
                    AddGraphicsPath(textElement, ref ctp, GetText(textElement, child));
                    ctp.Y += (float)shiftBy;
                }
                else if (nodeType == XmlNodeType.Element)
                {
                    string nodeName = child.Name;
                    if (string.Equals(nodeName, "tref"))
                    {
                        AddTRefElementPath((SvgTRefElement)child, ref ctp);
                    }
                    else if (string.Equals(nodeName, "tspan"))
                    {
                        AddTSpanElementPath((SvgTSpanElement)child, ref ctp);
                    }
                }
            }

            PaintMarkers(renderer, textElement, _graphics);

            _graphics = null;
        }
Example #23
0
        public override void BeforeRender(WpfDrawingRenderer renderer)
        {
            base.BeforeRender(renderer);

            if (renderer == null)
            {
                return;
            }

            _isLineSegment   = false;
            _setBrushOpacity = true;

            WpfDrawingContext context = renderer.Context;

            //SetQuality(context);
            //SetTransform(context);
            //SetMask(context);

//            _drawGroup = new DrawingGroup();

            SvgStyleableElement styleElm = (SvgStyleableElement)_svgElement;

            float opacityValue   = -1;
            bool  isStyleOpacity = false;

            string opacity = styleElm.GetAttribute("opacity");

            if (string.IsNullOrWhiteSpace(opacity))
            {
                opacity = styleElm.GetPropertyValue("opacity");
                if (!string.IsNullOrWhiteSpace(opacity))
                {
                    isStyleOpacity = true;
                }
            }
            if (!string.IsNullOrWhiteSpace(opacity))
            {
                opacityValue = (float)SvgNumber.ParseNumber(opacity);
                opacityValue = Math.Min(opacityValue, 1);
                opacityValue = Math.Max(opacityValue, 0);
                if (isStyleOpacity && (opacityValue >= 0 && opacityValue < 1))
                {
                    _setBrushOpacity = false;
                    if (styleElm.HasAttribute("fill-opacity") || (styleElm.HasAttribute("style") &&
                                                                  styleElm.GetAttribute("style").Contains("fill-opacity")))
                    {
                        _setBrushOpacity = true;
                    }
                }
            }
            //string eVisibility = _svgElement.GetAttribute("visibility");
            //string eDisplay    = _svgElement.GetAttribute("display");
            //if (string.Equals(eVisibility, "hidden") || string.Equals(eDisplay, "none"))
            //{
            //    opacityValue = 0;
            //}
            //else
            //{
            //    string sVisibility = styleElm.GetPropertyValue("visibility");
            //    string sDisplay = styleElm.GetPropertyValue("display");
            //    if (string.Equals(sVisibility, "hidden") || string.Equals(sDisplay, "none"))
            //    {
            //        opacityValue = 0;
            //    }
            //}
            string sVisibility = styleElm.GetPropertyValue("visibility");

            if (string.IsNullOrWhiteSpace(sVisibility))
            {
                sVisibility = _svgElement.GetAttribute("visibility");
            }
            string sDisplay = styleElm.GetPropertyValue("display");

            if (string.IsNullOrWhiteSpace(sDisplay))
            {
                sDisplay = _svgElement.GetAttribute("display");
            }
            if (string.Equals(sVisibility, "hidden") || string.Equals(sDisplay, "none"))
            {
                opacityValue = 0;
            }

            Transform pathTransform = this.Transform;

            if (pathTransform != null && !pathTransform.Value.IsIdentity)
            {
                if (_drawGroup == null)
                {
                    _drawGroup = new DrawingGroup();
                }
                _drawGroup.Transform = pathTransform;
            }
            else
            {
                pathTransform = null; // render any identity transform useless...
            }

            Geometry pathClip = this.ClipGeometry;

            if (pathClip != null && !pathClip.IsEmpty())
            {
                if (_drawGroup == null)
                {
                    _drawGroup = new DrawingGroup();
                }
                _drawGroup.ClipGeometry = pathClip;
            }
            else
            {
                pathClip = null; // render any empty geometry useless...
            }
            Brush pathMask = this.Masking;

            if (pathMask != null)
            {
                if (_drawGroup == null)
                {
                    _drawGroup = new DrawingGroup();
                }
                _drawGroup.OpacityMask = pathMask;
            }

            if (pathTransform != null || pathClip != null || pathMask != null || (opacityValue >= 0 && opacityValue < 1))
            {
                if (_drawGroup == null)
                {
                    _drawGroup = new DrawingGroup();
                }
                if ((opacityValue >= 0 && opacityValue < 1))
                {
                    _drawGroup.Opacity = opacityValue;
                }

                DrawingGroup curGroup = _context.Peek();
                Debug.Assert(curGroup != null);
                if (curGroup != null)
                {
                    curGroup.Children.Add(_drawGroup);
                    context.Push(_drawGroup);
                }
            }
            else
            {
                _drawGroup = null;
            }

            if (_drawGroup != null)
            {
                string elementClass = this.GetElementClass();
                if (!string.IsNullOrWhiteSpace(elementClass) && context.IncludeRuntime)
                {
                    SvgObject.SetClass(_drawGroup, elementClass);
                }

                string elementId = this.GetElementName();
                if (!string.IsNullOrWhiteSpace(elementId) && !context.IsRegisteredId(elementId))
                {
                    SvgObject.SetName(_drawGroup, elementId);

                    context.RegisterId(elementId);

                    if (context.IncludeRuntime)
                    {
                        SvgObject.SetId(_drawGroup, elementId);
                    }
                }
            }
        }
Example #24
0
        protected List <GdiGradientStop> GetGradientStops(XmlNodeList stops)
        {
            int itemCount = stops.Count;

            if (itemCount == 0)
            {
                return(new List <GdiGradientStop>());
            }
            var gradientStops = new List <GdiGradientStop>(itemCount);

            double lastOffset = 0;

            for (int i = 0; i < itemCount; i++)
            {
                SvgStopElement stop = (SvgStopElement)stops.Item(i);
                if (stop == null)
                {
                    continue;
                }
                string prop  = stop.GetAttribute("stop-color");
                string style = stop.GetAttribute("style");
                Color  color = Color.Transparent; // no auto-inherited...
                if (!string.IsNullOrWhiteSpace(prop) || !string.IsNullOrWhiteSpace(style))
                {
                    GdiSvgColor svgColor = new GdiSvgColor(stop, "stop-color");
                    color = svgColor.Color;
                }
                else
                {
                    color = Color.Black; // the default color...
                    double alpha = 255;
                    string opacity;

                    opacity = stop.GetAttribute("stop-opacity"); // no auto-inherit
                    if (opacity == "inherit")                    // if explicitly defined...
                    {
                        opacity = stop.GetPropertyValue("stop-opacity");
                    }
                    if (!string.IsNullOrWhiteSpace(opacity))
                    {
                        alpha *= SvgNumber.ParseNumber(opacity);
                    }

                    alpha = Math.Min(alpha, 255);
                    alpha = Math.Max(alpha, 0);

                    color = Color.FromArgb((byte)Convert.ToInt32(alpha), color.R, color.G, color.B);
                }

                double offset = (stop.Offset == null) ? 0 : stop.Offset.AnimVal;

                offset /= 100;
                offset  = Math.Max(lastOffset, offset);

                gradientStops.Add(new GdiGradientStop(color, (float)offset));
                lastOffset = offset;
            }

            if (itemCount == 0)
            {
                gradientStops.Add(new GdiGradientStop(Color.Black, 0));
                gradientStops.Add(new GdiGradientStop(Color.Black, 1));
            }

            return(gradientStops);
        }
        public override void Render(GdiGraphicsRenderer renderer)
        {
            base.Render(renderer);

            var             graphics = renderer.GdiGraphics;
            SvgImageElement iElement = (SvgImageElement)_svgElement;

            ImageAttributes imageAttributes = new ImageAttributes();

            float opacityValue = -1;

            string opacity = iElement.GetAttribute("opacity");

            if (string.IsNullOrWhiteSpace(opacity))
            {
                opacity = iElement.GetPropertyValue("opacity");
            }
            if (!string.IsNullOrWhiteSpace(opacity))
            {
                opacityValue = (float)SvgNumber.ParseNumber(opacity);
                opacityValue = Math.Min(opacityValue, 1);
                opacityValue = Math.Max(opacityValue, 0);
            }

            if (opacityValue >= 0 && opacityValue < 1)
            {
                ColorMatrix colorMatrix = new ColorMatrix();
                colorMatrix.Matrix00 = 1.00f;                 // Red
                colorMatrix.Matrix11 = 1.00f;                 // Green
                colorMatrix.Matrix22 = 1.00f;                 // Blue
                colorMatrix.Matrix33 = opacityValue;          // alpha
                colorMatrix.Matrix44 = 1.00f;                 // w

                imageAttributes.SetColorMatrix(colorMatrix, ColorMatrixFlag.Default, ColorAdjustType.Bitmap);
            }

            float width  = (float)iElement.Width.AnimVal.Value;
            float height = (float)iElement.Height.AnimVal.Value;

            RectangleF destRect = new RectangleF((float)iElement.X.AnimVal.Value,
                                                 (float)iElement.Y.AnimVal.Value, (float)iElement.Width.AnimVal.Value,
                                                 (float)iElement.Height.AnimVal.Value);

            RectangleF srcRect;
            RectangleF clipRect = destRect;

//            var container = graphics.BeginContainer();
            graphics.SetClip(new Region(clipRect), CombineMode.Intersect);

            Image     image  = null;
            SvgWindow svgWnd = null;

            if (iElement.IsSvgImage)
            {
                svgWnd = GetSvgWindow(graphics);
                if (width > 0 && height > 0)
                {
                    srcRect = new RectangleF(0, 0, width, height);
                }
                else
                {
                    SvgSvgElement svgEl = (SvgSvgElement)svgWnd.Document.RootElement;

                    SvgSizeF size = svgEl.GetSize();

                    srcRect = new RectangleF(new PointF(0, 0), new SizeF(size.Width, size.Height));
                }
            }
            else
            {
                image = GetBitmap(iElement);
                if (image == null)
                {
                    return;
                }
                srcRect = new RectangleF(0, 0, image.Width, image.Height);
            }

            ISvgAnimatedPreserveAspectRatio animatedAspectRatio = iElement.PreserveAspectRatio;

            if (animatedAspectRatio != null && animatedAspectRatio.AnimVal != null)
            {
                SvgPreserveAspectRatio     aspectRatio     = animatedAspectRatio.AnimVal as SvgPreserveAspectRatio;
                SvgPreserveAspectRatioType aspectRatioType =
                    (aspectRatio != null) ? aspectRatio.Align : SvgPreserveAspectRatioType.Unknown;

                if (aspectRatio != null && aspectRatioType != SvgPreserveAspectRatioType.None &&
                    aspectRatioType != SvgPreserveAspectRatioType.Unknown)
                {
                    var fScaleX = destRect.Width / srcRect.Width;
                    var fScaleY = destRect.Height / srcRect.Height;
                    var xOffset = 0.0f;
                    var yOffset = 0.0f;

                    SvgMeetOrSlice meetOrSlice = aspectRatio.MeetOrSlice;
                    if (meetOrSlice == SvgMeetOrSlice.Slice)
                    {
                        fScaleX = Math.Max(fScaleX, fScaleY);
                        fScaleY = Math.Max(fScaleX, fScaleY);
                    }
                    else
                    {
                        fScaleX = Math.Min(fScaleX, fScaleY);
                        fScaleY = Math.Min(fScaleX, fScaleY);
                    }

                    switch (aspectRatioType)
                    {
                    case SvgPreserveAspectRatioType.XMinYMin:
                        break;

                    case SvgPreserveAspectRatioType.XMidYMin:
                        xOffset = (destRect.Width - srcRect.Width * fScaleX) / 2;
                        break;

                    case SvgPreserveAspectRatioType.XMaxYMin:
                        xOffset = (destRect.Width - srcRect.Width * fScaleX);
                        break;

                    case SvgPreserveAspectRatioType.XMinYMid:
                        yOffset = (destRect.Height - srcRect.Height * fScaleY) / 2;
                        break;

                    case SvgPreserveAspectRatioType.XMidYMid:
                        xOffset = (destRect.Width - srcRect.Width * fScaleX) / 2;
                        yOffset = (destRect.Height - srcRect.Height * fScaleY) / 2;
                        break;

                    case SvgPreserveAspectRatioType.XMaxYMid:
                        xOffset = (destRect.Width - srcRect.Width * fScaleX);
                        yOffset = (destRect.Height - srcRect.Height * fScaleY) / 2;
                        break;

                    case SvgPreserveAspectRatioType.XMinYMax:
                        yOffset = (destRect.Height - srcRect.Height * fScaleY);
                        break;

                    case SvgPreserveAspectRatioType.XMidYMax:
                        xOffset = (destRect.Width - srcRect.Width * fScaleX) / 2;
                        yOffset = (destRect.Height - srcRect.Height * fScaleY);
                        break;

                    case SvgPreserveAspectRatioType.XMaxYMax:
                        xOffset = (destRect.Width - srcRect.Width * fScaleX);
                        yOffset = (destRect.Height - srcRect.Height * fScaleY);
                        break;
                    }

                    destRect = new RectangleF(destRect.X + xOffset, destRect.Y + yOffset,
                                              srcRect.Width * fScaleX, srcRect.Height * fScaleY);
                }
                if (image != null)
                {
                    SvgColorProfileElement colorProfile = (SvgColorProfileElement)iElement.ColorProfile;
                    if (colorProfile != null)
                    {
                        SvgUriReference svgUri     = colorProfile.UriReference;
                        Uri             profileUri = new Uri(svgUri.AbsoluteUri);

                        imageAttributes.SetOutputChannelColorProfile(profileUri.LocalPath, ColorAdjustType.Default);
                    }

                    graphics.DrawImage(this, image, destRect, srcRect, GraphicsUnit.Pixel, imageAttributes);

                    image.Dispose();
                    image = null;
                }
                else if (iElement.IsSvgImage && svgWnd != null)
                {
                    svgWnd.Resize((int)srcRect.Width, (int)srcRect.Height);

                    var currOffset = new PointF(graphics.Transform.OffsetX, graphics.Transform.OffsetY);
                    if (!currOffset.IsEmpty)
                    {
                        graphics.TranslateTransform(-currOffset.X, -currOffset.Y);
                    }
                    graphics.ScaleTransform(destRect.Width / srcRect.Width, destRect.Height / srcRect.Height);
                    if (!currOffset.IsEmpty)
                    {
                        graphics.TranslateTransform(currOffset.X + destRect.X, currOffset.Y + destRect.Y);
                    }

                    _embeddedRenderer.Render(svgWnd.Document);
                }

                graphics.ResetClip();
//                graphics.EndContainer(container);
            }

            if (_embeddedRenderer != null)
            {
                _embeddedRenderer.GdiGraphics = null;
                _embeddedRenderer.Dispose();
                _embeddedRenderer = null;
            }

            if (imageAttributes != null)
            {
                imageAttributes.Dispose();
                imageAttributes = null;
            }
        }
        public override void Render(WpfDrawingRenderer renderer)
        {
            WpfDrawingContext context      = renderer.Context;
            SvgImageElement   imageElement = (SvgImageElement)_svgElement;

            double x      = imageElement.X.AnimVal.Value;
            double y      = imageElement.Y.AnimVal.Value;
            double width  = imageElement.Width.AnimVal.Value;
            double height = imageElement.Height.AnimVal.Value;

            Rect destRect = new Rect(x, y, width, height);
            Rect clipRect = new Rect(x, y, width, height);

            ImageSource imageSource = null;

            if (imageElement.IsSvgImage)
            {
                if (imageElement.IsRootReferenced(imageElement.OwnerDocument.BaseURI))
                {
                    return;
                }

                SvgWindow wnd = GetSvgWindow();
                if (wnd == null)
                {
                    return;
                }
                //_embeddedRenderer.BackColor = Color.Empty;
                _embeddedRenderer.Render(wnd.Document);

                DrawingGroup imageGroup = _embeddedRenderer.Drawing as DrawingGroup;
                if (imageGroup != null &&
                    (imageGroup.Children != null && imageGroup.Children.Count == 1))
                {
                    DrawingGroup imageDrawing = imageGroup.Children[0] as DrawingGroup;
                    if (imageDrawing != null)
                    {
                        imageDrawing.ClipGeometry = null;

                        imageSource = new DrawingImage(imageDrawing);
                    }
                    else
                    {
                        imageGroup.ClipGeometry = null;

                        imageSource = new DrawingImage(imageGroup);
                    }
                }
                else
                {
                    imageSource = new DrawingImage(_embeddedRenderer.Drawing);
                }

                if (_embeddedRenderer != null)
                {
                    _embeddedRenderer.Dispose();
                    _embeddedRenderer = null;
                }
            }
            else
            {
                imageSource = GetBitmapSource(imageElement, context);
            }

            if (imageSource == null)
            {
                return;
            }

            //TODO--PAUL: Set the DecodePixelWidth/DecodePixelHeight?

            // Freeze the DrawingImage for performance benefits.
            //imageSource.Freeze();

            DrawingGroup drawGroup = null;

            ISvgAnimatedPreserveAspectRatio animatedAspectRatio = imageElement.PreserveAspectRatio;

            if (animatedAspectRatio != null && animatedAspectRatio.AnimVal != null)
            {
                SvgPreserveAspectRatio     aspectRatio     = animatedAspectRatio.AnimVal as SvgPreserveAspectRatio;
                SvgPreserveAspectRatioType aspectRatioType =
                    (aspectRatio != null) ? aspectRatio.Align : SvgPreserveAspectRatioType.Unknown;
                if (aspectRatio != null && aspectRatioType != SvgPreserveAspectRatioType.None &&
                    aspectRatioType != SvgPreserveAspectRatioType.Unknown)
                {
                    double imageWidth  = imageSource.Width;
                    double imageHeight = imageSource.Height;

                    double viewWidth  = destRect.Width;
                    double viewHeight = destRect.Height;

                    SvgMeetOrSlice meetOrSlice = aspectRatio.MeetOrSlice;
                    if (meetOrSlice == SvgMeetOrSlice.Meet)
                    {
                        if (imageWidth <= viewWidth && imageHeight <= viewHeight)
                        {
                            if (this.Transform == null)
                            {
                                if (!aspectRatio.IsDefaultAlign) // Cacxa
                                {
                                    destRect = this.GetBounds(destRect, new Size(imageWidth, imageHeight), aspectRatioType);
                                }
                                else
                                {
                                    Transform viewTransform = this.GetAspectRatioTransform(aspectRatio,
                                                                                           new SvgRect(0, 0, imageWidth, imageHeight),
                                                                                           new SvgRect(destRect.X, destRect.Y, destRect.Width, destRect.Height));

                                    if (viewTransform != null)
                                    {
                                        drawGroup           = new DrawingGroup();
                                        drawGroup.Transform = viewTransform;

                                        DrawingGroup lastGroup = context.Peek();
                                        Debug.Assert(lastGroup != null);

                                        if (lastGroup != null)
                                        {
                                            lastGroup.Children.Add(drawGroup);
                                        }

                                        destRect = this.GetBounds(destRect,
                                                                  new Size(imageWidth, imageHeight), aspectRatioType);

                                        // The origin is already handled by the view transform...
                                        destRect.X = 0;
                                        destRect.Y = 0;
                                    }
                                }
                            }
                            else
                            {
                                destRect = new Rect(0, 0, viewWidth, viewHeight);
                            }
                        }
                        else
                        {
                            if (this.Transform == null)
                            {
                                Transform viewTransform = this.GetAspectRatioTransform(aspectRatio,
                                                                                       new SvgRect(0, 0, imageWidth, imageHeight),
                                                                                       new SvgRect(destRect.X, destRect.Y, destRect.Width, destRect.Height));

                                if (viewTransform != null)
                                {
                                    drawGroup           = new DrawingGroup();
                                    drawGroup.Transform = viewTransform;

                                    DrawingGroup lastGroup = context.Peek();
                                    Debug.Assert(lastGroup != null);

                                    if (lastGroup != null)
                                    {
                                        lastGroup.Children.Add(drawGroup);
                                    }

                                    destRect = this.GetBounds(destRect,
                                                              new Size(imageWidth, imageHeight), aspectRatioType);

                                    // The origin is already handled by the view transform...
                                    destRect.X = 0;
                                    destRect.Y = 0;
                                }
                            }
                        }
                    }
                    else if (meetOrSlice == SvgMeetOrSlice.Slice)
                    {
                        var       fScaleX       = viewWidth / imageWidth;
                        var       fScaleY       = viewHeight / imageHeight;
                        Transform viewTransform = this.GetAspectRatioTransform(aspectRatio,
                                                                               new SvgRect(0, 0, imageWidth, imageHeight),
                                                                               new SvgRect(destRect.X, destRect.Y, destRect.Width, destRect.Height));

                        DrawingGroup sliceGroup = new DrawingGroup();
                        sliceGroup.ClipGeometry = new RectangleGeometry(clipRect);

                        DrawingGroup lastGroup = context.Peek();
                        Debug.Assert(lastGroup != null);

                        if (lastGroup != null)
                        {
                            lastGroup.Children.Add(sliceGroup);
                        }

                        if (viewTransform != null)
                        {
                            drawGroup           = new DrawingGroup();
                            drawGroup.Transform = viewTransform;

                            sliceGroup.Children.Add(drawGroup);

                            destRect = this.GetBounds(destRect,
                                                      new Size(imageWidth, imageHeight), aspectRatioType);

                            // The origin is already handled by the view transform...
                            destRect.X = 0;
                            destRect.Y = 0;
                        }
                        else
                        {
                            drawGroup = sliceGroup;
                        }
                    }
                }
            }

            ImageDrawing drawing = new ImageDrawing(imageSource, destRect);

            float opacityValue = -1;

            string opacity = imageElement.GetAttribute("opacity");

            if (string.IsNullOrWhiteSpace(opacity))
            {
                opacity = imageElement.GetPropertyValue("opacity");
            }
            if (!string.IsNullOrWhiteSpace(opacity))
            {
                opacityValue = (float)SvgNumber.ParseNumber(opacity);
                opacityValue = Math.Min(opacityValue, 1);
                opacityValue = Math.Max(opacityValue, 0);
            }

            Geometry  clipGeom  = this.ClipGeometry;
            Transform transform = this.Transform;

            bool ownedGroup = true;

            if (drawGroup == null)
            {
                drawGroup  = context.Peek();
                ownedGroup = false;
            }

            Debug.Assert(drawGroup != null);
            if (drawGroup != null)
            {
                if ((opacityValue >= 0 && opacityValue < 1) || (clipGeom != null && !clipGeom.IsEmpty()) ||
                    (transform != null && !transform.Value.IsIdentity))
                {
                    DrawingGroup clipGroup = ownedGroup ? drawGroup : new DrawingGroup();
                    if (opacityValue >= 0 && opacityValue < 1)
                    {
                        clipGroup.Opacity = opacityValue;
                    }
                    if (clipGeom != null)
                    {
                        SvgUnitType clipUnits = this.ClipUnits;
                        if (clipUnits == SvgUnitType.ObjectBoundingBox)
                        {
                            Rect drawingBounds = drawing.Bounds;

                            TransformGroup transformGroup = new TransformGroup();

                            // Scale the clip region (at (0, 0)) and translate to the top-left corner of the target.
                            transformGroup.Children.Add(
                                new ScaleTransform(drawingBounds.Width, drawingBounds.Height));
                            transformGroup.Children.Add(
                                new TranslateTransform(drawingBounds.X, drawingBounds.Y));

                            clipGeom.Transform = transformGroup;
                        }

                        clipGroup.ClipGeometry = clipGeom;
                    }
                    if (transform != null)
                    {
                        Transform curTransform = clipGroup.Transform;
                        if (curTransform != null && curTransform.Value.IsIdentity == false)
                        {
                            TransformGroup transformGroup = new TransformGroup();
                            transformGroup.Children.Add(curTransform);
                            transformGroup.Children.Add(transform);
                            clipGroup.Transform = transformGroup;
                        }
                        else
                        {
                            clipGroup.Transform = transform;
                        }
                    }

                    clipGroup.Children.Add(drawing);
                    if (!ownedGroup)
                    {
                        drawGroup.Children.Add(clipGroup);
                    }
                }
                else
                {
                    drawGroup.Children.Add(drawing);
                }

                string elementId = this.GetElementName();
                if (ownedGroup)
                {
                    string sVisibility = imageElement.GetPropertyValue("visibility");
                    string sDisplay    = imageElement.GetPropertyValue("display");
                    if (string.Equals(sVisibility, "hidden") || string.Equals(sDisplay, "none"))
                    {
                        drawGroup.Opacity = 0;
                    }

                    if (!_idAssigned && !string.IsNullOrWhiteSpace(elementId) && !context.IsRegisteredId(elementId))
                    {
                        context.RegisterId(elementId);

                        if (context.IncludeRuntime)
                        {
                            SvgObject.SetName(drawGroup, elementId);

                            SvgObject.SetId(drawGroup, elementId);
                        }
                    }

                    // Register this drawing with the Drawing-Document...
                    this.Rendered(drawGroup);
                }
                else if (!_idAssigned)
                {
                    if (!_idAssigned && !string.IsNullOrWhiteSpace(elementId) && !context.IsRegisteredId(elementId))
                    {
                        context.RegisterId(elementId);

                        if (context.IncludeRuntime)
                        {
                            SvgObject.SetName(imageSource, elementId);

                            SvgObject.SetId(imageSource, elementId);
                        }
                    }

                    // Register this drawing with the Drawing-Document...
                    this.Rendered(drawing);
                }
            }
        }
Example #27
0
        public override void Render(WpfDrawingRenderer renderer)
        {
            _isAggregated = false;

            if (_isLayer)
            {
                base.Render(renderer);

                return;
            }

            WpfDrawingContext context = renderer.Context;

            Geometry  clipGeom  = this.ClipGeometry;
            Transform transform = this.Transform;

            float opacityValue = -1;

            SvgAElement element = (SvgAElement)_svgElement;
            string      opacity = element.GetPropertyValue("opacity");

            if (string.IsNullOrWhiteSpace(opacity))
            {
                opacity = element.GetPropertyValue("opacity");
            }
            if (opacity != null && opacity.Length > 0)
            {
                opacityValue = (float)SvgNumber.ParseNumber(opacity);
                opacityValue = Math.Min(opacityValue, 1);
                opacityValue = Math.Max(opacityValue, 0);
            }

            WpfLinkVisitor linkVisitor = context.LinkVisitor;

            if (linkVisitor != null || clipGeom != null || transform != null || opacityValue >= 0)
            {
                _drawGroup = new DrawingGroup();

                string elementId = this.GetElementName();
                if (!string.IsNullOrWhiteSpace(elementId) && !context.IsRegisteredId(elementId))
                {
                    _drawGroup.SetValue(FrameworkElement.NameProperty, elementId);

                    context.RegisterId(elementId);

                    if (context.IncludeRuntime)
                    {
                        SvgObject.SetId(_drawGroup, elementId);
                    }
                }

                string elementClass = this.GetElementClass();
                if (!string.IsNullOrWhiteSpace(elementClass) && context.IncludeRuntime)
                {
                    SvgObject.SetClass(_drawGroup, elementClass);
                }

                DrawingGroup currentGroup = context.Peek();

                if (currentGroup == null)
                {
                    throw new InvalidOperationException("An existing group is expected.");
                }

                if (linkVisitor != null && linkVisitor.Aggregates && context.Links != null)
                {
                    if (!linkVisitor.Exists(elementId))
                    {
                        context.Links.Children.Add(_drawGroup);
                    }
                }
                else
                {
                    currentGroup.Children.Add(_drawGroup);
                }

                context.Push(_drawGroup);

                if (clipGeom != null)
                {
                    _drawGroup.ClipGeometry = clipGeom;
                }

                if (transform != null)
                {
                    _drawGroup.Transform = transform;
                }

                if (opacityValue >= 0)
                {
                    _drawGroup.Opacity = opacityValue;
                }

                string sVisibility = element.GetPropertyValue("visibility");
                string sDisplay    = element.GetPropertyValue("display");
                if (string.Equals(sVisibility, "hidden") || string.Equals(sDisplay, "none"))
                {
                    opacityValue       = 0;
                    _drawGroup.Opacity = 0;
                }

                if (linkVisitor != null)
                {
                    linkVisitor.Visit(_drawGroup, element, context, opacityValue);

                    _isAggregated = linkVisitor.IsAggregate;
                }
            }

            base.Render(renderer);
        }
Example #28
0
        public override void Render(GdiGraphicsRenderer renderer)
        {
            var             graphics = renderer.GdiGraphics;
            SvgImageElement iElement = (SvgImageElement)_svgElement;

            ImageAttributes imageAttributes = new ImageAttributes();

            string sOpacity = iElement.GetPropertyValue("opacity");

            if (sOpacity != null && sOpacity.Length > 0)
            {
                double      opacity       = SvgNumber.ParseNumber(sOpacity);
                ColorMatrix myColorMatrix = new ColorMatrix();
                myColorMatrix.Matrix00 = 1.00f;                 // Red
                myColorMatrix.Matrix11 = 1.00f;                 // Green
                myColorMatrix.Matrix22 = 1.00f;                 // Blue
                myColorMatrix.Matrix33 = (float)opacity;        // alpha
                myColorMatrix.Matrix44 = 1.00f;                 // w

                imageAttributes.SetColorMatrix(myColorMatrix, ColorMatrixFlag.Default, ColorAdjustType.Bitmap);
            }

            float width  = (float)iElement.Width.AnimVal.Value;
            float height = (float)iElement.Height.AnimVal.Value;

            RectangleF destRect = new RectangleF((float)iElement.X.AnimVal.Value,
                                                 (float)iElement.Y.AnimVal.Value, (float)iElement.Width.AnimVal.Value,
                                                 (float)iElement.Height.AnimVal.Value);

            Image image = null;

            if (iElement.IsSvgImage)
            {
                SvgWindow wnd = GetSvgWindow();
                _embeddedRenderer.BackColor = Color.Empty;
                _embeddedRenderer.Render(wnd.Document);

                image = _embeddedRenderer.RasterImage;
            }
            else
            {
                image = GetBitmap(iElement);
            }

            if (image != null)
            {
                // code extracted from FitToViewbox
                var spar = (SvgPreserveAspectRatio)iElement.PreserveAspectRatio.AnimVal ?? new SvgPreserveAspectRatio("none", iElement);

                double[] translateAndScale = spar.FitToViewBox(new SvgRect(0, 0, image.Width, image.Height),
                                                               new SvgRect(destRect.X, destRect.Y, destRect.Width, destRect.Height));
                graphics.TranslateTransform((float)translateAndScale[0], (float)translateAndScale[1]);
                graphics.ScaleTransform((float)translateAndScale[2], (float)translateAndScale[3]);
                graphics.DrawImage(this, image, new Rectangle(0, 0, image.Width, image.Height), 0f, 0f,
                                   image.Width, image.Height, GraphicsUnit.Pixel, imageAttributes);

                image.Dispose();
                image = null;
            }

            if (_embeddedRenderer != null)
            {
                _embeddedRenderer.Dispose();
                _embeddedRenderer = null;
            }

            if (imageAttributes != null)
            {
                imageAttributes.Dispose();
                imageAttributes = null;
            }
        }
Example #29
0
        public static Brush CreateViewportBrush(SvgStyleableElement svgElm)
        {
            string prop    = svgElm.GetAttribute("viewport-fill");
            string opacity = svgElm.GetAttribute("viewport-fill-opacity");          // no auto-inherit

            if (string.Equals(prop, "inherit", StringComparison.OrdinalIgnoreCase)) // if explicitly defined...
            {
                prop = svgElm.GetPropertyValue("viewport-fill");
            }
            if (string.Equals(opacity, "inherit", StringComparison.OrdinalIgnoreCase)) // if explicitly defined...
            {
                opacity = svgElm.GetPropertyValue("viewport-fill-opacity");
            }
            if (!string.IsNullOrWhiteSpace(prop))
            {
                if (string.Equals(prop, "currentColor", StringComparison.OrdinalIgnoreCase))
                {
                    var svgParent = svgElm.ParentNode as SvgStyleableElement;
                    if (svgParent != null)
                    {
                        prop = svgParent.GetPropertyValue(CssConstants.PropColor, "viewport-fill");
                    }
                }

                Color       color    = Colors.Transparent; // no auto-inherited...
                WpfSvgColor svgColor = new WpfSvgColor(svgElm, "viewport-fill");
                color = svgColor.Color;

                if (color.A == 255)
                {
                    double alpha = 255;

                    if (!string.IsNullOrWhiteSpace(opacity))
                    {
                        alpha *= SvgNumber.ParseNumber(opacity);
                    }

                    alpha = Math.Min(alpha, 255);
                    alpha = Math.Max(alpha, 0);

                    color = Color.FromArgb((byte)Convert.ToInt32(alpha), color.R, color.G, color.B);
                }

                var    brush        = new SolidColorBrush(color);
                double opacityValue = 1;
                if (!string.IsNullOrWhiteSpace(opacity) && double.TryParse(opacity, out opacityValue))
                {
                    brush.Opacity = opacityValue;
                }

                return(brush);
            }
            else
            {
                Color  color = Colors.Black; // the default color...
                double alpha = 255;

                if (!string.IsNullOrWhiteSpace(opacity))
                {
                    alpha *= SvgNumber.ParseNumber(opacity);
                }

                alpha = Math.Min(alpha, 255);
                alpha = Math.Max(alpha, 0);

                color = Color.FromArgb((byte)Convert.ToInt32(alpha), color.R, color.G, color.B);

                return(new SolidColorBrush(color));
            }
        }
        public override void Render(WpfDrawingRenderer renderer)
        {
            if (_drawGroup != null)
            {
                Geometry clipGeom = this.ClipGeometry;
                if (clipGeom != null)
                {
                    _drawGroup.ClipGeometry = clipGeom;
                }

                Transform transform = this.Transform;
                if (transform != null)
                {
                    _drawGroup.Transform = transform;
                }

                float opacityValue = -1;

                SvgGElement element = (SvgGElement)_svgElement;
                string      opacity = element.GetAttribute("opacity");
                if (string.IsNullOrWhiteSpace(opacity))
                {
                    opacity = element.GetPropertyValue("opacity");
                }
                if (!string.IsNullOrWhiteSpace(opacity))
                {
                    opacityValue = (float)SvgNumber.ParseNumber(opacity);
                    opacityValue = Math.Min(opacityValue, 1);
                    opacityValue = Math.Max(opacityValue, 0);
                }

                if (opacityValue >= 0 && opacityValue < 1)
                {
                    _drawGroup.Opacity = opacityValue;
                }

                string sVisibility = element.GetPropertyValue("visibility");
                string sDisplay    = element.GetPropertyValue("display");
                if (string.Equals(sVisibility, "hidden", StringComparison.OrdinalIgnoreCase))
                {
                    var isOverriden = false;
                    foreach (XmlNode child in element.ChildNodes)
                    {
                        if (child.NodeType == XmlNodeType.Element)
                        {
                            var svgElem = child as SvgElement;
                            if (svgElem != null && string.Equals(svgElem.GetAttribute("visibility"),
                                                                 "visible", StringComparison.OrdinalIgnoreCase))
                            {
                                isOverriden = true;
                                break;
                            }
                        }
                    }

                    if (!isOverriden)
                    {
                        _drawGroup.Opacity = 0;
                    }
                }
                else if (string.Equals(sDisplay, "none", StringComparison.OrdinalIgnoreCase))
                {
                    _drawGroup.Opacity = 0;
                }
            }

            // Register this drawing with the Drawing-Document...
            this.Rendered(_drawGroup);

            base.Render(renderer);
        }