Scene Updates and Raycasting

I’m developing a plugin which generates 100 components and place them on a terrain (with a collider) in the scene.

Issue 1: Scene is not updated

When I execute the plugin function to create components, the scene doesn’t update immediately. To see the changes, I often need to either reopen the project or close Godot entirely. Even then, the update only seems to apply roughly every 5th attempt.

Is there a way to force a scene refresh after the components are generated?
I am using editor_interface.reload_scene_from_path(map_scene.resource_path)

Issue 2: Raycasting the Terrain

I’m having issues with raycasting the terrain. I’m trying to use PhysicsServer3D.space_get_direct_state(terrain_node.get_world_3d()), but it’s showing an error in the console. What’s the correct way to get the physics space for raycasting in a scene which is not included in the viewport?

My Code

@tool
extends Node

var map_scene = preload("res://scenes/Map.tscn")
var component_scene = preload("res://scenes/Component.tscn")
var editor_interface: EditorInterface

func generate_random_components():

	var map_instance = map_scene.instantiate()

	# Find the Components node
	var components_node = map_instance.get_node_or_null("Components")
	if not components_node:
		print("Components node not found in the Map scene.")
		return
				
	# Remove all existing children from the Components node
	for child in components_node.get_children():
		print("Removing Component: " + child.name)
		components_node.remove_child(child)
		child.queue_free()
	
	# Generate Components
	for i in range(100):
		var component = component_scene.instantiate()
		var tag = tag_scene.instantiate()
		
		# Generate random X and Z coordinates
		var x = randf_range(-3.5, 3.5)
		var y = randf_range(-3.5, 3.5)
		var z = randf_range(-3.5, 3.5)
		
		# Raycast to find the Y coordinate on the terrain
		var space_state = PhysicsServer3D.space_get_direct_state(terrain_node.get_world_3d())
		var ray_start = Vector3(x, 5, z)  # Start high above the terrain
		var ray_end = Vector3(x, -1, z)   # End below the terrain
		var query = PhysicsRayQueryParameters3D.create(ray_start, ray_end)
		query.collision_mask = 1 # Terrain layer
		var intersection = space_state.intersect_ray(query)
		if intersection:
			y = intersection.position.y
			component.position = Vector3(x, y, z)
		else:
			# Fallback if raycast fails
			component.position = Vector3(x, 0, z)

		components_node.add_child(component, true)
		component.set_owner(map_instance)
				
	
	# Create a packed scene from our modified map instance
	var packed_scene = PackedScene.new()
	var result = packed_scene.pack(map_instance)
	if result == OK:
		# Save the modified scene back to disk
		var map_scene_path = map_scene.resource_path
		result = ResourceSaver.save(packed_scene, map_scene_path)
		print("Saved to: ", packed_scene)
		if result == OK:
			print("Successfully cleared existing components, added new ones, and saved Map scene at: ", map_scene_path)
		else:
			print("Failed to save modified Map scene. Error code: ", result)
	else:
		print("Failed to pack the modified scene. Error code: ", result)
	
	if Engine.is_editor_hint():
		print("Reloading scene")
		var editor_interface = Engine.get_singleton("EditorInterface")
		editor_interface.reload_scene_from_path(map_scene.resource_path)
	
	map_instance.free()