cirnogodot/Scripts/Actors/ScriptableBulletsEmitter3D.cs

149 lines
4.1 KiB
C#
Raw Normal View History

using System;
using Cirno.Scripts.AttackPatterns;
2025-06-20 15:39:19 +02:00
using Cirno.Scripts.Resources;
using Cirno.Scripts.Resources.BulletScripts;
using Godot;
using Godot.Collections;
2025-06-20 15:39:19 +02:00
namespace Cirno.Scripts.Actors;
[Tool]
public partial class ScriptableBulletsEmitter3D : Destructible3D, IActivable, IScriptHost3D
2025-06-20 15:39:19 +02:00
{
public Node3D ParentObject => this;
2025-07-07 12:06:27 +02:00
2025-06-20 15:39:19 +02:00
[Export]
public BulletScript3D Script { get; set; }
2025-07-07 12:06:27 +02:00
[Export] public string ActivationGroup { get; set; }
2025-06-20 15:39:19 +02:00
[Export]
public bool InvertSignal { get; private set; } = false;
[Export]
public bool EmitOnStart { get; set; } = false;
2025-10-09 09:11:25 +02:00
[Export]
public bool IndestructibleWhileDisabled { get; set; } = true;
// [Export] public bool Indestructible { get; private set; } = false;
// [Export] public float Health = 1f;
//
// [Export] public BulletResource ExplosionData { get; set; }
// [Export] public BulletOwner BulletGroup { get; set; } = BulletOwner.None;
// [Export] public Array<DamageResistance> DamageResistances { get; set; } = [];
2025-06-20 15:39:19 +02:00
[Signal]
public delegate void StateChangedEventHandler(bool isEmitting);
2025-10-09 09:11:25 +02:00
2025-06-20 15:39:19 +02:00
private bool _isActive = false;
//private BulletScript _scriptInstance;
protected BulletScript3D.BulletScriptMachine ScriptMachine;
public override void _Ready()
{
if (Engine.IsEditorHint()) return;
2025-09-22 18:19:40 +02:00
if (Script is null)
{
GD.PushWarning($"Emitter {Name} has no script assigned");
return;
}
2025-06-20 15:39:19 +02:00
//_scriptInstance = Script.Duplicate(true) as BulletScript;
2025-07-07 12:06:27 +02:00
if (!string.IsNullOrWhiteSpace(ActivationGroup))
{
this.AddToGroup(ActivationGroup);
}
2025-06-20 15:39:19 +02:00
ScriptMachine = Script.Make(this);
_homePosition = this.GlobalPosition;
if (EmitOnStart)
{
_isActive = true;
ScriptMachine.Start();
}
2025-10-09 09:11:25 +02:00
EmitSignalStateChanged(_isActive);
//EmitSignal(SignalName.StateChanged, _isActive);
2025-06-20 15:39:19 +02:00
}
public override void _func_godot_apply_properties(Dictionary<string, Variant> props)
{
ActivationGroup = props["targetname"].AsString();
var scriptPath = props["script_path"].AsString();
if (!string.IsNullOrWhiteSpace(scriptPath))
{
Script = GD.Load<BulletScript3D>(scriptPath);
}
else
{
2025-09-01 16:13:14 +02:00
GD.PushWarning($"Emitter {this.Name} {this.ActivationGroup} has no script assigned");
}
EmitOnStart = props["emit_on_start"].AsBool();
InvertSignal = props["invert_signal"].AsBool();
//TargetFunc = props["targetfunc"];
//TargetName = props["targetname"];
SetProperties(props);
}
2025-06-20 15:39:19 +02:00
public bool Activate(ActivationType activationType = ActivationType.Toggle)
{
if (Engine.IsEditorHint()) return false;
2025-06-20 15:39:19 +02:00
switch (activationType)
{
case ActivationType.Use:
case ActivationType.Toggle:
_isActive = !_isActive;
break;
case ActivationType.Open:
case ActivationType.Enable:
_isActive = !InvertSignal;
break;
case ActivationType.Close:
case ActivationType.Disable:
_isActive = InvertSignal;
break;
case ActivationType.Destroy:
_isActive = InvertSignal;
// TODO: Explode
break;
}
if (_isActive)
{
ScriptMachine.Start();
}
2025-10-09 09:11:25 +02:00
EmitSignalStateChanged(_isActive);
//EmitSignal(SignalName.StateChanged, _isActive);
2025-06-20 15:39:19 +02:00
return true;
}
public void Toggle()
{
this.Activate();
}
public override void _Process(double delta)
{
if (Engine.IsEditorHint()) return;
2025-06-20 15:39:19 +02:00
if (!_isActive) return;
ScriptMachine.UpdatePhase(delta);
}
private Vector3 _homePosition;
public Vector3 HomePosition => _homePosition;
public void ChangeSpriteDirection(Vector2 direction)
{
}
}