1
\$\begingroup\$

I'm generating a basic terrain and it looks something like this:

// Load the vertex and index array with the terrain data.
    for (j = 0; j<(m_terrainHeight - 1); j++)
    {
        for (i = 0; i<(m_terrainWidth - 1); i++)
        {
            index1 = (m_terrainHeight * j) + i;          // Top left.
            index2 = (m_terrainHeight * (j + 1)) + i;      // Bottom left.
            index3 = (m_terrainHeight * j) + (i + 1);      // Top right.
            index4 = (m_terrainHeight * (j + 1)) + (i + 1);  // Bottom right.

            // Top left
            vertices[index].position = glm::vec3(m_heightMap[index1].x, m_heightMap[index1].y, m_heightMap[index1].z);
            vertices[index].texture = glm::vec2(m_heightMap[index1].tu = 0.0f, m_heightMap[index1].tv = 0.0f);
            indices[index] = index;
            index++;

            // Bottom left.
            vertices[index].position = glm::vec3(m_heightMap[index2].x, m_heightMap[index2].y, m_heightMap[index2].z);
            vertices[index].texture = glm::vec2(m_heightMap[index2].tu = 0.0f, m_heightMap[index2].tv = 1.0f);
            indices[index] = index;
            index++;

            // Top right.
            vertices[index].position = glm::vec3(m_heightMap[index3].x, m_heightMap[index3].y, m_heightMap[index3].z);
            vertices[index].texture = glm::vec2(m_heightMap[index3].tu = 1.0f, m_heightMap[index3].tv = 0.0f);
            indices[index] = index;
            index++;

            // Top right.
            vertices[index].position = glm::vec3(m_heightMap[index3].x, m_heightMap[index3].y, m_heightMap[index3].z);
            vertices[index].texture = glm::vec2(m_heightMap[index3].tu = 1.0f, m_heightMap[index3].tv = 0.0f);
            indices[index] = index;
            index++;

            // Bottom left.
            vertices[index].position = glm::vec3(m_heightMap[index2].x, m_heightMap[index2].y, m_heightMap[index2].z);
            vertices[index].texture = glm::vec2(m_heightMap[index2].tu = 0.0f, m_heightMap[index2].tv = 1.0f);
            indices[index] = index;
            index++;

            // Bottom right
            vertices[index].position = glm::vec3(m_heightMap[index4].x, m_heightMap[index4].y, m_heightMap[index4].z);
            vertices[index].texture = glm::vec2(m_heightMap[index4].tu = 1.0f, m_heightMap[index4].tv = 1.0f);
            indices[index] = index;
            index++;
        }
    }

Now If I wanted to find which grid square the player is on, we could simply (if the camera position is relative to the terrain)

    //Grid square the camera is on
    int gridX = (int)std::floor(cameraX / gridSquareSize);
    int gridZ = (int)std::floor(cameraZ / gridSquareSize);

Continuing, we know that each face consists of two triangles, and the top triangle is represented by three vertices which index corresponds to top left, bottom left and top right. The bottom triangle would then be top right, bottom left and bottom right. Now I'm having a hard time trying to find height values (y-values) at these points because if I try to do

//Top left triangle
glm::vec3(0, vertices[(m_terrainHeight * gridZ) + gridX].position.y, 0) //Top left
glm::vec3(0, vertices[(m_terrainHeight * (gridZ) + 1) + gridX].position.y, 1) //Bottom left
glm::vec3(1, vertices[((m_terrainHeight * gridZ)) + (gridX + 1)].position.y, 0) //Top right

we conclude that the top left and bottom left position will be okay, but the top right position won't get the correct index, because as it is now (if we say that gridX = 0 and gridZ = 0), the index will generate a value of 1, which is not the correct height value at that position because the index we want should be 2 (top right). So, is there a way I could write the code so I would get the correct index for the triangles of the terrain?

\$\endgroup\$

1 Answer 1

2
\$\begingroup\$

You are storing 6 values for each "square": 3 vertex for each of the 2 triangles from the square.

For each square, you should advance 6 positions, and in each of those positions you have the info of each vertex.

Change the lines:

 vertices[(m_terrainHeight * gridZ) + gridX]    //Top left
 vertices[(m_terrainHeight * (gridZ) + 1) + gridX] //Bottom left
 vertices[((m_terrainHeight * gridZ)) + (gridX + 1)] // Top right

To:

 vertices[6*((m_terrainHeight * gridZ) + gridX)]   //Top left
 vertices[6*((m_terrainHeight * gridZ) + gridX)+1] //Bottom left
 vertices[6*((m_terrainHeight * gridZ) + gridX)+2] // Top right
\$\endgroup\$
7
  • \$\begingroup\$ Hmm, but if I do that and we assume that gridX = gridZ = 0 and m_terrainHeight = 256, it would mean I would get the 256th index, and that doesn't have to be the same as the index[1], or am I missing something? :) @Leo \$\endgroup\$
    – Riggs
    Sep 14, 2016 at 17:28
  • \$\begingroup\$ You would indeed get the 256 index. But take into account your are storing all the information in an array, which only has one dimension, to store the info of a surface, which is a two dimentional object. Conceptually, you are putting all rows (or columns) of the 2D surface one after another, which can be contained in a 1D structure. Moving left and right moves the index one position, but moving up and down requires to move to another row, which is stored "further" away into the array. See this image as reference: eli.thegreenplace.net/images/2015/column-major-2D.png \$\endgroup\$
    – Leo
    Sep 14, 2016 at 17:55
  • \$\begingroup\$ True, but I'm still not seeing the results I want to see, as the height values from the vertices isn't correct. I get like 6.24 for the bottom left which should be 0.533 because at this face the surface is almost flat, so the player moves up from 6.24 as the value retrieved says it should. I wonder what to do... @Leo \$\endgroup\$
    – Riggs
    Sep 14, 2016 at 18:28
  • \$\begingroup\$ Ì will edit my answer, as i completelly misunderstood one important point :) I'll put the new answer now. \$\endgroup\$
    – Leo
    Sep 14, 2016 at 18:43
  • \$\begingroup\$ Now that is correct! Thank you very much, sir! @Leo \$\endgroup\$
    – Riggs
    Sep 14, 2016 at 19:23

You must log in to answer this question.

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