Exemplo n.º 1
0
        private static IElement CreateSvgLine(XdObjectJson xdObject, List <IDefElement> defs)
        {
            var id       = xdObject.GetSimpleName().Replace(" ", "_");
            var dataName = xdObject.GetSimpleName();
            var shape    = xdObject.Shape;

            var parameter = new ElementParameter
            {
                Id = id
            };

            parameter.Transform = new Transform {
                Value = xdObject.Transform
            };

            var opacity = xdObject.Style?.Opacity;

            parameter.Opacity = opacity;

            if (xdObject.Group != null)
            {
                if (MaskGroupParser.Is(xdObject))
                {
                    var clipPathId = $"clip-path{defs.Count}";
                    parameter.ClipPath = $"url(#{clipPathId})";
                    var clipPathChildren = xdObject.Meta.Ux.ClipPathResources.Children.Select(x => CreateSvgLine(x, defs));
                    defs.Add(new ClipPathDefElement {
                        Id = clipPathId, Children = clipPathChildren.ToArray()
                    });
                }

                parameter.DataName = dataName;
                var blendMode = xdObject.Style?.BlendMode;
                var isolation = xdObject.Style?.Isolation;
                var children  = xdObject.Group.Children.Select(x => CreateSvgLine(x, defs)).ToArray();
                return(new GroupElement {
                    Parameter = parameter, Children = children, BlendMode = blendMode, Isolation = isolation
                });
            }

            XdStyleFillPatternJson image = null;
            var fill = xdObject.Style?.Fill;

            parameter.EnableFill = true;
            if (fill != null && fill.Type != "none")
            {
                var color = xdObject.Style.Fill.ToUnityColor();
                parameter.Fill = color;

                if (fill.Type == "solid" || fill.Type == "gradient")
                {
                    // nothing to do
                    // gradientはサポートしていないが、知らないタイプというわけではないのでスルー
                }
                else if (fill.Type == "pattern")
                {
                    image          = fill.Pattern;
                    parameter.Fill = null;
                }
                else
                {
                    Debug.LogWarning($"Unknown fill type {fill.Type} in {xdObject.Name}");
                }

                if (!string.IsNullOrWhiteSpace(shape.Winding))
                {
                    parameter.FillRule = shape.Winding;
                }
            }

            float?shapeR = null;

            if (shape.R != null)
            {
                if (shape.R is List <object> list)
                {
                    shapeR = (float)(double)list[0];
                }
                else if (shape.R is double d)
                {
                    shapeR = (float)d;
                }
                else
                {
                    throw new NotSupportedException($"Unknown shape.r type {shape.R.GetType()}");
                }
            }

            if (shapeR != null && shape.Type != CircleElement.Name)
            {
                parameter.Rx = shapeR;
                if (parameter.Rx > shape.Width / 2f)
                {
                    parameter.Rx = shape.Width / 2f;
                }
                if (parameter.Rx > shape.Height / 2f)
                {
                    parameter.Rx = shape.Height / 2f;
                }
            }

            var    stroke      = xdObject.Style?.Stroke;
            string strokeAlign = null;

            if (stroke != null && stroke.Type != "none")
            {
                parameter.EnableStroke     = true;
                parameter.Stroke           = stroke.ToUnityColor();
                parameter.StrokeWidth      = stroke.Width;
                parameter.StrokeMiterLimit = stroke.MiterLimit;

                if (!string.IsNullOrWhiteSpace(stroke.Join))
                {
                    parameter.StrokeLinejoin = stroke.Join;
                }

                if (!string.IsNullOrWhiteSpace(stroke.Cap))
                {
                    parameter.StrokeLinecap = stroke.Cap;
                }

                if (stroke.Dash != null)
                {
                    parameter.StrokeDasharray = stroke.Dash;
                }

                if (stroke.Align == null)
                {
                    strokeAlign = null;
                }
                else if (stroke.Align == "outside")
                {
                    strokeAlign = "outside";
                }
                else if (stroke.Align == "inside")
                {
                    strokeAlign = "inside";
                }
                else
                {
                    throw new NotSupportedException($"{xdObject} has unknown align type {stroke.Align}");
                }
            }

            if (image != null)
            {
                var imageBytes = XdImporter.XdFile.GetResource(fill.Pattern.Meta);
                return(new ImageElement {
                    Parameter = parameter, ImageBytes = imageBytes, Width = shape.Width, Height = shape.Height
                });
            }

            if (shape.Type == PathElement.Name)
            {
                return new PathElement {
                           Parameter = parameter, D = shape.Path
                }
            }
            ;

            if (shape.Type == CompoundElement.Name)
            {
                return new CompoundElement {
                           Parameter = parameter, D = shape.Path
                }
            }
            ;

            if (shape.Type == LineElement.Name)
            {
                return new LineElement {
                           Parameter = parameter, X1 = shape.X1, Y1 = shape.Y1, X2 = shape.X2, Y2 = shape.Y2
                }
            }
            ;

            if (shape.Type == RectElement.Name)
            {
                if (strokeAlign == "outside")
                {
                    return(RectElement.Outside(shape, parameter));
                }
                if (strokeAlign == "inside")
                {
                    return(RectElement.Inside(shape, parameter));
                }
                return(new RectElement {
                    Parameter = parameter, Width = shape.Width, Height = shape.Height
                });
            }

            if (shape.Type == CircleElement.Name)
            {
                if (strokeAlign == "outside")
                {
                    return(CircleElement.Outside(shape, parameter, shapeR));
                }
                if (strokeAlign == "inside")
                {
                    return(CircleElement.Inside(shape, parameter, shapeR));
                }
                return(new CircleElement {
                    Parameter = parameter, Cx = shape.Cx, Cy = shape.Cy, R = shapeR.Value
                });
            }

            if (shape.Type == EllipseElement.Name)
            {
                if (strokeAlign == "outside")
                {
                    return(EllipseElement.Outside(shape, parameter));
                }
                if (strokeAlign == "inside")
                {
                    return(EllipseElement.Inside(shape, parameter));
                }
                return(new EllipseElement {
                    Parameter = parameter, Cx = shape.Cx, Cy = shape.Cy, Rx = shape.Rx, Ry = shape.Ry
                });
            }

            throw new NotSupportedException($"Unknown type {shape.Type}");
        }
Exemplo n.º 2
0
        private static IElement CreateSvgLine(XdObjectJson xdObject, List <IDefElement> defs)
        {
            var id       = xdObject.Name.Replace(" ", "_");
            var dataName = xdObject.Name;
            var shape    = xdObject.Shape;

            var parameter = new ElementParameter
            {
                Id = id
            };

            var tx = xdObject.Transform?.Tx ?? 0f;
            var ty = xdObject.Transform?.Ty ?? 0f;

            parameter.Transform.X = tx;
            parameter.Transform.Y = ty;

            var opacity = xdObject.Style?.Opacity;

            parameter.Opacity = opacity;

            if (xdObject.Group != null)
            {
                parameter.DataName = dataName;
                if (xdObject.Meta?.Ux?.ClipPathResources?.Type == "clipPath")
                {
                    var clipPath = xdObject.Meta.Ux.ClipPathResources.Children[0];
                    parameter.ClipPath = "url(#clip-path)";

                    var clipPathPath = new PathElement
                    {
                        Parameter = new ElementParameter
                        {
                            Id        = "_Clipping_Path_",
                            DataName  = "Clipping Path",
                            Transform = new Transform
                            {
                                X = clipPath.Transform.Tx,
                                Y = clipPath.Transform.Ty,
                            },
                        },
                        D = clipPath.Shape.Path,
                    };
                    defs.Add(new ClipPathDefElement {
                        Id = "clip-path", Path = clipPathPath
                    });
                }

                var children = xdObject.Group.Children.Select(x => CreateSvgLine(x, defs)).ToArray();
                return(new GroupElement {
                    Parameter = parameter, Children = children
                });
            }

            var fill = xdObject.Style?.Fill;

            parameter.EnableFill = true;
            if (fill != null && fill.Type != "none")
            {
                var color = xdObject.GetFillColor();
                parameter.Fill = color;

                if (!string.IsNullOrWhiteSpace(shape.Winding))
                {
                    parameter.FillRule = shape.Winding;
                }
            }

            float?shapeR = null;

            if (shape.R != null)
            {
                if (shape.R is Newtonsoft.Json.Linq.JValue jValue)
                {
                    shapeR = (float)jValue;
                }
                else if (shape.R is Newtonsoft.Json.Linq.JArray jArray)
                {
                    shapeR = (float)jArray[0];
                }
                else if (shape.R is long l)
                {
                    shapeR = l;
                }
                else if (shape.R is double d)
                {
                    shapeR = (float)d;
                }
                else
                {
                    throw new NotSupportedException($"Unknown shape.r type {shape.R.GetType()}");
                }
            }

            if (shapeR != null && shape.Type != CircleElement.Name)
            {
                parameter.Rx = shapeR;
                if (parameter.Rx > shape.Width / 2f)
                {
                    parameter.Rx = shape.Width / 2f;
                }
                if (parameter.Rx > shape.Height / 2f)
                {
                    parameter.Rx = shape.Height / 2f;
                }
            }

            var    stroke      = xdObject.Style?.Stroke;
            string strokeAlign = null;

            if (stroke != null && stroke.Type != "none")
            {
                parameter.EnableStroke     = true;
                parameter.Stroke           = stroke.Color.Value;
                parameter.StrokeWidth      = stroke.Width;
                parameter.StrokeMiterLimit = stroke.MiterLimit;

                if (!string.IsNullOrWhiteSpace(stroke.Join))
                {
                    parameter.StrokeLinejoin = stroke.Join;
                }

                if (!string.IsNullOrWhiteSpace(stroke.Cap))
                {
                    parameter.StrokeLinecap = stroke.Cap;
                }

                if (stroke.Dash != null)
                {
                    parameter.StrokeDasharray = stroke.Dash;
                }

                if (stroke.Align == null)
                {
                    strokeAlign = null;
                }
                else if (stroke.Align == "outside")
                {
                    strokeAlign = "outside";
                }
                else if (stroke.Align == "inside")
                {
                    strokeAlign = "inside";
                }
                else
                {
                    throw new NotSupportedException($"{xdObject} has unknown align type {stroke.Align}");
                }
            }

            if (shape.Type == PathElement.Name)
            {
                return new PathElement {
                           Parameter = parameter, D = shape.Path
                }
            }
            ;

            if (shape.Type == CompoundElement.Name)
            {
                return new CompoundElement {
                           Parameter = parameter, D = shape.Path
                }
            }
            ;

            if (shape.Type == LineElement.Name)
            {
                return new LineElement {
                           Parameter = parameter, X1 = shape.X1, Y1 = shape.Y1, X2 = shape.X2, Y2 = shape.Y2
                }
            }
            ;

            if (shape.Type == RectElement.Name)
            {
                if (strokeAlign == "outside")
                {
                    return(RectElement.Outside(shape, parameter));
                }
                if (strokeAlign == "inside")
                {
                    return(RectElement.Inside(shape, parameter));
                }
                return(new RectElement {
                    Parameter = parameter, Width = shape.Width, Height = shape.Height
                });
            }

            if (shape.Type == CircleElement.Name)
            {
                if (strokeAlign == "outside")
                {
                    return(CircleElement.Outside(shape, parameter, shapeR));
                }
                if (strokeAlign == "inside")
                {
                    return(CircleElement.Inside(shape, parameter, shapeR));
                }
                return(new CircleElement {
                    Parameter = parameter, Cx = shape.Cx, Cy = shape.Cy, R = shapeR.Value
                });
            }

            if (shape.Type == EllipseElement.Name)
            {
                if (strokeAlign == "outside")
                {
                    return(EllipseElement.Outside(shape, parameter));
                }
                if (strokeAlign == "inside")
                {
                    return(EllipseElement.Inside(shape, parameter));
                }
                return(new EllipseElement {
                    Parameter = parameter, Cx = shape.Cx, Cy = shape.Cy, Rx = shape.Rx, Ry = shape.Ry
                });
            }

            throw new NotSupportedException($"Unknown type {shape.Type}");
        }