Anomalous infections (#31876)
* inner anomaly * anomaly pulse action * test anom mine * Update anomalies.yml * fix action cooldown * pyro_eyes * clientsystem * experiments * blya * some telegraphy * shock eyes! * shadow eyes * separate files * frosty eyes * fix * flora eyes * bluespace eyes * flesh eyes * redoing injction * auto add layers * пипяу * new injector component * stupid me * nice marker injectors * anomaly spawn on shutdown * gravity anom * dead anomaly spawning * add VOX states * sprite specific layers support * technology anom infection * auto detach anomalies that have moved away * Update anomaly_injections.yml * anomalyspawner integration * rock anomaly! * Update anomaly_injections.yml * fix crash bug * tag filter * fix anom dublication spawns * Update anomaly.yml * Update InnerBodyAnomalyComponent.cs * Update anomaly_injections.yml * dont spawn anomalies after decay * fix morb sprite, add end message * gravity resprite * admin logging, double injection fix * make flesh and living light mobs friendly to anomaly hosts * popups * severity feedback * sloth review * A * keep organs after gib * punpun host * sloth synchronization * Update arachnid.yml * increase infections spawnrate
50
Content.Client/Anomaly/Effects/ClientInnerBodySystem.cs
Normal file
@@ -0,0 +1,50 @@
|
|||||||
|
using Content.Shared.Anomaly.Components;
|
||||||
|
using Content.Shared.Anomaly.Effects;
|
||||||
|
using Content.Shared.Body.Components;
|
||||||
|
using Robust.Client.GameObjects;
|
||||||
|
|
||||||
|
namespace Content.Client.Anomaly.Effects;
|
||||||
|
|
||||||
|
public sealed class ClientInnerBodyAnomalySystem : SharedInnerBodyAnomalySystem
|
||||||
|
{
|
||||||
|
public override void Initialize()
|
||||||
|
{
|
||||||
|
SubscribeLocalEvent<InnerBodyAnomalyComponent, AfterAutoHandleStateEvent>(OnAfterHandleState);
|
||||||
|
SubscribeLocalEvent<InnerBodyAnomalyComponent, ComponentShutdown>(OnCompShutdown);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnAfterHandleState(Entity<InnerBodyAnomalyComponent> ent, ref AfterAutoHandleStateEvent args)
|
||||||
|
{
|
||||||
|
if (!TryComp<SpriteComponent>(ent, out var sprite))
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (ent.Comp.FallbackSprite is null)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (!sprite.LayerMapTryGet(ent.Comp.LayerMap, out var index))
|
||||||
|
index = sprite.LayerMapReserveBlank(ent.Comp.LayerMap);
|
||||||
|
|
||||||
|
if (TryComp<BodyComponent>(ent, out var body) &&
|
||||||
|
body.Prototype is not null &&
|
||||||
|
ent.Comp.SpeciesSprites.TryGetValue(body.Prototype.Value, out var speciesSprite))
|
||||||
|
{
|
||||||
|
sprite.LayerSetSprite(index, speciesSprite);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
sprite.LayerSetSprite(index, ent.Comp.FallbackSprite);
|
||||||
|
}
|
||||||
|
|
||||||
|
sprite.LayerSetVisible(index, true);
|
||||||
|
sprite.LayerSetShader(index, "unshaded");
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnCompShutdown(Entity<InnerBodyAnomalyComponent> ent, ref ComponentShutdown args)
|
||||||
|
{
|
||||||
|
if (!TryComp<SpriteComponent>(ent, out var sprite))
|
||||||
|
return;
|
||||||
|
|
||||||
|
var index = sprite.LayerMapGet(ent.Comp.LayerMap);
|
||||||
|
sprite.LayerSetVisible(index, false);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,4 +1,5 @@
|
|||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using System.Numerics;
|
||||||
using Content.Server.Anomaly.Components;
|
using Content.Server.Anomaly.Components;
|
||||||
using Content.Server.DeviceLinking.Systems;
|
using Content.Server.DeviceLinking.Systems;
|
||||||
using Content.Server.Power.Components;
|
using Content.Server.Power.Components;
|
||||||
@@ -10,6 +11,7 @@ using Content.Shared.Popups;
|
|||||||
using Content.Shared.Power;
|
using Content.Shared.Power;
|
||||||
using Robust.Shared.Audio.Systems;
|
using Robust.Shared.Audio.Systems;
|
||||||
using Content.Shared.Verbs;
|
using Content.Shared.Verbs;
|
||||||
|
using Robust.Shared.Timing;
|
||||||
|
|
||||||
namespace Content.Server.Anomaly;
|
namespace Content.Server.Anomaly;
|
||||||
|
|
||||||
@@ -25,6 +27,7 @@ public sealed partial class AnomalySynchronizerSystem : EntitySystem
|
|||||||
[Dependency] private readonly SharedTransformSystem _transform = default!;
|
[Dependency] private readonly SharedTransformSystem _transform = default!;
|
||||||
[Dependency] private readonly SharedPopupSystem _popup = default!;
|
[Dependency] private readonly SharedPopupSystem _popup = default!;
|
||||||
[Dependency] private readonly PowerReceiverSystem _power = default!;
|
[Dependency] private readonly PowerReceiverSystem _power = default!;
|
||||||
|
[Dependency] private readonly IGameTiming _timing = default!;
|
||||||
|
|
||||||
public override void Initialize()
|
public override void Initialize()
|
||||||
{
|
{
|
||||||
@@ -40,6 +43,34 @@ public sealed partial class AnomalySynchronizerSystem : EntitySystem
|
|||||||
SubscribeLocalEvent<AnomalyStabilityChangedEvent>(OnAnomalyStabilityChanged);
|
SubscribeLocalEvent<AnomalyStabilityChangedEvent>(OnAnomalyStabilityChanged);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public override void Update(float frameTime)
|
||||||
|
{
|
||||||
|
base.Update(frameTime);
|
||||||
|
|
||||||
|
var query = EntityQueryEnumerator<AnomalySynchronizerComponent, TransformComponent>();
|
||||||
|
while (query.MoveNext(out var uid, out var sync, out var xform))
|
||||||
|
{
|
||||||
|
if (sync.ConnectedAnomaly is null)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (_timing.CurTime < sync.NextCheckTime)
|
||||||
|
continue;
|
||||||
|
sync.NextCheckTime += sync.CheckFrequency;
|
||||||
|
|
||||||
|
if (Transform(sync.ConnectedAnomaly.Value).MapUid != Transform(uid).MapUid)
|
||||||
|
{
|
||||||
|
DisconnectFromAnomaly((uid, sync), sync.ConnectedAnomaly.Value);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!xform.Coordinates.TryDistance(EntityManager, Transform(sync.ConnectedAnomaly.Value).Coordinates, out var distance))
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (distance > sync.AttachRange)
|
||||||
|
DisconnectFromAnomaly((uid, sync), sync.ConnectedAnomaly.Value);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// If powered, try to attach a nearby anomaly.
|
/// If powered, try to attach a nearby anomaly.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@@ -73,10 +104,10 @@ public sealed partial class AnomalySynchronizerSystem : EntitySystem
|
|||||||
if (args.Powered)
|
if (args.Powered)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (!TryComp<AnomalyComponent>(ent.Comp.ConnectedAnomaly, out var anomaly))
|
if (ent.Comp.ConnectedAnomaly is null)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
DisconnectFromAnomaly(ent, anomaly);
|
DisconnectFromAnomaly(ent, ent.Comp.ConnectedAnomaly.Value);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void OnExamined(Entity<AnomalySynchronizerComponent> ent, ref ExaminedEvent args)
|
private void OnExamined(Entity<AnomalySynchronizerComponent> ent, ref ExaminedEvent args)
|
||||||
@@ -125,13 +156,16 @@ public sealed partial class AnomalySynchronizerSystem : EntitySystem
|
|||||||
|
|
||||||
//TODO: disconnection from the anomaly should also be triggered if the anomaly is far away from the synchronizer.
|
//TODO: disconnection from the anomaly should also be triggered if the anomaly is far away from the synchronizer.
|
||||||
//Currently only bluespace anomaly can do this, but for some reason it is the only one that cannot be connected to the synchronizer.
|
//Currently only bluespace anomaly can do this, but for some reason it is the only one that cannot be connected to the synchronizer.
|
||||||
private void DisconnectFromAnomaly(Entity<AnomalySynchronizerComponent> ent, AnomalyComponent anomaly)
|
private void DisconnectFromAnomaly(Entity<AnomalySynchronizerComponent> ent, EntityUid other)
|
||||||
{
|
{
|
||||||
if (ent.Comp.ConnectedAnomaly == null)
|
if (ent.Comp.ConnectedAnomaly == null)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
if (TryComp<AnomalyComponent>(other, out var anomaly))
|
||||||
|
{
|
||||||
if (ent.Comp.PulseOnDisconnect)
|
if (ent.Comp.PulseOnDisconnect)
|
||||||
_anomaly.DoAnomalyPulse(ent.Comp.ConnectedAnomaly.Value, anomaly);
|
_anomaly.DoAnomalyPulse(ent.Comp.ConnectedAnomaly.Value, anomaly);
|
||||||
|
}
|
||||||
|
|
||||||
_popup.PopupEntity(Loc.GetString("anomaly-sync-disconnected"), ent, PopupType.Large);
|
_popup.PopupEntity(Loc.GetString("anomaly-sync-disconnected"), ent, PopupType.Large);
|
||||||
_audio.PlayPvs(ent.Comp.ConnectedSound, ent);
|
_audio.PlayPvs(ent.Comp.ConnectedSound, ent);
|
||||||
|
|||||||
@@ -55,6 +55,7 @@ public sealed partial class AnomalySystem : SharedAnomalySystem
|
|||||||
SubscribeLocalEvent<AnomalyComponent, ComponentShutdown>(OnShutdown);
|
SubscribeLocalEvent<AnomalyComponent, ComponentShutdown>(OnShutdown);
|
||||||
SubscribeLocalEvent<AnomalyComponent, StartCollideEvent>(OnStartCollide);
|
SubscribeLocalEvent<AnomalyComponent, StartCollideEvent>(OnStartCollide);
|
||||||
|
|
||||||
|
|
||||||
InitializeGenerator();
|
InitializeGenerator();
|
||||||
InitializeScanner();
|
InitializeScanner();
|
||||||
InitializeVessel();
|
InitializeVessel();
|
||||||
@@ -86,7 +87,10 @@ public sealed partial class AnomalySystem : SharedAnomalySystem
|
|||||||
|
|
||||||
private void OnShutdown(Entity<AnomalyComponent> anomaly, ref ComponentShutdown args)
|
private void OnShutdown(Entity<AnomalyComponent> anomaly, ref ComponentShutdown args)
|
||||||
{
|
{
|
||||||
EndAnomaly(anomaly);
|
if (anomaly.Comp.CurrentBehavior is not null)
|
||||||
|
RemoveBehavior(anomaly, anomaly.Comp.CurrentBehavior.Value);
|
||||||
|
|
||||||
|
EndAnomaly(anomaly, spawnCore: false);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void OnStartCollide(Entity<AnomalyComponent> anomaly, ref StartCollideEvent args)
|
private void OnStartCollide(Entity<AnomalyComponent> anomaly, ref StartCollideEvent args)
|
||||||
|
|||||||
@@ -7,7 +7,7 @@ namespace Content.Server.Anomaly.Components;
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// a device that allows you to translate anomaly activity into multitool signals.
|
/// a device that allows you to translate anomaly activity into multitool signals.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[RegisterComponent, Access(typeof(AnomalySynchronizerSystem))]
|
[RegisterComponent, AutoGenerateComponentPause, Access(typeof(AnomalySynchronizerSystem))]
|
||||||
public sealed partial class AnomalySynchronizerComponent : Component
|
public sealed partial class AnomalySynchronizerComponent : Component
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@@ -34,6 +34,15 @@ public sealed partial class AnomalySynchronizerComponent : Component
|
|||||||
[DataField]
|
[DataField]
|
||||||
public float AttachRange = 0.4f;
|
public float AttachRange = 0.4f;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Periodicheski checks to see if the anomaly has moved to disconnect it.
|
||||||
|
/// </summary>
|
||||||
|
[DataField]
|
||||||
|
public TimeSpan CheckFrequency = TimeSpan.FromSeconds(1f);
|
||||||
|
|
||||||
|
[DataField, AutoPausedField]
|
||||||
|
public TimeSpan NextCheckTime = TimeSpan.Zero;
|
||||||
|
|
||||||
[DataField]
|
[DataField]
|
||||||
public ProtoId<SourcePortPrototype> DecayingPort = "Decaying";
|
public ProtoId<SourcePortPrototype> DecayingPort = "Decaying";
|
||||||
|
|
||||||
|
|||||||
236
Content.Server/Anomaly/Effects/InnerBodyAnomalySystem.cs
Normal file
@@ -0,0 +1,236 @@
|
|||||||
|
using Content.Server.Administration.Logs;
|
||||||
|
using Content.Server.Body.Systems;
|
||||||
|
using Content.Server.Chat.Managers;
|
||||||
|
using Content.Server.Jittering;
|
||||||
|
using Content.Server.Mind;
|
||||||
|
using Content.Server.Stunnable;
|
||||||
|
using Content.Shared.Actions;
|
||||||
|
using Content.Shared.Anomaly;
|
||||||
|
using Content.Shared.Anomaly.Components;
|
||||||
|
using Content.Shared.Anomaly.Effects;
|
||||||
|
using Content.Shared.Body.Components;
|
||||||
|
using Content.Shared.Chat;
|
||||||
|
using Content.Shared.Database;
|
||||||
|
using Content.Shared.Mobs;
|
||||||
|
using Content.Shared.Popups;
|
||||||
|
using Content.Shared.Whitelist;
|
||||||
|
using Robust.Shared.Audio.Systems;
|
||||||
|
using Robust.Shared.Physics.Events;
|
||||||
|
using Robust.Shared.Prototypes;
|
||||||
|
|
||||||
|
namespace Content.Server.Anomaly.Effects;
|
||||||
|
|
||||||
|
public sealed class InnerBodyAnomalySystem : SharedInnerBodyAnomalySystem
|
||||||
|
{
|
||||||
|
[Dependency] private readonly IAdminLogManager _adminLog = default!;
|
||||||
|
[Dependency] private readonly AnomalySystem _anomaly = default!;
|
||||||
|
[Dependency] private readonly ActionContainerSystem _actionContainer = default!;
|
||||||
|
[Dependency] private readonly SharedActionsSystem _actions = default!;
|
||||||
|
[Dependency] private readonly SharedAudioSystem _audio = default!;
|
||||||
|
[Dependency] private readonly BodySystem _body = default!;
|
||||||
|
[Dependency] private readonly IChatManager _chat = default!;
|
||||||
|
[Dependency] private readonly EntityWhitelistSystem _whitelist = default!;
|
||||||
|
[Dependency] private readonly JitteringSystem _jitter = default!;
|
||||||
|
[Dependency] private readonly MindSystem _mind = default!;
|
||||||
|
[Dependency] private readonly SharedPopupSystem _popup = default!;
|
||||||
|
[Dependency] private readonly IPrototypeManager _proto = default!;
|
||||||
|
[Dependency] private readonly StunSystem _stun = default!;
|
||||||
|
|
||||||
|
private readonly Color _messageColor = Color.FromSrgb(new Color(201, 22, 94));
|
||||||
|
|
||||||
|
public override void Initialize()
|
||||||
|
{
|
||||||
|
base.Initialize();
|
||||||
|
|
||||||
|
SubscribeLocalEvent<InnerBodyAnomalyInjectorComponent, StartCollideEvent>(OnStartCollideInjector);
|
||||||
|
|
||||||
|
SubscribeLocalEvent<InnerBodyAnomalyComponent, MapInitEvent>(OnMapInit);
|
||||||
|
SubscribeLocalEvent<InnerBodyAnomalyComponent, ComponentShutdown>(OnCompShutdown);
|
||||||
|
|
||||||
|
SubscribeLocalEvent<InnerBodyAnomalyComponent, AnomalyPulseEvent>(OnAnomalyPulse);
|
||||||
|
SubscribeLocalEvent<InnerBodyAnomalyComponent, AnomalyShutdownEvent>(OnAnomalyShutdown);
|
||||||
|
SubscribeLocalEvent<InnerBodyAnomalyComponent, AnomalySupercriticalEvent>(OnAnomalySupercritical);
|
||||||
|
SubscribeLocalEvent<InnerBodyAnomalyComponent, AnomalySeverityChangedEvent>(OnSeverityChanged);
|
||||||
|
|
||||||
|
SubscribeLocalEvent<InnerBodyAnomalyComponent, MobStateChangedEvent>(OnMobStateChanged);
|
||||||
|
|
||||||
|
SubscribeLocalEvent<AnomalyComponent, ActionAnomalyPulseEvent>(OnActionPulse);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnActionPulse(Entity<AnomalyComponent> ent, ref ActionAnomalyPulseEvent args)
|
||||||
|
{
|
||||||
|
if (args.Handled)
|
||||||
|
return;
|
||||||
|
|
||||||
|
_anomaly.DoAnomalyPulse(ent, ent.Comp);
|
||||||
|
|
||||||
|
args.Handled = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnStartCollideInjector(Entity<InnerBodyAnomalyInjectorComponent> ent, ref StartCollideEvent args)
|
||||||
|
{
|
||||||
|
if (ent.Comp.Whitelist is not null && !_whitelist.IsValid(ent.Comp.Whitelist, args.OtherEntity))
|
||||||
|
return;
|
||||||
|
if (TryComp<InnerBodyAnomalyComponent>(args.OtherEntity, out var innerAnom) && innerAnom.Injected)
|
||||||
|
return;
|
||||||
|
if (!_mind.TryGetMind(args.OtherEntity, out _, out var mindComponent))
|
||||||
|
return;
|
||||||
|
|
||||||
|
EntityManager.AddComponents(args.OtherEntity, ent.Comp.InjectionComponents);
|
||||||
|
QueueDel(ent);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnMapInit(Entity<InnerBodyAnomalyComponent> ent, ref MapInitEvent args)
|
||||||
|
{
|
||||||
|
AddAnomalyToBody(ent);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void AddAnomalyToBody(Entity<InnerBodyAnomalyComponent> ent)
|
||||||
|
{
|
||||||
|
if (!_proto.TryIndex(ent.Comp.InjectionProto, out var injectedAnom))
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (ent.Comp.Injected)
|
||||||
|
return;
|
||||||
|
|
||||||
|
ent.Comp.Injected = true;
|
||||||
|
|
||||||
|
EntityManager.AddComponents(ent, injectedAnom.Components);
|
||||||
|
|
||||||
|
_stun.TryParalyze(ent, TimeSpan.FromSeconds(ent.Comp.StunDuration), true);
|
||||||
|
_jitter.DoJitter(ent, TimeSpan.FromSeconds(ent.Comp.StunDuration), true);
|
||||||
|
|
||||||
|
if (ent.Comp.StartSound is not null)
|
||||||
|
_audio.PlayPvs(ent.Comp.StartSound, ent);
|
||||||
|
|
||||||
|
if (ent.Comp.StartMessage is not null &&
|
||||||
|
_mind.TryGetMind(ent, out _, out var mindComponent) &&
|
||||||
|
mindComponent.Session != null)
|
||||||
|
{
|
||||||
|
var message = Loc.GetString(ent.Comp.StartMessage);
|
||||||
|
var wrappedMessage = Loc.GetString("chat-manager-server-wrap-message", ("message", message));
|
||||||
|
_chat.ChatMessageToOne(ChatChannel.Server,
|
||||||
|
message,
|
||||||
|
wrappedMessage,
|
||||||
|
default,
|
||||||
|
false,
|
||||||
|
mindComponent.Session.Channel,
|
||||||
|
_messageColor);
|
||||||
|
|
||||||
|
_popup.PopupEntity(message, ent, ent, PopupType.MediumCaution);
|
||||||
|
|
||||||
|
_adminLog.Add(LogType.Anomaly,LogImpact.Extreme,$"{ToPrettyString(ent)} became anomaly host.");
|
||||||
|
}
|
||||||
|
Dirty(ent);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnAnomalyPulse(Entity<InnerBodyAnomalyComponent> ent, ref AnomalyPulseEvent args)
|
||||||
|
{
|
||||||
|
_stun.TryParalyze(ent, TimeSpan.FromSeconds(ent.Comp.StunDuration / 2 * args.Severity), true);
|
||||||
|
_jitter.DoJitter(ent, TimeSpan.FromSeconds(ent.Comp.StunDuration / 2 * args.Severity), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnAnomalySupercritical(Entity<InnerBodyAnomalyComponent> ent, ref AnomalySupercriticalEvent args)
|
||||||
|
{
|
||||||
|
if (!TryComp<BodyComponent>(ent, out var body))
|
||||||
|
return;
|
||||||
|
|
||||||
|
_body.GibBody(ent, true, body, splatModifier: 5f);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnSeverityChanged(Entity<InnerBodyAnomalyComponent> ent, ref AnomalySeverityChangedEvent args)
|
||||||
|
{
|
||||||
|
if (!_mind.TryGetMind(ent, out _, out var mindComponent) || mindComponent.Session == null)
|
||||||
|
return;
|
||||||
|
|
||||||
|
var message = string.Empty;
|
||||||
|
|
||||||
|
if (args.Severity >= 0.5 && ent.Comp.LastSeverityInformed < 0.5)
|
||||||
|
{
|
||||||
|
ent.Comp.LastSeverityInformed = 0.5f;
|
||||||
|
message = Loc.GetString("inner-anomaly-severity-info-50");
|
||||||
|
}
|
||||||
|
if (args.Severity >= 0.75 && ent.Comp.LastSeverityInformed < 0.75)
|
||||||
|
{
|
||||||
|
ent.Comp.LastSeverityInformed = 0.75f;
|
||||||
|
message = Loc.GetString("inner-anomaly-severity-info-75");
|
||||||
|
}
|
||||||
|
if (args.Severity >= 0.9 && ent.Comp.LastSeverityInformed < 0.9)
|
||||||
|
{
|
||||||
|
ent.Comp.LastSeverityInformed = 0.9f;
|
||||||
|
message = Loc.GetString("inner-anomaly-severity-info-90");
|
||||||
|
}
|
||||||
|
if (args.Severity >= 1 && ent.Comp.LastSeverityInformed < 1)
|
||||||
|
{
|
||||||
|
ent.Comp.LastSeverityInformed = 1f;
|
||||||
|
message = Loc.GetString("inner-anomaly-severity-info-100");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (message == string.Empty)
|
||||||
|
return;
|
||||||
|
|
||||||
|
var wrappedMessage = Loc.GetString("chat-manager-server-wrap-message", ("message", message));
|
||||||
|
_chat.ChatMessageToOne(ChatChannel.Server,
|
||||||
|
message,
|
||||||
|
wrappedMessage,
|
||||||
|
default,
|
||||||
|
false,
|
||||||
|
mindComponent.Session.Channel,
|
||||||
|
_messageColor);
|
||||||
|
|
||||||
|
_popup.PopupEntity(message, ent, ent, PopupType.MediumCaution);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnMobStateChanged(Entity<InnerBodyAnomalyComponent> ent, ref MobStateChangedEvent args)
|
||||||
|
{
|
||||||
|
if (args.NewMobState != MobState.Dead)
|
||||||
|
return;
|
||||||
|
|
||||||
|
_anomaly.ChangeAnomalyHealth(ent, -2); //Shutdown it
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnAnomalyShutdown(Entity<InnerBodyAnomalyComponent> ent, ref AnomalyShutdownEvent args)
|
||||||
|
{
|
||||||
|
RemoveAnomalyFromBody(ent);
|
||||||
|
RemCompDeferred<InnerBodyAnomalyComponent>(ent);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnCompShutdown(Entity<InnerBodyAnomalyComponent> ent, ref ComponentShutdown args)
|
||||||
|
{
|
||||||
|
RemoveAnomalyFromBody(ent);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void RemoveAnomalyFromBody(Entity<InnerBodyAnomalyComponent> ent)
|
||||||
|
{
|
||||||
|
if (!ent.Comp.Injected)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (_proto.TryIndex(ent.Comp.InjectionProto, out var injectedAnom))
|
||||||
|
EntityManager.RemoveComponents(ent, injectedAnom.Components);
|
||||||
|
|
||||||
|
_stun.TryParalyze(ent, TimeSpan.FromSeconds(ent.Comp.StunDuration), true);
|
||||||
|
|
||||||
|
if (ent.Comp.EndMessage is not null &&
|
||||||
|
_mind.TryGetMind(ent, out _, out var mindComponent) &&
|
||||||
|
mindComponent.Session != null)
|
||||||
|
{
|
||||||
|
var message = Loc.GetString(ent.Comp.EndMessage);
|
||||||
|
var wrappedMessage = Loc.GetString("chat-manager-server-wrap-message", ("message", message));
|
||||||
|
_chat.ChatMessageToOne(ChatChannel.Server,
|
||||||
|
message,
|
||||||
|
wrappedMessage,
|
||||||
|
default,
|
||||||
|
false,
|
||||||
|
mindComponent.Session.Channel,
|
||||||
|
_messageColor);
|
||||||
|
|
||||||
|
|
||||||
|
_popup.PopupEntity(message, ent, ent, PopupType.MediumCaution);
|
||||||
|
|
||||||
|
_adminLog.Add(LogType.Anomaly, LogImpact.Medium,$"{ToPrettyString(ent)} is no longer a host for the anomaly.");
|
||||||
|
}
|
||||||
|
|
||||||
|
ent.Comp.Injected = false;
|
||||||
|
RemCompDeferred<AnomalyComponent>(ent);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -202,6 +202,7 @@ namespace Content.Server.Explosion.EntitySystems
|
|||||||
args.Handled = true;
|
args.Handled = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private void HandleRattleTrigger(EntityUid uid, RattleComponent component, TriggerEvent args)
|
private void HandleRattleTrigger(EntityUid uid, RattleComponent component, TriggerEvent args)
|
||||||
{
|
{
|
||||||
if (!TryComp<SubdermalImplantComponent>(uid, out var implanted))
|
if (!TryComp<SubdermalImplantComponent>(uid, out var implanted))
|
||||||
@@ -230,7 +231,7 @@ namespace Content.Server.Explosion.EntitySystems
|
|||||||
private void OnTriggerCollide(EntityUid uid, TriggerOnCollideComponent component, ref StartCollideEvent args)
|
private void OnTriggerCollide(EntityUid uid, TriggerOnCollideComponent component, ref StartCollideEvent args)
|
||||||
{
|
{
|
||||||
if (args.OurFixtureId == component.FixtureID && (!component.IgnoreOtherNonHard || args.OtherFixture.Hard))
|
if (args.OurFixtureId == component.FixtureID && (!component.IgnoreOtherNonHard || args.OtherFixture.Hard))
|
||||||
Trigger(uid);
|
Trigger(uid, args.OtherEntity);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void OnSpawnTriggered(EntityUid uid, TriggerOnSpawnComponent component, MapInitEvent args)
|
private void OnSpawnTriggered(EntityUid uid, TriggerOnSpawnComponent component, MapInitEvent args)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
using System.Numerics;
|
using System.Numerics;
|
||||||
|
using Content.Shared.Anomaly.Effects;
|
||||||
using Content.Shared.Anomaly.Prototypes;
|
using Content.Shared.Anomaly.Prototypes;
|
||||||
using Content.Shared.Damage;
|
|
||||||
using Robust.Shared.Audio;
|
using Robust.Shared.Audio;
|
||||||
using Robust.Shared.GameStates;
|
using Robust.Shared.GameStates;
|
||||||
using Robust.Shared.Prototypes;
|
using Robust.Shared.Prototypes;
|
||||||
@@ -16,7 +16,7 @@ namespace Content.Shared.Anomaly.Components;
|
|||||||
/// Anomalies and their related components were designed here: https://hackmd.io/@ss14-design/r1sQbkJOs
|
/// Anomalies and their related components were designed here: https://hackmd.io/@ss14-design/r1sQbkJOs
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[RegisterComponent, NetworkedComponent, AutoGenerateComponentState, AutoGenerateComponentPause]
|
[RegisterComponent, NetworkedComponent, AutoGenerateComponentState, AutoGenerateComponentPause]
|
||||||
[Access(typeof(SharedAnomalySystem))]
|
[Access(typeof(SharedAnomalySystem), typeof(SharedInnerBodyAnomalySystem))]
|
||||||
public sealed partial class AnomalyComponent : Component
|
public sealed partial class AnomalyComponent : Component
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@@ -184,21 +184,21 @@ public sealed partial class AnomalyComponent : Component
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// The minimum amount of research points generated per second
|
/// The minimum amount of research points generated per second
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[DataField("minPointsPerSecond")]
|
[DataField]
|
||||||
public int MinPointsPerSecond = 10;
|
public int MinPointsPerSecond = 10;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The maximum amount of research points generated per second
|
/// The maximum amount of research points generated per second
|
||||||
/// This doesn't include the point bonus for being unstable.
|
/// This doesn't include the point bonus for being unstable.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[DataField("maxPointsPerSecond")]
|
[DataField]
|
||||||
public int MaxPointsPerSecond = 70;
|
public int MaxPointsPerSecond = 70;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The multiplier applied to the point value for the
|
/// The multiplier applied to the point value for the
|
||||||
/// anomaly being above the <see cref="GrowthThreshold"/>
|
/// anomaly being above the <see cref="GrowthThreshold"/>
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[DataField("growingPointMultiplier")]
|
[DataField]
|
||||||
public float GrowingPointMultiplier = 1.5f;
|
public float GrowingPointMultiplier = 1.5f;
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
@@ -252,10 +252,13 @@ public sealed partial class AnomalyComponent : Component
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
[ViewVariables(VVAccess.ReadWrite)]
|
[ViewVariables(VVAccess.ReadWrite)]
|
||||||
[DataField("offset")]
|
[DataField("offset")]
|
||||||
public Vector2 FloatingOffset = new(0, 0.15f);
|
public Vector2 FloatingOffset = new(0, 0);
|
||||||
|
|
||||||
public readonly string AnimationKey = "anomalyfloat";
|
public readonly string AnimationKey = "anomalyfloat";
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
[DataField]
|
||||||
|
public bool DeleteEntity = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -0,0 +1,72 @@
|
|||||||
|
using Content.Shared.Anomaly.Effects;
|
||||||
|
using Content.Shared.Body.Prototypes;
|
||||||
|
using Robust.Shared.Audio;
|
||||||
|
using Robust.Shared.GameStates;
|
||||||
|
using Robust.Shared.Prototypes;
|
||||||
|
using Robust.Shared.Utility;
|
||||||
|
|
||||||
|
namespace Content.Shared.Anomaly.Components;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// An anomaly within the body of a living being. Controls the ability to return to the standard state.
|
||||||
|
/// </summary>
|
||||||
|
[RegisterComponent, NetworkedComponent, AutoGenerateComponentState(true), Access(typeof(SharedInnerBodyAnomalySystem))]
|
||||||
|
public sealed partial class InnerBodyAnomalyComponent : Component
|
||||||
|
{
|
||||||
|
[DataField]
|
||||||
|
public bool Injected;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// A prototype of an entity whose components will be added to the anomaly host **AND** then removed at the right time
|
||||||
|
/// </summary>
|
||||||
|
[DataField(required: true)]
|
||||||
|
public EntProtoId? InjectionProto;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Duration of stun from the effect of the anomaly
|
||||||
|
/// </summary>
|
||||||
|
[DataField]
|
||||||
|
public float StunDuration = 4f;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// A message sent in chat to a player who has become infected by an anomaly
|
||||||
|
/// </summary>
|
||||||
|
[DataField]
|
||||||
|
public LocId? StartMessage = null;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// A message sent in chat to a player who has cleared an anomaly
|
||||||
|
/// </summary>
|
||||||
|
[DataField]
|
||||||
|
public LocId? EndMessage = "inner-anomaly-end-message";
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Sound, playing on becoming anomaly
|
||||||
|
/// </summary>
|
||||||
|
[DataField]
|
||||||
|
public SoundSpecifier? StartSound = new SoundPathSpecifier("/Audio/Effects/inneranomaly.ogg");
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Used to display messages to the player about their level of disease progression
|
||||||
|
/// </summary>
|
||||||
|
[DataField]
|
||||||
|
public float LastSeverityInformed = 0f;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The fallback sprite to be added on the original entity. Allows you to visually identify the feature and type of anomaly to other players
|
||||||
|
/// </summary>
|
||||||
|
[DataField, AutoNetworkedField]
|
||||||
|
public SpriteSpecifier? FallbackSprite = null;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Ability to use unique sprites for different body types
|
||||||
|
/// </summary>
|
||||||
|
[DataField, AutoNetworkedField]
|
||||||
|
public Dictionary<ProtoId<BodyPrototype>, SpriteSpecifier> SpeciesSprites = new();
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The key of the entity layer into which the sprite will be inserted
|
||||||
|
/// </summary>
|
||||||
|
[DataField]
|
||||||
|
public string LayerMap = "inner_anomaly_layer";
|
||||||
|
}
|
||||||
@@ -0,0 +1,21 @@
|
|||||||
|
using Content.Shared.Anomaly.Effects;
|
||||||
|
using Content.Shared.Whitelist;
|
||||||
|
using Robust.Shared.Prototypes;
|
||||||
|
|
||||||
|
namespace Content.Shared.Anomaly.Components;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// On contact with an entity, if it meets the conditions, it will transfer the specified components to it
|
||||||
|
/// </summary>
|
||||||
|
[RegisterComponent, Access(typeof(SharedInnerBodyAnomalySystem))]
|
||||||
|
public sealed partial class InnerBodyAnomalyInjectorComponent : Component
|
||||||
|
{
|
||||||
|
[DataField]
|
||||||
|
public EntityWhitelist? Whitelist;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// components that will be automatically removed after “curing”
|
||||||
|
/// </summary>
|
||||||
|
[DataField(required: true)]
|
||||||
|
public ComponentRegistry InjectionComponents = default!;
|
||||||
|
}
|
||||||
@@ -0,0 +1,5 @@
|
|||||||
|
namespace Content.Shared.Anomaly.Effects;
|
||||||
|
|
||||||
|
public abstract class SharedInnerBodyAnomalySystem : EntitySystem
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -1,13 +1,10 @@
|
|||||||
using Content.Shared.Administration.Logs;
|
using Content.Shared.Administration.Logs;
|
||||||
using Content.Shared.Anomaly.Components;
|
using Content.Shared.Anomaly.Components;
|
||||||
using Content.Shared.Anomaly.Prototypes;
|
using Content.Shared.Anomaly.Prototypes;
|
||||||
using Content.Shared.Damage;
|
|
||||||
using Content.Shared.Database;
|
using Content.Shared.Database;
|
||||||
using Content.Shared.Interaction;
|
|
||||||
using Content.Shared.Physics;
|
using Content.Shared.Physics;
|
||||||
using Content.Shared.Popups;
|
using Content.Shared.Popups;
|
||||||
using Content.Shared.Weapons.Melee.Components;
|
using Content.Shared.Weapons.Melee.Components;
|
||||||
using Content.Shared.Weapons.Melee.Events;
|
|
||||||
using Robust.Shared.Audio.Systems;
|
using Robust.Shared.Audio.Systems;
|
||||||
using Robust.Shared.Map;
|
using Robust.Shared.Map;
|
||||||
using Robust.Shared.Map.Components;
|
using Robust.Shared.Map.Components;
|
||||||
@@ -21,6 +18,7 @@ using Robust.Shared.Timing;
|
|||||||
using Robust.Shared.Utility;
|
using Robust.Shared.Utility;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Numerics;
|
using System.Numerics;
|
||||||
|
using Content.Shared.Actions;
|
||||||
|
|
||||||
namespace Content.Shared.Anomaly;
|
namespace Content.Shared.Anomaly;
|
||||||
|
|
||||||
@@ -36,6 +34,7 @@ public abstract class SharedAnomalySystem : EntitySystem
|
|||||||
[Dependency] protected readonly SharedPopupSystem Popup = default!;
|
[Dependency] protected readonly SharedPopupSystem Popup = default!;
|
||||||
[Dependency] private readonly IPrototypeManager _prototype = default!;
|
[Dependency] private readonly IPrototypeManager _prototype = default!;
|
||||||
[Dependency] private readonly IRobustRandom _random = default!;
|
[Dependency] private readonly IRobustRandom _random = default!;
|
||||||
|
[Dependency] private readonly SharedTransformSystem _transform = default!;
|
||||||
|
|
||||||
public override void Initialize()
|
public override void Initialize()
|
||||||
{
|
{
|
||||||
@@ -145,7 +144,7 @@ public abstract class SharedAnomalySystem : EntitySystem
|
|||||||
if (!Timing.IsFirstTimePredicted)
|
if (!Timing.IsFirstTimePredicted)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
Audio.PlayPvs(component.SupercriticalSound, uid);
|
Audio.PlayPvs(component.SupercriticalSound, Transform(uid).Coordinates);
|
||||||
|
|
||||||
if (_net.IsServer)
|
if (_net.IsServer)
|
||||||
Log.Info($"Raising supercritical event. Entity: {ToPrettyString(uid)}");
|
Log.Info($"Raising supercritical event. Entity: {ToPrettyString(uid)}");
|
||||||
@@ -169,7 +168,8 @@ public abstract class SharedAnomalySystem : EntitySystem
|
|||||||
/// <param name="uid">The anomaly being shut down</param>
|
/// <param name="uid">The anomaly being shut down</param>
|
||||||
/// <param name="component"></param>
|
/// <param name="component"></param>
|
||||||
/// <param name="supercritical">Whether or not the anomaly ended via supercritical event</param>
|
/// <param name="supercritical">Whether or not the anomaly ended via supercritical event</param>
|
||||||
public void EndAnomaly(EntityUid uid, AnomalyComponent? component = null, bool supercritical = false)
|
/// <param name="spawnCore">Create anomaly cores based on the result of completing an anomaly?</param>
|
||||||
|
public void EndAnomaly(EntityUid uid, AnomalyComponent? component = null, bool supercritical = false, bool spawnCore = true)
|
||||||
{
|
{
|
||||||
// Logging before resolve, in case the anomaly has deleted itself.
|
// Logging before resolve, in case the anomaly has deleted itself.
|
||||||
if (_net.IsServer)
|
if (_net.IsServer)
|
||||||
@@ -186,8 +186,13 @@ public abstract class SharedAnomalySystem : EntitySystem
|
|||||||
if (Terminating(uid) || _net.IsClient)
|
if (Terminating(uid) || _net.IsClient)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
Spawn(supercritical ? component.CorePrototype : component.CoreInertPrototype, Transform(uid).Coordinates);
|
if (spawnCore)
|
||||||
|
{
|
||||||
|
var core = Spawn(supercritical ? component.CorePrototype : component.CoreInertPrototype, Transform(uid).Coordinates);
|
||||||
|
_transform.PlaceNextTo(core, uid);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (component.DeleteEntity)
|
||||||
QueueDel(uid);
|
QueueDel(uid);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -458,3 +463,5 @@ public partial record struct AnomalySpawnSettings()
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
public bool SpawnOnSeverityChanged { get; set; } = false;
|
public bool SpawnOnSeverityChanged { get; set; } = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public sealed partial class ActionAnomalyPulseEvent : InstantActionEvent { }
|
||||||
|
|||||||
@@ -231,3 +231,8 @@
|
|||||||
copyright: '"beep_landmine.ogg" by kaktuscsc of Discord for SS14'
|
copyright: '"beep_landmine.ogg" by kaktuscsc of Discord for SS14'
|
||||||
license: "CC-BY-SA-3.0"
|
license: "CC-BY-SA-3.0"
|
||||||
source: https://github.com/YuriyKiss/space-station-14/commit/971a135a9c83aed46e967aac9302ab5b35562b5f
|
source: https://github.com/YuriyKiss/space-station-14/commit/971a135a9c83aed46e967aac9302ab5b35562b5f
|
||||||
|
|
||||||
|
- files: [inneranomaly.ogg]
|
||||||
|
copyright: 'created by waveplaySFX on Freesound'
|
||||||
|
license: "CC0-1.0"
|
||||||
|
source: https://freesound.org/people/waveplaySFX/sounds/553744/
|
||||||
|
|||||||
BIN
Resources/Audio/Effects/inneranomaly.ogg
Normal file
17
Resources/Locale/en-US/anomaly/inner_anomaly.ftl
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
inner-anomaly-start-message-pyro = You can feel the insane flame inside of you. You became the host of a pyroclastic anomaly.
|
||||||
|
inner-anomaly-start-message-shock = Lightning bolts quivering at your fingertips! You became the host of a electric anomaly.
|
||||||
|
inner-anomaly-start-message-shadow = There's an impenetrable darkness oozing out of you... You became the host of a shadow anomaly.
|
||||||
|
inner-anomaly-start-message-frost = The icy frost is binding your bones. You became the host of a ice anomaly.
|
||||||
|
inner-anomaly-start-message-flora = Leaves and flowers sprout through your skin! You became the host of a floral anomaly.
|
||||||
|
inner-anomaly-start-message-bluespace = Your thoughts are racing like mad! You became the host of a bluespace anomaly.
|
||||||
|
inner-anomaly-start-message-flesh = Your body is growing frantically. You became the host of a flesh anomaly.
|
||||||
|
inner-anomaly-start-message-grav = Everything becames unnaturally heavy and light at the same time... You became the host of a gravity anomaly.
|
||||||
|
inner-anomaly-start-message-tech = Your head is buzzing with the amount of chaotic information! You became the host of a tech anomaly.
|
||||||
|
inner-anomaly-start-message-rock = The crystals are growing through your bones! You became the host of a rock anomaly.
|
||||||
|
|
||||||
|
inner-anomaly-end-message = The abnormal activity within you disappears without a trace....
|
||||||
|
|
||||||
|
inner-anomaly-severity-info-50 = You feel that the anomaly is taking over half your body.
|
||||||
|
inner-anomaly-severity-info-75 = You feel that the anomaly is taking over a large part of your body.
|
||||||
|
inner-anomaly-severity-info-90 = You feel that the anomaly has almost completely taken over your body.
|
||||||
|
inner-anomaly-severity-info-100 = The anomaly inside you is growing uncontrollably, causing immense pain, and tearing you apart!
|
||||||
9
Resources/Prototypes/Actions/anomaly.yml
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
- type: entity
|
||||||
|
id: ActionAnomalyPulse
|
||||||
|
name: Anomaly pulse
|
||||||
|
description: Release a pulse of energy of your abnormal nature
|
||||||
|
components:
|
||||||
|
- type: InstantAction
|
||||||
|
icon: Structures/Specific/anomaly.rsi/anom1.png
|
||||||
|
event: !type:ActionAnomalyPulseEvent
|
||||||
|
useDelay: 30
|
||||||
@@ -9,6 +9,7 @@
|
|||||||
- sprite: Structures/Specific/anomaly.rsi
|
- sprite: Structures/Specific/anomaly.rsi
|
||||||
state: anom1
|
state: anom1
|
||||||
- type: RandomSpawner
|
- type: RandomSpawner
|
||||||
|
chance: 1
|
||||||
prototypes:
|
prototypes:
|
||||||
- AnomalyPyroclastic
|
- AnomalyPyroclastic
|
||||||
- AnomalyGravity
|
- AnomalyGravity
|
||||||
@@ -21,7 +22,9 @@
|
|||||||
- AnomalyFlora
|
- AnomalyFlora
|
||||||
- AnomalyShadow
|
- AnomalyShadow
|
||||||
- AnomalyTech
|
- AnomalyTech
|
||||||
chance: 1
|
rareChance: 0.3
|
||||||
|
rarePrototypes:
|
||||||
|
- RandomAnomalyInjectorSpawner
|
||||||
offset: 0.15 # not to put it higher. The anomaly sychnronizer looks for anomalies within this radius, and if the radius is higher, the anomaly can be attracted from a neighboring tile.
|
offset: 0.15 # not to put it higher. The anomaly sychnronizer looks for anomalies within this radius, and if the radius is higher, the anomaly can be attracted from a neighboring tile.
|
||||||
|
|
||||||
- type: entity
|
- type: entity
|
||||||
@@ -41,3 +44,27 @@
|
|||||||
- AnomalyRockUranium
|
- AnomalyRockUranium
|
||||||
chance: 1
|
chance: 1
|
||||||
offset: 0.15
|
offset: 0.15
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
id: RandomAnomalyInjectorSpawner
|
||||||
|
parent: MarkerBase
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: red
|
||||||
|
- sprite: Structures/Specific/Anomalies/tech_anom.rsi
|
||||||
|
state: pulse
|
||||||
|
- type: RandomSpawner
|
||||||
|
prototypes:
|
||||||
|
- AnomalyTrapPyroclastic
|
||||||
|
- AnomalyTrapElectricity
|
||||||
|
- AnomalyTrapShadow
|
||||||
|
- AnomalyTrapIce
|
||||||
|
- AnomalyTrapFlora
|
||||||
|
- AnomalyTrapBluespace
|
||||||
|
- AnomalyTrapFlesh
|
||||||
|
- AnomalyTrapGravity
|
||||||
|
- AnomalyTrapTech
|
||||||
|
- AnomalyTrapRock
|
||||||
|
chance: 1
|
||||||
|
|
||||||
@@ -1316,6 +1316,7 @@
|
|||||||
tags:
|
tags:
|
||||||
- VimPilot
|
- VimPilot
|
||||||
- DoorBumpOpener
|
- DoorBumpOpener
|
||||||
|
- AnomalyHost
|
||||||
- type: Reactive
|
- type: Reactive
|
||||||
groups:
|
groups:
|
||||||
Flammable: [ Touch ]
|
Flammable: [ Touch ]
|
||||||
|
|||||||
@@ -13,6 +13,11 @@
|
|||||||
true
|
true
|
||||||
NavSmash: !type:Bool
|
NavSmash: !type:Bool
|
||||||
true
|
true
|
||||||
|
- type: NPCImprintingOnSpawnBehaviour
|
||||||
|
spawnFriendsSearchRadius: 10
|
||||||
|
whitelist:
|
||||||
|
components:
|
||||||
|
- Anomaly # Friendly to inner anomaly host
|
||||||
- type: NpcFactionMember
|
- type: NpcFactionMember
|
||||||
factions:
|
factions:
|
||||||
- SimpleHostile
|
- SimpleHostile
|
||||||
|
|||||||
@@ -16,6 +16,11 @@
|
|||||||
- type: NpcFactionMember
|
- type: NpcFactionMember
|
||||||
factions:
|
factions:
|
||||||
- SimpleHostile
|
- SimpleHostile
|
||||||
|
- type: NPCImprintingOnSpawnBehaviour
|
||||||
|
spawnFriendsSearchRadius: 10
|
||||||
|
whitelist:
|
||||||
|
components:
|
||||||
|
- Anomaly # Friendly to inner anomaly host
|
||||||
- type: MovementIgnoreGravity
|
- type: MovementIgnoreGravity
|
||||||
- type: MovementSpeedModifier
|
- type: MovementSpeedModifier
|
||||||
baseWalkSpeed: 3.5
|
baseWalkSpeed: 3.5
|
||||||
|
|||||||
@@ -809,6 +809,7 @@
|
|||||||
- CannotSuicide
|
- CannotSuicide
|
||||||
- DoorBumpOpener
|
- DoorBumpOpener
|
||||||
- VimPilot
|
- VimPilot
|
||||||
|
- AnomalyHost
|
||||||
- type: Loadout
|
- type: Loadout
|
||||||
prototypes: [ MobMonkeyGear ]
|
prototypes: [ MobMonkeyGear ]
|
||||||
- type: Grammar
|
- type: Grammar
|
||||||
|
|||||||
@@ -23,6 +23,7 @@
|
|||||||
- FootstepSound
|
- FootstepSound
|
||||||
- DoorBumpOpener
|
- DoorBumpOpener
|
||||||
- SpiderCraft
|
- SpiderCraft
|
||||||
|
- AnomalyHost
|
||||||
- type: Butcherable
|
- type: Butcherable
|
||||||
butcheringType: Spike
|
butcheringType: Spike
|
||||||
spawned:
|
spawned:
|
||||||
|
|||||||
@@ -212,6 +212,7 @@
|
|||||||
- CanPilot
|
- CanPilot
|
||||||
- FootstepSound
|
- FootstepSound
|
||||||
- DoorBumpOpener
|
- DoorBumpOpener
|
||||||
|
- AnomalyHost
|
||||||
|
|
||||||
- type: entity
|
- type: entity
|
||||||
save: false
|
save: false
|
||||||
|
|||||||
@@ -5,6 +5,7 @@
|
|||||||
description: An impossible object. Should you be standing this close to it?
|
description: An impossible object. Should you be standing this close to it?
|
||||||
components:
|
components:
|
||||||
- type: Anomaly
|
- type: Anomaly
|
||||||
|
offset: 0, 0.15
|
||||||
pulseSound:
|
pulseSound:
|
||||||
collection: RadiationPulse
|
collection: RadiationPulse
|
||||||
params:
|
params:
|
||||||
|
|||||||
@@ -0,0 +1,353 @@
|
|||||||
|
- type: entity
|
||||||
|
id: AnomalyInjectionBase
|
||||||
|
abstract: true
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
radius: 1.3
|
||||||
|
energy: 2.5
|
||||||
|
castShadows: false
|
||||||
|
- type: ActionGrant
|
||||||
|
actions:
|
||||||
|
- ActionAnomalyPulse
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: AnomalyInjectionBase
|
||||||
|
id: AnomalyInjectionPyroclastic
|
||||||
|
categories: [ HideSpawnMenu ]
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
color: "#E25822"
|
||||||
|
- type: PyroclasticAnomaly
|
||||||
|
maximumIgnitionRadius: 3
|
||||||
|
- type: TempAffectingAnomaly
|
||||||
|
tempChangePerSecond: 10
|
||||||
|
hotspotExposeTemperature: 500
|
||||||
|
- type: GasProducerAnomaly
|
||||||
|
releasedGas: 3
|
||||||
|
releaseOnMaxSeverity: true
|
||||||
|
spawnRadius: 4
|
||||||
|
tileCount: 5
|
||||||
|
tempChange: 420
|
||||||
|
- type: ProjectileAnomaly
|
||||||
|
projectilePrototype: ProjectileAnomalyFireball
|
||||||
|
projectileSpeed: 0.5
|
||||||
|
minProjectiles: 1
|
||||||
|
maxProjectiles: 3
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: AnomalyInjectionBase
|
||||||
|
id: AnomalyInjectionElectric
|
||||||
|
categories: [ HideSpawnMenu ]
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
color: "#ffffaa"
|
||||||
|
- type: ElectricityAnomaly
|
||||||
|
minBoltCount: 1
|
||||||
|
maxBoltCount: 3
|
||||||
|
maxElectrocuteRange: 4
|
||||||
|
maxElectrocuteDamage: 10
|
||||||
|
maxElectrocuteDuration: 4
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: AnomalyInjectionBase
|
||||||
|
id: AnomalyInjectionShadow
|
||||||
|
categories: [ HideSpawnMenu ]
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
color: "#793a80"
|
||||||
|
- type: EntitySpawnAnomaly
|
||||||
|
entries:
|
||||||
|
- settings:
|
||||||
|
spawnOnPulse: true
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 5
|
||||||
|
maxAmount: 10
|
||||||
|
maxRange: 2
|
||||||
|
spawns:
|
||||||
|
- ShadowKudzuWeak
|
||||||
|
- settings:
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 15
|
||||||
|
maxAmount: 20
|
||||||
|
maxRange: 25
|
||||||
|
spawns:
|
||||||
|
- ShadowKudzu
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: AnomalyInjectionBase
|
||||||
|
id: AnomalyInjectionIce
|
||||||
|
categories: [ HideSpawnMenu ]
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
color: "#befaff"
|
||||||
|
- type: ExplosionAnomaly
|
||||||
|
supercriticalExplosion: Cryo
|
||||||
|
explosionTotalIntensity: 150
|
||||||
|
explosionDropoff: 2
|
||||||
|
explosionMaxTileIntensity: 20
|
||||||
|
- type: ProjectileAnomaly
|
||||||
|
projectilePrototype: ProjectileIcicle
|
||||||
|
minProjectiles: 1
|
||||||
|
maxProjectiles: 4
|
||||||
|
- type: EntitySpawnAnomaly
|
||||||
|
entries:
|
||||||
|
- settings:
|
||||||
|
spawnOnStabilityChanged: true
|
||||||
|
minAmount: 3
|
||||||
|
maxAmount: 8
|
||||||
|
maxRange: 2
|
||||||
|
spawns:
|
||||||
|
- IceCrust
|
||||||
|
- type: TempAffectingAnomaly
|
||||||
|
tempChangePerSecond: -10
|
||||||
|
hotspotExposeTemperature: -500
|
||||||
|
- type: GasProducerAnomaly
|
||||||
|
releasedGas: 8 # Frezon. Please replace if there is a better way to specify this
|
||||||
|
releaseOnMaxSeverity: true
|
||||||
|
spawnRadius: 0
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: AnomalyInjectionBase
|
||||||
|
id: AnomalyInjectionFlora
|
||||||
|
categories: [ HideSpawnMenu ]
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
color: "#6270bb"
|
||||||
|
- type: TileSpawnAnomaly
|
||||||
|
entries:
|
||||||
|
- settings:
|
||||||
|
spawnOnPulse: true
|
||||||
|
minAmount: 2
|
||||||
|
maxAmount: 5
|
||||||
|
maxRange: 2
|
||||||
|
floor: FloorAstroGrass
|
||||||
|
- settings:
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 5
|
||||||
|
maxAmount: 15
|
||||||
|
maxRange: 7
|
||||||
|
floor: FloorAstroGrass
|
||||||
|
- type: EntitySpawnAnomaly
|
||||||
|
entries:
|
||||||
|
- settings:
|
||||||
|
spawnOnPulse: true
|
||||||
|
minAmount: 1
|
||||||
|
maxAmount: 3
|
||||||
|
maxRange: 1
|
||||||
|
spawns:
|
||||||
|
- KudzuFlowerFriendly
|
||||||
|
- settings:
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 2
|
||||||
|
maxAmount: 6
|
||||||
|
maxRange: 3
|
||||||
|
spawns:
|
||||||
|
- KudzuFlowerAngry
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: AnomalyInjectionBase
|
||||||
|
id: AnomalyInjectionBluespace
|
||||||
|
categories: [ HideSpawnMenu ]
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
color: "#00ccff"
|
||||||
|
- type: BluespaceAnomaly
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: AnomalyInjectionBase
|
||||||
|
id: AnomalyInjectionFlesh
|
||||||
|
categories: [ HideSpawnMenu ]
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
color: "#cb5b7e"
|
||||||
|
- type: TileSpawnAnomaly
|
||||||
|
entries:
|
||||||
|
- settings:
|
||||||
|
spawnOnPulse: true
|
||||||
|
spawnOnStabilityChanged: true
|
||||||
|
minAmount: 1
|
||||||
|
maxAmount: 3
|
||||||
|
maxRange: 2
|
||||||
|
floor: FloorFlesh
|
||||||
|
- settings:
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 5
|
||||||
|
maxAmount: 15
|
||||||
|
maxRange: 5
|
||||||
|
floor: FloorFlesh
|
||||||
|
- type: EntitySpawnAnomaly
|
||||||
|
entries:
|
||||||
|
- settings:
|
||||||
|
spawnOnPulse: true
|
||||||
|
minAmount: 1
|
||||||
|
maxAmount: 2
|
||||||
|
minRange: 1.5
|
||||||
|
maxRange: 2.5
|
||||||
|
spawns:
|
||||||
|
- FleshBlocker
|
||||||
|
- settings:
|
||||||
|
spawnOnPulse: true
|
||||||
|
maxAmount: 1
|
||||||
|
minRange: 2.5
|
||||||
|
maxRange: 4.5
|
||||||
|
spawns:
|
||||||
|
- MobFleshJared
|
||||||
|
- MobFleshGolem
|
||||||
|
- MobFleshClamp
|
||||||
|
- MobFleshLover
|
||||||
|
- settings:
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 5
|
||||||
|
maxAmount: 8
|
||||||
|
minRange: 5
|
||||||
|
maxRange: 15
|
||||||
|
spawns:
|
||||||
|
- FleshBlocker
|
||||||
|
- settings:
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 2
|
||||||
|
maxAmount: 5
|
||||||
|
maxRange: 8
|
||||||
|
spawns:
|
||||||
|
- MobFleshJared
|
||||||
|
- MobFleshGolem
|
||||||
|
- MobFleshClamp
|
||||||
|
- MobFleshLover
|
||||||
|
- settings:
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 2
|
||||||
|
maxAmount: 4
|
||||||
|
maxRange: 10
|
||||||
|
spawns:
|
||||||
|
- FleshKudzu
|
||||||
|
- settings:
|
||||||
|
spawnOnShutdown: true
|
||||||
|
maxAmount: 2
|
||||||
|
maxRange: 1
|
||||||
|
spawns:
|
||||||
|
- MobFleshJared
|
||||||
|
- MobFleshGolem
|
||||||
|
- MobFleshClamp
|
||||||
|
- MobFleshLover
|
||||||
|
- FleshKudzu
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: AnomalyInjectionBase
|
||||||
|
id: AnomalyInjectionGravity
|
||||||
|
categories: [ HideSpawnMenu ]
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
color: "#1e070e"
|
||||||
|
- type: GravityAnomaly
|
||||||
|
maxGravityWellRange: 4
|
||||||
|
maxThrowRange: 3
|
||||||
|
maxThrowStrength: 5
|
||||||
|
spaceRange: 1
|
||||||
|
- type: GravityWell
|
||||||
|
maxRange: 0.7
|
||||||
|
- type: SingularityDistortion
|
||||||
|
intensity: 100
|
||||||
|
falloffPower: 2.7
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: AnomalyInjectionBase
|
||||||
|
id: AnomalyInjectionTech
|
||||||
|
categories: [ HideSpawnMenu ]
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
color: "#56c1e8"
|
||||||
|
- type: TechAnomaly
|
||||||
|
linkRadius:
|
||||||
|
min: 2
|
||||||
|
max: 5
|
||||||
|
linkCountPerPulse:
|
||||||
|
min: 1
|
||||||
|
max: 4
|
||||||
|
linkCountSupercritical: 15
|
||||||
|
- type: DeviceLinkSource
|
||||||
|
ports:
|
||||||
|
- Pulse
|
||||||
|
- Timer
|
||||||
|
- type: WirelessNetworkConnection
|
||||||
|
range: 10
|
||||||
|
- type: DeviceNetwork
|
||||||
|
deviceNetId: Wireless
|
||||||
|
receiveFrequencyId: BasicDevice
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: AnomalyInjectionBase
|
||||||
|
id: AnomalyInjectionRock
|
||||||
|
categories: [ HideSpawnMenu ]
|
||||||
|
components:
|
||||||
|
- type: PointLight
|
||||||
|
color: "#5ca8cb"
|
||||||
|
- type: TileSpawnAnomaly
|
||||||
|
entries:
|
||||||
|
- settings:
|
||||||
|
spawnOnPulse: true
|
||||||
|
minAmount: 7
|
||||||
|
maxAmount: 10
|
||||||
|
maxRange: 4
|
||||||
|
floor: FloorAsteroidTile
|
||||||
|
- settings:
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 15
|
||||||
|
maxAmount: 25
|
||||||
|
maxRange: 6
|
||||||
|
floor: FloorAsteroidTile
|
||||||
|
- type: EntitySpawnAnomaly
|
||||||
|
entries:
|
||||||
|
- settings:
|
||||||
|
spawnOnPulse: true
|
||||||
|
minAmount: 4
|
||||||
|
maxAmount: 8
|
||||||
|
minRange: 1
|
||||||
|
maxRange: 3
|
||||||
|
spawns:
|
||||||
|
- WallSpawnAsteroid
|
||||||
|
- WallSpawnAsteroid
|
||||||
|
- WallSpawnAsteroid
|
||||||
|
- WallSpawnAsteroid
|
||||||
|
- WallSpawnAsteroid
|
||||||
|
- WallSpawnAsteroidSilver
|
||||||
|
- WallSpawnAsteroidSilverCrab
|
||||||
|
- WallSpawnAsteroidIron
|
||||||
|
- WallSpawnAsteroidIronCrab
|
||||||
|
- WallSpawnAsteroidQuartz
|
||||||
|
- WallSpawnAsteroidQuartzCrab
|
||||||
|
- settings:
|
||||||
|
spawnOnPulse: true
|
||||||
|
maxAmount: 3
|
||||||
|
minRange: 2.5
|
||||||
|
maxRange: 4.5
|
||||||
|
spawns:
|
||||||
|
- CrystalPink
|
||||||
|
- CrystalCyan
|
||||||
|
- settings:
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 15
|
||||||
|
maxAmount: 20
|
||||||
|
minRange: 2
|
||||||
|
maxRange: 7
|
||||||
|
spawns:
|
||||||
|
- CrystalPink
|
||||||
|
- CrystalCyan
|
||||||
|
- WallSpawnAsteroid
|
||||||
|
- WallSpawnAsteroid
|
||||||
|
- WallSpawnAsteroid
|
||||||
|
- WallSpawnAsteroid
|
||||||
|
- WallSpawnAsteroidSilver
|
||||||
|
- WallSpawnAsteroidSilverCrab
|
||||||
|
- WallSpawnAsteroidIron
|
||||||
|
- WallSpawnAsteroidIronCrab
|
||||||
|
- WallSpawnAsteroidQuartz
|
||||||
|
- WallSpawnAsteroidQuartzCrab
|
||||||
|
- settings:
|
||||||
|
spawnOnSuperCritical: true
|
||||||
|
minAmount: 3
|
||||||
|
maxAmount: 5
|
||||||
|
maxRange: 3
|
||||||
|
spawns:
|
||||||
|
- MobSpawnCrabSilver
|
||||||
|
- MobSpawnCrabIron
|
||||||
|
- MobSpawnCrabQuartz
|
||||||
@@ -0,0 +1,320 @@
|
|||||||
|
- type: entity
|
||||||
|
name: anomaly injector
|
||||||
|
parent: MarkerBase
|
||||||
|
id: BaseAnomalyInjector
|
||||||
|
abstract: true
|
||||||
|
components:
|
||||||
|
- type: Physics
|
||||||
|
bodyType: Static
|
||||||
|
fixedRotation: true
|
||||||
|
- type: AmbientSound
|
||||||
|
range: 5
|
||||||
|
volume: -5
|
||||||
|
sound:
|
||||||
|
path: /Audio/Ambience/anomaly_drone.ogg
|
||||||
|
- type: Fixtures
|
||||||
|
fixtures:
|
||||||
|
anom:
|
||||||
|
shape:
|
||||||
|
!type:PhysShapeCircle
|
||||||
|
radius: 2.27 # i love 27
|
||||||
|
hard: false
|
||||||
|
mask:
|
||||||
|
- MobMask
|
||||||
|
layer:
|
||||||
|
- MobLayer
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
whitelist:
|
||||||
|
tags:
|
||||||
|
- AnomalyHost
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: BaseAnomalyInjector
|
||||||
|
id: AnomalyTrapPyroclastic
|
||||||
|
suffix: Pyroclastic
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: pink
|
||||||
|
- sprite: Structures/Specific/Anomalies/pyro_anom.rsi
|
||||||
|
state: pulse
|
||||||
|
- sprite: Mobs/Species/Human/parts.rsi
|
||||||
|
state: full
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
injectionComponents:
|
||||||
|
- type: Anomaly
|
||||||
|
deleteEntity: false
|
||||||
|
maxPointsPerSecond: 100
|
||||||
|
corePrototype: AnomalyCorePyroclastic
|
||||||
|
- type: InnerBodyAnomaly
|
||||||
|
injectionProto: AnomalyInjectionPyroclastic
|
||||||
|
startMessage: inner-anomaly-start-message-pyro
|
||||||
|
fallbackSprite:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: fire
|
||||||
|
speciesSprites:
|
||||||
|
Vox:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: fire_VOX
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: BaseAnomalyInjector
|
||||||
|
id: AnomalyTrapElectricity
|
||||||
|
suffix: Electricity
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: pink
|
||||||
|
- sprite: Structures/Specific/anomaly.rsi
|
||||||
|
state: anom3-pulse
|
||||||
|
- sprite: Mobs/Species/Human/parts.rsi
|
||||||
|
state: full
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
injectionComponents:
|
||||||
|
- type: Anomaly
|
||||||
|
deleteEntity: false
|
||||||
|
maxPointsPerSecond: 100
|
||||||
|
corePrototype: AnomalyCoreElectricity
|
||||||
|
- type: InnerBodyAnomaly
|
||||||
|
injectionProto: AnomalyInjectionElectric
|
||||||
|
startMessage: inner-anomaly-start-message-shock
|
||||||
|
fallbackSprite:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: shock
|
||||||
|
speciesSprites:
|
||||||
|
Vox:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: shock_VOX
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: BaseAnomalyInjector
|
||||||
|
id: AnomalyTrapShadow
|
||||||
|
suffix: Shadow
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: pink
|
||||||
|
- sprite: Structures/Specific/Anomalies/shadow_anom.rsi
|
||||||
|
state: pulse
|
||||||
|
- sprite: Mobs/Species/Human/parts.rsi
|
||||||
|
state: full
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
injectionComponents:
|
||||||
|
- type: Anomaly
|
||||||
|
deleteEntity: false
|
||||||
|
maxPointsPerSecond: 100
|
||||||
|
corePrototype: AnomalyCoreShadow
|
||||||
|
- type: InnerBodyAnomaly
|
||||||
|
injectionProto: AnomalyInjectionShadow
|
||||||
|
startMessage: inner-anomaly-start-message-shadow
|
||||||
|
fallbackSprite:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: shadow
|
||||||
|
speciesSprites:
|
||||||
|
Vox:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: shadow_VOX
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: BaseAnomalyInjector
|
||||||
|
id: AnomalyTrapIce
|
||||||
|
suffix: Ice
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: pink
|
||||||
|
- sprite: Structures/Specific/Anomalies/ice_anom.rsi
|
||||||
|
state: pulse
|
||||||
|
- sprite: Mobs/Species/Human/parts.rsi
|
||||||
|
state: full
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
injectionComponents:
|
||||||
|
- type: Anomaly
|
||||||
|
deleteEntity: false
|
||||||
|
maxPointsPerSecond: 100
|
||||||
|
corePrototype: AnomalyCoreIce
|
||||||
|
- type: InnerBodyAnomaly
|
||||||
|
injectionProto: AnomalyInjectionIce
|
||||||
|
startMessage: inner-anomaly-start-message-frost
|
||||||
|
fallbackSprite:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: frost
|
||||||
|
speciesSprites:
|
||||||
|
Vox:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: frost_VOX
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: BaseAnomalyInjector
|
||||||
|
id: AnomalyTrapFlora
|
||||||
|
suffix: Flora
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: pink
|
||||||
|
- sprite: Structures/Specific/Anomalies/flora_anom.rsi
|
||||||
|
state: pulse
|
||||||
|
- sprite: Mobs/Species/Human/parts.rsi
|
||||||
|
state: full
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
injectionComponents:
|
||||||
|
- type: Anomaly
|
||||||
|
deleteEntity: false
|
||||||
|
maxPointsPerSecond: 100
|
||||||
|
corePrototype: AnomalyCoreFlora
|
||||||
|
- type: InnerBodyAnomaly
|
||||||
|
injectionProto: AnomalyInjectionFlora
|
||||||
|
startMessage: inner-anomaly-start-message-flora
|
||||||
|
fallbackSprite:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: flora
|
||||||
|
speciesSprites:
|
||||||
|
Vox:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: flora_VOX
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: BaseAnomalyInjector
|
||||||
|
id: AnomalyTrapBluespace
|
||||||
|
suffix: Bluespace
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: pink
|
||||||
|
- sprite: Structures/Specific/anomaly.rsi
|
||||||
|
state: anom4-pulse
|
||||||
|
- sprite: Mobs/Species/Human/parts.rsi
|
||||||
|
state: full
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
injectionComponents:
|
||||||
|
- type: Anomaly
|
||||||
|
deleteEntity: false
|
||||||
|
maxPointsPerSecond: 100
|
||||||
|
corePrototype: AnomalyCoreBluespace
|
||||||
|
- type: InnerBodyAnomaly
|
||||||
|
injectionProto: AnomalyInjectionBluespace
|
||||||
|
startMessage: inner-anomaly-start-message-bluespace
|
||||||
|
fallbackSprite:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: bluespace
|
||||||
|
speciesSprites:
|
||||||
|
Vox:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: bluespace_VOX
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: BaseAnomalyInjector
|
||||||
|
id: AnomalyTrapFlesh
|
||||||
|
suffix: Flesh
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: pink
|
||||||
|
- sprite: Structures/Specific/anomaly.rsi
|
||||||
|
state: anom5-pulse
|
||||||
|
- sprite: Mobs/Species/Human/parts.rsi
|
||||||
|
state: full
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
injectionComponents:
|
||||||
|
- type: Anomaly
|
||||||
|
deleteEntity: false
|
||||||
|
maxPointsPerSecond: 100
|
||||||
|
corePrototype: AnomalyCoreFlesh
|
||||||
|
- type: InnerBodyAnomaly
|
||||||
|
injectionProto: AnomalyInjectionFlesh
|
||||||
|
startMessage: inner-anomaly-start-message-flesh
|
||||||
|
fallbackSprite:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: flesh
|
||||||
|
speciesSprites:
|
||||||
|
Vox:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: flesh_VOX
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: BaseAnomalyInjector
|
||||||
|
id: AnomalyTrapGravity
|
||||||
|
suffix: Gravity
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: pink
|
||||||
|
- sprite: Structures/Specific/anomaly.rsi
|
||||||
|
state: anom2-pulse
|
||||||
|
- sprite: Mobs/Species/Human/parts.rsi
|
||||||
|
state: full
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
injectionComponents:
|
||||||
|
- type: Anomaly
|
||||||
|
deleteEntity: false
|
||||||
|
maxPointsPerSecond: 100
|
||||||
|
corePrototype: AnomalyCoreGravity
|
||||||
|
- type: InnerBodyAnomaly
|
||||||
|
injectionProto: AnomalyInjectionGravity
|
||||||
|
startMessage: inner-anomaly-start-message-grav
|
||||||
|
fallbackSprite:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: grav
|
||||||
|
speciesSprites:
|
||||||
|
Vox:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: grav_VOX
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: BaseAnomalyInjector
|
||||||
|
id: AnomalyTrapTech
|
||||||
|
suffix: Tech
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: pink
|
||||||
|
- sprite: Structures/Specific/Anomalies/tech_anom.rsi
|
||||||
|
state: pulse
|
||||||
|
- sprite: Mobs/Species/Human/parts.rsi
|
||||||
|
state: full
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
injectionComponents:
|
||||||
|
- type: Anomaly
|
||||||
|
deleteEntity: false
|
||||||
|
maxPointsPerSecond: 100
|
||||||
|
corePrototype: AnomalyCoreTech
|
||||||
|
- type: InnerBodyAnomaly
|
||||||
|
injectionProto: AnomalyInjectionTech
|
||||||
|
startMessage: inner-anomaly-start-message-tech
|
||||||
|
fallbackSprite:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: tech
|
||||||
|
speciesSprites:
|
||||||
|
Vox:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: tech_VOX
|
||||||
|
|
||||||
|
- type: entity
|
||||||
|
parent: BaseAnomalyInjector
|
||||||
|
id: AnomalyTrapRock
|
||||||
|
suffix: Rock
|
||||||
|
components:
|
||||||
|
- type: Sprite
|
||||||
|
layers:
|
||||||
|
- state: pink
|
||||||
|
- sprite: Structures/Specific/anomaly.rsi
|
||||||
|
state: anom6-pulse
|
||||||
|
color: "#5ca8cb"
|
||||||
|
- sprite: Mobs/Species/Human/parts.rsi
|
||||||
|
state: full
|
||||||
|
- type: InnerBodyAnomalyInjector
|
||||||
|
injectionComponents:
|
||||||
|
- type: Anomaly
|
||||||
|
deleteEntity: false
|
||||||
|
maxPointsPerSecond: 100
|
||||||
|
corePrototype: AnomalyCoreRock
|
||||||
|
- type: InnerBodyAnomaly
|
||||||
|
injectionProto: AnomalyInjectionRock
|
||||||
|
startMessage: inner-anomaly-start-message-rock
|
||||||
|
fallbackSprite:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: rock
|
||||||
|
speciesSprites:
|
||||||
|
Vox:
|
||||||
|
sprite: Structures/Specific/Anomalies/inner_anom_layer.rsi
|
||||||
|
state: rock_VOX
|
||||||
@@ -15,6 +15,9 @@
|
|||||||
- type: Tag
|
- type: Tag
|
||||||
id: Ambrosia
|
id: Ambrosia
|
||||||
|
|
||||||
|
- type: Tag
|
||||||
|
id: AnomalyHost
|
||||||
|
|
||||||
- type: Tag
|
- type: Tag
|
||||||
id: AppraisalTool
|
id: AppraisalTool
|
||||||
|
|
||||||
|
|||||||
|
After Width: | Height: | Size: 864 B |
|
After Width: | Height: | Size: 1.0 KiB |
|
After Width: | Height: | Size: 1007 B |
|
After Width: | Height: | Size: 1.5 KiB |
|
After Width: | Height: | Size: 1.3 KiB |
|
After Width: | Height: | Size: 1.4 KiB |
|
After Width: | Height: | Size: 1.8 KiB |
|
After Width: | Height: | Size: 1.9 KiB |
|
After Width: | Height: | Size: 2.6 KiB |
|
After Width: | Height: | Size: 2.7 KiB |
|
After Width: | Height: | Size: 2.8 KiB |
|
After Width: | Height: | Size: 3.3 KiB |
@@ -0,0 +1,643 @@
|
|||||||
|
{
|
||||||
|
"version": 1,
|
||||||
|
"size": {
|
||||||
|
"x": 32,
|
||||||
|
"y": 32
|
||||||
|
},
|
||||||
|
"license": "CC-BY-SA-3.0",
|
||||||
|
"copyright": "Created by TheShuEd (github) for Space Station 14",
|
||||||
|
"states": [
|
||||||
|
{
|
||||||
|
"name": "bluespace",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "bluespace_VOX",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "fire",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "fire_VOX",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "flesh",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.8,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.8,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.8,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.8,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "flesh_VOX",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.8,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.8,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.8,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.8,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "flora",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "flora_VOX",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "frost",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "frost_VOX",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "grav",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "grav_VOX",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3,
|
||||||
|
0.3
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "rock",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.9,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.9,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.9,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.9,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "rock_VOX",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.9,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.9,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.9,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.9,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "shadow",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "shadow_VOX",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "shock",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "shock_VOX",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2,
|
||||||
|
0.2
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "tech",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.4,
|
||||||
|
0.2,
|
||||||
|
0.4
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.4,
|
||||||
|
0.2,
|
||||||
|
0.4
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.4,
|
||||||
|
0.2,
|
||||||
|
0.4
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.4,
|
||||||
|
0.2,
|
||||||
|
0.4
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "tech_VOX",
|
||||||
|
"directions": 4,
|
||||||
|
"delays": [
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.4,
|
||||||
|
0.2,
|
||||||
|
0.4
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.4,
|
||||||
|
0.2,
|
||||||
|
0.4
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.4,
|
||||||
|
0.2,
|
||||||
|
0.4
|
||||||
|
],
|
||||||
|
[
|
||||||
|
0.2,
|
||||||
|
0.4,
|
||||||
|
0.2,
|
||||||
|
0.4
|
||||||
|
]
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
After Width: | Height: | Size: 1.4 KiB |
|
After Width: | Height: | Size: 1.4 KiB |
|
After Width: | Height: | Size: 768 B |
|
After Width: | Height: | Size: 1002 B |
|
After Width: | Height: | Size: 879 B |
|
After Width: | Height: | Size: 2.0 KiB |
|
After Width: | Height: | Size: 1.2 KiB |
|
After Width: | Height: | Size: 1.2 KiB |
|
Before Width: | Height: | Size: 1.2 KiB After Width: | Height: | Size: 1.2 KiB |
|
Before Width: | Height: | Size: 429 B After Width: | Height: | Size: 513 B |