Single Chunk Removed at a Time

:information_source: Attention Topic was automatically imported from the old Question2Answer platform.
:bust_in_silhouette: Asked By codelyoko373

I’m attempting to create a chunk generation system for my game for a randomized world. The code I used was originally from this tutorial: but I’ve made some changes as originally the supplied function that’d get what chunks to generate around the player, and then pass that to a separate thread to generate them would only run once (As in it’d only generate 1 chunk even though 20 chunks needed to be generated).

I managed to get it working by implementing a simple for loop that is ran by the thread. This function will be called whenever the player enters a new chunk:

func GenerateChunks():
var player_position = player.position / 32;
var player_x = int(player_position.x) / chunk_size;
var player_y = int(player_position.y) / chunk_size;

xRange = range(player_x - chunk_amount, player_x + chunk_amount);
yRange = range(player_y - chunk_amount, player_y + chunk_amount);

for x in xRange:
	for y in yRange:
		var key = str(x) + "," + str(y); #The key for each Chunk (The Identifier)
		unready_chunks[key] = Vector2(x, y);

		var chunk = GetChunk(x, y);
		if chunk != null:
			chunk.should_remove = false;
if not thread.is_active():
	thread.start(self, "CreateChunks", [thread]);

It’ll basically work out the chunks meant to be around the player, add them to a dictionary and then start a thread to generate them. This Thread runs this CreateChunks function:

func CreateChunks(thread):
for key in unready_chunks:
	var x = unready_chunks[key].x;
	var y = unready_chunks[key].y;
	var chunk =, x * chunk_size, y * chunk_size, chunk_size, map);
	chunk.position = Vector2(x * chunk_size, y * chunk_size);
	unready_chunks[key] = chunk;


Which will actually create the chunk object, reassign the values within the dictionary and call the LoadDone function to end the thread.

func LoadDone():
for chunk in unready_chunks.values():
	add_child(chunk); #Adds the Chunk to the Child object in the scene
	var key = str(chunk.position.x / chunk_size) + "," + str(chunk.position.y / chunk_size);
	chunks[key] = chunk;


This then loops through those created chunks again, adds them as a child to the world object and adds the chunk to another dictionary that stores the generated chunks.

This all works fine but the issue I’m having is with removing chunks that are meant to be out of range of the player. Along with the GenerateChunks function, these two functions are also called:

func CleanUpChunks():
for key in chunks:
	var chunk = chunks[key];
	if chunk.should_remove:

func ResetChunks():
for key in chunks:
	chunks[key].should_remove = true;

This should set all chunks to be removed unless specified by the GenerateChunks function. The issue though is only ONE chunk is set to be removed when there should be multiple. It’s clearly got something to do with my new thread system as the original code I got from that video had the GenerateChunks function called every frame. I’ve replaced that function with this one instead that’ll check differences in the players position to know when to generate new chunks:

func CheckForNeededChunkGeneration():
var player_position = player.position / 32;
var player_x = int(player_position.x) / chunk_size;
var player_y = int(player_position.y) / chunk_size;

var xRangeTemp = range(player_x - chunk_amount, player_x + chunk_amount);
var yRangeTemp = range(player_y - chunk_amount, player_y + chunk_amount);

if xRange != xRangeTemp or yRange != yRangeTemp:

Wasn’t exactly sure how to word all of this so if you have any questions then please ask. I’m just wondering if anyone by chance has any clue to why this is happening with only one chunk being removed at a time.

:bust_in_silhouette: Reply From: Jason Swearingen

Hi, I just started godot, so not sure how helpful I’ll be (also using c# not gdscript…)

anyway, I suggest you get this working WITHOUT threads. then add threads.

as to speculate what’s wrong:

I am guessing that the first time through your CheckForNeededChunkGeneration() method, RestChunks() is called and it works properly (some number of chunks flagged for delete)

the second pass through CheckForNeededChunkGeneration() then CleanUpChunks(); is stalling out on the first chunk it deletes. you could easily verify this by logging how many times through the loop it gets.