Files
przygody-pana-cegly/scripts/components/PlayerController.cs

112 lines
3.2 KiB
C#

using System.Collections.Generic;
using Godot;
using Mr.BrickAdventures.Autoloads;
using Mr.BrickAdventures.scripts.Resources;
namespace Mr.BrickAdventures.scripts.components;
[GlobalClass]
public partial class PlayerController : CharacterBody2D
{
[Export] private Node MovementAbilitiesContainer { get; set; }
[Export] public MovementPreset DefaultPreset { get; set; }
[Signal] public delegate void JumpInitiatedEventHandler();
[Signal] public delegate void MovementAbilitiesChangedEventHandler();
public Vector2 LastDirection { get; private set; } = Vector2.Right;
public Vector2 PreviousVelocity { get; private set; } = Vector2.Zero;
private List<MovementAbility> _abilities = [];
private PlayerInputHandler _inputHandler;
public IReadOnlyList<MovementAbility> GetActiveAbilities() => _abilities;
public override void _Ready()
{
SkillManager.Instance?.RegisterPlayer(this);
// Wire HealthComponent signals to global EventBus events
var health = GetNodeOrNull<HealthComponent>("HealthComponent");
if (health != null)
{
health.Death += () => EventBus.EmitPlayerDied(GlobalPosition);
health.HealthChanged += (delta, total) =>
{
if (delta < 0f) EventBus.EmitPlayerDamaged(Mathf.Abs(delta), total, GlobalPosition);
else EventBus.EmitPlayerHealed(delta, total, GlobalPosition);
};
}
_inputHandler = GetNode<PlayerInputHandler>("PlayerInputHandler");
if (DefaultPreset != null)
ApplyPreset(DefaultPreset);
EmitSignalMovementAbilitiesChanged();
EventBus.EmitPlayerSpawned(this);
}
public override void _PhysicsProcess(double delta)
{
var velocity = Velocity;
foreach (var ability in _abilities)
{
velocity = ability.ProcessMovement(velocity, delta);
}
if (_inputHandler.MoveDirection.X != 0)
{
LastDirection = new Vector2(_inputHandler.MoveDirection.X > 0 ? 1 : -1, 0);
}
PreviousVelocity = Velocity;
Velocity = velocity;
MoveAndSlide();
}
public void ApplyPreset(MovementPreset preset)
{
if (preset == null) return;
ClearMovementAbilities();
Velocity = Vector2.Zero;
foreach (var scene in preset.Abilities)
{
if (scene != null)
AddAbility(scene.Instantiate<MovementAbility>());
}
EmitSignalMovementAbilitiesChanged();
}
public void AddAbility(MovementAbility ability)
{
MovementAbilitiesContainer.AddChild(ability);
ability.Initialize(this);
_abilities.Add(ability);
}
public void ClearMovementAbilities()
{
foreach (var ability in _abilities)
{
ability.QueueFree();
}
_abilities.Clear();
}
public void RemoveAbility<T>() where T : MovementAbility
{
for (var i = _abilities.Count - 1; i >= 0; i--)
{
if (_abilities[i] is T)
{
var ability = _abilities[i];
_abilities.RemoveAt(i);
ability.QueueFree();
break;
}
}
}
}