You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
reacted with thumbs up emoji reacted with thumbs down emoji reacted with laugh emoji reacted with hooray emoji reacted with confused emoji reacted with heart emoji reacted with rocket emoji reacted with eyes emoji
Uh oh!
There was an error while loading. Please reload this page.
-
Good question. This is where architecture either stays clean or turns into wiring hell.
Short answer:
There are cleaner patterns.
First: Understand the rule
A signal does nothing unless something connects to it.
Declaring:
does NOT automatically notify anyone.
Godot will never auto-connect across scenes.
So the real question becomes:
Pattern 1 — Parent wires child (most common, clean)
Component emits.
Parent listens.
Example:
Parent:
Why this is good
You must connect once per usage — but it’s clean.
Pattern 2 — Self-connecting component (when appropriate)
Sometimes a component depends on another component.
Example:
This removes wiring from parent.
Otherwise this becomes hidden coupling.
Pattern 3 — Auto-connect by convention (cleanest for components)
This is my recommendation for you.
Component emits signal.
Parent does NOT manually wire specific functions.
Instead:
This scales:
Pattern 4 — Editor connection (low code, high coupling)
In the editor:
Good for UI.
Not great for reusable gameplay components.
Pattern 5 — Global event bus (advanced)
Autoload:
Components emit:
Systems listen globally.
Good for:
Not for local combat.
What you SHOULD do in your current project
For gameplay components (HealthComp, MovementComp, etc.):
Use Pattern 1.
Parent wires child in
_ready().It is explicit.
It is predictable.
It is not heavy.
It scales fine.
You are not building a reactive framework.
You are building a game.
Important mental model
Signals are not magic binding.
They are just:
Someone must choose to care.
Final answer
Yes, you must connect signals.
No, there is no automatic connection.
The clean way:
_ready()If you want, next we can:
Good.
Now you’re asking the right architectural question.
You’re worried that:
Correct instinct.
And the answer is:
👉 If the parent needs component internals, your signal direction is wrong.
The Core Rule (Important)
A component should:
The parent should:
If the parent is manipulating
_currentHP, armor, etc.You’ve broken encapsulation.
In your specific case
You have:
That function lives in
HealthComp.Good.
That means:
So far so good.
Where you’re going wrong conceptually
You’re thinking the parent must define:
But that’s only true if:
It doesn’t have to be.
Correct Architecture (simple and clean)
Let the component connect to what hits it
Instead of:
Do:
So in enemy:
Now:
Even Better (cleaner still)
Remove
_on_basic_enemy_hitentirely.Just connect directly:
If signature matches.
Now:
When should parent handle signals?
Only when:
Example:
That’s correct ownership.
What you must avoid
Parent doing:
or
Parent recalculating max HP.
That kills component isolation.
So your fear is valid — but misapplied
You don’t need to move variables to parent.
You need to:
Short Answer
No — you do NOT need to move component variables to parent.
If you feel like you must, it means:
Connect the emitter directly to the component that cares.
If you want, we can:
Tell me which direction you want.
Good. That’s a precise requirement.
You’re fine with the parent doing wiring,
you just don’t want this:
That’s reasonable. You want wiring without logic living in the parent.
The clean solution
You don’t need a parent handler function.
You can connect directly to the sibling’s method.
Instead of:
Do this:
That’s it.
No wrapper function.
No glue logic.
No duplication.
Even cleaner (multiple listeners)
If multiple components should react:
Parent only wires.
Components own behavior.
Why this is correct architecture
Parent becomes a mediator, not a logic holder.
That’s good design.
If you want even less visual noise
You can group connections:
Still no parent logic.
Important boundary
Parent should:
Parent should NOT:
You’re on the right side of that boundary.
Final answer
Yes — let the parent connect signals.
No — you do not need wrapper functions.
Just do:
That’s the cleanest version of what you want.
If you want next:
Tell me which direction.
Beta Was this translation helpful? Give feedback.
All reactions