43 lines
1.6 KiB
C#
43 lines
1.6 KiB
C#
|
|
using Godot;
|
||
|
|
using Theriapolis.Core;
|
||
|
|
|
||
|
|
namespace Theriapolis.GodotHost.Rendering;
|
||
|
|
|
||
|
|
/// <summary>
|
||
|
|
/// Player marker — small dot with a thin facing tick. Drawn at
|
||
|
|
/// <see cref="C.PLAYER_MARKER_SCREEN_PX"/>/2 wp; the owner sets
|
||
|
|
/// <see cref="Node2D.Scale"/> = 1/zoom every frame so the on-screen size
|
||
|
|
/// stays constant across the seamless zoom range.
|
||
|
|
///
|
||
|
|
/// Mirrors the MonoGame PlayerSprite's visual vocabulary — dark outline,
|
||
|
|
/// faction-red fill, optional facing tick. Phase-7-styled `PlayerSprite`
|
||
|
|
/// proper (walking animation frames) lands later.
|
||
|
|
/// </summary>
|
||
|
|
public partial class PlayerMarker : Node2D
|
||
|
|
{
|
||
|
|
private const float RadiusWorldPx = C.PLAYER_MARKER_SCREEN_PX * 0.5f;
|
||
|
|
private const float FacingTickPx = RadiusWorldPx * 1.4f;
|
||
|
|
|
||
|
|
/// <summary>Facing direction in radians; 0 = +X. Drives the optional
|
||
|
|
/// tick rendered on the body's leading edge.</summary>
|
||
|
|
public float FacingAngleRad { get; set; }
|
||
|
|
|
||
|
|
/// <summary>When true, draws a small tick at the leading edge so the
|
||
|
|
/// player can read facing without a full sprite. Hidden at low zoom
|
||
|
|
/// to avoid clutter.</summary>
|
||
|
|
public bool ShowFacingTick { get; set; } = true;
|
||
|
|
|
||
|
|
public override void _Draw()
|
||
|
|
{
|
||
|
|
DrawCircle(Vector2.Zero, RadiusWorldPx, new Color(0, 0, 0, 0.78f));
|
||
|
|
DrawCircle(Vector2.Zero, RadiusWorldPx * 0.85f, new Color(0.86f, 0.31f, 0.24f));
|
||
|
|
|
||
|
|
if (ShowFacingTick)
|
||
|
|
{
|
||
|
|
var dir = new Vector2(Mathf.Cos(FacingAngleRad), Mathf.Sin(FacingAngleRad));
|
||
|
|
DrawLine(dir * (RadiusWorldPx * 0.4f), dir * FacingTickPx,
|
||
|
|
new Color(1f, 0.96f, 0.86f), width: RadiusWorldPx * 0.18f, antialiased: false);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|