Component System Overview
What is a Component?
Components are modular pieces of functionality that can be attached to units to give them specific capabilities. Rather than building units through inheritance, you compose them from components.
Component-Based Architecture Benefits
- Modularity - Each component handles one responsibility
- Reusability - Use the same components on different unit types
- Flexibility - Mix and match components to create varied units
- Testability - Components can be tested independently
- Performance - Only required components are active
Base Component Class
All components extend from the base class RTS_Component, which always has a reference to its entity (usually the parent).
func fetch_entity() -> RTS_Entity:
return get_parent() as RTS_Entity
and can be turned on and off:
func set_component_inactive():
component_is_active = false
func set_component_active():
assert(!component_is_active,"RTS_Component set active twice. You're game logic is probably flawed.")
component_is_active = true
If not required otherwise, leaving set_component_active_on_ready set to true is usually the right choice.
RTS_Component is the main building block for creating modular and scalable, yet unique entity behaviors. For developers wanting to adopt this framework, it is recommended to create your own unique components which add features and complexity to entities by extending this base class.
Here we briefly introduce the most common components that are included in the RTS Entity Controller.
Note that RTS_Ability and many other scripts (such as RTS_Weapon) also inherit from RTS_Component.
Common Components
Selection & Interaction
- SelectableComponent - Make units clickable and selectable
- [BoxableComponent] - Enable box selection support, see SelectableComponent
- [PickablePhysics] - Enables clicking units to select using raycast, see SelectableComponent
Movement & Navigation
- MovableComponent - Unit movement and pathfinding
Health & Combat
- HealthComponent - Hit points and health management
- DefenseComponent - Armor and damage reduction
- Attack components - See Attack System
Visuals & Animation
- VisualComponent - Rendering and visibility
- [AnimationTreeComponent] - AnimationTree and AnimationPlayer integration. Also see Attack System
Example: ExampleUnit.tscn
As alluded to in Entity System, components usually (but not always) sit as direct children underneath the entity:
ExampleUnit (RTS_Entity)
├── (...)
├── SelectableComponent
├── MovableComponent
├── HealthComponent
├── DefenseComponent
├── AnimationTreeComponent
Creating Custom Components
Creating custom components is as easy as inheriting from RTS_Component. The easiest thing to forget is to properly implement
func set_component_inactive()
func set_component_active()
so that components can be turned off which should disable any heavy computation or update loops.
Next Steps
- Learn about specific components in the detailed guides
- Selectable Component
- Movable Component
- Creating custom abilities