Project Foundations Deep Dive (load on demand)
MANDATORY for naming tables, typed-GDScript migration, and architecture samples beyond bundled scripts. Do not re-inline EventBus / SceneManager code in chat.
Naming conventions (full)
| Artifact | Convention | Example |
|---|---|---|
| Files / folders | snake_case |
player_controller.gd |
| Nodes | PascalCase |
PlayerSprite |
| Exports | snake_case |
@export var max_health |
| Private members | _ prefix |
var _current_health |
| Signals | past-tense snake_case |
signal health_changed |
| Stable refs | %SceneUniqueNames |
%Hitbox |
C# exception: PascalCase class/file match.
Feature folder layout
/project.godot
/common/
/entities/player/
/ui/main_menu/
/levels/
/addons/Version control
.gitignore— ignore.godot/(use project_bootstrapper.gd; starter ignore file:godot.gitignorebeside this skill’sSKILL.md)..gdignoreon raw.psd/.blendsource drops.
Typed GDScript 2.0 migration
:=when RHS type is obvious.Array[Enemy],Dictionary[StringName, float].- Explicit
-> voidreturn types. as Timerfor safe casts.- Project Settings → Debug → GDScript → Untyped Declaration =
WarnorError.
Full guide: godot-gdscript-mastery.
Expert: threaded scene manager
MANDATORY async_resource_loader.gd — do not paste duplicate SceneManager samples.
func load_scene(path: String) -> void:
if ResourceLoader.load_threaded_request(path) == OK:
set_process(true)
func _process(_delta: float) -> void:
var progress := []
match ResourceLoader.load_threaded_get_status(_target_path, progress):
ResourceLoader.THREAD_LOAD_IN_PROGRESS:
progress_updated.emit(progress[0] * 100.0)
ResourceLoader.THREAD_LOAD_LOADED:
var scene := ResourceLoader.load_threaded_get(_target_path) as PackedScene
get_tree().change_scene_to_packed(scene)
set_process(false)Expert: global event bus
MANDATORY global_event_bus.gd.
# Publisher: EventBus.player_died.emit()
# Subscriber: EventBus.player_died.connect(_on_player_death)Expert: project metadata Resource
build_metadata_provider.gd / base_data_resource.gd:
class_name ProjectMetadata extends Resource
@export var version: String = "1.0.0"
static func load_metadata(path: String = "user://metadata.res") -> ProjectMetadata:
if ResourceLoader.exists(path):
return ResourceLoader.load(path) as ProjectMetadata
return ProjectMetadata.new()Godot 4.7 foundations
- Asset Store replaces Asset Library for third-party discovery.
- Default stretch
canvas_items+expand— test UI on new projects.
Workflow: new project
project.godot+ project_bootstrapper.gd folders.- Godot-aware
.gitignore. - README documenting feature-based layout.
- Register Autoloads only after ownership decision tree (SKILL.md).