CityRenderingEngine/generator/ChunkLoader.cpp
/* This function is the loop in which the ChunkLoader will perform the loading and unloading operations. */
This function is the loop in which the ChunkLoader will perform the loading and unloading operations.
This function is the loop in which the ChunkLoader will perform the loading and unloading operations .
int chunkLoaderLoop(void *data) {
    ChunkLoader *loader = (ChunkLoader*) data;
    while (loader->isExecuting()) {
        if (loader->getQueue()->size() > 0) {
            loader->lockMutex();
            ChunkOperation operation = loader->getQueue()->front();
            loader->unlockMutex();
            if (operation.load) {
                Chunk *chunk = nullptr;
                City *city = operation.city;
                city->lockMutex();
                bool duplicate = false;
                auto itEnd = city->getChunks()->end();
                for (auto it = city->getChunks()->begin(); it != itEnd; it++) {
                    if (operation.chunkPos == (*it)->getChunkPos()) {
                        duplicate = true;
                    }
                }
                city->unlockMutex();
                if (!duplicate) {
                    if (Chunk::chunkExists(operation.chunkPos)) {
                        chunk = Chunk::loadChunk(operation.chunkPos, operation.city);
                    } else {
                        chunk = ChunkGenerator::generateChunk(operation.city, operation.chunkPos);
                    }
                    if (chunk != nullptr) {
                        operation.city->addChunk(chunk);
                    }
                }
                loader->lockMutex();
                loader->getQueue()->pop_front();
                loader->unlockMutex();
            } else {
                Chunk *chunk = operation.city->getChunkAt(operation.chunkPos, false);
                if (chunk != nullptr) {
                    if (Naquadah::getInstance()->getCurrentScene()->isEntityInScene(chunk->getEntityName())) {
                        Naquadah::getInstance()->getCurrentScene()->removeEntity(chunk->getEntityName());
                    } else if (chunk->isSafeToDelete()) {
                        loader->lockMutex();
                        loader->getQueue()->pop_front();
                        loader->unlockMutex();
                        operation.city->removeChunk(chunk);
                        chunk->unload();
                        delete chunk;
                        chunk = nullptr;
                    }
                } else {
                    loader->lockMutex();
                    loader->getQueue()->pop_front();
                    loader->unlockMutex();
                }
            }
        }
    }
    delete loader;
    return 0;
}
int chunkLoaderLoop ( void * data ) { ChunkLoader * loader = ( ChunkLoader * ) data ; while ( loader -> isExecuting ( ) ) { if ( loader -> getQueue ( ) -> size ( ) > 0 ) { loader -> lockMutex ( ) ; ChunkOperation operation = loader -> getQueue ( ) -> front ( ) ; loader -> unlockMutex ( ) ; if ( operation . load ) { Chunk * chunk = nullptr ; City * city = operation . city ; city -> lockMutex ( ) ; bool duplicate = false ; auto itEnd = city -> getChunks ( ) -> end ( ) ; for ( auto it = city -> getChunks ( ) -> begin ( ) ; it != itEnd ; it ++ ) { if ( operation . chunkPos == ( * it ) -> getChunkPos ( ) ) { duplicate = true ; } } city -> unlockMutex ( ) ; if ( ! duplicate ) { if ( Chunk :: chunkExists ( operation . chunkPos ) ) { chunk = Chunk :: loadChunk ( operation . chunkPos , operation . city ) ; } else { chunk = ChunkGenerator :: generateChunk ( operation . city , operation . chunkPos ) ; } if ( chunk != nullptr ) { operation . city -> addChunk ( chunk ) ; } } loader -> lockMutex ( ) ; loader -> getQueue ( ) -> pop_front ( ) ; loader -> unlockMutex ( ) ; } else { Chunk * chunk = operation . city -> getChunkAt ( operation . chunkPos , false ) ; if ( chunk != nullptr ) { if ( Naquadah :: getInstance ( ) -> getCurrentScene ( ) -> isEntityInScene ( chunk -> getEntityName ( ) ) ) { Naquadah :: getInstance ( ) -> getCurrentScene ( ) -> removeEntity ( chunk -> getEntityName ( ) ) ; } else if ( chunk -> isSafeToDelete ( ) ) { loader -> lockMutex ( ) ; loader -> getQueue ( ) -> pop_front ( ) ; loader -> unlockMutex ( ) ; operation . city -> removeChunk ( chunk ) ; chunk -> unload ( ) ; delete chunk ; chunk = nullptr ; } } else { loader -> lockMutex ( ) ; loader -> getQueue ( ) -> pop_front ( ) ; loader -> unlockMutex ( ) ; } } } } delete loader ; return 0 ; }
This function is the loop in which the ChunkLoader will perform the loading and unloading operations.
This function is the loop in which the ChunkLoader will perform the loading and unloading operations .
// Load the Chunk // We first check if while on the queue, the Chunk wasn't loaded already // Load it from the disk // Generate it // Add it to the Scene // Unload the Chunk /* The unload works in three steps: The Chunk is first removed from the entity list of CityScene,
                     * then when CityScene finishes using it, the render thread will be notified of the Chunk's unload
                     * and will unload and delete all OpenGL resources on the end of its next render() call. Finally,
                     * when the Chunk is void of all OpenGL references and is not being used by anything anymore, it's
                     * safe to actually unload and delete it.
                     */ // This gives the update() method of the Chunk time to finish, and makes sure it won't be called again. // Only remove the Chunk from the queue once it's fully unloaded // If Chunk is null, it probably was deleted already, so just remove it from the queue. // Clean up and finish