ECS botany except for plantholder (#6466)
This commit is contained in:
87
Content.Server/Botany/Systems/BotanySystem.Plant.cs
Normal file
87
Content.Server/Botany/Systems/BotanySystem.Plant.cs
Normal file
@@ -0,0 +1,87 @@
|
||||
using System.Collections.Generic;
|
||||
using Content.Server.Botany.Components;
|
||||
using Content.Server.Chemistry.EntitySystems;
|
||||
using Content.Server.Popups;
|
||||
using Content.Shared.GameTicking;
|
||||
using JetBrains.Annotations;
|
||||
using Robust.Shared.GameObjects;
|
||||
using Robust.Shared.IoC;
|
||||
using Robust.Shared.Prototypes;
|
||||
using Robust.Shared.Random;
|
||||
|
||||
namespace Content.Server.Botany.Systems
|
||||
{
|
||||
[UsedImplicitly]
|
||||
public sealed partial class BotanySystem : EntitySystem
|
||||
{
|
||||
[Dependency] private readonly IPrototypeManager _prototypeManager = default!;
|
||||
[Dependency] private readonly PopupSystem _popupSystem = default!;
|
||||
[Dependency] private readonly IRobustRandom _robustRandom = default!;
|
||||
[Dependency] private readonly SolutionContainerSystem _solutionContainerSystem = default!;
|
||||
|
||||
private int _nextUid = 0;
|
||||
private float _timer = 0f;
|
||||
|
||||
public readonly Dictionary<int, SeedPrototype> Seeds = new();
|
||||
|
||||
public override void Initialize()
|
||||
{
|
||||
base.Initialize();
|
||||
|
||||
SubscribeLocalEvent<RoundRestartCleanupEvent>(Reset);
|
||||
|
||||
InitializeSeeds();
|
||||
|
||||
PopulateDatabase();
|
||||
}
|
||||
|
||||
private void PopulateDatabase()
|
||||
{
|
||||
_nextUid = 0;
|
||||
|
||||
Seeds.Clear();
|
||||
|
||||
foreach (var seed in _prototypeManager.EnumeratePrototypes<SeedPrototype>())
|
||||
{
|
||||
AddSeedToDatabase(seed);
|
||||
}
|
||||
}
|
||||
|
||||
public bool AddSeedToDatabase(SeedPrototype seed)
|
||||
{
|
||||
// If it's not -1, it's already in the database. Probably.
|
||||
if (seed.Uid != -1)
|
||||
return false;
|
||||
|
||||
seed.Uid = GetNextSeedUid();
|
||||
Seeds[seed.Uid] = seed;
|
||||
return true;
|
||||
}
|
||||
|
||||
private int GetNextSeedUid()
|
||||
{
|
||||
return _nextUid++;
|
||||
}
|
||||
|
||||
public override void Update(float frameTime)
|
||||
{
|
||||
base.Update(frameTime);
|
||||
|
||||
_timer += frameTime;
|
||||
if (_timer < 3f)
|
||||
return;
|
||||
|
||||
_timer = 0f;
|
||||
|
||||
foreach (var plantHolder in EntityManager.EntityQuery<PlantHolderComponent>())
|
||||
{
|
||||
plantHolder.Update();
|
||||
}
|
||||
}
|
||||
|
||||
public void Reset(RoundRestartCleanupEvent ev)
|
||||
{
|
||||
PopulateDatabase();
|
||||
}
|
||||
}
|
||||
}
|
||||
35
Content.Server/Botany/Systems/BotanySystem.Produce.cs
Normal file
35
Content.Server/Botany/Systems/BotanySystem.Produce.cs
Normal file
@@ -0,0 +1,35 @@
|
||||
using Content.Server.Botany.Components;
|
||||
using Content.Shared.FixedPoint;
|
||||
using Robust.Server.GameObjects;
|
||||
using Robust.Shared.GameObjects;
|
||||
using Robust.Shared.Maths;
|
||||
|
||||
namespace Content.Server.Botany.Systems;
|
||||
|
||||
public partial class BotanySystem
|
||||
{
|
||||
public void ProduceGrown(EntityUid uid, ProduceComponent produce)
|
||||
{
|
||||
if (!_prototypeManager.TryIndex<SeedPrototype>(produce.SeedName, out var seed))
|
||||
return;
|
||||
|
||||
if (TryComp(uid, out SpriteComponent? sprite))
|
||||
{
|
||||
sprite.LayerSetRSI(0, seed.PlantRsi);
|
||||
sprite.LayerSetState(0, seed.PlantIconState);
|
||||
}
|
||||
|
||||
var solutionContainer = _solutionContainerSystem.EnsureSolution(uid, produce.SolutionName);
|
||||
|
||||
solutionContainer.RemoveAllSolution();
|
||||
foreach (var (chem, quantity) in seed.Chemicals)
|
||||
{
|
||||
var amount = FixedPoint2.New(quantity.Min);
|
||||
if (quantity.PotencyDivisor > 0 && seed.Potency > 0)
|
||||
amount += FixedPoint2.New(seed.Potency / quantity.PotencyDivisor);
|
||||
amount = FixedPoint2.New((int) MathHelper.Clamp(amount.Float(), quantity.Min, quantity.Max));
|
||||
solutionContainer.MaxVolume += amount;
|
||||
solutionContainer.AddReagent(chem, amount);
|
||||
}
|
||||
}
|
||||
}
|
||||
143
Content.Server/Botany/Systems/BotanySystem.Seed.cs
Normal file
143
Content.Server/Botany/Systems/BotanySystem.Seed.cs
Normal file
@@ -0,0 +1,143 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using Content.Server.Botany.Components;
|
||||
using Content.Shared.Examine;
|
||||
using Content.Shared.Random.Helpers;
|
||||
using Content.Shared.Tag;
|
||||
using Robust.Server.GameObjects;
|
||||
using Robust.Shared.GameObjects;
|
||||
using Robust.Shared.IoC;
|
||||
using Robust.Shared.Localization;
|
||||
using Robust.Shared.Map;
|
||||
using Robust.Shared.Player;
|
||||
using Robust.Shared.Prototypes;
|
||||
using Robust.Shared.Random;
|
||||
using Robust.Shared.Utility;
|
||||
|
||||
namespace Content.Server.Botany.Systems;
|
||||
|
||||
public partial class BotanySystem
|
||||
{
|
||||
public void InitializeSeeds()
|
||||
{
|
||||
SubscribeLocalEvent<SeedComponent, ExaminedEvent>(OnExamined);
|
||||
}
|
||||
|
||||
private void OnExamined(EntityUid uid, SeedComponent component, ExaminedEvent args)
|
||||
{
|
||||
if (!args.IsInDetailsRange)
|
||||
return;
|
||||
|
||||
if (!_prototypeManager.TryIndex<SeedPrototype>(component.SeedName, out var seed))
|
||||
return;
|
||||
|
||||
args.PushMarkup(Loc.GetString($"seed-component-description", ("seedName", seed.DisplayName)));
|
||||
|
||||
if (!seed.RoundStart)
|
||||
{
|
||||
args.PushMarkup(Loc.GetString($"seed-component-has-variety-tag", ("seedUid", seed.Uid)));
|
||||
}
|
||||
else
|
||||
{
|
||||
args.PushMarkup(Loc.GetString($"seed-component-plant-yield-text", ("seedYield", seed.Yield)));
|
||||
args.PushMarkup(Loc.GetString($"seed-component-plant-potency-text", ("seedPotency", seed.Potency)));
|
||||
}
|
||||
}
|
||||
|
||||
#region SeedPrototype prototype stuff
|
||||
|
||||
public EntityUid SpawnSeedPacket(SeedPrototype proto, EntityCoordinates transformCoordinates)
|
||||
{
|
||||
var seed = Spawn(SeedPrototype.Prototype, transformCoordinates);
|
||||
|
||||
var seedComp = EnsureComp<SeedComponent>(seed);
|
||||
seedComp.SeedName = proto.ID;
|
||||
|
||||
if (TryComp(seed, out SpriteComponent? sprite))
|
||||
{
|
||||
// TODO visualizer
|
||||
// SeedPrototype state will always be seed. Blame the spriter if that's not the case!
|
||||
sprite.LayerSetSprite(0, new SpriteSpecifier.Rsi(proto.PlantRsi, "seed"));
|
||||
}
|
||||
|
||||
string val = Loc.GetString("botany-seed-packet-name", ("seedName", proto.SeedName), ("seedNoun", proto.SeedNoun));
|
||||
MetaData(seed).EntityName = val;
|
||||
|
||||
return seed;
|
||||
}
|
||||
|
||||
public IEnumerable<EntityUid> AutoHarvest(SeedPrototype proto, EntityCoordinates position, int yieldMod = 1)
|
||||
{
|
||||
if (position.IsValid(EntityManager) &&
|
||||
proto.ProductPrototypes.Count > 0)
|
||||
return GenerateProduct(proto, position, yieldMod);
|
||||
|
||||
return Enumerable.Empty<EntityUid>();
|
||||
}
|
||||
|
||||
public IEnumerable<EntityUid> Harvest(SeedPrototype proto, EntityUid user, int yieldMod = 1)
|
||||
{
|
||||
if (AddSeedToDatabase(proto)) proto.Name = proto.Uid.ToString();
|
||||
|
||||
if (proto.ProductPrototypes.Count == 0 || proto.Yield <= 0)
|
||||
{
|
||||
_popupSystem.PopupCursor(Loc.GetString("botany-harvest-fail-message"),
|
||||
Filter.Entities(user));
|
||||
return Enumerable.Empty<EntityUid>();
|
||||
}
|
||||
|
||||
_popupSystem.PopupCursor(Loc.GetString("botany-harvest-success-message", ("name", proto.DisplayName)),
|
||||
Filter.Entities(user));
|
||||
return GenerateProduct(proto, Transform(user).Coordinates, yieldMod);
|
||||
}
|
||||
|
||||
public IEnumerable<EntityUid> GenerateProduct(SeedPrototype proto, EntityCoordinates position, int yieldMod = 1)
|
||||
{
|
||||
var totalYield = 0;
|
||||
if (proto.Yield > -1)
|
||||
{
|
||||
if (yieldMod < 0)
|
||||
{
|
||||
yieldMod = 1;
|
||||
totalYield = proto.Yield;
|
||||
}
|
||||
else
|
||||
totalYield = proto.Yield * yieldMod;
|
||||
|
||||
totalYield = Math.Max(1, totalYield);
|
||||
}
|
||||
|
||||
var products = new List<EntityUid>();
|
||||
|
||||
for (var i = 0; i < totalYield; i++)
|
||||
{
|
||||
var product = _robustRandom.Pick(proto.ProductPrototypes);
|
||||
|
||||
var entity = Spawn(product, position);
|
||||
entity.RandomOffset(0.25f);
|
||||
products.Add(entity);
|
||||
|
||||
var produce = EnsureComp<ProduceComponent>(entity);
|
||||
|
||||
produce.SeedName = proto.ID;
|
||||
ProduceGrown(entity, produce);
|
||||
|
||||
if (proto.Mysterious)
|
||||
{
|
||||
var metaData = MetaData(entity);
|
||||
metaData.EntityName += "?";
|
||||
metaData.EntityDescription += " " + Loc.GetString("botany-mysterious-description-addon");
|
||||
}
|
||||
}
|
||||
|
||||
return products;
|
||||
}
|
||||
|
||||
public bool CanHarvest(SeedPrototype proto, EntityUid? held = null)
|
||||
{
|
||||
return !proto.Ligneous || proto.Ligneous && held != null && held.Value.HasTag("BotanySharp");
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
32
Content.Server/Botany/Systems/LogSystem.cs
Normal file
32
Content.Server/Botany/Systems/LogSystem.cs
Normal file
@@ -0,0 +1,32 @@
|
||||
using Content.Server.Botany.Components;
|
||||
using Content.Shared.ActionBlocker;
|
||||
using Content.Shared.Interaction;
|
||||
using Content.Shared.Random.Helpers;
|
||||
using Content.Shared.Tag;
|
||||
using Robust.Shared.GameObjects;
|
||||
|
||||
namespace Content.Server.Botany.Systems;
|
||||
|
||||
public sealed class LogSystem : EntitySystem
|
||||
{
|
||||
public override void Initialize()
|
||||
{
|
||||
base.Initialize();
|
||||
|
||||
SubscribeLocalEvent<LogComponent, InteractUsingEvent>(OnInteractUsing);
|
||||
}
|
||||
|
||||
private void OnInteractUsing(EntityUid uid, LogComponent component, InteractUsingEvent args)
|
||||
{
|
||||
if (args.Used.HasTag("BotanySharp"))
|
||||
{
|
||||
for (var i = 0; i < component.SpawnCount; i++)
|
||||
{
|
||||
var plank = Spawn(component.SpawnedPrototype, Transform(uid).Coordinates);
|
||||
plank.RandomOffset(0.25f);
|
||||
}
|
||||
|
||||
QueueDel(uid);
|
||||
}
|
||||
}
|
||||
}
|
||||
52
Content.Server/Botany/Systems/SeedExtractorSystem.cs
Normal file
52
Content.Server/Botany/Systems/SeedExtractorSystem.cs
Normal file
@@ -0,0 +1,52 @@
|
||||
using Content.Server.Botany.Components;
|
||||
using Content.Server.Popups;
|
||||
using Content.Server.Power.Components;
|
||||
using Content.Shared.Interaction;
|
||||
using Robust.Shared.GameObjects;
|
||||
using Robust.Shared.IoC;
|
||||
using Robust.Shared.Localization;
|
||||
using Robust.Shared.Player;
|
||||
using Robust.Shared.Prototypes;
|
||||
using Robust.Shared.Random;
|
||||
|
||||
namespace Content.Server.Botany.Systems;
|
||||
|
||||
public sealed class SeedExtractorSystem : EntitySystem
|
||||
{
|
||||
[Dependency] private readonly IRobustRandom _random = default!;
|
||||
[Dependency] private readonly IPrototypeManager _prototypeManager = default!;
|
||||
[Dependency] private readonly PopupSystem _popupSystem = default!;
|
||||
[Dependency] private readonly BotanySystem _botanySystem = default!;
|
||||
|
||||
public override void Initialize()
|
||||
{
|
||||
base.Initialize();
|
||||
|
||||
SubscribeLocalEvent<SeedExtractorComponent, InteractUsingEvent>(OnInteractUsing);
|
||||
}
|
||||
|
||||
private void OnInteractUsing(EntityUid uid, SeedExtractorComponent component, InteractUsingEvent args)
|
||||
{
|
||||
if (!TryComp<ApcPowerReceiverComponent>(uid, out var powerReceiverComponent) || !powerReceiverComponent.Powered)
|
||||
return;
|
||||
|
||||
if (TryComp(args.Used, out ProduceComponent? produce))
|
||||
{
|
||||
if (!_prototypeManager.TryIndex<SeedPrototype>(produce.SeedName, out var seed))
|
||||
return;
|
||||
|
||||
_popupSystem.PopupCursor(Loc.GetString("seed-extractor-component-interact-message",("name", args.Used)),
|
||||
Filter.Entities(args.User));
|
||||
|
||||
QueueDel(args.Used);
|
||||
|
||||
var random = _random.Next(component.MinSeeds, component.MaxSeeds);
|
||||
var coords = Transform(uid).Coordinates;
|
||||
|
||||
for (var i = 0; i < random; i++)
|
||||
{
|
||||
_botanySystem.SpawnSeedPacket(seed, coords);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user