namespace ICRebuild.Core; public readonly struct ActionRangeCheckScope : IDisposable { [ThreadStatic] private static bool active; private readonly bool previous; private ActionRangeCheckScope(bool allowed) { previous=active; active=allowed; } public static ActionRangeCheckScope Enter(bool allowed) => new(allowed); public static bool Active => active; public void Dispose() => active=previous; } public static class TargetRadiusPolicy { // One target radius is used consistently by native drawing, attack checks and gap-closer placement. // Never add the bonus to the player's own radius (which would double the landing displacement). public static float Adjust(GameFrame frame,nint actor,uint entityId,float original,float extra) => frame.Ready && actor!=0 && actor!=frame.LocalAddress && actor==frame.TargetAddress && entityId==frame.TargetEntityId && float.IsFinite(original) && original>=0 ? original+Policies.FiniteClamp(extra,0,5) : original; } public sealed record TargetRadiusObservation(uint EntityId,float Original,float Effective); public readonly struct NativeTargetRingScope : IDisposable { [ThreadStatic] private static bool active; private readonly bool previous; private NativeTargetRingScope(bool allowed) { previous=active; active=allowed; } public static NativeTargetRingScope Enter(bool allowed) => new(allowed); public static bool Active => active; public void Dispose() => active=previous; }