cirnogodot/Scripts/Interactables/3D/AnimatedSwitch3D.cs
2025-07-09 12:00:23 +02:00

124 lines
No EOL
2.8 KiB
C#

using Godot;
using Godot.Collections;
namespace Cirno.Scripts.Interactables._3D;
[Tool]
public partial class AnimatedSwitch3D : Switch3D
{
[Export] public DoorState State { get; set; } = DoorState.Closed;
[Signal]
public delegate void OpeningEventHandler();
[Signal]
public delegate void ClosingEventHandler();
[Signal]
public delegate void SetClosedEventHandler();
[Signal]
public delegate void SetOpenEventHandler();
private bool _isAnimating = false;
public override void _Ready()
{
if (Engine.IsEditorHint()) return;
base._Ready();
SyncAnimation();
}
public override void _func_godot_apply_properties(Dictionary<string, Variant> props)
{
base._func_godot_apply_properties(props);
// TargetGroup = props["target"].AsString();
// if (props.TryGetValue("key", out var prop))
// {
// RequirementKeys = [prop.AsString()];
// }
// if (props.TryGetValue("activationtype", out var type))
// {
// var t = Enum.TryParse(type, true, out ActivationType activationType);
// if (t)
// {
// ActivationType = activationType;
// }
// }
var startEnabled = props["start_enabled"].AsBool();
State = startEnabled ? DoorState.Open : DoorState.Closed;
}
private void SyncAnimation()
{
if (State is DoorState.Closed)
{
EmitSignalSetClosed();
}
else
{
EmitSignalSetOpen();
}
}
public void ClosedAnimationFinished()
{
State = DoorState.Closed;
_isAnimating = false;
}
public void OpenAnimationFinished()
{
State = DoorState.Open;
_isAnimating = false;
}
private void ChangeState(DoorState newState)
{
if (_isAnimating) return;
if (State == newState) return;
switch (newState)
{
case DoorState.Open:
EmitSignalOpening();
break;
case DoorState.Closed:
EmitSignalClosing();
break;
}
_isAnimating = true;
}
public override bool Activate(ActivationType activationType = ActivationType.Toggle)
{
if (_isAnimating) return false;
switch (State)
{
case DoorState.Closed:
if (base.Activate(ActivationType.Open))
{
ChangeState(DoorState.Open);
return true;
}
break;
case DoorState.Open:
if (base.Activate(ActivationType.Close))
{
ChangeState(DoorState.Closed);
return true;
}
break;
}
return false;
}
}