using Godot; using System; public partial class Joystick : Control { private Vector2 _startTouchPos = Vector2.Zero; private Vector2 _currentTouchPos = Vector2.Zero; private bool _touching = false; [Export] public float DeadzoneRadius = 30f; [Export] public float MaxRadius = 90f; public override void _GuiInput(InputEvent @event) { if (@event is InputEventScreenTouch touch) { if (touch.Pressed) { _touching = true; _startTouchPos = touch.Position; _currentTouchPos = touch.Position; } else { _touching = false; } } else if (@event is InputEventScreenDrag drag && _touching) { _currentTouchPos = drag.Position; } } public Vector2 GetDirection() { if (!_touching) return Vector2.Zero; Vector2 offset = _currentTouchPos - _startTouchPos; if (offset.Length() < DeadzoneRadius) return Vector2.Zero; return offset.Normalized() * Mathf.Min(offset.Length(), MaxRadius); } public override void _Draw() { Vector2 center = new Vector2(0, 0); Vector2 handleOffset = _touching ? (_currentTouchPos - _startTouchPos).Normalized() * Mathf.Min((_currentTouchPos - _startTouchPos).Length(), MaxRadius) : Vector2.Zero; DrawCircle(center, MaxRadius, new Color(1, 1, 1, 1), false); DrawCircle(center, DeadzoneRadius, new Color(1, 1, 0, 1), false); DrawCircle(center + handleOffset, DeadzoneRadius, new Color(1, 1, 1, 0.3f), false); // 当前触点 } public override void _Process(double delta) { QueueRedraw(); } }