Game crush for no reason

Im making an enemy boss that will throw bullets.
Ive made a bullet manager and a script for the attack. Everything works because there is no error, but because i have a loop the game is not responding! Is there a specific reason?

We can’t tell you without seeing the code.

Do you know where that loop is?

Generally, watch out for very large for-loops and any while loops. Are you sure they are ever exited?

Yes, the loop is ending.
The loop is large, because i run it while the angle is less than 360° and is gong up by 4 every time loop is called. So its 0° to 360° (90 times).

Have you checked that when the game stops responding, it’s really because of this loop? (Print something every iteration and see if it continues printing while the game is frozen)

And does the game fully freeze or does it recover (after the loop finishes)?

If it does recover, optimise the loop for performance.
If it doesn’t, could you please share your code? That would make things a lot easier

Oh, there is a misunderstanding. There is no crush in the game. The engine falls! (i need to restart the engine). Also, yes the loop is the problem. I checked

Your while loop is clearly not finishing in that case. Post your code and we will tell you any potential causes for this. Or try adding in a counter that limits the while loop to, say, 90 iterations and then breaks it.

This is partly why I always try to avoid while loops. They can get trapped into infinite looping quite easily by mistake.

I don’t think any one will be able to help you further without some sample code to look at. Sorry.

1 Like

func circle():
var bullet = bullet_scene.instantiate()
get_tree().current_scene.call_deferred (“add_child”, bullet)

func spawn():
for i in 3:
while fire_angle <= 360:
if bullet_count > 60:
bullet_count
break
circle()
bullet_count +=1
fire_angle += 4

If you put the code between two sets of three backticks each, you won’t lose the indentation:
```
code
```
This:

func foo() -> void:
    pass

vs this:
func foo() → void:
pass

We’ll need to know the indentation, because without it the function could look many ways.
That being said, if it looks like this on your end, it should be fine (at least it shouldn’t hang):

func circle():
    var bullet = bullet_scene.instantiate()
    get_tree().current_scene.call_deferred (“add_child”, bullet)

func spawn():
    for i in 3:
        while fire_angle <= 360:
            if bullet_count > 60:
                bullet_count
                break
            circle()
            bullet_count +=1
            fire_angle += 4

There are a few things I will add though:

  1. The line bullet_count doesn’t do anything; you can remove it.
  2. You don’t seem to be setting the position or “direction” of any bullets anywhere?
  3. What is the purpose of the for-loop?
  4. Where are fire_angle and bullet_count declared, initialised and reset?
2 Likes

Yes i totally understand what you say.
The bullet_count is used for the break, and for is just to create 3 circles.
Is it more helpfull like this ?

extends Node
class_name bullet_manager

@export var bullet_scene: PackedScene # The bullet scene to use
@export var pool_size: int = 500      # How many bullets to pre-instantiate

var bullet_pool: Array = []
var active_bullets: Array = [] 

func _ready():
	# 1. Initialize the pool
	for i in range(pool_size):
		var bullet = bullet_scene.instantiate()
		get_parent().add_child(bullet) # Add to the scene tree once
		bullet.visible = false
		bullet.set_process(false) # Disable processing for inactive bullets
		bullet_pool.append(bullet)
		get_tree().current_scene.call_deferred("add_child", bullet)


func spawn_bullet(position: Vector2, direction: Vector2):
	if not bullet_pool.is_empty():
		# A. Retrieve and remove the bullet from the pool
		var bullet = bullet_pool.pop_front()
		
		# B. Set its new state (reactivate)
		bullet.global_position = position
		bullet.direction = direction 
		
		# C. Make it visible and active
		bullet.visible = true
		bullet.set_process(true) 
		
		active_bullets.append(bullet) # Track it as active


func return_to_pool(bullet:Area2D):
	# Call this from the bullet's script when it hits something or leaves the screen
	# 1. Reset its state
	bullet.visible = false
	bullet.set_process(false)
	
	# 2. Return it to the pool for reuse
	bullet_pool.append(bullet)
	active_bullets.erase(bullet) # Remove from active list

extends State

@export var bullet1 : PackedScene
@onready var hero: CharacterBody2D = $"../../hero"

var fire_angle: float = 0.0  # Tracks the current firing angle (in degrees)
var angle_step: float = 10.0 # How much to rotate the angle for the next bullet
var spin_rate: float = 1.0   # How fast the spiral spins (speed of angle change)

func enter():
	super.enter()
	spawn()


func circle():
	# 1. Calculate the direction vector from the current angle
	var angle_rad = deg_to_rad(fire_angle)
	var direction = Vector2.RIGHT.rotated(angle_rad).normalized()
	# 2. Call central bullet manager to fire the bullet
	var boss_node = owner
	boss_node.manager.spawn_bullet(boss_node.global_position, direction)
	# 3. Increment the angle for the next shot (this creates the rotation/spiral)
	fire_angle += angle_step 
	# 4. Keep the angle within 0-360 degrees (optional cleanup)
	if fire_angle >= 360.0:
		fire_angle -= 360.0



func spawn():
	angle_step = 8
	for i in 3: # do it 3 times
		while fire_angle < 360: # spawn bullets for 360 degrees
			if bullet_used > 60: # spawn only 60 bullets
				bullet_used = 0
				break
			circle() # calculate the angle to spawn
			fire_angle += angle_step
			bullet_used += 1

var bullet_used:int = 0
1 Like

I think that your fire_angle is always under 360, as circle() is called during the while loop. So you never leave the first for loop. try a print(i) to check if you get out of the first for loop

The problem is that the engine is crushing not the game. So when i hit “play” the engine stops responding.

Are you sure that method is not called when the scene starts ?
To be sure try to run an empty scene, and remove all your singletons. if it crashes then something is wrong with the engine, so restart the computer. maybe the memory used by your previous runs hasn’t be releases for some reason..

if your empty scene runs, renable the singletons and try again. Ok renable your code bit by bit until finding what is wrong. Check also if Godot has some logs somewhere. Always useful to debug crashing application.

1 Like