Fix pinpointer flicker (#15452)
This commit is contained in:
@@ -1,57 +1,60 @@
|
||||
using Robust.Shared.GameStates;
|
||||
using Robust.Shared.Serialization;
|
||||
|
||||
namespace Content.Shared.Pinpointer
|
||||
namespace Content.Shared.Pinpointer;
|
||||
|
||||
/// <summary>
|
||||
/// Displays a sprite on the item that points towards the target component.
|
||||
/// </summary>
|
||||
[RegisterComponent, NetworkedComponent]
|
||||
[AutoGenerateComponentState]
|
||||
[Access(typeof(SharedPinpointerSystem))]
|
||||
public sealed partial class PinpointerComponent : Component
|
||||
{
|
||||
// TODO: Type serializer oh god
|
||||
[DataField("component")]
|
||||
public string? Component;
|
||||
|
||||
[DataField("mediumDistance"), ViewVariables(VVAccess.ReadWrite)]
|
||||
public float MediumDistance = 16f;
|
||||
|
||||
[DataField("closeDistance"), ViewVariables(VVAccess.ReadWrite)]
|
||||
public float CloseDistance = 8f;
|
||||
|
||||
[DataField("reachedDistance"), ViewVariables(VVAccess.ReadWrite)]
|
||||
public float ReachedDistance = 1f;
|
||||
|
||||
/// <summary>
|
||||
/// Displays a sprite on the item that points towards the target component.
|
||||
/// Pinpointer arrow precision in radians.
|
||||
/// </summary>
|
||||
[RegisterComponent]
|
||||
[NetworkedComponent]
|
||||
[Access(typeof(SharedPinpointerSystem))]
|
||||
public sealed class PinpointerComponent : Component
|
||||
{
|
||||
// TODO: Type serializer oh god
|
||||
[DataField("component")]
|
||||
public string? Component;
|
||||
[DataField("precision"), ViewVariables(VVAccess.ReadWrite)]
|
||||
public double Precision = 0.09;
|
||||
|
||||
[DataField("mediumDistance")]
|
||||
public float MediumDistance = 16f;
|
||||
[ViewVariables]
|
||||
public EntityUid? Target = null;
|
||||
|
||||
[DataField("closeDistance")]
|
||||
public float CloseDistance = 8f;
|
||||
[ViewVariables]
|
||||
[AutoNetworkedField]
|
||||
public bool IsActive = false;
|
||||
|
||||
[DataField("reachedDistance")]
|
||||
public float ReachedDistance = 1f;
|
||||
[ViewVariables]
|
||||
[AutoNetworkedField]
|
||||
public Angle ArrowAngle;
|
||||
|
||||
/// <summary>
|
||||
/// Pinpointer arrow precision in radians.
|
||||
/// </summary>
|
||||
[DataField("precision")]
|
||||
public double Precision = 0.09;
|
||||
[ViewVariables]
|
||||
[AutoNetworkedField]
|
||||
public Distance DistanceToTarget = Distance.Unknown;
|
||||
|
||||
public EntityUid? Target = null;
|
||||
public bool IsActive = false;
|
||||
public Angle ArrowAngle;
|
||||
public Distance DistanceToTarget = Distance.Unknown;
|
||||
public bool HasTarget => DistanceToTarget != Distance.Unknown;
|
||||
}
|
||||
|
||||
[Serializable, NetSerializable]
|
||||
public sealed class PinpointerComponentState : ComponentState
|
||||
{
|
||||
public bool IsActive;
|
||||
public Angle ArrowAngle;
|
||||
public Distance DistanceToTarget;
|
||||
}
|
||||
|
||||
[Serializable, NetSerializable]
|
||||
public enum Distance : byte
|
||||
{
|
||||
Unknown,
|
||||
Reached,
|
||||
Close,
|
||||
Medium,
|
||||
Far
|
||||
}
|
||||
[ViewVariables]
|
||||
public bool HasTarget => DistanceToTarget != Distance.Unknown;
|
||||
}
|
||||
|
||||
[Serializable, NetSerializable]
|
||||
public enum Distance : byte
|
||||
{
|
||||
Unknown,
|
||||
Reached,
|
||||
Close,
|
||||
Medium,
|
||||
Far
|
||||
}
|
||||
|
||||
@@ -1,86 +1,52 @@
|
||||
using Robust.Shared.GameStates;
|
||||
namespace Content.Shared.Pinpointer;
|
||||
|
||||
namespace Content.Shared.Pinpointer
|
||||
public abstract class SharedPinpointerSystem : EntitySystem
|
||||
{
|
||||
public abstract class SharedPinpointerSystem : EntitySystem
|
||||
/// <summary>
|
||||
/// Manually set distance from pinpointer to target
|
||||
/// </summary>
|
||||
public void SetDistance(EntityUid uid, Distance distance, PinpointerComponent? pinpointer = null)
|
||||
{
|
||||
public override void Initialize()
|
||||
{
|
||||
base.Initialize();
|
||||
SubscribeLocalEvent<PinpointerComponent, ComponentGetState>(GetCompState);
|
||||
}
|
||||
if (!Resolve(uid, ref pinpointer))
|
||||
return;
|
||||
|
||||
private void GetCompState(EntityUid uid, PinpointerComponent pinpointer, ref ComponentGetState args)
|
||||
{
|
||||
args.State = new PinpointerComponentState
|
||||
{
|
||||
IsActive = pinpointer.IsActive,
|
||||
ArrowAngle = pinpointer.ArrowAngle,
|
||||
DistanceToTarget = pinpointer.DistanceToTarget
|
||||
};
|
||||
}
|
||||
if (distance == pinpointer.DistanceToTarget)
|
||||
return;
|
||||
|
||||
/// <summary>
|
||||
/// Manually set distance from pinpointer to target
|
||||
/// </summary>
|
||||
public void SetDistance(EntityUid uid, Distance distance, PinpointerComponent? pinpointer = null)
|
||||
{
|
||||
if (!Resolve(uid, ref pinpointer))
|
||||
return;
|
||||
pinpointer.DistanceToTarget = distance;
|
||||
Dirty(pinpointer);
|
||||
}
|
||||
|
||||
if (distance == pinpointer.DistanceToTarget)
|
||||
return;
|
||||
/// <summary>
|
||||
/// Try to manually set pinpointer arrow direction.
|
||||
/// If difference between current angle and new angle is smaller than
|
||||
/// pinpointer precision, new value will be ignored and it will return false.
|
||||
/// </summary>
|
||||
public bool TrySetArrowAngle(EntityUid uid, Angle arrowAngle, PinpointerComponent? pinpointer = null)
|
||||
{
|
||||
if (!Resolve(uid, ref pinpointer))
|
||||
return false;
|
||||
|
||||
pinpointer.DistanceToTarget = distance;
|
||||
Dirty(pinpointer);
|
||||
}
|
||||
if (pinpointer.ArrowAngle.EqualsApprox(arrowAngle, pinpointer.Precision))
|
||||
return false;
|
||||
|
||||
/// <summary>
|
||||
/// Try to manually set pinpointer arrow direction.
|
||||
/// If difference between current angle and new angle is smaller than
|
||||
/// pinpointer precision, new value will be ignored and it will return false.
|
||||
/// </summary>
|
||||
public bool TrySetArrowAngle(EntityUid uid, Angle arrowAngle, PinpointerComponent? pinpointer = null)
|
||||
{
|
||||
if (!Resolve(uid, ref pinpointer))
|
||||
return false;
|
||||
pinpointer.ArrowAngle = arrowAngle;
|
||||
Dirty(pinpointer);
|
||||
|
||||
if (pinpointer.ArrowAngle.EqualsApprox(arrowAngle, pinpointer.Precision))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
pinpointer.ArrowAngle = arrowAngle;
|
||||
Dirty(pinpointer);
|
||||
/// <summary>
|
||||
/// Activate/deactivate pinpointer screen. If it has target it will start tracking it.
|
||||
/// </summary>
|
||||
public void SetActive(EntityUid uid, bool isActive, PinpointerComponent? pinpointer = null)
|
||||
{
|
||||
if (!Resolve(uid, ref pinpointer))
|
||||
return;
|
||||
if (isActive == pinpointer.IsActive)
|
||||
return;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Activate/deactivate pinpointer screen. If it has target it will start tracking it.
|
||||
/// </summary>
|
||||
public void SetActive(EntityUid uid, bool isActive, PinpointerComponent? pinpointer = null)
|
||||
{
|
||||
if (!Resolve(uid, ref pinpointer))
|
||||
return;
|
||||
if (isActive == pinpointer.IsActive)
|
||||
return;
|
||||
|
||||
pinpointer.IsActive = isActive;
|
||||
Dirty(pinpointer);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Toggle Pinpointer screen. If it has target it will start tracking it.
|
||||
/// </summary>
|
||||
/// <returns>True if pinpointer was activated, false otherwise</returns>
|
||||
public bool TogglePinpointer(EntityUid uid, PinpointerComponent? pinpointer = null)
|
||||
{
|
||||
if (!Resolve(uid, ref pinpointer))
|
||||
return false;
|
||||
|
||||
var isActive = !pinpointer.IsActive;
|
||||
SetActive(uid, isActive, pinpointer);
|
||||
return isActive;
|
||||
}
|
||||
pinpointer.IsActive = isActive;
|
||||
Dirty(pinpointer);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user