2021-02-11 01:13:03 -08:00
|
|
|
using Robust.Client.GameObjects;
|
|
|
|
|
using Robust.Client.Graphics;
|
2019-12-06 02:08:17 +01:00
|
|
|
using Robust.Shared.Prototypes;
|
|
|
|
|
|
2021-06-09 22:19:39 +02:00
|
|
|
namespace Content.Client.Interactable.Components
|
2019-12-06 02:08:17 +01:00
|
|
|
{
|
|
|
|
|
[RegisterComponent]
|
2023-08-22 18:14:33 -07:00
|
|
|
public sealed partial class InteractionOutlineComponent : Component
|
2019-12-06 02:08:17 +01:00
|
|
|
{
|
2020-08-24 14:10:28 +02:00
|
|
|
[Dependency] private readonly IPrototypeManager _prototypeManager = default!;
|
2021-12-08 12:09:43 +01:00
|
|
|
[Dependency] private readonly IEntityManager _entMan = default!;
|
2020-08-24 14:10:28 +02:00
|
|
|
|
2021-04-19 09:52:40 +02:00
|
|
|
private const float DefaultWidth = 1;
|
2023-08-13 20:26:59 -04:00
|
|
|
|
|
|
|
|
[ValidatePrototypeId<ShaderPrototype>]
|
2020-04-22 17:50:55 +02:00
|
|
|
private const string ShaderInRange = "SelectionOutlineInrange";
|
2023-08-13 20:26:59 -04:00
|
|
|
|
|
|
|
|
[ValidatePrototypeId<ShaderPrototype>]
|
2020-04-22 17:50:55 +02:00
|
|
|
private const string ShaderOutOfRange = "SelectionOutline";
|
2023-08-13 20:26:59 -04:00
|
|
|
|
2021-04-19 09:52:40 +02:00
|
|
|
private bool _inRange;
|
|
|
|
|
private ShaderInstance? _shader;
|
|
|
|
|
private int _lastRenderScale;
|
2019-12-06 02:08:17 +01:00
|
|
|
|
2023-10-19 12:34:31 -07:00
|
|
|
public void OnMouseEnter(EntityUid uid, bool inInteractionRange, int renderScale)
|
2019-12-06 02:08:17 +01:00
|
|
|
{
|
2021-04-19 09:52:40 +02:00
|
|
|
_lastRenderScale = renderScale;
|
|
|
|
|
_inRange = inInteractionRange;
|
2023-10-19 12:34:31 -07:00
|
|
|
if (_entMan.TryGetComponent(uid, out SpriteComponent? sprite) && sprite.PostShader == null)
|
2019-12-06 02:08:17 +01:00
|
|
|
{
|
2022-07-15 14:28:51 +12:00
|
|
|
// TODO why is this creating a new instance of the outline shader every time the mouse enters???
|
|
|
|
|
_shader = MakeNewShader(inInteractionRange, renderScale);
|
|
|
|
|
sprite.PostShader = _shader;
|
2019-12-06 02:08:17 +01:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2023-10-19 12:34:31 -07:00
|
|
|
public void OnMouseLeave(EntityUid uid)
|
2019-12-06 02:08:17 +01:00
|
|
|
{
|
2023-10-19 12:34:31 -07:00
|
|
|
if (_entMan.TryGetComponent(uid, out SpriteComponent? sprite))
|
2019-12-06 02:08:17 +01:00
|
|
|
{
|
2022-07-15 14:28:51 +12:00
|
|
|
if (sprite.PostShader == _shader)
|
|
|
|
|
sprite.PostShader = null;
|
2019-12-06 02:08:17 +01:00
|
|
|
sprite.RenderOrder = 0;
|
|
|
|
|
}
|
2021-04-19 09:52:40 +02:00
|
|
|
|
|
|
|
|
_shader?.Dispose();
|
|
|
|
|
_shader = null;
|
2019-12-06 02:08:17 +01:00
|
|
|
}
|
|
|
|
|
|
2023-10-19 12:34:31 -07:00
|
|
|
public void UpdateInRange(EntityUid uid, bool inInteractionRange, int renderScale)
|
2019-12-06 02:08:17 +01:00
|
|
|
{
|
2023-10-19 12:34:31 -07:00
|
|
|
if (_entMan.TryGetComponent(uid, out SpriteComponent? sprite)
|
2022-07-15 14:28:51 +12:00
|
|
|
&& sprite.PostShader == _shader
|
2021-04-19 09:52:40 +02:00
|
|
|
&& (inInteractionRange != _inRange || _lastRenderScale != renderScale))
|
2019-12-06 02:08:17 +01:00
|
|
|
{
|
2021-04-19 09:52:40 +02:00
|
|
|
_inRange = inInteractionRange;
|
|
|
|
|
_lastRenderScale = renderScale;
|
2022-07-15 14:28:51 +12:00
|
|
|
|
2021-04-19 09:52:40 +02:00
|
|
|
_shader = MakeNewShader(_inRange, _lastRenderScale);
|
|
|
|
|
sprite.PostShader = _shader;
|
2019-12-06 02:08:17 +01:00
|
|
|
}
|
|
|
|
|
}
|
2021-04-19 09:52:40 +02:00
|
|
|
|
|
|
|
|
private ShaderInstance MakeNewShader(bool inRange, int renderScale)
|
|
|
|
|
{
|
|
|
|
|
var shaderName = inRange ? ShaderInRange : ShaderOutOfRange;
|
|
|
|
|
|
|
|
|
|
var instance = _prototypeManager.Index<ShaderPrototype>(shaderName).InstanceUnique();
|
|
|
|
|
instance.SetParameter("outline_width", DefaultWidth * renderScale);
|
|
|
|
|
return instance;
|
|
|
|
|
}
|
2019-12-06 02:08:17 +01:00
|
|
|
}
|
|
|
|
|
}
|