I am making a tile based game. Recently I moved to drawing tiles as primitives to speed up things and also allow for easier lighting (Vertex Shader).

I then took it a step further and made some calculations to "merge" together tiles into the same primitive to gain even more performance, and to get around UV texture problems I simply did this...

if (!top)
    //Adds the top vertices
    thisquad.Vertices[0] = new VertexPositionTexture(new Vector3(new Vector2(p.X, p.Y), 0), new Vector2(0, 0));
    thisquad.Vertices[1] = new VertexPositionTexture(new Vector3(new Vector2(Tile.Size + p.X, p.Y), 0), new Vector2(1, 0));
    top = true;
//Extends the bottom vertices
thisquad.Vertices[2] = new VertexPositionTexture(new Vector3(new Vector2(p.X, Tile.Size + p.Y), 0), new Vector2(0, currentquadtilecount));
thisquad.Vertices[3] = new VertexPositionTexture(new Vector3(new Vector2(Tile.Size + p.X, Tile.Size + p.Y), 0), new Vector2(1, currentquadtilecount));

With currentquadtilecount starting at 1, if a tile is floating on its own it will display the texture properly, but for every second tile that merges, the texture is flipped. As shown below...

Example Image

What am I doing wrong? Is this even the right way to do this??


  • \$\begingroup\$ And did it speed things up? I always found SpriteBatch to be very efficient when used correctly (probably more than a typical hand rolled version). And by the way you can do both vertex/pixel shaders and tile merging quite easily with the SpriteBatch too. \$\endgroup\$ Commented Dec 31, 2011 at 12:21
  • \$\begingroup\$ E.g. For a vertex shader example with SpriteBatch check this. There's also a pixel shader version at the end which I left in for future reference. Basically pass the effect to SpriteBatch.Begin(). As for merging tiles together with SpriteBatch, read this (although it was written before XNA4 came out). Basically turn on TextureAddressMode.Wrap and use a source rectangle corresponding to the size you want the entire merged area to be. \$\endgroup\$ Commented Dec 31, 2011 at 12:28
  • \$\begingroup\$ Oh yes it did! (I have a key to change between 2D and 3D drawing) With a full screen of tiles, 2D was running at 500fps. while 3D ran at 800-900fps. \$\endgroup\$
    – ZeunO8
    Commented Dec 31, 2011 at 12:35
  • \$\begingroup\$ That's really cool then! I've read about this before, maybe I'll look into it sometime. :-) \$\endgroup\$ Commented Dec 31, 2011 at 12:41
  • \$\begingroup\$ Yup! That Nuclex Framework looks quite interesting, I tried to do a similar thing (group batching) and found that building up the list of Vertices and Indices was much slower, so gave up on that idea. Feel free to ask for my source for my primitive drawing whenever. :) \$\endgroup\$
    – ZeunO8
    Commented Dec 31, 2011 at 12:47

1 Answer 1


I'm almost sure this is because you're using TextureAddressMode.Mirror instead of TextureAddressMode.Wrap.

Change the value in the sampler state before rendering the primitives. I think it should be something like:

GraphicsDevice.SamplerStates[0].AddressU = TextureAddressMode.Wrap;
GraphicsDevice.SamplerStates[0].AddressV = TextureAddressMode.Wrap;
  • \$\begingroup\$ It is already .Wrap by default, and changing it to Mirror or Clamp does not work either.. ? \$\endgroup\$
    – ZeunO8
    Commented Dec 31, 2011 at 12:29
  • \$\begingroup\$ Are you sure it's not being changed to Mirror somewhere between that point and when the primitives are finally drawn? Do a System.Diagnostics.Debug.WriteLine(GraphicsDevice.SamplerStates[0].AddressU); right before the line that actually draws the primitives. \$\endgroup\$ Commented Dec 31, 2011 at 12:33
  • \$\begingroup\$ Ahh derp.. Found the problem... I was setting the UV Address mode WITHIN the Shader.. sampler TextureSampler = sampler_state { texture = <xTexture>; magfilter = LINEAR; minfilter = LINEAR; mipfilter = NONE; AddressU = wrap; AddressV = wrap;}; fixed it.. \$\endgroup\$
    – ZeunO8
    Commented Dec 31, 2011 at 12:38
  • \$\begingroup\$ Glad you found it. That was going to be my next suggestion, because I wasn't sure if you were already using a shader or not. \$\endgroup\$ Commented Dec 31, 2011 at 12:42

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .