I am currently developing a c++ minecraft clone in sfml and am trying to implement parallelism for rendering and modifying the chunks using a thread pool. The main issue I am currently facing is how to efficiently implement this. Currently the function which handles rendering and modifying chunks data (changing octaves, persistence, frequency in the perlin noise value) uses two nested for loops and I would like to try to run these operations in parallel such that I can modify the chunks noise much faster, as now its slow when I have > 100 chunks created.
void chunkManager::renderChunks(bool update){
for(int i = -Manage::renderDistance; i <= Manage::renderDistance; ++i){
for(int j = -Manage::renderDistance; j <= Manage::renderDistance; ++j){
loadChunk(chunkPosition.x + i, chunkPosition.y + j, update);
}
}
for(auto &pair : chunks){
window.draw(pair.second);
}
}
This is also what my load function does, it just takes these chunks and the corresponding coordinates and creates it if it doesnt exist or update is true
void chunkManager::loadChunk(int chunkX, int chunkY, bool update){
sf::Vector2i blockCoords(chunkX * Chunks::size, chunkY * Chunks::size); // converted from chunk space to blocks in game space
auto chunkIter = chunks.find({chunkX, chunkY});
if (chunkIter == chunks.end() || update) {
auto chunk = Chunk();
chunk.setVisibleBlocks(blockCoords, perlin, octaves, persistence, frequency);
chunks[{chunkX, chunkY}] = chunk;
}
}
I have attempted to use the BS::thread_pool class in order to implement this, but I have been unable to figure out how to properly implement it for a nested loop. I tried just add a loop inside of the pool.submit_loop member and use either x or y as the argument but this will only render the starting area around the player, and it seemed to be less efficient than my first approach. If anyone has any suggestions for a smarter approach I would very much appreciate it.
void chunkManager::renderChunks(bool update){
//this creates the render view for the player, so in this case it would me Manage::renderDistance chunks that the player can see.
const BS::multi_future<void> loop_future = pool.submit_loop(-Manage::renderDistance, Manage::renderDistance + 1 ,
[this, update](const int y)
{
for(int x = -Manage::renderDistance; x <= Manage::renderDistance; ++x){
this->loadChunk(x,y,update);
}
});
loop_future.wait();
for(auto &pair : chunks){
window.draw(pair.second);
}
}
3