MonoGame.Extended
MonoGame.Extended copied to clipboard
[Tiled] Objects render order
Hi i have this for map render:
var viewMatrix = ScreenManager.Instance.Camera.GetViewMatrix();
var projectionMatrix = Matrix.CreateOrthographicOffCenter(0, ScreenManager.Instance.GraphicsDevice.Viewport.Width, ScreenManager.Instance.GraphicsDevice.Viewport.Height, 0, 0f, -1f);
#region Under object layers
mapRenderer.Draw(mapTiles.GetLayer("Ground"), ref viewMatrix, ref projectionMatrix);
mapRenderer.Draw(mapTiles.GetLayer("Layer1"), ref viewMatrix, ref projectionMatrix);
mapRenderer.Draw(mapTiles.GetLayer("Layer2"), ref viewMatrix, ref projectionMatrix);
mapRenderer.Draw(mapTiles.GetLayer("Layer3"), ref viewMatrix, ref projectionMatrix);
#endregion
foreach (DynamicEntity entity in Entities.Values)
entity.Draw(spriteBatch);
#region Above objects layers
mapRenderer.Draw(mapTiles.GetLayer("TopLayer1"), ref viewMatrix, ref projectionMatrix);
mapRenderer.Draw(mapTiles.GetLayer("TopLayer2"), ref viewMatrix, ref projectionMatrix);
mapRenderer.Draw(mapTiles.GetLayer("TopLayer3"), ref viewMatrix, ref projectionMatrix);
#endregion
Camera follow player it works great but all dynamic entities are above TopLayers and above gui mouse. Can you please advise how to force spritebatch to keep the order?
The API around this stuff is quite complicated unfortunately. If I remember correctly you'll need to play with the depth value on the SpriteBatch
.
The plan is to improve and clean up the Tiled API in the 2.0
branch to make this kind of stuff easier.
If you could provide a project that reproduces the problem I'll look into it further.
What I do in my code is draw all my "Gound level" layers, SpriteBatch.Begin()
, draw your entities, SpriteBatch.End()
, draw all "upper level" layers.
From my understanding of the TiledMapRenderer system in the API before the 2.0
changes, mapRenderer.Draw()
writes "directly" to the graphics card. SpriteBatch is rendered to the graphics card when SpriteBatch.End()
is called. Your entity.Draw()
calls are just queuing up the rendering, then the upper layers are drawn (i.e. behind the character) before the characters are actually drawn.
@stefanrbk Thank you i did this and now it works perfect ;)
@davidbezdek no worries! Since you are also working with TiledMaps, have you been noticing any graphics glitches like what I posted in #476?
So, I have been putting some thought into how we could make this rendering a little easier without having to break it down per layer now that we can use group layers, etc. We could do an Action
-based delegate or event in the TiledMapRenderer
or TiledMapLayer
for SpriteBatch
-related processing, or have the ability to pass in a pre-made ECS system to link to the renderer, or something else even. What do you guys think?
Can't just add a couple of methods to the renderer that will take an array of strings or a range and render them in order?
My own renderer still has the layers similar to that, but each layer has a bunch of tiles, their depth gets calculated and they are added to my ECS and drawn automatically.
Our renderer for Tiled maps allows you to pass in a TiledMap
to render the whole map or a TiledMapLayer
to render just that layer. I have 2-4 layers which need to be rendered under the ECS entities and at least 1 layer to render above. We currently don't have a way to change the depth of the render/not sure if we could change the depth of the render for the maps as they are rendered with models directly on the graphics card. The map renderer and the ECS run completely separately, so that is what i'm trying to figure out how we would want to link them together.
Edit: I'm wrong, there is a depth setting for the layer draw functions. I'm gonna look at that quickly...