Exemple #1
0
        /// <summary>
        /// Constructor
        /// </summary>
        /// <param name="spineAnimationItem"></param>
        /// <param name="skeletonData"></param>
        public SpineAnimationWindow(WzSpineAnimationItem spineAnimationItem)
        {
            IsMouseVisible = true;

            //Window.IsBorderless = true;
            //Window.Position = new Point(0, 0);
            Window.Title    = "Spine";
            IsFixedTimeStep = false;             // dont cap fps

            graphicsDeviceMgr = new GraphicsDeviceManager(this)
            {
                SynchronizeWithVerticalRetrace = false,                 // dont cap fps
                HardwareModeSwitch             = true,
                GraphicsProfile             = GraphicsProfile.HiDef,
                IsFullScreen                = false,
                PreferMultiSampling         = true,
                SupportedOrientations       = DisplayOrientation.Default,
                PreferredBackBufferWidth    = 1366,
                PreferredBackBufferHeight   = 768,
                PreferredBackBufferFormat   = SurfaceFormat.Color,
                PreferredDepthStencilFormat = DepthFormat.Depth24Stencil8,
            };
            graphicsDeviceMgr.ApplyChanges();

            this.wzSpineObject = new WzSpineObject(spineAnimationItem);
        }
        /// <summary>
        /// Constructor
        /// </summary>
        /// <param name="spineAnimationItem"></param>
        /// <param name="title_path">The path of the spine animation to set as title</param>
        public SpineAnimationWindow(WzSpineAnimationItem spineAnimationItem, string title_path)
        {
            IsMouseVisible = true;

            //Window.IsBorderless = true;
            //Window.Position = new Point(0, 0);
            Window.Title          = title_path;
            IsFixedTimeStep       = false;       // dont cap fps
            Content.RootDirectory = "Content";

            // Res
            this.UserScreenScaleFactor = (float)ScreenDPIUtil.GetScreenScaleFactor();
            this.matrixScale           = Matrix.CreateScale(UserScreenScaleFactor);

            // Graphics
            graphicsDeviceMgr = new GraphicsDeviceManager(this)
            {
                SynchronizeWithVerticalRetrace = true,                 // max fps with the monitor
                HardwareModeSwitch             = true,
                GraphicsProfile             = GraphicsProfile.HiDef,
                IsFullScreen                = false,
                PreferMultiSampling         = true,
                SupportedOrientations       = DisplayOrientation.Default,
                PreferredBackBufferWidth    = (int)(1366 * UserScreenScaleFactor),               // XNA isnt DPI aware.
                PreferredBackBufferHeight   = (int)(768 * UserScreenScaleFactor),
                PreferredBackBufferFormat   = SurfaceFormat.Color /*RGBA8888*/ | SurfaceFormat.Bgr32 | SurfaceFormat.Dxt1 | SurfaceFormat.Dxt5,
                PreferredDepthStencilFormat = DepthFormat.Depth24Stencil8,
            };
            graphicsDeviceMgr.ApplyChanges();

            this.wzSpineObject = new WzSpineObject(spineAnimationItem);
        }
Exemple #3
0
        public DXSpineObject(WzSpineObject spineObject, int x, int y, System.Drawing.PointF _origin, int delay = 0)
        {
            this.spineObject = spineObject;
            this._x          = x;
            this._y          = y;
            this._origin     = _origin;
            this.delay       = delay;

            spineObject.bounds.Update(spineObject.skeleton, true);
        }
Exemple #4
0
        /// <summary>
        /// Load frames from WzSubProperty or WzCanvasProperty
        /// </summary>
        /// <param name="texturePool"></param>
        /// <param name="source"></param>
        /// <param name="x"></param>
        /// <param name="y"></param>
        /// <param name="device"></param>
        /// <param name="usedProps"></param>
        /// <param name="spineAni">Spine animation path</param>
        /// <returns></returns>
        private static List <IDXObject> LoadFrames(TexturePool texturePool, WzImageProperty source, int x, int y, GraphicsDevice device, ref List <WzObject> usedProps, string spineAni = null)
        {
            List <IDXObject> frames = new List <IDXObject>();

            source = WzInfoTools.GetRealProperty(source);

            if (source is WzSubProperty property1 && property1.WzProperties.Count == 1)
            {
                source = property1.WzProperties[0];
            }

            if (source is WzCanvasProperty property) //one-frame
            {
                bool bLoadedSpine = LoadSpineMapObjectItem(source, source, device, spineAni);
                if (!bLoadedSpine)
                {
                    string    canvasBitmapPath = property.FullPath;
                    Texture2D textureFromCache = texturePool.GetTexture(canvasBitmapPath);
                    if (textureFromCache != null)
                    {
                        source.MSTag = textureFromCache;
                    }
                    else
                    {
                        source.MSTag = property.GetLinkedWzCanvasBitmap().ToTexture2D(device);

                        // add to cache
                        texturePool.AddTextureToPool(canvasBitmapPath, (Texture2D)source.MSTag);
                    }
                }
                usedProps.Add(source);

                if (source.MSTagSpine != null)
                {
                    WzSpineObject         spineObject = (WzSpineObject)source.MSTagSpine;
                    System.Drawing.PointF origin      = property.GetCanvasOriginPosition();

                    frames.Add(new DXSpineObject(spineObject, x, y, origin));
                }
                else if (source.MSTag != null)
                {
                    Texture2D             texture = (Texture2D)source.MSTag;
                    System.Drawing.PointF origin  = property.GetCanvasOriginPosition();

                    frames.Add(new DXObject(x - (int)origin.X, y - (int)origin.Y, texture));
                }
                else // fallback
                {
                    Texture2D             texture = Properties.Resources.placeholder.ToTexture2D(device);
                    System.Drawing.PointF origin  = property.GetCanvasOriginPosition();

                    frames.Add(new DXObject(x - (int)origin.X, y - (int)origin.Y, texture));
                }
            }
            else if (source is WzSubProperty) // animated
            {
                WzImageProperty _frameProp;
                int             i = 0;

                while ((_frameProp = WzInfoTools.GetRealProperty(source[(i++).ToString()])) != null)
                {
                    if (_frameProp is WzSubProperty) // issue with 867119250
                    {
                        frames.AddRange(LoadFrames(texturePool, _frameProp, x, y, device, ref usedProps, null));
                    }
                    else
                    {
                        WzCanvasProperty frameProp;

                        if (_frameProp is WzUOLProperty) // some could be UOL. Ex: 321100000 Mirror world: [Mirror World] Leafre
                        {
                            WzObject linkVal = ((WzUOLProperty)_frameProp).LinkValue;
                            if (linkVal is WzCanvasProperty linkCanvas)
                            {
                                frameProp = linkCanvas;
                            }
                            else
                            {
                                continue;
                            }
                        }
                        else
                        {
                            frameProp = (WzCanvasProperty)_frameProp;
                        }

                        int delay = (int)InfoTool.GetOptionalInt(frameProp["delay"], 100);

                        bool bLoadedSpine = LoadSpineMapObjectItem((WzImageProperty)frameProp.Parent, frameProp, device, spineAni);
                        if (!bLoadedSpine)
                        {
                            if (frameProp.MSTag == null)
                            {
                                string    canvasBitmapPath = frameProp.FullPath;
                                Texture2D textureFromCache = texturePool.GetTexture(canvasBitmapPath);
                                if (textureFromCache != null)
                                {
                                    frameProp.MSTag = textureFromCache;
                                }
                                else
                                {
                                    frameProp.MSTag = frameProp.GetLinkedWzCanvasBitmap().ToTexture2D(device);

                                    // add to cache
                                    texturePool.AddTextureToPool(canvasBitmapPath, (Texture2D)frameProp.MSTag);
                                }
                            }
                        }
                        usedProps.Add(frameProp);

                        if (frameProp.MSTagSpine != null)
                        {
                            WzSpineObject         spineObject = (WzSpineObject)frameProp.MSTagSpine;
                            System.Drawing.PointF origin      = frameProp.GetCanvasOriginPosition();

                            frames.Add(new DXSpineObject(spineObject, x, y, origin, delay));
                        }
                        else if (frameProp.MSTag != null)
                        {
                            Texture2D             texture = (Texture2D)frameProp.MSTag;
                            System.Drawing.PointF origin  = frameProp.GetCanvasOriginPosition();

                            frames.Add(new DXObject(x - (int)origin.X, y - (int)origin.Y, texture, delay));
                        }
                        else
                        {
                            Texture2D             texture = Properties.Resources.placeholder.ToTexture2D(device);
                            System.Drawing.PointF origin  = frameProp.GetCanvasOriginPosition();

                            frames.Add(new DXObject(x - (int)origin.X, y - (int)origin.Y, texture, delay));
                        }
                    }
                }
            }
            return(frames);
        }
Exemple #5
0
        /// <summary>
        /// Load spine object from WzImageProperty (bg, map item)
        /// </summary>
        /// <param name="source"></param>
        /// <param name="prop"></param>
        /// <param name="device"></param>
        /// <returns></returns>
        private static bool LoadSpineMapObjectItem(WzImageProperty source, WzImageProperty prop, GraphicsDevice device, string spineAniPath = null)
        {
            WzImageProperty spineAtlas = null;

            bool bIsObjectLayer = source.Parent.Name == "spine";

            if (bIsObjectLayer) // load spine if the source is already the directory we need
            {
                string spineAtlasPath = ((WzStringProperty)source["spine"])?.GetString();
                if (spineAtlasPath != null)
                {
                    spineAtlas = source[spineAtlasPath + ".atlas"];
                }
            }
            else if (spineAniPath != null)
            {
                WzImageProperty spineSource = (WzImageProperty)source.Parent?.Parent["spine"]?[source.Name];

                string spineAtlasPath = ((WzStringProperty)spineSource["spine"])?.GetString();
                if (spineAtlasPath != null)
                {
                    spineAtlas = spineSource[spineAtlasPath + ".atlas"];
                }
            }
            else   // simply check if 'spine' WzStringProperty exist, fix for Adele town
            {
                string spineAtlasPath = ((WzStringProperty)source["spine"])?.GetString();
                if (spineAtlasPath != null)
                {
                    spineAtlas     = source[spineAtlasPath + ".atlas"];
                    bIsObjectLayer = true;
                }
            }

            if (spineAtlas != null)
            {
                if (spineAtlas is WzStringProperty stringObj)
                {
                    if (!stringObj.IsSpineAtlasResources)
                    {
                        return(false);
                    }

                    WzSpineObject spineObject = new WzSpineObject(new WzSpineAnimationItem(stringObj));

                    spineObject.spineAnimationItem.LoadResources(device); //  load spine resources (this must happen after window is loaded)
                    spineObject.skeleton = new Skeleton(spineObject.spineAnimationItem.SkeletonData);
                    //spineObject.skeleton.R =153;
                    //spineObject.skeleton.G = 255;
                    //spineObject.skeleton.B = 0;
                    //spineObject.skeleton.A = 1f;

                    // Skin
                    foreach (Skin skin in spineObject.spineAnimationItem.SkeletonData.Skins)
                    {
                        spineObject.skeleton.SetSkin(skin); // just set the first skin
                        break;
                    }

                    // Define mixing between animations.
                    spineObject.stateData = new AnimationStateData(spineObject.skeleton.Data);
                    spineObject.state     = new AnimationState(spineObject.stateData);
                    if (!bIsObjectLayer)
                    {
                        spineObject.state.TimeScale = 0.1f;
                    }

                    if (spineAniPath != null)
                    {
                        spineObject.state.SetAnimation(0, spineAniPath, true);
                    }
                    else
                    {
                        int i = 0;
                        foreach (Animation animation in spineObject.spineAnimationItem.SkeletonData.Animations)
                        {
                            spineObject.state.SetAnimation(i++, animation.Name, true);
                        }
                    }
                    prop.MSTagSpine = spineObject;
                    return(true);
                }
            }
            return(false);
        }
Exemple #6
0
        /// <summary>
        /// Load game assets
        /// </summary>
        protected override void LoadContent()
        {
            WzDirectory MapWzFile   = Program.WzManager["map"]; // Map.wz
            WzDirectory UIWZFile    = Program.WzManager["ui"];
            WzDirectory SoundWZFile = Program.WzManager["sound"];

            this.bBigBangUpdate  = UIWZFile["UIWindow2.img"]?["BigBang!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!"] != null; // different rendering for pre and post-bb, to support multiple vers
            this.bBigBang2Update = UIWZFile["UIWindow2.img"]?["BigBang2!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!"] != null;

            // BGM
            if (Program.InfoManager.BGMs.ContainsKey(mapBoard.MapInfo.bgm))
            {
                audio = new WzMp3Streamer(Program.InfoManager.BGMs[mapBoard.MapInfo.bgm], true);
                if (audio != null)
                {
                    audio.Volume = 0.3f;
                    audio.Play();
                }
            }
            if (mapBoard.VRRectangle == null)
            {
                vr_fieldBoundary = new Rectangle(0, 0, mapBoard.MapSize.X, mapBoard.MapSize.Y);
            }
            else
            {
                vr_fieldBoundary = new Rectangle(mapBoard.VRRectangle.X + mapBoard.CenterPoint.X, mapBoard.VRRectangle.Y + mapBoard.CenterPoint.Y, mapBoard.VRRectangle.Width, mapBoard.VRRectangle.Height);
            }
            //SetStyle(ControlStyles.AllPaintingInWmPaint | ControlStyles.Opaque, true);

            // test benchmark
#if DEBUG
            var watch = new System.Diagnostics.Stopwatch();
            watch.Start();
#endif

            /////// Background and objects
            List <WzObject> usedProps = new List <WzObject>();

            // Objects
            Task t_tiles = Task.Run(() =>
            {
                foreach (LayeredItem tileObj in mapBoard.BoardItems.TileObjs)
                {
                    WzImageProperty tileParent = (WzImageProperty)tileObj.BaseInfo.ParentObject;

                    mapObjects[tileObj.LayerNumber].Add(
                        MapSimulatorLoader.CreateMapItemFromProperty(texturePool, tileParent, tileObj.X, tileObj.Y, mapBoard.CenterPoint, _DxDeviceManager.GraphicsDevice, ref usedProps, tileObj is IFlippable ? ((IFlippable)tileObj).Flip : false));
                }
            });

            // Background
            Task t_Background = Task.Run(() =>
            {
                foreach (BackgroundInstance background in mapBoard.BoardItems.BackBackgrounds)
                {
                    WzImageProperty bgParent = (WzImageProperty)background.BaseInfo.ParentObject;

                    backgrounds_back.Add(
                        MapSimulatorLoader.CreateBackgroundFromProperty(texturePool, bgParent, background, _DxDeviceManager.GraphicsDevice, ref usedProps, background.Flip));
                }
                foreach (BackgroundInstance background in mapBoard.BoardItems.FrontBackgrounds)
                {
                    WzImageProperty bgParent = (WzImageProperty)background.BaseInfo.ParentObject;

                    backgrounds_front.Add(
                        MapSimulatorLoader.CreateBackgroundFromProperty(texturePool, bgParent, background, _DxDeviceManager.GraphicsDevice, ref usedProps, background.Flip));
                }
            });

            // Reactors
            Task t_reactor = Task.Run(() =>
            {
                foreach (ReactorInstance reactor in mapBoard.BoardItems.Reactors)
                {
                    //WzImage imageProperty = (WzImage)NPCWZFile[reactorInfo.ID + ".img"];

                    ReactorItem reactorItem = MapSimulatorLoader.CreateReactorFromProperty(texturePool, reactor, _DxDeviceManager.GraphicsDevice, ref usedProps);
                    mapObjects_Reactors.Add(reactorItem);
                }
            });

            // NPCs
            Task t_npc = Task.Run(() =>
            {
                foreach (NpcInstance npc in mapBoard.BoardItems.NPCs)
                {
                    //WzImage imageProperty = (WzImage) NPCWZFile[npcInfo.ID + ".img"];
                    if (npc.Hide)
                    {
                        continue;
                    }

                    NpcItem npcItem = MapSimulatorLoader.CreateNpcFromProperty(texturePool, npc, _DxDeviceManager.GraphicsDevice, ref usedProps);
                    mapObjects_NPCs.Add(npcItem);
                }
            });

            // Mobs
            Task t_mobs = Task.Run(() =>
            {
                foreach (MobInstance mob in mapBoard.BoardItems.Mobs)
                {
                    //WzImage imageProperty = Program.WzManager.FindMobImage(mobInfo.ID); // Mob.wz Mob2.img Mob001.wz
                    if (mob.Hide)
                    {
                        continue;
                    }
                    MobItem npcItem = MapSimulatorLoader.CreateMobFromProperty(texturePool, mob, _DxDeviceManager.GraphicsDevice, ref usedProps);
                    mapObjects_Mobs.Add(npcItem);
                }
            });

            // Portals
            Task t_portal = Task.Run(() =>
            {
                WzSubProperty portalParent = (WzSubProperty)MapWzFile["MapHelper.img"]["portal"];

                WzSubProperty gameParent = (WzSubProperty)portalParent["game"];
                //WzSubProperty editorParent = (WzSubProperty) portalParent["editor"];

                foreach (PortalInstance portal in mapBoard.BoardItems.Portals)
                {
                    PortalItem portalItem = MapSimulatorLoader.CreatePortalFromProperty(texturePool, gameParent, portal, _DxDeviceManager.GraphicsDevice, ref usedProps);
                    if (portalItem != null)
                    {
                        mapObjects_Portal.Add(portalItem);
                    }
                }
            });

            // Tooltips
            Task t_tooltips = Task.Run(() =>
            {
                WzSubProperty farmFrameParent = (WzSubProperty)UIWZFile["UIToolTip.img"]?["Item"]?["FarmFrame"];
                foreach (ToolTipInstance tooltip in mapBoard.BoardItems.ToolTips)
                {
                    TooltipItem item = MapSimulatorLoader.CreateTooltipFromProperty(texturePool, UserScreenScaleFactor, farmFrameParent, tooltip, _DxDeviceManager.GraphicsDevice);

                    mapObjects_tooltips.Add(item);
                }
            });

            // Cursor
            Task t_cursor = Task.Run(() =>
            {
                WzImageProperty cursorImageProperty = (WzImageProperty)UIWZFile["Basic.img"]?["Cursor"];
                this.mouseCursor = MapSimulatorLoader.CreateMouseCursorFromProperty(texturePool, cursorImageProperty, 0, 0, _DxDeviceManager.GraphicsDevice, ref usedProps, false);
            });

            // Spine object
            Task t_spine = Task.Run(() =>
            {
                skeletonMeshRenderer = new SkeletonMeshRenderer(GraphicsDevice)
                {
                    PremultipliedAlpha = false,
                };
                skeletonMeshRenderer.Effect.World = this.matrixScale;
            });

            // Minimap
            Task t_minimap = Task.Run(() =>
            {
                if (!mapBoard.MapInfo.hideMinimap)
                {
                    miniMap = MapSimulatorLoader.CreateMinimapFromProperty(UIWZFile, mapBoard, GraphicsDevice, UserScreenScaleFactor, mapBoard.MapInfo.strMapName, mapBoard.MapInfo.strStreetName, SoundWZFile, bBigBangUpdate);
                }
            });

            while (!t_tiles.IsCompleted || !t_Background.IsCompleted || !t_reactor.IsCompleted || !t_npc.IsCompleted || !t_mobs.IsCompleted || !t_portal.IsCompleted ||
                   !t_tooltips.IsCompleted || !t_cursor.IsCompleted || !t_spine.IsCompleted || !t_minimap.IsCompleted)
            {
                Thread.Sleep(100);
            }

#if DEBUG
            // test benchmark
            watch.Stop();
            Debug.WriteLine($"Map WZ files loaded. Execution Time: {watch.ElapsedMilliseconds} ms");
#endif
            //
            spriteBatch = new SpriteBatch(GraphicsDevice);

            // default positioning for character
            SetCameraMoveX(true, true, 0);
            SetCameraMoveY(true, true, 0);

            ///////////// Border
            int leftRightVRDifference = (int)((vr_fieldBoundary.Right - vr_fieldBoundary.Left) * RenderObjectScaling);
            if (leftRightVRDifference < RenderWidth) // viewing range is smaller than the render width..
            {
                this.bDrawVRBorderLeftRight = true;  // flag

                this.texture_vrBoundaryRectLeft   = CreateVRBorder(VR_BORDER_WIDTHHEIGHT, vr_fieldBoundary.Height, _DxDeviceManager.GraphicsDevice);
                this.texture_vrBoundaryRectRight  = CreateVRBorder(VR_BORDER_WIDTHHEIGHT, vr_fieldBoundary.Height, _DxDeviceManager.GraphicsDevice);
                this.texture_vrBoundaryRectTop    = CreateVRBorder(vr_fieldBoundary.Width * 2, VR_BORDER_WIDTHHEIGHT, _DxDeviceManager.GraphicsDevice);
                this.texture_vrBoundaryRectBottom = CreateVRBorder(vr_fieldBoundary.Width * 2, VR_BORDER_WIDTHHEIGHT, _DxDeviceManager.GraphicsDevice);
            }

            /*
             * DXObject leftDXVRObject = new DXObject(
             *  vr_fieldBoundary.Left - VR_BORDER_WIDTHHEIGHT,
             *  vr_fieldBoundary.Top,
             *  texture_vrBoundaryRectLeft);
             * this.leftVRBorderDrawableItem = new BaseDXDrawableItem(leftDXVRObject, false);
             * //new BackgroundItem(int cx, int cy, int rx, int ry, BackgroundType.Regular, 255, true, leftDXVRObject, false, (int) RenderResolution.Res_All);
             *
             * // Right VR
             * DXObject rightDXVRObject = new DXObject(
             *  vr_fieldBoundary.Right,
             *  vr_fieldBoundary.Top,
             *  texture_vrBoundaryRectRight);
             * this.rightVRBorderDrawableItem = new BaseDXDrawableItem(rightDXVRObject, false);
             */
            ///////////// End Border

            // Debug items
            System.Drawing.Bitmap bitmap_debug = new System.Drawing.Bitmap(1, 1);
            bitmap_debug.SetPixel(0, 0, System.Drawing.Color.White);
            texture_debugBoundaryRect = bitmap_debug.ToTexture2D(_DxDeviceManager.GraphicsDevice);

            // cleanup
            // clear used items
            foreach (WzObject obj in usedProps)
            {
                // Spine events
                WzSpineObject spineObj = (WzSpineObject)obj.MSTagSpine;
                if (spineObj != null)
                {
                    spineObj.state.Start    += Start;
                    spineObj.state.End      += End;
                    spineObj.state.Complete += Complete;
                    spineObj.state.Event    += Event;
                }

                obj.MSTag      = null;
                obj.MSTagSpine = null; // cleanup
            }
            usedProps.Clear();
        }
        /// <summary>
        /// Load frames from WzSubProperty or WzCanvasProperty
        /// </summary>
        /// <param name="texturePool"></param>
        /// <param name="source"></param>
        /// <param name="x"></param>
        /// <param name="y"></param>
        /// <param name="device"></param>
        /// <param name="usedProps"></param>
        /// <param name="spineAni">Spine animation path</param>
        /// <returns></returns>
        private static List <IDXObject> LoadFrames(TexturePool texturePool, WzImageProperty source, int x, int y, GraphicsDevice device, ref List <WzObject> usedProps, string spineAni = null)
        {
            List <IDXObject> frames = new List <IDXObject>();

            source = WzInfoTools.GetRealProperty(source);

            if (source is WzSubProperty property1 && property1.WzProperties.Count == 1)
            {
                source = property1.WzProperties[0];
            }

            if (source is WzCanvasProperty property) //one-frame
            {
                bool bLoadedSpine = LoadSpineMapObjectItem(source, source, device, spineAni);
                if (!bLoadedSpine)
                {
                    string    canvasBitmapPath = property.FullPath;
                    Texture2D textureFromCache = texturePool.GetTexture(canvasBitmapPath);
                    if (textureFromCache != null)
                    {
                        source.MSTag = textureFromCache;
                    }
                    else
                    {
                        source.MSTag = BoardItem.TextureFromBitmap(device, property.GetLinkedWzCanvasBitmap());

                        // add to cache
                        texturePool.AddTextureToPool(canvasBitmapPath, (Texture2D)source.MSTag);
                    }
                }
                usedProps.Add(source);

                if (source.MSTagSpine != null)
                {
                    WzSpineObject         spineObject = (WzSpineObject)source.MSTagSpine;
                    System.Drawing.PointF origin      = property.GetCanvasOriginPosition();

                    frames.Add(new DXSpineObject(spineObject, x, y, origin));
                }
                else if (source.MSTag != null)
                {
                    Texture2D             texture = (Texture2D)source.MSTag;
                    System.Drawing.PointF origin  = property.GetCanvasOriginPosition();

                    frames.Add(new DXObject(x - (int)origin.X, y - (int)origin.Y, texture));
                }
                else // fallback
                {
                    Texture2D             texture = BoardItem.TextureFromBitmap(device, Properties.Resources.placeholder);
                    System.Drawing.PointF origin  = property.GetCanvasOriginPosition();

                    frames.Add(new DXObject(x - (int)origin.X, y - (int)origin.Y, texture));
                }
            }
            else if (source is WzSubProperty) // animated
            {
                WzCanvasProperty frameProp;
                int i = 0;

                while ((frameProp = (WzCanvasProperty)WzInfoTools.GetRealProperty(source[(i++).ToString()])) != null)
                {
                    int delay = (int)InfoTool.GetOptionalInt(frameProp["delay"], 100);

                    bool bLoadedSpine = LoadSpineMapObjectItem((WzImageProperty)frameProp.Parent, frameProp, device, spineAni);
                    if (!bLoadedSpine)
                    {
                        if (frameProp.MSTag == null)
                        {
                            string    canvasBitmapPath = frameProp.FullPath;
                            Texture2D textureFromCache = texturePool.GetTexture(canvasBitmapPath);
                            if (textureFromCache != null)
                            {
                                frameProp.MSTag = textureFromCache;
                            }
                            else
                            {
                                frameProp.MSTag = BoardItem.TextureFromBitmap(device, frameProp.GetLinkedWzCanvasBitmap());

                                // add to cache
                                texturePool.AddTextureToPool(canvasBitmapPath, (Texture2D)frameProp.MSTag);
                            }
                        }
                    }
                    usedProps.Add(frameProp);

                    if (frameProp.MSTagSpine != null)
                    {
                        WzSpineObject         spineObject = (WzSpineObject)frameProp.MSTagSpine;
                        System.Drawing.PointF origin      = frameProp.GetCanvasOriginPosition();

                        frames.Add(new DXSpineObject(spineObject, x, y, origin, delay));
                    }
                    else if (frameProp.MSTag != null)
                    {
                        Texture2D             texture = (Texture2D)frameProp.MSTag;
                        System.Drawing.PointF origin  = frameProp.GetCanvasOriginPosition();

                        frames.Add(new DXObject(x - (int)origin.X, y - (int)origin.Y, texture, delay));
                    }
                    else
                    {
                        Texture2D             texture = BoardItem.TextureFromBitmap(device, Properties.Resources.placeholder);
                        System.Drawing.PointF origin  = frameProp.GetCanvasOriginPosition();

                        frames.Add(new DXObject(x - (int)origin.X, y - (int)origin.Y, texture, delay));
                    }
                }
            }
            return(frames);
        }
        /// <summary>
        /// Map item
        /// </summary>
        /// <param name="source"></param>
        /// <param name="x"></param>
        /// <param name="y"></param>
        /// <param name="mapCenterX"></param>
        /// <param name="mapCenterY"></param>
        /// <param name="device"></param>
        /// <param name="usedProps"></param>
        /// <param name="flip"></param>
        /// <returns></returns>
        public static MapItem CreateMapItemFromProperty(WzImageProperty source, int x, int y, Point mapCenter, GraphicsDevice device, ref List <WzObject> usedProps, bool flip)
        {
            source = WzInfoTools.GetRealProperty(source);

            if (source is WzSubProperty && ((WzSubProperty)source).WzProperties.Count == 1)
            {
                source = ((WzSubProperty)source).WzProperties[0];
            }

            if (source is WzCanvasProperty) //one-frame
            {
                bool bLoadedSpine = LoadSpineMapObjectItem(source, source, device, null);
                if (!bLoadedSpine)
                {
                    if (source.MSTag == null)
                    {
                        source.MSTag = BoardItem.TextureFromBitmap(device, ((WzCanvasProperty)source).GetLinkedWzCanvasBitmap());
                    }
                }
                usedProps.Add(source);

                if (source.MSTagSpine != null)
                {
                    WzSpineObject         spineObject = (WzSpineObject)source.MSTagSpine;
                    System.Drawing.PointF origin      = ((WzCanvasProperty)source).GetCanvasOriginPosition();

                    return(new MapItem(new DXSpineObject(spineObject, x + mapCenter.X, y + mapCenter.Y, origin), flip));
                }
                else if (source.MSTag != null)
                {
                    Texture2D             texture = (Texture2D)source.MSTag;
                    System.Drawing.PointF origin  = ((WzCanvasProperty)source).GetCanvasOriginPosition();

                    return(new MapItem(new DXObject(x - (int)origin.X + mapCenter.X, y - (int)origin.Y + mapCenter.Y, texture), flip));
                }
                else // fallback
                {
                    Texture2D             texture = BoardItem.TextureFromBitmap(device, Properties.Resources.placeholder);
                    System.Drawing.PointF origin  = ((WzCanvasProperty)source).GetCanvasOriginPosition();

                    return(new MapItem(new DXObject(x - (int)origin.X + mapCenter.X, y - (int)origin.Y + mapCenter.Y, texture), flip));
                }
            }
            else if (source is WzSubProperty) // animated
            {
                WzCanvasProperty frameProp;
                int i = 0;
                List <IDXObject> frames = new List <IDXObject>();
                while ((frameProp = (WzCanvasProperty)WzInfoTools.GetRealProperty(source[(i++).ToString()])) != null)
                {
                    int delay = (int)InfoTool.GetOptionalInt(frameProp["delay"], 100);

                    bool bLoadedSpine = LoadSpineMapObjectItem((WzImageProperty)frameProp.Parent, frameProp, device, null);
                    if (!bLoadedSpine)
                    {
                        if (frameProp.MSTag == null)
                        {
                            frameProp.MSTag = BoardItem.TextureFromBitmap(device, frameProp.GetLinkedWzCanvasBitmap());
                        }
                    }
                    usedProps.Add(frameProp);

                    if (frameProp.MSTagSpine != null)
                    {
                        WzSpineObject         spineObject = (WzSpineObject)frameProp.MSTagSpine;
                        System.Drawing.PointF origin      = frameProp.GetCanvasOriginPosition();

                        frames.Add(new DXSpineObject(spineObject, x + mapCenter.X, y + mapCenter.Y, origin, delay));
                    }
                    else if (frameProp.MSTag != null)
                    {
                        Texture2D             texture = (Texture2D)frameProp.MSTag;
                        System.Drawing.PointF origin  = frameProp.GetCanvasOriginPosition();

                        frames.Add(new DXObject(x - (int)origin.X + mapCenter.X, y - (int)origin.Y + mapCenter.Y, texture, delay));
                    }
                    else
                    {
                        Texture2D             texture = BoardItem.TextureFromBitmap(device, Properties.Resources.placeholder);
                        System.Drawing.PointF origin  = frameProp.GetCanvasOriginPosition();

                        frames.Add(new DXObject(x - (int)origin.X + mapCenter.X, y - (int)origin.Y + mapCenter.Y, texture, delay));
                    }
                }
                return(new MapItem(frames, flip));
            }
            else
            {
                throw new Exception("unsupported property type in map simulator");
            }
        }
        /// <summary>
        /// Background
        /// </summary>
        /// <param name="source"></param>
        /// <param name="bgInstance"></param>
        /// <param name="mapCenterX"></param>
        /// <param name="mapCenterY"></param>
        /// <param name="device"></param>
        /// <param name="usedProps"></param>
        /// <param name="flip"></param>
        /// <returns></returns>
        public static BackgroundItem CreateBackgroundFromProperty(WzImageProperty source, BackgroundInstance bgInstance, int mapCenterX, int mapCenterY, GraphicsDevice device, ref List <WzObject> usedProps, bool flip)
        {
            source = WzInfoTools.GetRealProperty(source);
            if (source is WzSubProperty && ((WzSubProperty)source).WzProperties.Count == 1)
            {
                source = ((WzSubProperty)source).WzProperties[0];
            }

            if (source is WzCanvasProperty) //one-frame
            {
                bool bLoadedSpine = LoadSpineMapObjectItem(source, source, device, bgInstance.SpineAni);
                if (!bLoadedSpine)
                {
                    if (source.MSTag == null)
                    {
                        source.MSTag = BoardItem.TextureFromBitmap(device, ((WzCanvasProperty)source).GetLinkedWzCanvasBitmap());
                    }
                }
                usedProps.Add(source);

                if (source.MSTagSpine != null)
                {
                    WzSpineObject         spineObject = (WzSpineObject)source.MSTagSpine;
                    System.Drawing.PointF origin      = ((WzCanvasProperty)source).GetCanvasOriginPosition();
                    DXSpineObject         dxobj       = new DXSpineObject(spineObject, bgInstance.BaseX - (int)origin.X /* - mapCenterX*/, bgInstance.BaseY - (int)origin.Y /* - mapCenterY*/, origin);

                    return(new BackgroundItem(bgInstance.cx, bgInstance.cy, bgInstance.rx, bgInstance.ry, bgInstance.type, bgInstance.a, bgInstance.front, dxobj, flip, bgInstance.screenMode));
                }
                else if (source.MSTag != null)
                {
                    Texture2D             texture = (Texture2D)source.MSTag;
                    System.Drawing.PointF origin  = ((WzCanvasProperty)source).GetCanvasOriginPosition();
                    DXObject dxobj = new DXObject(bgInstance.BaseX - (int)origin.X /* - mapCenterX*/, bgInstance.BaseY - (int)origin.Y /* - mapCenterY*/, texture);

                    return(new BackgroundItem(bgInstance.cx, bgInstance.cy, bgInstance.rx, bgInstance.ry, bgInstance.type, bgInstance.a, bgInstance.front, dxobj, flip, bgInstance.screenMode));
                }
                else  // default fallback if all things fail
                {
                    Texture2D             texture = BoardItem.TextureFromBitmap(device, Properties.Resources.placeholder);
                    System.Drawing.PointF origin  = ((WzCanvasProperty)source).GetCanvasOriginPosition();
                    DXObject dxobj = new DXObject(bgInstance.BaseX - (int)origin.X /* - mapCenterX*/, bgInstance.BaseY - (int)origin.Y /* - mapCenterY*/, texture);

                    return(new BackgroundItem(bgInstance.cx, bgInstance.cy, bgInstance.rx, bgInstance.ry, bgInstance.type, bgInstance.a, bgInstance.front, dxobj, flip, bgInstance.screenMode));
                }
            }
            else if (source is WzSubProperty) // animated
            {
                WzCanvasProperty frameProp;
                int i = 0;
                List <IDXObject> frames = new List <IDXObject>();
                while ((frameProp = (WzCanvasProperty)WzInfoTools.GetRealProperty(source[(i++).ToString()])) != null)
                {
                    int delay = (int)InfoTool.GetOptionalInt(frameProp["delay"], 100);

                    bool bLoadedSpine = LoadSpineMapObjectItem((WzImageProperty)frameProp.Parent, frameProp, device, bgInstance.SpineAni);
                    if (!bLoadedSpine)
                    {
                        if (frameProp.MSTag == null)
                        {
                            frameProp.MSTag = BoardItem.TextureFromBitmap(device, frameProp.GetLinkedWzCanvasBitmap());
                        }
                    }
                    usedProps.Add(source);

                    if (frameProp.MSTagSpine != null)
                    {
                        WzSpineObject         spineObject = (WzSpineObject)frameProp.MSTagSpine;
                        System.Drawing.PointF origin      = frameProp.GetCanvasOriginPosition();
                        DXSpineObject         dxobj       = new DXSpineObject(spineObject, bgInstance.BaseX - (int)origin.X /* - mapCenterX*/, bgInstance.BaseY - (int)origin.Y /* - mapCenterY*/, origin, delay);

                        frames.Add(dxobj);
                    }
                    else if (frameProp.MSTag != null)
                    {
                        Texture2D             texture = (Texture2D)frameProp.MSTag;
                        System.Drawing.PointF origin  = frameProp.GetCanvasOriginPosition();
                        DXObject dxObj = new DXObject(bgInstance.BaseX - (int)origin.X /* - mapCenterX*/, bgInstance.BaseY - (int)origin.Y /* - mapCenterY*/, texture, delay);

                        frames.Add(dxObj);
                    }
                    else // default fallback if all things fail
                    {
                        Texture2D             texture = BoardItem.TextureFromBitmap(device, Properties.Resources.placeholder);
                        System.Drawing.PointF origin  = frameProp.GetCanvasOriginPosition();
                        DXObject dxObj = new DXObject(bgInstance.BaseX - (int)origin.X /* - mapCenterX*/, bgInstance.BaseY - (int)origin.Y /* - mapCenterY*/, texture, delay);

                        frames.Add(dxObj);
                    }
                }
                return(new BackgroundItem(bgInstance.cx, bgInstance.cy, bgInstance.rx, bgInstance.ry, bgInstance.type, bgInstance.a, bgInstance.front, frames, flip, bgInstance.screenMode));
            }
            else
            {
                throw new Exception("Unsupported property type in map simulator");
            }
        }