Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Station AI #1423

Merged
merged 27 commits into from
Jan 11, 2025
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
d8ae58e
Station AI (#30944)
metalgearsloth Aug 28, 2024
c866ffb
Verb tweaks (#31309)
metalgearsloth Aug 25, 2024
d6b0b99
ItemToggle + slots stuff (#31312)
metalgearsloth Aug 25, 2024
56451fa
Station AI (#30944)
ElectroJr Jun 18, 2024
bdafdeb
Move SleepingSystem to Shared & cleanup (#28672)
Tayrtahn Jun 14, 2024
ede16f0
Potentially re-add EE changes?
sleepyyapril Jan 4, 2025
661bdba
Fix build errors
sleepyyapril Jan 4, 2025
006acf3
Add ContainerComp (#31311)
metalgearsloth Aug 25, 2024
b7e34aa
Localize ai dataset names (#33608)
MilenVolf Dec 6, 2024
b8e2844
Add LocalizedDatasetPrototype (#28310)
Tayrtahn May 28, 2024
c9e0e5d
SetStationAiName for testing
sleepyyapril Jan 4, 2025
0334cc6
Use EntityManager.System<>
sleepyyapril Jan 4, 2025
00adaa3
Re-add improved random sentience event (#29123)
Psychpsyo Aug 18, 2024
b262e8f
no name!
Psychpsyo Sep 8, 2024
385b667
fix shitcode
sleepyyapril Jan 4, 2025
f5e6583
HideSpawnMenu
sleepyyapril Jan 4, 2025
1b7d820
Merge branch 'master' into station-ai
sleepyyapril Jan 4, 2025
1ad367b
Yippee
sleepyyapril Jan 4, 2025
1f416da
Merge branch 'station-ai' of https://github.com/sleepyyapril/Einstein…
sleepyyapril Jan 4, 2025
ca0b40a
The Den Mass Cherry-Pick 01/06/25 (#1443)
angelofallars Jan 5, 2025
975c905
Automatic Changelog Update (#1443)
SimpleStation14 Jan 5, 2025
632cf60
Merge branch 'master' into station-ai
VMSolidus Jan 5, 2025
9c65527
Merge branch 'master' into station-ai
VMSolidus Jan 10, 2025
6941a01
Update dev_map.yml
VMSolidus Jan 11, 2025
5a13b27
How the fuck did AI not have these?
VMSolidus Jan 11, 2025
0b0e9a8
I managed to get both AI Latejoin and Prisoner Latejoin working at th…
metalgearsloth Aug 29, 2024
5242ceb
Make AI Not Spawn With Clothes
VMSolidus Jan 11, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 5 additions & 8 deletions Content.Client/Chat/UI/EmotesMenu.xaml.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,18 +19,15 @@ public sealed partial class EmotesMenu : RadialMenu
[Dependency] private readonly IPrototypeManager _prototypeManager = default!;
[Dependency] private readonly ISharedPlayerManager _playerManager = default!;

private readonly SpriteSystem _spriteSystem;
private readonly EntityWhitelistSystem _whitelistSystem;

public event Action<ProtoId<EmotePrototype>>? OnPlayEmote;

public EmotesMenu()
{
IoCManager.InjectDependencies(this);
RobustXamlLoader.Load(this);

_spriteSystem = _entManager.System<SpriteSystem>();
_whitelistSystem = _entManager.System<EntityWhitelistSystem>();
var spriteSystem = _entManager.System<SpriteSystem>();
var whitelistSystem = _entManager.System<EntityWhitelistSystem>();

var main = FindControl<RadialContainer>("Main");

Expand All @@ -40,8 +37,8 @@ public EmotesMenu()
var player = _playerManager.LocalSession?.AttachedEntity;
if (emote.Category == EmoteCategory.Invalid ||
emote.ChatTriggers.Count == 0 ||
!(player.HasValue && _whitelistSystem.IsWhitelistPassOrNull(emote.Whitelist, player.Value)) ||
_whitelistSystem.IsBlacklistPass(emote.Blacklist, player.Value))
!(player.HasValue && whitelistSystem.IsWhitelistPassOrNull(emote.Whitelist, player.Value)) ||
whitelistSystem.IsBlacklistPass(emote.Blacklist, player.Value))
continue;

if (!emote.Available &&
Expand All @@ -63,7 +60,7 @@ public EmotesMenu()
{
VerticalAlignment = VAlignment.Center,
HorizontalAlignment = HAlignment.Center,
Texture = _spriteSystem.Frame0(emote.Icon),
Texture = spriteSystem.Frame0(emote.Icon),
TextureScale = new Vector2(2f, 2f),
};

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ namespace Content.Client.Silicons.Laws.SiliconLawEditUi;

public sealed class SiliconLawEui : BaseEui
{
public readonly EntityManager _entityManager = default!;
private readonly EntityManager _entityManager;

private SiliconLawUi _siliconLawUi;
private EntityUid _target;
Expand Down
28 changes: 28 additions & 0 deletions Content.Client/Silicons/StationAi/StationAiBoundUserInterface.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
using Content.Shared.Silicons.StationAi;
using Robust.Client.UserInterface;

namespace Content.Client.Silicons.StationAi;

public sealed class StationAiBoundUserInterface : BoundUserInterface
{
private StationAiMenu? _menu;

public StationAiBoundUserInterface(EntityUid owner, Enum uiKey) : base(owner, uiKey)
{
}

protected override void Open()
{
base.Open();
_menu = this.CreateWindow<StationAiMenu>();
_menu.Track(Owner);

_menu.OnAiRadial += args =>
{
SendPredictedMessage(new StationAiRadialMessage()
{
Event = args,
});
};
}
}
13 changes: 13 additions & 0 deletions Content.Client/Silicons/StationAi/StationAiMenu.xaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<ui:RadialMenu xmlns="https://spacestation14.io"
xmlns:ui="clr-namespace:Content.Client.UserInterface.Controls"
BackButtonStyleClass="RadialMenuBackButton"
CloseButtonStyleClass="RadialMenuCloseButton"
VerticalExpand="True"
HorizontalExpand="True"
MinSize="450 450">

<!-- Main -->
<ui:RadialContainer Name="Main" VerticalExpand="True" HorizontalExpand="True" Radius="64" ReserveSpaceForHiddenChildren="False">
</ui:RadialContainer>

</ui:RadialMenu>
128 changes: 128 additions & 0 deletions Content.Client/Silicons/StationAi/StationAiMenu.xaml.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,128 @@
using System.Numerics;
using Content.Client.UserInterface.Controls;
using Content.Shared.Silicons.StationAi;
using Robust.Client.AutoGenerated;
using Robust.Client.GameObjects;
using Robust.Client.Graphics;
using Robust.Client.UserInterface.Controls;
using Robust.Client.UserInterface.XAML;
using Robust.Shared.Timing;

namespace Content.Client.Silicons.StationAi;

[GenerateTypedNameReferences]
public sealed partial class StationAiMenu : RadialMenu
{
[Dependency] private readonly IClyde _clyde = default!;
[Dependency] private readonly IEntityManager _entManager = default!;
[Dependency] private readonly IEyeManager _eyeManager = default!;

public event Action<BaseStationAiAction>? OnAiRadial;

private EntityUid _tracked;

public StationAiMenu()
{
IoCManager.InjectDependencies(this);
RobustXamlLoader.Load(this);
}

public void Track(EntityUid owner)
{
_tracked = owner;

if (!_entManager.EntityExists(_tracked))
{
Close();
return;
}

BuildButtons();
UpdatePosition();
}

private void BuildButtons()
{
var ev = new GetStationAiRadialEvent();
_entManager.EventBus.RaiseLocalEvent(_tracked, ref ev);

var main = FindControl<RadialContainer>("Main");
main.DisposeAllChildren();
var sprites = _entManager.System<SpriteSystem>();

foreach (var action in ev.Actions)
{
// TODO: This radial boilerplate is quite annoying
var button = new StationAiMenuButton(action.Event)
{
StyleClasses = { "RadialMenuButton" },
SetSize = new Vector2(64f, 64f),
ToolTip = action.Tooltip != null ? Loc.GetString(action.Tooltip) : null,
};

if (action.Sprite != null)
{
var texture = sprites.Frame0(action.Sprite);
var scale = Vector2.One;

if (texture.Width <= 32)
{
scale *= 2;
}

var tex = new TextureRect
{
VerticalAlignment = VAlignment.Center,
HorizontalAlignment = HAlignment.Center,
Texture = texture,
TextureScale = scale,
};

button.AddChild(tex);
}

button.OnPressed += args =>
{
OnAiRadial?.Invoke(action.Event);
Close();
};
main.AddChild(button);
}
}

protected override void FrameUpdate(FrameEventArgs args)
{
base.FrameUpdate(args);
UpdatePosition();
}

private void UpdatePosition()
{
if (!_entManager.TryGetComponent(_tracked, out TransformComponent? xform))
{
Close();
return;
}

if (!xform.Coordinates.IsValid(_entManager))
{
Close();
return;
}

var coords = _entManager.System<SpriteSystem>().GetSpriteScreenCoordinates((_tracked, null, xform));

if (!coords.IsValid)
{
Close();
return;
}

OpenScreenAt(coords.Position, _clyde);
}
}

public sealed class StationAiMenuButton(BaseStationAiAction action) : RadialMenuTextureButton
{
public BaseStationAiAction Action = action;
}
23 changes: 16 additions & 7 deletions Content.Client/Silicons/StationAi/StationAiOverlay.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,17 @@
using Robust.Client.Player;
using Robust.Shared.Enums;
using Robust.Shared.Map.Components;
using Robust.Shared.Physics;
using Robust.Shared.Prototypes;
using Robust.Shared.Timing;

namespace Content.Client.Silicons.StationAi;

public sealed class StationAiOverlay : Overlay
{
[Dependency] private readonly IClyde _clyde = default!;
[Dependency] private readonly IEntityManager _entManager = default!;
[Dependency] private readonly IGameTiming _timing = default!;
[Dependency] private readonly IPlayerManager _player = default!;
[Dependency] private readonly IPrototypeManager _proto = default!;

Expand All @@ -22,6 +25,9 @@ public sealed class StationAiOverlay : Overlay
private IRenderTexture? _staticTexture;
private IRenderTexture? _stencilTexture;

private float _updateRate = 1f / 30f;
private float _accumulator;

public StationAiOverlay()
{
IoCManager.InjectDependencies(this);
Expand All @@ -47,19 +53,22 @@ protected override void Draw(in OverlayDrawArgs args)
_entManager.TryGetComponent(playerEnt, out TransformComponent? playerXform);
var gridUid = playerXform?.GridUid ?? EntityUid.Invalid;
_entManager.TryGetComponent(gridUid, out MapGridComponent? grid);
_entManager.TryGetComponent(gridUid, out BroadphaseComponent? broadphase);

var invMatrix = args.Viewport.GetWorldToLocalMatrix();
_accumulator -= (float) _timing.FrameTime.TotalSeconds;

if (grid != null)
if (grid != null && broadphase != null)
{
// TODO: Pass in attached entity's grid.
// TODO: Credit OD on the moved to code
// TODO: Call the moved-to code here.

_visibleTiles.Clear();
var lookups = _entManager.System<EntityLookupSystem>();
var xforms = _entManager.System<SharedTransformSystem>();
_entManager.System<StationAiVisionSystem>().GetView((gridUid, grid), worldBounds, _visibleTiles);

if (_accumulator <= 0f)
{
_accumulator = MathF.Max(0f, _accumulator + _updateRate);
_visibleTiles.Clear();
_entManager.System<StationAiVisionSystem>().GetView((gridUid, broadphase, grid), worldBounds, _visibleTiles);
}

var gridMatrix = xforms.GetWorldMatrix(gridUid);
var matty = Matrix3x2.Multiply(gridMatrix, invMatrix);
Expand Down
30 changes: 30 additions & 0 deletions Content.Client/Silicons/StationAi/StationAiSystem.Airlock.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
using Content.Shared.Doors.Components;
using Content.Shared.Silicons.StationAi;
using Robust.Shared.Utility;

namespace Content.Client.Silicons.StationAi;

public sealed partial class StationAiSystem
{
private void InitializeAirlock()
{
SubscribeLocalEvent<DoorBoltComponent, GetStationAiRadialEvent>(OnDoorBoltGetRadial);
}

private void OnDoorBoltGetRadial(Entity<DoorBoltComponent> ent, ref GetStationAiRadialEvent args)
{
args.Actions.Add(new StationAiRadial()
{
Sprite = ent.Comp.BoltsDown ?
new SpriteSpecifier.Rsi(
new ResPath("/Textures/Structures/Doors/Airlocks/Standard/basic.rsi"), "open") :
new SpriteSpecifier.Rsi(
new ResPath("/Textures/Structures/Doors/Airlocks/Standard/basic.rsi"), "closed"),
Tooltip = ent.Comp.BoltsDown ? Loc.GetString("bolt-open") : Loc.GetString("bolt-close"),
Event = new StationAiBoltEvent()
{
Bolted = !ent.Comp.BoltsDown,
}
});
}
}
32 changes: 32 additions & 0 deletions Content.Client/Silicons/StationAi/StationAiSystem.Light.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
using Content.Shared.Item.ItemToggle.Components;
using Content.Shared.Light.Components;
using Content.Shared.Silicons.StationAi;
using Robust.Shared.Utility;

namespace Content.Client.Silicons.StationAi;

public sealed partial class StationAiSystem
{
// Used for surveillance camera lights

private void InitializePowerToggle()
{
SubscribeLocalEvent<ItemTogglePointLightComponent, GetStationAiRadialEvent>(OnLightGetRadial);
}

private void OnLightGetRadial(Entity<ItemTogglePointLightComponent> ent, ref GetStationAiRadialEvent args)
{
if (!TryComp(ent.Owner, out ItemToggleComponent? toggle))
return;

args.Actions.Add(new StationAiRadial()
{
Tooltip = Loc.GetString("toggle-light"),
Sprite = new SpriteSpecifier.Texture(new ResPath("/Textures/Interface/VerbIcons/light.svg.192dpi.png")),
Event = new StationAiLightEvent()
{
Enabled = !toggle.Activated
}
});
}
}
6 changes: 3 additions & 3 deletions Content.Client/Silicons/StationAi/StationAiSystem.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

namespace Content.Client.Silicons.StationAi;

public sealed partial class StationAiSystem : EntitySystem
public sealed partial class StationAiSystem : SharedStationAiSystem
{
[Dependency] private readonly IOverlayManager _overlayMgr = default!;
[Dependency] private readonly IPlayerManager _player = default!;
Expand All @@ -15,8 +15,8 @@ public sealed partial class StationAiSystem : EntitySystem
public override void Initialize()
{
base.Initialize();
// InitializeAirlock();
// InitializePowerToggle();
InitializeAirlock();
InitializePowerToggle();

SubscribeLocalEvent<StationAiOverlayComponent, LocalPlayerAttachedEvent>(OnAiAttached);
SubscribeLocalEvent<StationAiOverlayComponent, LocalPlayerDetachedEvent>(OnAiDetached);
Expand Down
5 changes: 3 additions & 2 deletions Content.Client/Verbs/VerbSystem.cs
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,7 @@ public bool TryGetEntityMenuEntities(MapCoordinates targetPos, [NotNullWhen(true

// Get entities
List<EntityUid> entities;
var examineFlags = LookupFlags.All & ~LookupFlags.Sensors;

// Do we have to do FoV checks?
if ((visibility & MenuVisibility.NoFov) == 0)
Expand All @@ -85,15 +86,15 @@ public bool TryGetEntityMenuEntities(MapCoordinates targetPos, [NotNullWhen(true

// Then check every entity
entities = new();
foreach (var ent in _entityLookup.GetEntitiesInRange(targetPos, EntityMenuLookupSize))
foreach (var ent in _entityLookup.GetEntitiesInRange(targetPos, EntityMenuLookupSize, flags: examineFlags))
{
if (_examine.CanExamine(player.Value, targetPos, Predicate, ent, examiner))
entities.Add(ent);
}
}
else
{
entities = _entityLookup.GetEntitiesInRange(targetPos, EntityMenuLookupSize).ToList();
entities = _entityLookup.GetEntitiesInRange(targetPos, EntityMenuLookupSize, flags: examineFlags).ToList();
}

if (entities.Count == 0)
Expand Down
1 change: 1 addition & 0 deletions Content.Server/Administration/Systems/AdminVerbSystem.cs
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@
using System.Linq;
using System.Numerics;
using Content.Server.Silicons.Laws;
using Content.Shared.Silicons.Laws;
using Content.Shared.Silicons.Laws.Components;
using Robust.Server.Player;
using Robust.Shared.Physics.Components;
Expand Down
Loading
Loading