/// <summary> /// Used when the patch below is more detailed, and we are filling the bottom row /// </summary> /// <param name="pIndexBuilder"></param> /// <param name="hSkip"></param> /// <param name="hHalfSkip"></param> /// <param name="bLeft"></param> /// <param name="bRight"></param> private void AddTrianglesBottomRow(IndexBuilder pIndexBuilder, int nY, int hSkip, int hHalfSkip, bool bLeft, bool bRight) { int nStartX = 0, nEndX = _patchSize - 1; if (bLeft) { pIndexBuilder.AddIndex(0, nY + hSkip); pIndexBuilder.AddIndex(0, nY + hHalfSkip); pIndexBuilder.AddIndex(hHalfSkip, nY + hSkip); pIndexBuilder.AddIndex(0, nY); pIndexBuilder.AddIndex(hSkip, nY + hSkip); pIndexBuilder.AddIndex(hSkip, nY); nStartX = hSkip; } // if right patch is more detailed, don't fill the end block normally if (bRight) { nEndX -= hSkip; } for (int x = nStartX; x < nEndX; x += hSkip) { pIndexBuilder.AddIndex(x, nY + hSkip); pIndexBuilder.AddIndex(x, nY); pIndexBuilder.AddIndex(x + hHalfSkip, nY + hSkip); pIndexBuilder.AddIndex(x + hSkip, nY); pIndexBuilder.AddIndex(x + hSkip, nY + hSkip); if (x != _patchSize - 1 - hSkip) { pIndexBuilder.AddLastIndexAgain(); } } if (bRight) { int nRightX = _patchSize - 1 - hSkip; pIndexBuilder.AddIndex(nRightX, nY + hSkip); pIndexBuilder.AddIndex(nRightX, nY); pIndexBuilder.AddIndex(nRightX + hHalfSkip, nY + hSkip); pIndexBuilder.AddIndex(nRightX + hSkip, nY + hSkip); pIndexBuilder.AddLastIndexAgain(); pIndexBuilder.AddIndex(nRightX, nY); pIndexBuilder.AddIndex(nRightX + hSkip, nY + hHalfSkip); pIndexBuilder.AddIndex(nRightX + hSkip, nY); } }
private IndexCollection[] BuildIndices(int numLevels, int level) { // calculate number of vertices int nNumVerticesOneSide = GetPowerOfTwo((int)(numLevels - 1 - level)) + 1; int nNumVertices = nNumVerticesOneSide * nNumVerticesOneSide; // calculate number of primitives int nNumRows = nNumVerticesOneSide - 1; // for level 0, we only have set of indices because we never adapt to neighbours int nTotalNeighbourCodes = (level == 0) ? 1 : TotalNeighbourCodes; IndexCollection[] indices = new IndexCollection[nTotalNeighbourCodes]; int hSkip = GetPowerOfTwo(level); int hHalfSkip = hSkip / 2; for (int j = 0; j < nTotalNeighbourCodes; j++) { bool bLeft, bRight, bTop, bBottom; GetNeighboursBoolean(j, out bLeft, out bRight, out bTop, out bBottom); // generate indices if (level == numLevels - 1) { indices[j] = AddHighestLevelTriangles(hSkip, hHalfSkip, j); } else { IndexBuilder pIndexBuilder = new IndexBuilder(this); for (int y = 0; y < _patchSize - hSkip; y += hSkip) { AddTriangleRow(pIndexBuilder, y, hSkip, hHalfSkip, bLeft, bRight, bTop, bBottom); } indices[j] = pIndexBuilder.Indices; } } return(indices); }
private void AddTriangleRow(IndexBuilder pIndexBuilder, int nY, int hSkip, int hHalfSkip, bool bLeft, bool bRight, bool bTop, bool bBottom) { // special case for top row when patch above is more detailed if (bTop && nY == 0) { AddTrianglesTopRow(pIndexBuilder, hSkip, hHalfSkip, bLeft, bRight); return; } // if this is not the first row, add index for degenerate triangle // coming from previous row (this is so that we can keep the triangle list going) if (nY != 0) { pIndexBuilder.AddIndex(0, nY + hSkip); } // special case for bottom row when patch below is more detailed if (bBottom && (nY == _patchSize - 1 - hSkip)) { AddTrianglesBottomRow(pIndexBuilder, nY, hSkip, hHalfSkip, bLeft, bRight); return; } int nStartX = 0, nEndX = _patchSize; // special case if left patch (or left and top patch, or left and bottom patch) is more detailed if (bLeft) { pIndexBuilder.AddIndex(0, nY + hSkip); pIndexBuilder.AddIndex(0, nY + hHalfSkip); pIndexBuilder.AddIndex(hSkip, nY + hSkip); pIndexBuilder.AddIndex(0, nY); pIndexBuilder.AddIndex(hSkip, nY); pIndexBuilder.AddLastIndexAgain(); // shift starting x pos nStartX = hSkip; } // if right patch is more detailed, don't fill the end block normally if (bRight) { nEndX -= hSkip; } // standard row filler for (int x = nStartX; x < nEndX; x += hSkip) { pIndexBuilder.AddIndex(x, nY + hSkip); pIndexBuilder.AddIndex(x, nY); } // special case if right patch is more detailed if (bRight) { int nRightX = _patchSize - 1 - hSkip; pIndexBuilder.AddIndex(nRightX, nY + hSkip); pIndexBuilder.AddLastIndexAgain(); pIndexBuilder.AddIndex(nRightX + hSkip, nY + hSkip); pIndexBuilder.AddIndex(nRightX, nY); pIndexBuilder.AddIndex(nRightX + hSkip, nY + hHalfSkip); pIndexBuilder.AddIndex(nRightX + hSkip, nY); } // if this is not last row, add extra index for degenerate triangle if (nY != _patchSize - 1 - hSkip) { pIndexBuilder.AddLastIndexAgain(); } }
private IndexCollection[] BuildIndices(int numLevels, int level) { // calculate number of vertices int nNumVerticesOneSide = GetPowerOfTwo((int) (numLevels - 1 - level)) + 1; int nNumVertices = nNumVerticesOneSide * nNumVerticesOneSide; // calculate number of primitives int nNumRows = nNumVerticesOneSide - 1; // for level 0, we only have set of indices because we never adapt to neighbours int nTotalNeighbourCodes = (level == 0) ? 1 : TotalNeighbourCodes; IndexCollection[] indices = new IndexCollection[nTotalNeighbourCodes]; int hSkip = GetPowerOfTwo(level); int hHalfSkip = hSkip / 2; for (int j = 0; j < nTotalNeighbourCodes; j++) { bool bLeft, bRight, bTop, bBottom; GetNeighboursBoolean(j, out bLeft, out bRight, out bTop, out bBottom); // generate indices if (level == numLevels - 1) { indices[j] = AddHighestLevelTriangles(hSkip, hHalfSkip, j); } else { IndexBuilder pIndexBuilder = new IndexBuilder(this); for (int y = 0; y < _patchSize - hSkip; y += hSkip) AddTriangleRow(pIndexBuilder, y, hSkip, hHalfSkip, bLeft, bRight, bTop, bBottom); indices[j] = pIndexBuilder.Indices; } } return indices; }
/// <summary> /// Used when the patch above is more detailed, and we are filling the top row /// </summary> /// <param name="pIndexBuilder"></param> /// <param name="hSkip"></param> /// <param name="hHalfSkip"></param> /// <param name="bLeft"></param> /// <param name="bRight"></param> private void AddTrianglesTopRow(IndexBuilder pIndexBuilder, int hSkip, int hHalfSkip, bool bLeft, bool bRight) { int nStartX = 0, nEndX = _patchSize - 1; if (bLeft) { pIndexBuilder.AddIndex(0, 0); pIndexBuilder.AddIndex(hHalfSkip, 0); pIndexBuilder.AddIndex(0, hHalfSkip); pIndexBuilder.AddIndex(hSkip, 0); pIndexBuilder.AddIndex(0, hSkip); pIndexBuilder.AddIndex(hSkip, hSkip); nStartX = hSkip; } // if right patch is more detailed, don't fill the end block normally if (bRight) { nEndX -= hSkip; } for (int x = nStartX; x < nEndX; x += hSkip) { pIndexBuilder.AddIndex(x, 0); pIndexBuilder.AddIndex(x + hHalfSkip, 0); pIndexBuilder.AddIndex(x, hSkip); pIndexBuilder.AddIndex(x + hSkip, 0); pIndexBuilder.AddIndex(x + hSkip, hSkip); if (x != _patchSize - 1) { pIndexBuilder.AddLastIndexAgain(); } if (x == _patchSize - hSkip - 1) { pIndexBuilder.AddLastIndexAgain(); } } if (bRight) { int nRightX = _patchSize - 1 - hSkip; pIndexBuilder.AddIndex(nRightX, 0); pIndexBuilder.AddLastIndexAgain(); pIndexBuilder.AddIndex(nRightX, hSkip); pIndexBuilder.AddIndex(nRightX + hHalfSkip, 0); pIndexBuilder.AddIndex(nRightX + hSkip, 0); pIndexBuilder.AddLastIndexAgain(); pIndexBuilder.AddIndex(nRightX, hSkip); pIndexBuilder.AddIndex(nRightX + hSkip, hHalfSkip); pIndexBuilder.AddIndex(nRightX + hSkip, hSkip); } // don't need to add degenerate triangle due to weird indexing }