Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- enum Face
- {
- North = 1,
- East = 2,
- South = 4,
- West = 8,
- Top = 16,
- Bottom = 32
- };
- int numBlocksPerSection = chunkSizeX * sectionHeight * chunkSizeZ;
- bool handled[] = new bool[numBlocksPerSection];
- Face activeFace = (Face)1;
- // iterate over all 6 faces
- for (int f = 0; f < 6; ++f)
- {
- // reset all blocks not to be handled
- memset(handled, FALSE, numBlocksPerSection);
- for(int x = 0; x < chunkSizeX; ++x)
- {
- for(int y = 0; y < sectionHeight; ++y)
- {
- for(int z = 0; z < chunkSizeZ; ++z)
- {
- // global and relative indices
- int iGlobal = x + chunkSizeX * ((y + currentSection * sectionHeight) + chunkSizeY * z);
- int iRelative = x + chunkSizeX * (y + sectionHeight * z);
- Face faces = currentChunk.blockData[iGlobal].VisibleFaces;
- // continue if face is not visible or was handled already
- if(!(faces & activeFace) || handled[iRelative])
- {
- handled[iRelative] = true;
- continue;
- }
- int width = 1, height = 1, depth = 1;
- // skip width check if activeFace is East or West -> no width
- if(!(activeFace & East || activeFace & West))
- {
- // calculate width for same faces being adjacent to current block
- for(; width < chunkSizeX - x &&
- currentChunk.blockData[SHIFT_INDEX_X(iGlobal, width)].VisibleFaces & tmp &&
- currentChunk.blockData[iGlobal].Type == currentChunk.blockData[SHIFT_INDEX_X(iGlobal, width)].Type &&
- && !handled[SHIFT_SECTIONINDEX_X(iRelative, width)]; ++width);
- }
- bool done = false;
- // skip depth check if activeFace is North or South -> no depth
- if(!(activeFace & North || activeFace & South))
- {
- // calculate depth for same faces being adjacent to current block
- for(; depth < chunkSizeZ - z; ++depth)
- {
- // this time add another loop, to make sure, only increment depth if all blocks inside the width range are same
- for(int u = 0; u < width; ++u)
- {
- int indexGlobal = SHIFT_INDEX_X(SHIFT_INDEX_Z(iGlobal, depth), u);
- int indexRelative = SHIFT_RELATIVEINDEX_X(SHIFT_RELATIVEINDEX_Z(iRelative, depth), u);
- if(!(currentChunk.blockData[indexGlobal].VisibleFaces & activeFace &&
- currentChunk.blockData[iGlobal].Type == currentChunk.blockData[indexGlobal].Type) ||
- handled[indexRelative])
- {
- done = true;
- break;
- }
- }
- if(done)
- break;
- }
- }
- done = false;
- // skip height check if activeFace is Top or Bottom -> no height
- if(!(activeFace & Top || activeFace & Bottom))
- {
- // calculate height
- for(; height < sectionHeight - y; ++height)
- {
- // add loops for width and depth
- for(int u = 0; u < width; ++u)
- {
- for(int v = 0; v < depth; ++v)
- {
- int indexGlobal = SHIFT_INDEX_X(SHIFT_INDEX_Y(SHIFT_INDEX_Z(iGlobal, v), height), u);
- int indexRelative = SHIFT_RELATIVEINDEX_X(SHIFT_RELATIVEINDEX_Y(SHIFT_RELATIVEINDEX_Z(iRelative, v), height), u);
- if(!(currentChunk.blockData[indexGlobal].VisibleFaces & activeFace ||
- currentChunk.blockData[iGlobal].Type == currentChunk.blockData[indexGlobal].Type) ||
- handled[indexRelative])
- {
- done = true;
- break;
- }
- }
- if(done) break;
- }
- if(done) break;
- }
- }
- // make sure we add the calculated face range to the handled array
- for(int a = 0; a < width; ++a)
- for(int b = 0; b < height; ++b)
- for(int c = 0; c < depth; ++c)
- handled[SHIFT_RELATIVEINDEX_X(SHIFT_RELATIVEINDEX_Y(SHIFT_RELATIVEINDEX_Z(iRelative, c), b), a)] = true;
- // add the quad's vertices here, dependent on the activeFace,
- // e.g. for North and a counter-clockwise ordering:
- // position1 = vector3(width + x + currentChunk.x, y + currentChunk.y, depth + z + currentChunk.z);
- // position2 = vector3(width + x + currentChunk.x, y + height + currentChunk.y, depth + z + currentChunk.z);
- // position3 = vector3(x + currentChunk.x, y + height + currentChunk.y, depth + z + currentChunk.z);
- // position4 = vector3(x + currentChunk.x, y + currentChunk.y, depth + z + currentChunk.z);
- }
- }
- }
- activeFace = (Face)(activeFace * 2);
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement