/// <summary>
 /// Import the sprite animation
 /// </summary>
 public override void Import(ImportFile file)
 {
     using (var sourceFile = File.OpenRead(file.Filename))
         using (var targetWriter = new ResourceWriter(File.OpenWrite(file.TargetFilename), typeof(ImageAnimation)))
             Import(sourceFile, targetWriter);
 }
Example #2
0
        private void Import(ImportFile file, XmlDocument doc, ResourceWriter writer)
        {
            var map    = doc.GetElementsByTagName("map")[0];
            var width  = int.Parse(map.Attributes["width"].Value);
            var height = int.Parse(map.Attributes["height"].Value);

            writer.Write((ushort)width);
            writer.Write((ushort)height);
            writer.Write((ushort)int.Parse(map.Attributes["tilewidth"].Value));
            writer.Write((ushort)int.Parse(map.Attributes["tileheight"].Value));

            var layers   = map.SelectNodes("objectgroup | layer");
            var tilesets = map.SelectNodes("tileset");

            // Write tile sets
            var tileSetFirstId = new int[tilesets.Count];

            writer.Write((ushort)tileSetFirstId.Length);
            for (int i = 0; i < tileSetFirstId.Length; i++)
            {
                XmlNode tileSet = tilesets[i];
                var     source  = tileSet.Attributes["source"].Value;

                tileSetFirstId[i] = int.Parse(tileSet.Attributes["firstgid"].Value);

                var uri1 = new Uri(Path.Combine(Path.GetDirectoryName(file.TargetFilename), source));
                var uri2 = new Uri(file.TargetDirectory + "\\");
                var name = Path.ChangeExtension(uri2.MakeRelativeUri(uri1).ToString(), null);

                writer.Write(name);
            }

            // Write layers
            writer.Write((ushort)layers.Count);

            foreach (XmlNode layer in layers)
            {
                writer.Write(layer.Attributes["name"]?.Value ?? "");
                writer.Write((ushort)width);
                writer.Write((ushort)height);

                // Properties
                var objprops = layer.SelectNodes("properties/property");
                writer.Write((ushort)objprops.Count);

                foreach (XmlNode objprop in objprops)
                {
                    writer.Write(objprop.Attributes["name"].Value);
                    writer.Write(objprop.Attributes["value"].Value);
                }

                switch (layer.Name)
                {
                case "layer":
                {
                    // Write tiles
                    var data     = layer["data"];
                    var encoding = data.Attributes["encoding"].Value;
                    if (encoding != "csv")
                    {
                        throw new ImportException($"encoding '{encoding}' not supported");
                    }

                    var ids = data.InnerText.Split(',');
                    writer.Write((ushort)ids.Length);
                    for (int i = 0; i < ids.Length; i++)
                    {
                        var id = int.Parse(ids[i]);
                        if (id == 0)
                        {
                            writer.Write((ushort)0xFFFF);
                            continue;
                        }

                        int tileSetId;
                        for (tileSetId = 0; tileSetId < tileSetFirstId.Length - 1 && id >= tileSetFirstId[tileSetId + 1]; tileSetId++)
                        {
                            ;
                        }

                        writer.Write((ushort)tileSetId);
                        writer.Write((ushort)(id - tileSetFirstId[tileSetId]));
                    }

                    // Write objects
                    writer.Write((ushort)0);

                    break;
                }

                case "objectgroup":
                {
                    // No tiles
                    writer.Write((ushort)0);

                    var properties = layer.SelectNodes("properties/property");

                    // Write objects
                    var objects = layer.SelectNodes("object");
                    writer.Write((ushort)objects.Count);

                    foreach (XmlNode o in objects)
                    {
                        XmlNode obj      = o;
                        var     template = obj.Attributes["template"]?.Value;
                        if (template != null)
                        {
                            var templateDoc = new XmlDocument();
                            templateDoc.Load(Path.Combine(Path.GetDirectoryName(file.Filename), template));
                            obj = templateDoc.SelectSingleNode("/template/object");
                        }

                        writer.Write(o.Attributes["name"]?.Value ?? obj.Attributes["name"]?.Value ?? "");
                        writer.Write(o.Attributes["type"]?.Value ?? obj.Attributes["type"]?.Value ?? "");
                        writer.Write(new Vector2(float.Parse(o.Attributes["x"].Value), float.Parse(o.Attributes["y"].Value)));

                        // Point
                        if (obj.SelectSingleNode("point") != null)
                        {
                            writer.Write((byte)TileMap.ShapeType.Point);
                        }
                        // Polygon
                        else if (obj.SelectSingleNode("polygon") != null)
                        {
                            writer.Write((byte)TileMap.ShapeType.Polygon);

                            var points = obj.SelectSingleNode("polygon").Attributes["points"].Value.Split(new char[] { ' ' });
                            writer.Write((ushort)points.Length);
                            for (int i = 0; i < points.Length; i++)
                            {
                                writer.Write(Vector2.Parse(points[i]));
                            }
                        }
                        // Polyline
                        else if (obj.SelectSingleNode("polyline") != null)
                        {
                            writer.Write((byte)TileMap.ShapeType.PolyLine);

                            var points = obj.SelectSingleNode("polyline").Attributes["points"].Value.Split(new char[] { ' ' });
                            writer.Write((ushort)points.Length);
                            for (int i = 0; i < points.Length; i++)
                            {
                                writer.Write(Vector2.Parse(points[i]));
                            }
                        }
                        // Ellipse
                        else if (obj.SelectSingleNode("ellipse") != null)
                        {
                            writer.Write((byte)TileMap.ShapeType.Circle);
                            writer.Write(float.Parse(o.Attributes["width"]?.Value ?? obj.Attributes["width"]?.Value ?? "0"));
                            writer.Write(float.Parse(o.Attributes["height"]?.Value ?? obj.Attributes["height"]?.Value ?? "0"));
                        }
                        // Box
                        else
                        {
                            writer.Write((byte)TileMap.ShapeType.Box);
                            writer.Write(float.Parse(o.Attributes["width"]?.Value ?? obj.Attributes["width"]?.Value ?? "0"));
                            writer.Write(float.Parse(o.Attributes["height"]?.Value ?? obj.Attributes["height"]?.Value ?? "0"));
                        }

                        // Properties
                        var layerprops = obj.SelectNodes("properties/property");
                        writer.Write((ushort)layerprops.Count);

                        foreach (XmlNode layerProp in layerprops)
                        {
                            writer.Write(layerProp.Attributes["name"].Value);
                            writer.Write(layerProp.Attributes["value"].Value);
                        }
                    }

                    break;
                }
                }
            }
        }
Example #3
0
        private void Import(ImportFile file, XmlDocument doc, ResourceWriter writer)
        {
            var tileset    = doc.GetElementsByTagName("tileset")[0];
            var images     = doc.GetElementsByTagName("image");
            var tiles      = doc.GetElementsByTagName("tile");
            var columns    = int.Parse(tileset.Attributes["columns"].Value);
            var spacing    = int.Parse(tileset.Attributes["spacing"]?.Value ?? "0");
            var tilewidth  = int.Parse(tileset.Attributes["tilewidth"].Value);
            var tileheight = int.Parse(tileset.Attributes["tileheight"].Value);
            var tilecount  = int.Parse(tileset.Attributes["tilecount"].Value);

            if (images.Count == 0)
            {
                throw new ImportException("TileSet has no images");
            }
            if (images.Count > 1)
            {
                throw new ImportException("Multiple TileSet images not supported");
            }

            var image = images[0].Attributes["source"].Value;

            if (Path.ChangeExtension(image, null) != Path.GetFileName(file.Name))
            {
                throw new ImportException("TileSet image must be same name as the tile set");
            }

            image = Path.ChangeExtension(file.Filename, Path.GetExtension(image));

            writer.Write((ushort)tilewidth);
            writer.Write((ushort)tileheight);
            writer.Write((ushort)tilecount);
            writer.Write((ushort)tiles.Count);

            // Write the image
            using (var source = File.OpenRead(image))
                ImageImporter.Import(source, writer, Thickness.Empty, SixLabors.Primitives.Rectangle.Empty);

            // Embed the tile images into the tile set
            foreach (XmlNode tile in tiles)
            {
                var id = int.Parse(tile.Attributes["id"].Value);
                var x  = id % columns;
                var y  = id / columns;

                x = (x * tilewidth) + x * spacing;
                y = (y * tileheight) + y * spacing;

                writer.Write((ushort)id);
                writer.Write((ushort)x);
                writer.Write((ushort)y);

                WriteProperties(writer, tile["properties"]);

                var objectGroup = tile["objectgroup"];
                if (objectGroup != null)
                {
                    writer.Write((ushort)objectGroup.ChildNodes.Count);

                    foreach (XmlNode obj in objectGroup)
                    {
                        var objx = int.Parse(obj.Attributes["x"].Value);
                        var objy = int.Parse(obj.Attributes["y"].Value);

                        var polygon = obj["polygon"];
                        if (null != polygon)
                        {
                            var points = polygon.Attributes["points"].Value.Split(new char[] { ' ' });
                            writer.Write((ushort)points.Length);
                            for (int i = 0; i < points.Length; i++)
                            {
                                writer.Write(Vector2.Parse(points[i]) + new Vector2(objx, objy));
                            }
                        }
                        else
                        {
                            writer.Write((ushort)0);
                        }

                        WriteProperties(writer, obj["properties"]);
                    }
                }
                else
                {
                    writer.Write((ushort)0);
                }
            }
        }