Monday, March 21, 2011

Rendering Regular Grids on XNA

First of all credits to the thought process and article of Dan Lecocq. In this very first post of my blog about this and that, I would like to keep things easy for me and provide an implementation of rendering regular 2D grids in XNA.

In my Grid class, I have the following class members:


// The 2-D array to hold the height values at grid points.
double[,] height;

// x-resolution and y-resolution of the 2D grid.
int xRes;
int yRes;

// the difference in x and y-direction of
// two successive grid points.
double xStep;
double yStep;

// Vertex position, color, and index arrays.
VertexPositionColor[] vertices;
int[] indices;


As you can guess, I have used XNA's DrawUserIndexedPrimitive method. The data is allocated in the constructor as follows:


public Grid(int nX, int nY, double x_Length, double y_Length)
{
height = new double[nX, nY];

xRes = nX;
yRes = nY;

xStep = x_Length / (double)nX;
yStep = y_Length / (double)nY;

vertices = new VertexPositionColor[xRes * yRes];
indices = new int[2 * xRes * (yRes - 1)];

InitVertexBuffer();
}


The real deal is initializing the vertex buffer, especially the index information.


private void InitVertexBuffer()
{
// First initialize vertex buffer
for (int j = 0; j < yRes; j++)
{
for (int i = 0; i < xRes; i++)
{
vertices[j * xRes + i] =
new VertexPositionColor(new Vector3((float)(i * xStep), (float)(j * yStep), (float)(height[i, j])),
new Color(0f, 0.9f, 0.9f, 0.6f)); // Of course give it any color you want...
}
}

// Now initialize indices
int index = 0;
for (int j = 0; j < yRes - 1; j++)
{
int toSub = j % 2 == 0 ? (xRes - 1) : (xRes + 1);

for (int i = 0; i < xRes; i++)
{
indices[j * 2 * xRes + i * 2] = index;
index += xRes;
indices[j * 2 * xRes + i * 2 + 1] = index;
index -= toSub;
}
index += toSub;
}
}


And finally, rendering of the grid:


public void DrawGrid(GraphicsDevice graphicsDevice)
{
graphicsDevice.DrawUserIndexedPrimitives
(PrimitiveType.TriangleStrip,
vertices,
0,
xRes * yRes,
indices,
0,
(xRes) * (yRes - 1) * 2 - 2);
}


So, you have setup your Game class, added your Grid class, and hit F5. What? Displaying strips instead of the whole grid? If I were you, I would check back face culling :).

That's it, hope it will help anyone out there!

No comments:

Post a Comment