From 32d8cc0c1e50744594029daae6b7032c2644e2b7 Mon Sep 17 00:00:00 2001 From: Peter Wedder Date: Thu, 26 Nov 2020 14:53:42 +0200 Subject: [PATCH] Rerun of "Add Reagent Grinder/Juicer" (#2570) * commit skeleton reagent grinder component * add reagentgrinder bounduserinterface, add suffix to grinder yml, add reagentgrinder sprites * implement much more of the grinder ui functionality * get more use out of hasbeaker bool * complete wiring up most of the chamber/beaker UI controls * remove whitelist prototype id. add grindable tag component * add juiceable component * rename boolparam to be clearer * more juice * add some juice reagents and apply them to their drink prototypes * re add glassyellow * implement juicing and results * add time delay to grindjuice * add reagent grinder visualizer, add reagent grinder sounds, fix some yaml errors too * interface has clear indication of currennt operation, and busy status * add ReagentGrinder to Client ignnored components * Update Content.Client/GameObjects/Components/Kitchen/ReagentGrinderBoundUserInterface.cs Co-authored-by: metalgearsloth <31366439+metalgearsloth@users.noreply.github.com> * Update Content.Client/GameObjects/Components/Kitchen/ReagentGrinderBoundUserInterface.cs Co-authored-by: metalgearsloth <31366439+metalgearsloth@users.noreply.github.com> * Update Content.Shared/Kitchen/SharedReagentGrinderComponent.cs Co-authored-by: metalgearsloth <31366439+metalgearsloth@users.noreply.github.com> * implemennt sloth changes * fix isbusy * Disable grind/juice buttons if there's nothing to grind or juice, also some misc fixes * unsubscribe from messages on remove + fix xmlcomment * fix bounding box * Add these to dictionary * Add these to client ignore * Whitespace and unneeded import fixes * tommy's toes * Where'd these newlines come from * power * improve bounding box * Check power better & show contents when beaker is ejected * check power here * Disable eject buttons when running * improve comments * readwrite for viewvars on work time and capacity * Address most of Sloth's reviews * Make this cleaner * add grindablecomponent to motherfucking everything * Fix reviews * some more null suppressions * remove unused random field Co-authored-by: scuffedjays Co-authored-by: namespace-Memory <66768086+namespace-Memory@users.noreply.github.com> Co-authored-by: metalgearsloth <31366439+metalgearsloth@users.noreply.github.com> --- .../ReagentGrinderBoundUserInterface.cs | 292 ++++++++++++++ .../Kitchen/ReagentGrinderVisualizer.cs | 17 + Content.Client/IgnoredComponents.cs | 3 + .../Components/Kitchen/GrindableComponent.cs | 13 + .../Components/Kitchen/JuiceableComponent.cs | 23 ++ .../Kitchen/ReagentGrinderComponent.cs | 375 ++++++++++++++++++ .../EntitySystems/ReagentGrinderSystem.cs | 19 + Content.Shared/GameObjects/ContentNetIDs.cs | 1 + .../Kitchen/SharedReagentGrinderComponent.cs | 126 ++++++ Resources/Audio/Machines/blender.ogg | Bin 0 -> 36334 bytes Resources/Audio/Machines/juicer.ogg | Bin 0 -> 34955 bytes .../Specific/Cooking/reagent_grinder.yml | 35 ++ .../Entities/Objects/Consumable/botany.yml | 41 ++ .../Entities/Objects/Consumable/drinks.yml | 112 +++++- .../Entities/Objects/Consumable/food.yml | 178 +++++++-- Resources/Prototypes/Reagents/drinks.yml | 151 ++++++- .../Power/juicer.rsi/juicer0.png | Bin 0 -> 579 bytes .../Power/juicer.rsi/juicer1.png | Bin 0 -> 598 bytes .../Constructible/Power/juicer.rsi/meta.json | 1 + SpaceStation14.sln.DotSettings | 2 + 20 files changed, 1347 insertions(+), 42 deletions(-) create mode 100644 Content.Client/GameObjects/Components/Kitchen/ReagentGrinderBoundUserInterface.cs create mode 100644 Content.Client/GameObjects/Components/Kitchen/ReagentGrinderVisualizer.cs create mode 100644 Content.Server/GameObjects/Components/Kitchen/GrindableComponent.cs create mode 100644 Content.Server/GameObjects/Components/Kitchen/JuiceableComponent.cs create mode 100644 Content.Server/GameObjects/Components/Kitchen/ReagentGrinderComponent.cs create mode 100644 Content.Server/GameObjects/EntitySystems/ReagentGrinderSystem.cs create mode 100644 Content.Shared/Kitchen/SharedReagentGrinderComponent.cs create mode 100644 Resources/Audio/Machines/blender.ogg create mode 100644 Resources/Audio/Machines/juicer.ogg create mode 100644 Resources/Prototypes/Entities/Constructible/Specific/Cooking/reagent_grinder.yml create mode 100644 Resources/Textures/Constructible/Power/juicer.rsi/juicer0.png create mode 100644 Resources/Textures/Constructible/Power/juicer.rsi/juicer1.png create mode 100644 Resources/Textures/Constructible/Power/juicer.rsi/meta.json diff --git a/Content.Client/GameObjects/Components/Kitchen/ReagentGrinderBoundUserInterface.cs b/Content.Client/GameObjects/Components/Kitchen/ReagentGrinderBoundUserInterface.cs new file mode 100644 index 0000000000..41ae8e015e --- /dev/null +++ b/Content.Client/GameObjects/Components/Kitchen/ReagentGrinderBoundUserInterface.cs @@ -0,0 +1,292 @@ +using System.Collections.Generic; +using Robust.Client.GameObjects.Components.UserInterface; +using Robust.Client.UserInterface; +using Robust.Client.UserInterface.Controls; +using Robust.Client.UserInterface.CustomControls; +using Robust.Shared.GameObjects.Components.UserInterface; +using Robust.Shared.Localization; +using Robust.Shared.Maths; +using Content.Shared.Kitchen; +using Robust.Shared.GameObjects; +using Content.Shared.Chemistry; +using Robust.Shared.IoC; +using Robust.Shared.Interfaces.GameObjects; +using Robust.Shared.Prototypes; +using Robust.Client.GameObjects; + +namespace Content.Client.GameObjects.Components.Kitchen +{ + public class ReagentGrinderBoundUserInterface : BoundUserInterface + { + [Dependency] private readonly IEntityManager _entityManager = default!; + [Dependency] private readonly IPrototypeManager _prototypeManager = default!; + + private GrinderMenu _menu; + private Dictionary _chamberVisualContents = new Dictionary(); + private Dictionary _beakerVisualContents = new Dictionary(); + public ReagentGrinderBoundUserInterface(ClientUserInterfaceComponent owner, object uiKey) : base(owner, uiKey) { } + + protected override void Open() + { + base.Open(); + _menu = new GrinderMenu(this); + _menu.OpenCentered(); + _menu.OnClose += Close; + _menu.GrindButton.OnPressed += args => SendMessage(new SharedReagentGrinderComponent.ReagentGrinderGrindStartMessage()); + _menu.JuiceButton.OnPressed += args => SendMessage(new SharedReagentGrinderComponent.ReagentGrinderJuiceStartMessage()); + _menu.ChamberContentBox.EjectButton.OnPressed += args => SendMessage(new SharedReagentGrinderComponent.ReagentGrinderEjectChamberAllMessage()); + _menu.BeakerContentBox.EjectButton.OnPressed += args => SendMessage(new SharedReagentGrinderComponent.ReagentGrinderEjectBeakerMessage()); + _menu.ChamberContentBox.BoxContents.OnItemSelected += args => + { + SendMessage(new SharedReagentGrinderComponent.ReagentGrinderEjectChamberContentMessage(_chamberVisualContents[args.ItemIndex])); + }; + + _menu.BeakerContentBox.BoxContents.OnItemSelected += args => + { + SendMessage(new SharedReagentGrinderComponent.ReagentGrinderVaporizeReagentIndexedMessage(_beakerVisualContents[args.ItemIndex])); + }; + } + + protected override void Dispose(bool disposing) + { + base.Dispose(disposing); + if (!disposing) + { + return; + } + + _chamberVisualContents?.Clear(); + _beakerVisualContents?.Clear(); + _menu?.Dispose(); + } + + protected override void UpdateState(BoundUserInterfaceState state) + { + base.UpdateState(state); + if (!(state is ReagentGrinderInterfaceState cState)) + { + return; + } + _menu.BeakerContentBox.EjectButton.Disabled = !cState.HasBeakerIn; + _menu.ChamberContentBox.EjectButton.Disabled = cState.ChamberContents.Length <= 0; + _menu.GrindButton.Disabled = !cState.CanGrind || !cState.Powered; + _menu.JuiceButton.Disabled = !cState.CanJuice || !cState.Powered; + RefreshContentsDisplay(cState.ReagentQuantities, cState.ChamberContents, cState.HasBeakerIn); + } + + protected override void ReceiveMessage(BoundUserInterfaceMessage message) + { + base.ReceiveMessage(message); + switch (message) + { + case SharedReagentGrinderComponent.ReagentGrinderWorkStartedMessage workStarted: + _menu.GrindButton.Disabled = true; + _menu.GrindButton.Modulate = workStarted.GrinderProgram == SharedReagentGrinderComponent.GrinderProgram.Grind ? Color.Green : Color.White; + _menu.JuiceButton.Disabled = true; + _menu.JuiceButton.Modulate = workStarted.GrinderProgram == SharedReagentGrinderComponent.GrinderProgram.Juice ? Color.Green : Color.White; + _menu.BeakerContentBox.EjectButton.Disabled = true; + _menu.ChamberContentBox.EjectButton.Disabled = true; + break; + case SharedReagentGrinderComponent.ReagentGrinderWorkCompleteMessage doneMessage: + _menu.GrindButton.Disabled = false; + _menu.JuiceButton.Disabled = false; + _menu.GrindButton.Modulate = Color.White; + _menu.JuiceButton.Modulate = Color.White; + _menu.BeakerContentBox.EjectButton.Disabled = false; + _menu.ChamberContentBox.EjectButton.Disabled = false; + break; + } + } + + private void RefreshContentsDisplay(IList reagents, IReadOnlyList containedSolids, bool isBeakerAttached) + { + //Refresh chamber contents + _chamberVisualContents.Clear(); + _menu.ChamberContentBox.BoxContents.Clear(); + foreach (var uid in containedSolids) + { + if (!_entityManager.TryGetEntity(uid, out var entity)) + { + return; + } + var texture = entity.GetComponent().Icon?.Default; + + var solidItem = _menu.ChamberContentBox.BoxContents.AddItem(entity.Name, texture); + var solidIndex = _menu.ChamberContentBox.BoxContents.IndexOf(solidItem); + _chamberVisualContents.Add(solidIndex, uid); + } + + //Refresh beaker contents + _beakerVisualContents.Clear(); + _menu.BeakerContentBox.BoxContents.Clear(); + //if no beaker is attached use this guard to prevent hitting a null reference. + if (!isBeakerAttached || reagents == null) + { + return; + } + + //Looks like we have a beaker attached. + if (reagents.Count <= 0) + { + _menu.BeakerContentBox.BoxContents.AddItem(Loc.GetString("Empty")); + } + else + { + for (var i = 0; i < reagents.Count; i++) + { + var goodIndex = _prototypeManager.TryIndex(reagents[i].ReagentId, out ReagentPrototype proto); + var reagentName = goodIndex ? Loc.GetString($"{reagents[i].Quantity} {proto.Name}") : Loc.GetString("???"); + var reagentAdded = _menu.BeakerContentBox.BoxContents.AddItem(reagentName); + var reagentIndex = _menu.BeakerContentBox.BoxContents.IndexOf(reagentAdded); + _beakerVisualContents.Add(reagentIndex, reagents[i]); + } + } + } + + public class GrinderMenu : SS14Window + { + /*The contents of the chamber and beaker will both be vertical scroll rectangles. + * Will have a vsplit to split the g/j buttons from the contents menu. + * |--------------------------------\ + * | | Chamber [E] Beaker [E] | + * | [G] | | | | | | + * | | | | | | | + * | | | | | | | + * | [J] | |-----| |-----| | + * | | | + * \---------------------------------/ + * + */ + + private ReagentGrinderBoundUserInterface Owner { get; set; } + protected override Vector2? CustomSize => (512, 256); + + //We'll need 4 buttons, grind, juice, eject beaker, eject the chamber contents. + //The other 2 are referenced in the Open function. + public Button GrindButton { get; } + public Button JuiceButton { get; } + + public LabelledContentBox ChamberContentBox { get; } + public LabelledContentBox BeakerContentBox { get; } + + public sealed class LabelledContentBox : VBoxContainer + { + public string LabelText { get; set; } + public ItemList BoxContents { get; set; } + + public Button EjectButton { get; set; } + + private Label _label; + + public LabelledContentBox(string labelText, string buttonText) + { + + _label = new Label + { + Text = labelText, + Align = Label.AlignMode.Center, + }; + + EjectButton = new Button + { + Text = buttonText, + TextAlign = Label.AlignMode.Center, + }; + + var vSplit = new HSplitContainer + { + Children = + { + _label, + EjectButton + } + }; + + AddChild(vSplit); + BoxContents = new ItemList + { + SizeFlagsVertical = SizeFlags.FillExpand, + SizeFlagsHorizontal = SizeFlags.FillExpand, + SelectMode = ItemList.ItemListSelectMode.Button, + SizeFlagsStretchRatio = 2, + CustomMinimumSize = (100, 128) + }; + AddChild(BoxContents); + } + } + + public GrinderMenu(ReagentGrinderBoundUserInterface owner = null) + { + Owner = owner; + Title = Loc.GetString("All-In-One Grinder 3000"); + + var hSplit = new HBoxContainer + { + SizeFlagsHorizontal = SizeFlags.Fill, + SizeFlagsVertical = SizeFlags.Fill + }; + + var vBoxGrindJuiceButtonPanel = new VBoxContainer + { + SizeFlagsVertical = SizeFlags.ShrinkCenter + }; + + GrindButton = new Button + { + Text = Loc.GetString("Grind"), + TextAlign = Label.AlignMode.Center, + CustomMinimumSize = (64, 64) + }; + + JuiceButton = new Button + { + Text = Loc.GetString("Juice"), + TextAlign = Label.AlignMode.Center, + CustomMinimumSize = (64, 64) + }; + + vBoxGrindJuiceButtonPanel.AddChild(GrindButton); + //inner button padding + vBoxGrindJuiceButtonPanel.AddChild(new Control + { + CustomMinimumSize = (0, 16), + }); + vBoxGrindJuiceButtonPanel.AddChild(JuiceButton); + + ChamberContentBox = new LabelledContentBox(Loc.GetString("Chamber"), Loc.GetString("Eject Contents")) + { + //Modulate = Color.Red, + SizeFlagsVertical = SizeFlags.FillExpand, + SizeFlagsHorizontal = SizeFlags.FillExpand, + SizeFlagsStretchRatio = 2, + + }; + + BeakerContentBox = new LabelledContentBox(Loc.GetString("Beaker"), Loc.GetString("Eject Beaker")) + { + //Modulate = Color.Blue, + SizeFlagsVertical = SizeFlags.FillExpand, + SizeFlagsHorizontal = SizeFlags.FillExpand, + SizeFlagsStretchRatio = 2, + }; + + hSplit.AddChild(vBoxGrindJuiceButtonPanel); + + //Padding between the g/j buttons panel and the itemlist boxes panel. + hSplit.AddChild(new Control + { + CustomMinimumSize = (16, 0), + }); + hSplit.AddChild(ChamberContentBox); + + //Padding between the two itemlists. + hSplit.AddChild(new Control + { + CustomMinimumSize = (8, 0), + }); + hSplit.AddChild(BeakerContentBox); + Contents.AddChild(hSplit); + } + } + } +} diff --git a/Content.Client/GameObjects/Components/Kitchen/ReagentGrinderVisualizer.cs b/Content.Client/GameObjects/Components/Kitchen/ReagentGrinderVisualizer.cs new file mode 100644 index 0000000000..aed64cad27 --- /dev/null +++ b/Content.Client/GameObjects/Components/Kitchen/ReagentGrinderVisualizer.cs @@ -0,0 +1,17 @@ +using Robust.Client.GameObjects; +using Robust.Client.Interfaces.GameObjects.Components; +using static Content.Shared.Kitchen.SharedReagentGrinderComponent; + +namespace Content.Client.GameObjects.Components.Kitchen +{ + public class ReagentGrinderVisualizer : AppearanceVisualizer + { + public override void OnChangeData(AppearanceComponent component) + { + base.OnChangeData(component); + var sprite = component.Owner.GetComponent(); + component.TryGetData(ReagentGrinderVisualState.BeakerAttached, out bool hasBeaker); + sprite.LayerSetState(0, $"juicer{(hasBeaker ? "1" : "0")}"); + } + } +} diff --git a/Content.Client/IgnoredComponents.cs b/Content.Client/IgnoredComponents.cs index 9833230e94..816f88f7d3 100644 --- a/Content.Client/IgnoredComponents.cs +++ b/Content.Client/IgnoredComponents.cs @@ -209,6 +209,9 @@ "CrematoriumEntityStorage", "RandomArcade", "RandomSpriteState", + "ReagentGrinder", + "Grindable", + "Juiceable", "WelderRefinable", "ConveyorAssembly", "TwoWayLever", diff --git a/Content.Server/GameObjects/Components/Kitchen/GrindableComponent.cs b/Content.Server/GameObjects/Components/Kitchen/GrindableComponent.cs new file mode 100644 index 0000000000..a0d484260d --- /dev/null +++ b/Content.Server/GameObjects/Components/Kitchen/GrindableComponent.cs @@ -0,0 +1,13 @@ +using Robust.Shared.GameObjects; + +namespace Content.Server.GameObjects.Components.Kitchen +{ + /// + /// Tag component that denotes an entity as Grindable by the reagentgrinder. + /// + [RegisterComponent] + public class GrindableComponent : Component + { + public override string Name => "Grindable"; + } +} diff --git a/Content.Server/GameObjects/Components/Kitchen/JuiceableComponent.cs b/Content.Server/GameObjects/Components/Kitchen/JuiceableComponent.cs new file mode 100644 index 0000000000..bb4ae5a6a7 --- /dev/null +++ b/Content.Server/GameObjects/Components/Kitchen/JuiceableComponent.cs @@ -0,0 +1,23 @@ +using Content.Shared.Chemistry; +using Robust.Shared.GameObjects; +using Robust.Shared.Serialization; +using Robust.Shared.ViewVariables; + +namespace Content.Server.GameObjects.Components.Kitchen +{ + /// + /// Tag component that denotes an entity as Juiceable + /// + [RegisterComponent] + public class JuiceableComponent : Component + { + public override string Name => "Juiceable"; + [ViewVariables] public Solution JuiceResultSolution; + public override void ExposeData(ObjectSerializer serializer) + { + base.ExposeData(serializer); + serializer.DataField(this, x => x.JuiceResultSolution, "result", new Solution()); + + } + } +} diff --git a/Content.Server/GameObjects/Components/Kitchen/ReagentGrinderComponent.cs b/Content.Server/GameObjects/Components/Kitchen/ReagentGrinderComponent.cs new file mode 100644 index 0000000000..c0b9cd6fc1 --- /dev/null +++ b/Content.Server/GameObjects/Components/Kitchen/ReagentGrinderComponent.cs @@ -0,0 +1,375 @@ +#nullable enable +using System; +using System.Linq; +using System.Threading.Tasks; +using Content.Server.GameObjects.Components.Chemistry; +using Content.Server.GameObjects.Components.GUI; +using Content.Server.GameObjects.Components.Items.Storage; +using Content.Server.GameObjects.Components.Power.ApcNetComponents; +using Content.Server.Interfaces.GameObjects.Components.Items; +using Content.Server.Utility; +using Content.Shared.Chemistry; +using Content.Shared.Interfaces; +using Content.Shared.Interfaces.GameObjects.Components; +using Content.Shared.Kitchen; +using Content.Shared.Utility; +using Robust.Server.GameObjects; +using Robust.Server.GameObjects.Components.Container; +using Robust.Server.GameObjects.Components.UserInterface; +using Robust.Server.GameObjects.EntitySystems; +using Robust.Server.Interfaces.GameObjects; +using Robust.Shared.Audio; +using Robust.Shared.GameObjects; +using Robust.Shared.GameObjects.Components.Timers; +using Robust.Shared.GameObjects.Systems; +using Robust.Shared.Interfaces.GameObjects; +using Robust.Shared.Localization; +using Robust.Shared.Serialization; +using Robust.Shared.ViewVariables; + +namespace Content.Server.GameObjects.Components.Kitchen +{ + + /// + /// The combo reagent grinder/juicer. The reason why grinding and juicing are seperate is simple, + /// think of grinding as a utility to break an object down into its reagents. Think of juicing as + /// converting something into its single juice form. E.g, grind an apple and get the nutriment and sugar + /// it contained, juice an apple and get "apple juice". + /// + [RegisterComponent] + [ComponentReference(typeof(IActivate))] + public class ReagentGrinderComponent : SharedReagentGrinderComponent, IActivate, IInteractUsing + { + private AudioSystem _audioSystem = default!; + [ViewVariables] private ContainerSlot _beakerContainer = default!; + + /// + /// Can be null since we won't always have a beaker in the grinder. + /// + [ViewVariables] private SolutionContainerComponent? _heldBeaker = default!; + + /// + /// Contains the things that are going to be ground or juiced. + /// + [ViewVariables] private Container _chamber = default!; + + [ViewVariables] private bool ChamberEmpty => _chamber.ContainedEntities.Count <= 0; + [ViewVariables] private bool HasBeaker => _beakerContainer.ContainedEntity != null; + [ViewVariables] private BoundUserInterface? UserInterface => Owner.GetUIOrNull(ReagentGrinderUiKey.Key); + + private bool Powered => !Owner.TryGetComponent(out PowerReceiverComponent? receiver) || receiver.Powered; + + /// + /// Should the BoundUI be told to update? + /// + private bool _uiDirty = true; + /// + /// Is the machine actively doing something and can't be used right now? + /// + private bool _busy = false; + + //YAML serialization vars + [ViewVariables(VVAccess.ReadWrite)] private int _storageCap = 16; + [ViewVariables(VVAccess.ReadWrite)] private int _workTime = 3500; //3.5 seconds, completely arbitrary for now. + + public override void ExposeData(ObjectSerializer serializer) + { + base.ExposeData(serializer); + serializer.DataField(ref _storageCap, "chamberCapacity", 16); + serializer.DataField(ref _workTime, "workTime", 3500); + } + + public override void Initialize() + { + base.Initialize(); + //A slot for the beaker where the grounds/juices will go. + _beakerContainer = + ContainerManagerComponent.Ensure($"{Name}-reagentContainerContainer", Owner); + + //A container for the things that WILL be ground/juiced. Useful for ejecting them instead of deleting them from the hands of the user. + _chamber = + ContainerManagerComponent.Ensure($"{Name}-entityContainerContainer", Owner); + + if (UserInterface != null) + { + UserInterface.OnReceiveMessage += UserInterfaceOnReceiveMessage; + } + + if (Owner.TryGetComponent(out PowerReceiverComponent? receiver)) + { + receiver.OnPowerStateChanged += OnPowerStateChanged; + } + + _audioSystem = EntitySystem.Get(); + } + + public override void OnRemove() + { + base.OnRemove(); + if (UserInterface != null) + { + UserInterface.OnReceiveMessage -= UserInterfaceOnReceiveMessage; + } + + if (Owner.TryGetComponent(out PowerReceiverComponent? receiver)) + { + receiver.OnPowerStateChanged -= OnPowerStateChanged; + } + } + + private void UserInterfaceOnReceiveMessage(ServerBoundUserInterfaceMessage message) + { + if(_busy) + { + return; + } + + switch(message.Message) + { + case ReagentGrinderGrindStartMessage msg: + if (!Powered) break; + ClickSound(); + DoWork(message.Session.AttachedEntity!, GrinderProgram.Grind); + break; + + case ReagentGrinderJuiceStartMessage msg: + if (!Powered) break; + ClickSound(); + DoWork(message.Session.AttachedEntity!, GrinderProgram.Juice); + break; + + case ReagentGrinderEjectChamberAllMessage msg: + if(!ChamberEmpty) + { + ClickSound(); + for (var i = _chamber.ContainedEntities.Count - 1; i >= 0; i--) + { + EjectSolid(_chamber.ContainedEntities.ElementAt(i).Uid); + } + } + break; + + case ReagentGrinderEjectChamberContentMessage msg: + if (!ChamberEmpty) + { + EjectSolid(msg.EntityID); + ClickSound(); + _uiDirty = true; + } + break; + + case ReagentGrinderEjectBeakerMessage msg: + ClickSound(); + EjectBeaker(message.Session.AttachedEntity); + //EjectBeaker will dirty the UI for us, we don't have to do it explicitly here. + break; + } + } + + private void OnPowerStateChanged(object? sender, PowerStateEventArgs e) + { + _uiDirty = true; + } + + private void ClickSound() + { + _audioSystem.PlayFromEntity("/Audio/Machines/machine_switch.ogg", Owner, AudioParams.Default.WithVolume(-2f)); + } + + private void SetAppearance() + { + if (Owner.TryGetComponent(out AppearanceComponent? appearance)) + { + appearance.SetData(ReagentGrinderVisualState.BeakerAttached, HasBeaker); + } + } + + public void OnUpdate() + { + if(_uiDirty) + { + UpdateInterface(); + _uiDirty = false; + } + } + + // This doesn't check for UI dirtiness so handle that when calling this. + private void UpdateInterface() + { + bool canJuice = false; + bool canGrind = false; + if (HasBeaker) + { + foreach (var entity in _chamber.ContainedEntities) + { + if (!canJuice && entity.HasComponent()) canJuice = true; + if (!canGrind && entity.HasComponent()) canGrind = true; + if (canJuice && canGrind) break; + } + } + + UserInterface?.SetState(new ReagentGrinderInterfaceState + ( + _busy, + HasBeaker, + Powered, + canJuice, + canGrind, + _chamber.ContainedEntities.Select(item => item.Uid).ToArray(), + //Remember the beaker can be null! + _heldBeaker?.Solution.Contents.ToArray() + )); + _uiDirty = false; + } + + private void EjectSolid(EntityUid entityID) + { + if (_busy) + return; + + if (Owner.EntityManager.TryGetEntity(entityID, out var entity)) + { + _chamber.Remove(entity); + + //Give the ejected entity a tiny bit of offset so each one is apparent in case of a big stack, + //but (hopefully) not enough to clip it through a solid (wall). + entity.RandomOffset(0.4f); + } + _uiDirty = true; + } + + /// + /// Tries to eject whatever is in the beaker slot. Puts the item in the user's hands or failing that on top + /// of the grinder. + /// + private void EjectBeaker(IEntity? user) + { + if (!HasBeaker || _heldBeaker == null || _busy) + return; + + _beakerContainer.Remove(_beakerContainer.ContainedEntity); + + if (user == null || !user.TryGetComponent(out var hands) || !_heldBeaker.Owner.TryGetComponent(out var item)) + return; + hands.PutInHandOrDrop(item); + + _heldBeaker = null; + _uiDirty = true; + SetAppearance(); + } + + void IActivate.Activate(ActivateEventArgs eventArgs) + { + if (!eventArgs.User.TryGetComponent(out IActorComponent? actor)) + { + return; + } + _uiDirty = true; + UserInterface?.Toggle(actor.playerSession); + } + + public async Task InteractUsing(InteractUsingEventArgs eventArgs) + { + if (!eventArgs.User.TryGetComponent(out IHandsComponent? hands)) + { + Owner.PopupMessage(eventArgs.User, Loc.GetString("You have no hands.")); + return true; + } + + IEntity heldEnt = eventArgs.Using; + + //First, check if user is trying to insert a beaker. + //No promise it will be a beaker right now, but whatever. + //Maybe this should whitelist "beaker" in the prototype id of heldEnt? + if(heldEnt.TryGetComponent(out SolutionContainerComponent? beaker) && beaker.Capabilities.HasFlag(SolutionContainerCaps.FitsInDispenser)) + { + _beakerContainer.Insert(heldEnt); + _heldBeaker = beaker; + _uiDirty = true; + //We are done, return. Insert the beaker and exit! + SetAppearance(); + ClickSound(); + return true; + } + + //Next, see if the user is trying to insert something they want to be ground/juiced. + if(!heldEnt.TryGetComponent(out GrindableComponent? grind) && !heldEnt.TryGetComponent(out JuiceableComponent? juice)) + { + //Entity did NOT pass the whitelist for grind/juice. + //Wouldn't want the clown grinding up the Captain's ID card now would you? + //Why am I asking you? You're biased. + return false; + } + + //Cap the chamber. Don't want someone putting in 500 entities and ejecting them all at once. + //Maybe I should have done that for the microwave too? + if (_chamber.ContainedEntities.Count >= _storageCap) + { + return false; + } + + if (!_chamber.Insert(heldEnt)) + return false; + + _uiDirty = true; + return true; + } + + /// + /// The wzhzhzh of the grinder. Processes the contents of the grinder and puts the output in the beaker. + /// + /// true for wanting to juice, false for wanting to grind. + private async void DoWork(IEntity user, GrinderProgram program) + { + //Have power, are we busy, chamber has anything to grind, a beaker for the grounds to go? + if(!Powered || _busy || ChamberEmpty || !HasBeaker || _heldBeaker == null) + { + return; + } + + _busy = true; + + UserInterface?.SendMessage(new ReagentGrinderWorkStartedMessage(program)); + switch (program) + { + case GrinderProgram.Grind: + _audioSystem.PlayFromEntity("/Audio/Machines/blender.ogg", Owner, AudioParams.Default); + //Get each item inside the chamber and get the reagents it contains. Transfer those reagents to the beaker, given we have one in. + Owner.SpawnTimer(_workTime, (Action) (() => + { + foreach (var item in _chamber.ContainedEntities.ToList()) + { + if (!item.HasComponent()) continue; + if (!item.TryGetComponent(out var solution)) continue; + if (_heldBeaker.CurrentVolume + solution.CurrentVolume > _heldBeaker.MaxVolume) continue; + _heldBeaker.TryAddSolution(solution.Solution); + solution.RemoveAllSolution(); + item.Delete(); + } + + _busy = false; + _uiDirty = true; + UserInterface?.SendMessage(new ReagentGrinderWorkCompleteMessage()); + })); + break; + + case GrinderProgram.Juice: + _audioSystem.PlayFromEntity("/Audio/Machines/juicer.ogg", Owner, AudioParams.Default); + Owner.SpawnTimer(_workTime, (Action) (() => + { + foreach (var item in _chamber.ContainedEntities.ToList()) + { + if (!item.TryGetComponent(out var juiceMe)) continue; + if (_heldBeaker.CurrentVolume + juiceMe.JuiceResultSolution.TotalVolume > _heldBeaker.MaxVolume) continue; + _heldBeaker.TryAddSolution(juiceMe.JuiceResultSolution); + item.Delete(); + } + UserInterface?.SendMessage(new ReagentGrinderWorkCompleteMessage()); + _busy = false; + _uiDirty = true; + })); + break; + } + } + } +} diff --git a/Content.Server/GameObjects/EntitySystems/ReagentGrinderSystem.cs b/Content.Server/GameObjects/EntitySystems/ReagentGrinderSystem.cs new file mode 100644 index 0000000000..85a4682d4b --- /dev/null +++ b/Content.Server/GameObjects/EntitySystems/ReagentGrinderSystem.cs @@ -0,0 +1,19 @@ +using Content.Server.GameObjects.Components.Kitchen; +using JetBrains.Annotations; +using Robust.Shared.GameObjects.Systems; + +namespace Content.Server.GameObjects.EntitySystems +{ + [UsedImplicitly] + internal sealed class ReagentGrinderSystem : EntitySystem + { + public override void Update(float frameTime) + { + base.Update(frameTime); + foreach (var comp in ComponentManager.EntityQuery()) + { + comp.OnUpdate(); + } + } + } +} diff --git a/Content.Shared/GameObjects/ContentNetIDs.cs b/Content.Shared/GameObjects/ContentNetIDs.cs index 8e1c89dd5e..7d4905c7f0 100644 --- a/Content.Shared/GameObjects/ContentNetIDs.cs +++ b/Content.Shared/GameObjects/ContentNetIDs.cs @@ -85,6 +85,7 @@ public const uint GAS_TANK = 1079; public const uint SINGULARITY = 1080; public const uint CHARACTERINFO = 1081; + public const uint REAGENT_GRINDER = 1082; // Net IDs for integration tests. public const uint PREDICTION_TEST = 10001; diff --git a/Content.Shared/Kitchen/SharedReagentGrinderComponent.cs b/Content.Shared/Kitchen/SharedReagentGrinderComponent.cs new file mode 100644 index 0000000000..6aa00b33ea --- /dev/null +++ b/Content.Shared/Kitchen/SharedReagentGrinderComponent.cs @@ -0,0 +1,126 @@ +using System; +using Content.Shared.Chemistry; +using Content.Shared.GameObjects; +using Robust.Shared.GameObjects; +using Robust.Shared.GameObjects.Components.UserInterface; +using Robust.Shared.Serialization; + +namespace Content.Shared.Kitchen +{ + public abstract class SharedReagentGrinderComponent : Component + { + public override string Name => "ReagentGrinder"; + public override uint? NetID => ContentNetIDs.REAGENT_GRINDER; + + [Serializable, NetSerializable] + public class ReagentGrinderGrindStartMessage : BoundUserInterfaceMessage + { + public ReagentGrinderGrindStartMessage() + { + } + } + + [Serializable, NetSerializable] + public class ReagentGrinderJuiceStartMessage : BoundUserInterfaceMessage + { + public ReagentGrinderJuiceStartMessage() + { + } + } + + [Serializable, NetSerializable] + public class ReagentGrinderEjectChamberAllMessage : BoundUserInterfaceMessage + { + public ReagentGrinderEjectChamberAllMessage() + { + } + } + + [Serializable, NetSerializable] + public class ReagentGrinderEjectBeakerMessage : BoundUserInterfaceMessage + { + public ReagentGrinderEjectBeakerMessage() + { + } + } + + [Serializable, NetSerializable] + public class ReagentGrinderEjectChamberContentMessage : BoundUserInterfaceMessage + { + public EntityUid EntityID; + public ReagentGrinderEjectChamberContentMessage(EntityUid entityID) + { + EntityID = entityID; + } + } + + [Serializable, NetSerializable] + public class ReagentGrinderVaporizeReagentIndexedMessage : BoundUserInterfaceMessage + { + public Solution.ReagentQuantity ReagentQuantity; + public ReagentGrinderVaporizeReagentIndexedMessage(Solution.ReagentQuantity reagentQuantity) + { + ReagentQuantity = reagentQuantity; + } + } + + [Serializable, NetSerializable] + public class ReagentGrinderWorkStartedMessage : BoundUserInterfaceMessage + { + public GrinderProgram GrinderProgram; + public ReagentGrinderWorkStartedMessage(GrinderProgram grinderProgram) + { + GrinderProgram = grinderProgram; + } + } + + [Serializable, NetSerializable] + public class ReagentGrinderWorkCompleteMessage : BoundUserInterfaceMessage + { + public ReagentGrinderWorkCompleteMessage() + { + } + } + + [Serializable, NetSerializable] + public enum ReagentGrinderVisualState : byte + { + BeakerAttached + } + + [NetSerializable, Serializable] + public enum ReagentGrinderUiKey : byte + { + Key + } + + [Serializable, NetSerializable] + public enum GrinderProgram : byte + { + Grind, + Juice + } + } + + [NetSerializable, Serializable] + public sealed class ReagentGrinderInterfaceState : BoundUserInterfaceState + { + public bool IsBusy; + public bool HasBeakerIn; + public bool Powered; + public bool CanJuice; + public bool CanGrind; + public EntityUid[] ChamberContents; + public Solution.ReagentQuantity[] ReagentQuantities; + public ReagentGrinderInterfaceState(bool isBusy, bool hasBeaker, bool powered, bool canJuice, bool canGrind, EntityUid[] chamberContents, Solution.ReagentQuantity[] heldBeakerContents) + { + IsBusy = isBusy; + HasBeakerIn = hasBeaker; + Powered = powered; + CanJuice = canJuice; + CanGrind = canGrind; + ChamberContents = chamberContents; + ReagentQuantities = heldBeakerContents; + } + } +} diff --git a/Resources/Audio/Machines/blender.ogg b/Resources/Audio/Machines/blender.ogg new file mode 100644 index 0000000000000000000000000000000000000000..72dd92af3bfe8d3a77f94b1179ab92dc65600adc GIT binary patch literal 36334 zcmd42byQqU*Du&ea0~7dT!TZS!QI^n?$)>y+@0VAcXxNU;O@cQ0|c1P^Ss~v?yR|Y zX3d&^rn-}3X2(xU5AckZZcR%E3nm38b5a{iBlUmKNu@|x znORtwS(({LX%uYjEFGLoL8f-jw11%?KKwhBL|8-}j1B?7HCCk+Pg92D@wH^KUg`bDxhtq`BI56J`<4q591fE27Eahg6fsQ*$Az=#GIM%8fO z4T=dg16t4x9ymLES~!rhqdPdr1Wf^{GeAS!hnb)VCo>icFkdDJJappG!y3&HY2-Y!%`U%$Yzr|@y z{S?m`^8lI%Qe^|Wj9lY_rg3HKVWu_8thQxkujpV&{LzHr{uQJU*LZ^E@JFJe@PCO(3jVn+{zE!@efsPWIJs;Q{iuBfVMrSMI&^UtZOO|z>lfScgGBSlPY!FJBY zWzAV_BgJ;@QBMckRY}cuLsf5$OKs^vZ{@*9YthB{hEMHYcFu)=&e?Rq#a72fPw!Dy zB}Hy2*>ujub}iXd&&_n@kz>wTZ%)m0#aVB~)l{QdPwT;F&Lwy&+0;P8R14Qt?=e_s zDS6*nZ$raWgG(LUtFsimv*_|QjZZ-hjI1}!uBYLmXP}|Cw8$}+^cQ(WRZq(mjI5`z z=rYaz7kQ0SPb1|ovPO!_hBKJiRO`2z#)FI2Qu5BC?GBgT(xaNzLom4aFLJAk9816mYp7V%8ZN8*JRrrO;atP?~Z25#$&Q67)sN21y@}QJH+63*8YRf zp1X@4p54abMB63O@MXcv*xZ7xahlJDmYIQD%nmM3_tjo$S#?GgJyJ0PV)yy!Q2k3+ zT~yWSOBuLHx7JsC+I9PCX)Th@}Y6GttVU(Mq9-C^~A(vuLX- zuq-OI%(m1{H%~9JEUTkUuVS!Fx75xyOHVIOE3!zhvQ96mh$x~RFR~h|vrMl$Ypb(u zud-Rov;3!NlU~HoURSBGjTe=z)>)P{*_4&pwwIkf*V&%7foEb{R>YW5X7v}jj$y6s zGk8{ik<$;;ionybNiU<<$u3U+i+m7X1O{iwC@LFEIZP`9BcFt4TmOS>wOVGG{uh}s zqlj+2%J!w}bga&8!5>KNDRF30OCUj7mA?=;Go#_Mbe z>TO=yEYkloE4sBh#+NqmtS-l@?90n4PX9J9o~s;A+n77*Y+lMLp4;fx+U!qR*B*RC z!7ix6VY>!iCtw$RFa?ul*ll&x)O0xI7Me`KE(qRIzp~4%fLGC?+(Lt`R*LP{Ces}- zbF-<=gUeE~i@}o5-jeCYL0jGVcwOa7S^0C*#Y>;VY1I`10D$WN0KhTlB4Og!p##Fe zyF%30C>FSA zOm6VLwfuv&miw=_K=`Wy0D*g&V14FUt=1V!WrMX^TGn(fnQ|DOX9>2H4wzC@T2^&> zn*J~4^aQM*e<*EjOzC;0Wo4&rbyZ-alvUBU*PWe$D`lr+RSYkEWo=dTV3nTs)qsbC zO|aHvzYgBryDne);ww+vnEv#!AW1*~w&76#Up{bF#5gFkV{2NBNCQZr0RGG{WPxbH zFl0e-%F<+oN$BA1dK-LMH5A69VK)&2pizSrB0^j6_nQ09h4=qjNdE6S{+A<4|L>sw zmm~gP!TY(4=X=1-Lf| zjpuLiPwj7^Ed5UtJ~v4b05A-I0(|jDE+@~#jQ)WAcX5J45P!myAIeifLNP+I$UN3u6HXv0)Qv@WE;| zJwK4}2@fE8phSa20dc86B->m3nV@uk4(h=Q!wI8((rzr%&nSH7z|OKbN=2b^ zHEiH4s2k;w^Yp1wZgQAJ;jtY7AUbV}ad9{b9nKzG`JGnO9j4bi%H+g!B>kP0~suE*cLti;#uAeP+T>$Q7%vxh(u2D8jps(vU@XjOQ@ zkh#YT0H`DcYzz3K{`6z`BJ~B<3^vmt1oVX*E-cuZA1YzM&4HH0NZ5=M@HVQ}%V?&r zT6;5G6v=vvFBR|w5|HVtX0kEc=#r+K=3b1bsfh~rEhL^)6%%)VDJH;KNjpPhdo}ONZzQG zHXNg+Puk1{0WaB16@@8)OvnbQ)vwt}Mk(pHCgv)A+kK`NTq-oT z6i*e){kjlDaj= zSepHn0P|b2!*@F@RN^+Z8OqMs1{u5+LG_PM=6Kaj%hmFF5zUdP55UNRGr4=%5VxAN1iBfk>Ip*boy{SFjq{ z5XD!LQDJn*j?DCO*h|_%Oc0C$UpE0Mqx)C$iTZIc3fO9+<4>^*%`I;?nK--<0PbZ` zwUuAdMXvA8#<2lE=`=3GKk?}D1vdcC=Al>trU*ZXGqpQ~v7lAO z0&Z~2XHazi#Q87Cazn2{ngBZ46UVd|M&1%CltKU$a?gnx3rysssFh597}sp*S2RjL zJQ+5E=tXB_cTbkc{Y&v89dBQLG*&%q8dh)s*k|6z$FWpU!Ym#Ff2I>MUA4ykCU>SN zGx32EUC?xY;STn1>{cRgczQ3hW4v~^9b5>6gR;EWqu!$r{Tta7u7rw-0!{oAyAU0M}H-P8V8?S;>lV#wOYNap@RuzcXK+uPRfCWm@J3UIheb$3dpqwDN|vl@*DYk5glIn*)k#i~&D!=BBEX8#Ja0xRokKh*cFubUUuQ*LLVBt#TPz@1}tI4lWwD`@u`#rUs6v& zAmBE&;w@d-)2gZ}3!jnqeE1IFQ?T$|(tw1!-y4A<^@SXa+c75tHA2cN&DcgNFOQ4QLk9W3)28b>>`ezhV zFk4yO%^!{Gm*#8P-n`gBn5=O~AHLUO*bwzJEF855zi9SkwUPL6$eiW!^UbMlJ0+KW z(A^V_w;bazJ}s=Cc?Kx>x`fnABBjJ^n< z)LDHIukGudpne-+=HuscTK$zCAgUr=_@YEDIlwtqx#K#yXlB{Cakf~rgS`i_dJJ|A zmc+X+IPM(T3NV_n^Q7eDjtik5)fmV;YTssaw%>6O-gS}itt`GKq{y{3YT#OryTLL>}=jq~3X zUVc#&(^T{ZOgz*E&Ji5=z}Ix(qtE3IyB5Y-$jh6MC(&<0JvyR?CG}_S63HsPu8%1Q z;*p}Z`9%u7yTj{yD7H`u*i#0>=&JerF83A;*dd-Erd-WQU*Vr$n(n(Ah16Bs|5UDF z3RU%d?L|MsmVr7Jf#8kfNP`IWUX;sQ?l1FmMGsW-Ne?6pamhQ$W5+mu)cl^7EC1DHMn66opU8+4zA8C3Ha`iQ%2Pm#hN*J2Ze#$%N-6;aHaWPnY3czF$)jYU8tpU7&)j!rorl zQ>Xlh$h0r4(DRN~9#@O}EbbpfJ_Q-N@|K34BRm~Jd-4Fnl!bA~$BUkM2vxO$5jj36 zDWQgRSSwij=Or;0$HO!&D_j!{T@A@GUv1&ARbu!Jv*sRsk2w0@IEgdQWtGoFo@Huj zz5}1=Oad&n^#8C|Rg64F!Ztn!!ANT2$RtoqkZ)ZzU1#5G3Px?N{jw3ER9(9>$_1YV zSs$M8D0j7&y*o1@`gynKbn_BblTynov+-J7%1z6oP#2lL4_xHUbo&;r=2Xw}iCHpW zkZ`eK$Squ7cfWV5VLkf%RN*MPdASTQF5bHJ3x-u+ne0VZ_qPyQPSve`+LIvls3sRtK)Aq!`zx&vob{GcH_W$|8gen(b+KnLjv;uAS=? zz)Y{L5hQ7*VxUZ`s=a#F%$ZxtwX`y4pZ|*42BoU9%YEn-A15gw(s7MHMtwM` zSChp!1PxGC<5tc&`C_!H?T-GMk9HFgvGH=2W{zMlpMnf2s}v0Rc0O!lOo1VAljhBaK!!e&5hSopN>+6#=&gxG{z->Ck zNYt|qaEd=?i>nRiwqvwud#F?Am>_PyQ|4yF-Fi`1jqYw}z2fDVQeCwWO53d~)u9br zp|`LVyXwYc<|X-bt2@a1mJQ*c+#(Ds8q0YniTo-rD%ginI;4YFg@gUv=E*fWnSRx- zS?8gc8g6cWq$)QT5N3ZCP%VJp)S_BL_2XNyb^9rZPv3Hc@QL$ z^FDXHW#u*@)FTqE;^QXYVhEySe9;nLL~c?p>Rd$_KGHVZ5G_(RxwD0Lh>LS#hO@xly&2gbeh9H2CGE#e0pE8&0 z38R}gIfQ7EMUiQ^JMr6|u>I5r?`eC_hHIL>;VbfO6y?FfV4Vr~W=Cv;bY;z?b+xj) z<&)H#n?`g0yZa+5p?#s&tFpSdZhJn9Z;jL7RQNB{o&i$@-cLb{P)72y1^zpix!XDOhD?_6+c8&g_{Mel^V9_tG<)1Sd9uIT+*mqK#PvcA=R zGkgwzxM&MT{xwu6Xw+mV9I-xPO#LzBFx>1>lcU~L-Ad3rQIm?fdJ29_gk?^Q!mu0P z(;VjKN2;ynjCJg0ri1gX_a^j-qhXwin6|6A`5eA$;1yhSy_+w#(@vkF^wvDe$HZym zL~(Q1di_?IUj~Rqju{f|f1Uy?Qq#lYx@8Be)$f+O`w86%wJR0z!=bApTG=Uneu;_A zSO*Y46Ui@fUKqjn@nA;nSSg#BM#<`YX3u11^Xyrh6EE2!PR29zhC0JTWDd%#yH?Jj@?ITRW^$@XpR^II483^C^dGaF*;lY<+ z!V4=2bH0w~$zV2xzKLtk(U&5#;By_UF7WanIrql!(RD65b+&EqxH7IC&K!~{=cbpS z>!;RtPj+^``xA<^5JJXmpOK3JPZhdVIZxt)EpLn#@x7M9wq&xHLn0*!mxD`pKbT|r zVD~)H#dqRR9O1JrZCP>iv8RO4Gc+;}O%JLMlMLGnO`8Q|_6hRW=*{uTpMfl`VcvQ< z9BJ+12U2}AjiwuOUUuW&W^BEVJAbme_`EA^W>vjhDlU8JiT6)Owr#$pELaBh<3>3* zydJyC_4{(w7C`y)0Ih1WP{u)A4ll!P6!p!Gn#hd6#$p0Hv zAE!k+T8|N7dS7)RkSC?m3U|Q|6XQRJ5ZnKK2muAI^3%135J$#Dge8S121F&q#)L$~ zMn{H4h6hJ}PmGIBiVY3(l}1qv-x}um%wQ<1Pi;+2IU)zBF;T}bF~vP#@rtN=wWPlo z9^d-4iUP55$_S+6Z8q=uHT|TwoGx2Yyj32HRO{t>t?yqyH|kxYTY~nKHtUCp(@v)SLdBZryQG)9+tX)f?e!tL2lActJifv8@=BGsJ2^earsS$$Id;!y3$T6W8uKd`ctC6-b^o;pEtvjO*lZ3B7_4 ztU!bi?D-~><^%P`U+Z%T?HLN>rqm{Lg^J&J9dEvBG;ajIK|vSPgyNW#=FmdjfB=W{ z$E8_rwdAR+XW6LW7}~Us41ET&?YtbQ`*Dm-<9VJ z2t=wYu4yi@>L&F+;L0>({`_L4m_Nsrs2Li1X8mXP^c=e<&CyIwAQmPl|^FCPxIk%BTU8pnYy@`0$p%>csNmT?xn zFY6;8$4wYX`Yo244^hV_s9QONMj80d$&G4$d8;umzKH{vV5QNNRFcGSLV4XVlQw;V zuLV(Plt2W~z`f|zhSqDf__h;7;w4Dw0-+0k3XS#-`fmGaMn68F5-JOz7+Fa5@&2%r zOT#UN&sBLuNTcC{;>kq0E58Pg1`l$AZodVM>7&G0d;BAG#32cZ5WNN(7oHoL>Gw7F zXUXA0d$y^oelG5=ws=Q7D*^^VoTfvn_EnP~X9YY_y73j1eALb6iJV=eh zJwff`;?Yx&c?iC-Gg%pdu-SCP6ngGdik{3xIJLyga48J%^(S;LP0m4wc-bcHT|6W> zMl@w?)p+UW;z$*B(o;utFk>Wl}sCy^6%R-IWQW44K3xpGq<#2hJn{Q6TqA*`+bq&5p zhIh@cB@J9Y&$7Wg$lkd-o%8$moA!Nlb1b8_7+MOkVWF4>XwUD>seFjjZ!{Nc4f?f* z)tZMV@?Gc1`Pt~BJts8K;Xz6OE!Ux{i4*|@;$KDsQZ?pc+sC!7B&R7n$2EW&2S#*p zQ3IEu-v0(@v9#}HmJe!J80)@q_f4!uAxx7M{#DDx9-z2vIq zoZAqc#8=q(R|x)}$s-CYL79)#vMGGt?1Yx(2O5_Ud?{{M>sL-d2kWGM2@tEj~#Q{jjnj3OQ6bA`EF=w z&cvL;qx>0A{qyPieP}jgRXz=`rGMf;cD~vq>Ym(!+_zYSvXl7tyhGj`4?!!XKYf{3 zzyS+!7acLF@h`m}T5`Dklw9-eW``!9op*vveTY`q9#hW|H*Sdp-H3J#4jeidjYViR zYjGx3_74O;JlqSk{$er}Ss)T?EFZT0SUVktIBB;AYx<1Kd72^K6|mRWmi=rx{YG$G zs3=^rF7JfrXL@2BaR(nc6k}xLgzsPXg5%iR3IAhGKv@pfB6S8u;+lw92gN;y8?lHu zfJOJHeZngdLN7s7ZQE1Z2>Ye`0e>KY}glbxWO4crK1>6qj>SScs=)VU-BNS-M7pR{La zc`r`IFyA#EzS;o8#82fT_(&2zf$od&vZ6E3svoM)`#M} z09VbB2eivRt6!J!aG{>$L$N4zLBhFp&pP{b#b7?x%VCD=M@ zL5C7+%7kVn)Brdt_|RIrw--EKiPIRy*42maTZ8aP3Us_BsfGL|5yFVD7xOj=ee>vv z`-c(mXwd5NoH2KY3e&F#T#2xS(v81eGn-@O?n zLsRf<@!n}yo0L%2qj-yDYunmfLIj!&I(m{ZOc5Q|`MQ{rg&EyCps+;GxzJu#47b85 zaY6iSZc3z?gBGA8-u2wof~<6b!QBgN!6XurCII{>`u=0&6S*gGr~VS-K#`S3tS5Sa zvUWL%Jx6D20d}hJPPKTK>eN_7#adsC&6gMM{$|s zOs<$F-34#(l zozs z`0UzP?qN3JiLt|e>$jwSj2dlhdu&yOl}QL7cCS~E} zt~}!Oh@1cP>rRpv0i?~om`kcNKf-tN(@8>o8Tr;oD_yV1b#-MZO$Gxmxc@67S%A^Q zNaAs*6KYA1khsS&xxZOr+T(HkR?0A_sE8LX8g|Zsh6R~28+<22TlYER zY;1I_ph4t4Zol~XR&S?zZRpo}9=Trs7a6l3?R~%EsK<)=zvdQKyqK~bdlm{SJ@4y! zErs(w(cH&pd(3S76lcC4lRo3;%})$UUMy2!z=$q$Ok2h=Hf(RQWnd7Dd+H0KWaVjZ zcRywhBmG#zm1QtT#SI{)Bd(f1vbpM_cW;Bc5A@V1)>EeVhzIg=6DZnnZk%h5&tIx% z_ZG+?Q>kV2{iySua$j?dpTiWtV$7aPzs`*pOjF z+C=>5!aj3$9>P8emCy9+2YdTWRt#1Ak7&3mADY)F|^fOhcFto8vKG#xxG zuGXMf~Q&&t$ z-%M4>6Fonh_&lX5nirU+QNoXLbJ&EvJ$Anycf4(}yK>r?W{MI4gHLbgHE5gSU}td* zr5v`n!<9wC9G33m&D*r5w6>G9n8w?2_9tM~N~F3gR{|zPT0DdM2{E0cd*g`@u1gHl z@22h(jlztGzop0dY&pR}foOe*6rd4|sQXtVjWqz9c*NL6VP2L6wc2~fQeI2T;Ux=~vH6LUxsOh(WSmdc-K{1|1$J%YqYA~`)pV{F1U8p&!joT5R+?rl2*h{Oo zCVn69KL}$I^8hx1#0YwSvZDr@z8zA#oBpCD9fb5xr=$^gB-)dF;HTr5F)>A+xoT2g zE1XF+bZ1W9WEl}U?bT*7CaC#U`m8oTaF8>X(j&_uxq;Dn2|%!H9fBVwSX+QBO!J9D zSHqcHgVc@I@cqD;C0*99w@^>!I^u~$Z;52!Obx-Zj%Lkimfllojjn&ZLAv)zK`9Qq z>5zIZO)k?k%^EX_WwGo(ERrW*S{}JK!eXJTw{_kiKAnp!cwBblOyAT zL!%?&qk`fhA|m2K!$U$tBEw_BJ9wQ{>L6)TFuM&B4kMkLytVTp#SW=VMYZ7NF=I}K zYWuC1x`g92!rBVRbX~P7IypPe@`2F_E-%<@gla+$&2i~ehF|@vY0-uDH^8u=`(^Da z9U!~cSLyDzIe+0qw1?H8kKe!UUr~U$RNP6gYoIdkl>baKL7jVPJS!TPe!zhEp~H8c z$!b-jZz6605FeHXhl~ zyLW6`&lev%dg4hjPb{X;Wg9F^#(GRO6KA8M-V~LWg!9nd1$=Ugs{QUmZdA^1v<8#2 zK!sXWC>tY4!OKCO{ZVpw%E_#moU*xK*%VueGXYKoYUD?y~@i!XAX<>4HwY$v=O$E=Vs*C(Sz>r)u1u~v%*9QcOe(} zw&p0QeJ^_dvL%rtZG6k8vENXKibcoHFW~7w@e*+h@S-6qsz@v4R&;r~lO;`@3lOBM zOAE~u3n=iI)^IsH|Dt8EnG|}H$)uU-SfcZ5G;eS<$sQLd#LTdv#0VkJsGtBq4TBuvSmdYGs%$kW?;{HZU&aep?GB_u= zC!Xym0<@#OVHSK*@_oORG4$xcRMDLe){j#FD&lxO}YB=rAqdBT!&aL=G z)$vbv;7}DhqV=98uLM!UkF-4ykJgQ2m?LJ=sVF_*;7#pY{!wiOHw-n}ZA2bEfegFy z*n&+y(k~U{DY7(q_~q=eTmbPH(XR8X6cy;RVH6HoHr7ESgH{T3zh}Np#|ztm`d9vB zwPHW>dlY_kx7o`>arXI)pwDMXH66H}SATYBk~iYTD^D7!ps@7e4i}osizV7&=q~8L zz5P5{$Zmd1Wk(OIY5jQC(0P;h0S9YcKWYu{=TTRQ0mlTCYui?hKa}HKyLZ*~Msi?4 zL*z}=J|Xl~x_k|yKHjEe+$V(qpvIMV>7Z--smDmgxNu;&XY;L9%VqtbN!Q*>qI>!t zJ2t36xWa_3?HOm5YUGf0>VrtAhE{T3rjq$M22X9-4~61un@79(Z4zCHSuAo*C>=h6`RNpS+@K^b0Km3g|*e$`K90jhMvi!(8>due}UX9qOv-Nui zKWnuZ9DZ2j#?yL67p8sQi!fnr4^q9D2pzAPT>WcJhY#$!bSEzI@hPPD!oPz4*qp78 z)@2sl_z-IJ)N3rbI}96T@}(0W!2-u}@Tm+{U7cuCD>GF9zTo*RgzNX*_WdXxXYG>U zKb&FUm%&wAWJ*4;-o#wp+Us1(R3^c(#dJ2!R@G4o{(-b+7-Dm?2Vz*&J|x_HRWt6U z@8`fQaWOS73~L){Z|mZ}r`P>5^ywp^1F}lhBFmgLRi5jw!4PR92iqZCv~DOgXx`a4RA$Mv~jy=a*lz_(c4S@^tD={pjfK!rRF8Xn6jBP)#~e zVT@8L|M(k^lRgWcdq?llJh$@5;FRw7AFQGq={;g2(t;mr_rs=)eDOR0*~dhxDtT;& zy}H|8YsczQp!kMN41h@iT>glyeNOtKiU39P3(V@eT8y;?u{gI2xvt6v4Xf?JzUsxF z5mTsrBX>VSndL{*oix_ARG)yuF~iSn?b6%o3isY08G+tg3CuIm%$pZticxoB9_vrx z42z~~A8?cqdwEpF9$_18^aBzU*(Cfm&qovwrMg;)%)ZxPF5}?#hnH+%IG$Xj;OVD0 zFo%$G9`P;S@^OvqiC`f)7R5~D@BevQ_mQXyT5 z#_|1^1Ked&{Lzn=c*xqgH&h2fNuDT0xn#0g#+Yt)D7}@bQRks99ZAwEQ>Mb4DSUVU z-(w=XW`h(V%W%=u+f-JgFe6UfFR#~f9mfLk z#>r{KSeO^j1?o*v`m=i<^n7r9YHFpm<*{8&m*<}P!<>vxLPud)h@!>q3_1X_SC%Da zhuDP3SC43&p5(a@Z}7xJ_u>4h6sY7;JKr=urj-tMFwiEHj78T%xE?1iI@-ySsCN@Fx;<3IhdLW){d$h6as_O7f2@fmV8v+xu=!v(f{~3sIjr(c4A`{mN z0FLeybu=e^w<$lw;xsN<^PCom^hxD;X1_NN$K5PhwR;%&-ljD-D~(Jx#YDkP^Berm zv$w3h*G@tiKHqpsXQR;;G)pwXx=$|Mo_G`tKlvG_Me=Jz$_K*9D@5Aa?I^s}VOJGY zvxlf5410*MgBcg`^j4nR+M$qAI*-y2mhral+js#`6KdZ+~PIidyfls4iAeSF)>x?kyhZltCTJ2#W4 zN*ku^39Xqw5s+iAyS-K{%FMP33q2!=bzMYZsF(UZi7JSiCy{BtwE44a?CF##4K~-L zqfi&qytP37fpd>?qf|o&__l6@?dP}8Fsn0%j6ZmK@w7sH>@Dnp)>^*O_tM!g<}-Rd z_EQ4^BR3j7#!PBW=$tH4+}}H#4>S%L8}gt851fF4LdA#73=dd1Wv)PaJH>Fe%dbwW zAOd)VvK+o;N5%ucL!&fV1L~nTlwhhg#!tCg*2B6wp8-lZ<-y)sJdgmf??2(m`vG0R zO;U@j&F27*fMIhEf<&8#l_O*T0|z^Nz1mu01zz0H^IOLqm&&Gv567oe*^126oDc=+ zA%3S7<8SMPa*?SOg3g^EIIoAEa;*YU5uFLAmme|f@bfN;TXDf~f zN#Rhh0N`AA9CN$XeC#AJ82R3FVOWd_U1&AOnHAyd{Tk2^ngPDR&7LwgJ!_(gC)TJ# z#2XK8%`|-kvlPmM%z?i8o>LwDwp|tHFn^U>>N25y3|VSS zvDkLiwEm3GE5s){khxJgp?%V55`&x8Y14kxoMn``y6fRVxO|Tmc_ZbLzDgeM2`_^*N;kHVOUZ2A~KrO>Wid-j6IO38h*25InPe) zw2&=n-7Sm39xD7I&Rmft#_&FumOI`jMIpxP8l|*khtBx<_awecKgEUBEKBc)lLi2> zPLt@`d75u)jsKy9>y}B0N*E@fhaz^|D|5+c^I=tJYod9gN^PV|a4 zRlW?Jkx8R6ame5QaXVp(LgGga#FA|^sw!1PjdO41&oD%Jjx}-ZEugBCWZ7Vf)=i*3 z@RSY1T6S^Zo~nPWGUswVJl6TjD!(^`p0=Kql7;TsFe8EKaK4Px6r$$9wnFqv=4PM0r3d#ja1D6Eq%(9Ec~Iv?ub=A3IVjm`E1laiq9(mEi4(4c)!kQ6@QHRNtqx#QBV`QL7+gb$8>G?<^B%PE5$SK=*64W)iQ@ofuP=F^ zyN-zvRQ|a3KxQ+w4d2?xr&^~3VGOmY3`Sk^=P+FFPj^T4=cW)ea{CTwv_8b#60;J7 zNG%sT%F=!IL4oO41EQ`({mdWx&E1qswc&#sXVmU2O8oj>&h>OOiP}Dtw|^$Sm6S-7 z+_N0{q4YjmFQNazptf?k4{gB0eB?qvN7Yt&*_#Q4%2k#Ue^UhNKd((p{P$4=_}_8> zgHFf+L@}Z9;ZcdvN#7$QBBElWA`+vL5)xt(BEr8##V6?_5JNJqWE;kOh}zk`>pYLw z%Qd4-2r3-)v`T%LDmbSo>x#9>B*;rm+~DRxyqU>4Vs*64*jl%AVA`Dx$)9;ljV_3| z{Qb7LpLJF0C6_Ks>09PqHbmgKMr9p9fvYL)qW<2g?t8sr38!IBM=O7a@xC>!J55HI zEkhxR#}X3+*h_|k5Ymc(1@DKsHQUB|ciCep&jLjaV4sX=0oi;t^k z=8FLgi=u)UIl~{*ZK{ggiVwSQL?``kmL~leKV&w_jnQ%leF$fv4KwRqePtW_!d>f$4(^C$eIowN+pC4dBy8Z#M zxxAq{)oj-GX2@iSgp=Aqj^^20D2Xn<#F)D`3RL%;;&~+GCE3Cog>V^u`9pF3(T!F9 zNcu4Dk-nEK2t&Bcs>^7gD_$cUZ&E(y;lAbi7xme^r`==)7c93ti9&kE^dA}Gg7@g6 zArh2JkNB#m9Yq30fq9k-~t3jH@G>1ElnPDL%$-S-k1MzA4bAN1XzKeuQsK;gZ8FsZTZK#Yy^B~eg=}h z5^1!6*x;=%f)qSSW1nz}F`tj#NRx%+Wz%+Oa1&Gb^FN3*U^?H~ZFDs#w=!Q3IrCSd zWD_xSHl4rPV)ir9McQSns8vVHw=D=v!;i+~6FLH27AK;PgJyd4SU7pym#a%idEb6- zSSZr5RR*$qUi~?Wp5n6Ye;@=H?r6u8>pY&G`sJl}llTc}zXx(O@edq0T7KCF2uBP% zgq2_-VpKvl@00=K*w{xGLEIG;7eanbEY&qlpxZ*v{ibCg-5+^VLkYGeJE>4)dqXlF z5~yc&Z~AlagAu33_w40La#rCMF3M9LdxZfz;>N2^6({ zUl&@P51+b5l%DpN+N|DG*ZLw(e?<_R=}TVMe zOCX>7KLGDQ5Wga)&vlBb=#K`O$9t!+id@x)S$zsZv%B%8YCPddaf|1#b=yj~Y8Xz8T&~P{Q7{>S|$rx}JA?=1slo-NSuag*HV}o+uUh_rN?WnsCJD)l)_IyE6lsh?G$9ROZ#k)BZHaZ!?XSx-EHjCqq`hAoOC*Z zZ68(E&Q@M|3`R22wtPc!_tfJ6JZ)W)u1UNx7Iy7))8 zV+8Y(+m(4|B-g=!RS#HZcPDD#tdl<7l+SH-!!NPX2+Do@3nj4nNi%?<)N8DCB*k8@ ziY!ZYo1f9L7zWJEURAb*S8-CBgbK)U7lsBN+RZCIVg_wt^b3sP;l;DLqy;tsP^1>& z$Wq%qbgY)fm3F-N*#6(IYe(3NEjhx#ZXJ)bqFfxoI!=3XRYaf2#N<=&r!m$YlV0*c z?07;r6$AHARx8#n*@#K0hgj#(IqmYCJDVwml&-4=a>t@J2R*6rEa?pLun$vo#z}w3 zhe=8|XP^dLY#22DDb8EwC>A~~Go?f9ubgfGgW)vjNZA-tX8XN24^!GnmyxBrM z%<^W+uQrFZ4(o{Lg4UWtpEF|@Gv{)$i@j#nDVOq5;;6`e@SbGJFQLz5o~b?4ZfdTA zIXm*V(+T5r=EQv}XIjMzHk@o0_5E1}IX5lEyHCrpLeIMT*w(RE@#d(C@CG?OkFH>rIyV(+G z=TD%pSm*h^NO}n|-dsKEbEA(UbB%F{x^DtGX~;iwX~VVVUekxc?Uu!84qZeir2JWt ziUA2fD#mG|N_VgF)u7pT#A;8P3}s9lM~5#^d2;vS1_0jb4S)%=fZ2gDT+7Br7oDUf zwQPbcJ?xQ#|9+{qE!~&H<*7bCi&W3YDH3Ujam52vd5n=P$a%CQ8}7She>zIPYaff} zbDwzM{a8zS=rme=I$ugB5q`_WVw>$0!Go)3)ps2AWX#4xT4ik(Hd)&p zA=Zr_q`FNTzb5^%uC82qz2y z+=C_$(uoOv>J1b*QY$9P8U$mw+ar6Oac9z-B!`fdPkJSIIDj?4@ZWW^l`F1 zF4Zm6d}gnzP(PLQRnPvwgL+81mBMe0C$zaJABwN2u6$=2K>D@q0D^6G~ zPFV41j2C2?>IujsOOmiAsh&3(8(*og`Ph%AOWbxACOzql;)C4XNdtUj>ZhmaHJzni;%~wFiDaK1meC+qSD-bdIclYy-i3Q&tMG8YiF|Ois zEAkJvllrHydD0yuGD5d!F;kf2bIci7%uUU=F`L=&A73NVl{zMBz-cOU-W<7>xf~ea zR4<B5DU};flwA1?5CfE^T!dI^(=~JlO?}Me!x`*<%yxlZB*9#pa#R<)GUCBx_R$W z0KWO%K#3VvuxUEP#`sY0_0{!C947$4!n0r^yWx9md%tzGZ2bJz{xy(MSeGJ1dmsyc zPk5;3>-enf80}4^-`rngUY=@Mztl;-COGWk*xDNo?Tok_g1u_chMjgAoL|dZ`m4Vj zKO~b+HwJ^hHb)XC#q!q_M#2@tVN>RPpBd5QB#@Hyt z>`KflmCVsnxO+iHyY+|^^_}b5$5pc>=G|8r|E(>$w;@xy9H*;p=Y2z6HaqmlS%$6( zq?_(ad?M5Hnj(wYL8dNJfAdS57tl%`ueJ;54=}`OqX-@AMc_dL^1@Eu$G~3Fj z+i|Re#A=yhQ>9=1V9lapPTW`vQDMVWbBef~3{nI#p{yVDI5MUb3$Xu<>NdVD&3ZKg zkc+(EpB^3>9!{3%-r$`s@O&+U$T#$=;c&uAh|{h0IJFU*y^W3>s0$TG zraU20Q(!+o^lGzR{E2~@%eOP=%ydtkvedy3fl%Lmlj)(K4pVi6{@=-A?<)M2b~RD} zUI!9Gw-XWux|nvt;4J4f#+@d%tdk2NF%zIL1I>&DJ}MsIOXS^5jt6*tt&Vw|m`t3O zs|LVQPLQM4m*3pp`^Wz|^8T(m{QZv>VK2PW#+k@!Wyaoi$R)WdBy2EKXLw~OBy}vh zypu53KHue*E(oEg-Cg`r+|=qhMPIJxhU-%8J1xE4c3KgREA!4f_ERD3EU)zoW!{?n z;8je7%ygpl1RKBvx~oJ2Uh2(&nzWqBwt(lC=FuZxIkc6XwFF?vI+%ndCG-793w_() zv32tp8%$^w${^6KhJc6O?qL@Dwir!6XQyS>fRV|xWpFzjbo4ZnvAcbsC9ojK)c1<` zF4W_~CBBztg}8%^ylAwKXH5H^L9;K~^ai(eEm0*oBUcs$wB}3Im*uf18%w@c)C>{; z!Yoz20KOW|(jI$?&D#RT@K&#R;&r_e+qMQkR+1!PE8gf8W4xz+H7lCCehp()j6^hR zE~$?y`PCf1z{m_2HKsH7MWCKiIK)rn|L}Y|Pc_k~Yozk>0nT=MXZG=PRK9&jM`O>I zAz97l_0Tbh=HhVb%~%Zamv`Bt^vjwL2gs$o3^hP@=dsoJNzu<5M?Xq}qEAYa08eLU zQvd+KL;?T+0001uT>tFcuu&QnG`CsJlyE&%Xs3= zY*r%gl0ff-HD#d>)(`1f=_>Nn=N1$Eo4%Y?q<+LW-DlxKQx{(b#%-^r&nZkI!A%U> z^@~AvGR$r9uPZ!Ewy!T$X~jSVIC>GSJ^80+Sw^p-1FROt1OVR3%>W;!fjuuUhHD*b z9@Ei56g(?1VU}gL|G2^AHEg;u&tEJKS>Kdz8yhV-;z&cXQPSZZNm+pM$=X#UOo;gR{aD|S`D&3HH6)uAIpdo@L#=3> zR^*^*_UR^FqY(y1W{D7C1GH)@K$wvM0Dk(-gBa6;$vF$MF(@N&B4X*dN$U*^VIWu-7X178j4-gh$jC^pkBC=!XM7q{9~?c8vV3}me8NR z&eYuUZHwBcDU%CDKM41n!j4G!YlcUYu@x~!5LI=5eAP9B#rx9vAlCevaR}6Vr8lEn zUh={yPXHzcF^5N#4xYLVfeh|o-z%CiJ~?w_J}g4&82~iPO2Vw}Wxl?*dEOuw8;&N& zQ<4Nc(C|VeTwCwfH@nuvI<*_|9jA;!SaIqx-`OZ`6gbgMaCbY@=y>?T8`n<~1%L0j zNp;FuTw|F~ygX7%8NK)fWT{GFpBKl4U1jo~EF~?1_8_~2E=SsOeZ?ppU96zZrT+uo znhmIlEJ5$NdoYIAd9qGU!bUp)5UvYy666^+{p;D<)2D9v)^-xls;%6V*VaG8!suM* z=~X$Ay&6+xoQ#i$`3i?jO^UmjHJ!mmPj_$wK~X*#ohR9_y4}UNsRSmVyZsZ~X!0j% zhv<4`5pO#arpLc+tkUAhw|N_z6VfNou#a!;|DipwJr@Qt0&{q@x9&uv0G=8Si5R&G z-0cEmc&*Vr7XfTE08&$MIINe7B|ZIGwP>#-`3bJ8fd^^B_VK3DM@`DZ@VK-4KtKC* zQa?Fn0xgljZC*Q*U45QO(SdDKWhs}H-~UbOyiQLnQ90vrJJStqaLfOX9`zfDaDJ}T zrvyGOutBBZpnk)ESYY+6+L@thlY`oOI^*EJj0Nlh{wmI(8eL7{IWFAB__)!s2+%D7 zP=td?SoZjc!T$dCG*+-npH@F0O8jH+w8R=uIh1KeYFpY)feEX?Hn$T%o=SM&v3;HYVj=bjQJtoJgn7 zfeOerdQ48~&mva=c#OrU1b+IpP)ruV;q3*+aOn{#;^{U}ngkOT|ATGDPx^E73Vr{* zu}kc=$LF!Idh&fPN3C#864m7&F|$PmJMOA?^Bk30H}mhV`Ju-;c|zskiq7I}%5coa zzAllFY15JO$XEZKvtkSwf&aI|0z5b9 zS^yrqRYf}KXqlI34UL@sshLwfUpT@N0FW$6SVi;o^&IUu?s?j9rjqURlIWmCvFU5L zb8I}YM4a@r>sx$wrj|masR`^>)I9}#ldLwX$MKdvHQo4jDV#Ag=yRqcP-kD%u^x@s zs{QRJJJ)I!A|71S>2v5;?U1H!2q%a9s;fMZay)sUXb&EOcb3`{E+!?nfc zICac*?xu1|ibQ5)%X|2iwS=yA_(pyI@`7?F7`hElvU2`4uO^PR`TgwkJ;hwxM?m$LA42yKxLbDz)yYFEX&s*xJNalg@*T%D>7$YMc)nJbQi|W7lVS%ym;%WcWfPUXP7XQTJ~K#vkQ1GQ z+Qv=3U9{y!pr2NKIM>xq}Q$E_z?cT)(I|dce4Ir5QRUTX&QFLmLeypv(0X1)?}~y|G(5Y z8vfhF+^!vQj?^cB^Ky%<^iTwl$a@_3?aWMQchXq7rujJUB!^?#(FV(0(|oGT z7QS1KmGtrl#4(vTTzdBur)q#gv_?@)+JFFv8R5mhQyJ<>%qze}!Oh=vg)#wNdd&-y zbQm1H8DqFGrj1aTk<5bOu=u`(WyOZG#rDa^1;78PWmO$BgJLly|7+PyI8&#hyQhOi z*iU@Dt>o*3W}5sz%{peaOV}*P)sZEsh4^~J;Bb&eDY@5Cjqml7Qb?Pe+dca&WquG( zys2D*e(AKK9flm^?ai?ucm?={W!p zoF$yFtln1|Hs;rjhmzFy*cEL-Kw=Uta%mZa*EIL{p+Fs~TpltLBO|SN>0;Ar$tY~Q zFa4yS^e$zYZ8fo@ZjX@73R=9zH&!P>&C!txVa~j#u}5w!jq_?j{!N4Iv%uLmAT<*o zM(55ydIqyVz}SpxO(_Ll>dlir`6@Qs1B~gDcHRdQLd_BYu<)KFvb?^ZTS)f$ZvNQD zo-8r&cJDx%K~oGD!D3M<`};o*Q{9#NZ|l>Bitt>8W!bs@8J@eRBvC**7OrmdZ>1K| zd>7C_q<|Hf6j?vl8jp@!;q)v6oWt+WEVe3or$fgV%D{Z)24=5#qmfP0=^GZ{?Ll-V z0Dk%1NRXm?(Ks$JCRa3~`*m;>nFYhly!}lNlNtF?&+8kx|HWf?)MHa>Ht!^Tyk|^J zS(D|^U~Vp)m$GKIt@g>q^)<3Ph`6QIH0PLJe?--uE4s_Qu?9@Z^5IgL4}*Lh#PK zMkF72nzk$?hWK!__l%{uUF>cWDclaGB=iC<%VTO&wkc~TB#0lfe@w&=ruJO)_E4|) ze!Sf$sic#r=>}`GXTFebYeS{82|%#*w!sa)nhmi@Y6i}EAsfSmI<$e4Qfm=b7P=gp zJ@a_xVNKms`2LuW=nav((+=#jL^i^J?4LPPDL!bK_yL;Dm+&;(fC zsM~r0{>rs*N-9U^v=?~3kli+$AX&;7W)_T}^R``^8EcQ>5;`3JvSIrGU#JV2@W~nqpZg-5!tE%?aHa#>BVmfU-te}O(87omw0$-;c#-;b7 zB;=+%R*%x>Opv}=5}Hrv9}s1Eetz~Y0xvAE@sh;le`OV+b2@N zI05=IgRShv&}CMyrh}1}NVdjUv6?ETc6A39eZ~xR?FsEddpdS@l-ltz#kcZGb0%`8(}qV!Hj54Jr`K>}i5p?=IS$>Nwdq?+p;=;;zp0$+v_7&_ z#Bm+FJzejeobBn@xp^c^*TQ<#zMe6RFqbvGB0X4vOfcjl=UnqXD;jb8Ick~c;7%WQ z3Oe!TRlEEN0Nxr_fD2k+&kM0JT$>h5)Jq+ltt64HwNvvSx0HK~5mF3>4rs3~#ZX4!$Z5$QV}9IOPIkd`pd1 zu*jeRC^DxQ4vWVodfN84p#Fxw=WOosbpdHLslPgRQbmD1^(uE-QFz?7z%eWY4f?!# zM2s~QnhAB2%*AjQhsD=nq>pSfw&q)GWFtpru4{W_8~?)U7SkZ3P%-CdSP*AJXh~Q0 zEey6M46-TB=+JcGOqmS{hSiX10Y2LeO^KWio_j%TjF&L4O&58P)G{Vvx$1X)D^?q4 zf@%8i>0475hC%lnTa*+W@*{|A>Js}ixRoUrgAsx|YrBM#5Sof|*i5cLk*?_5d=2>z zzl7ta`WQum%wcgU)4AEjlk8(hjlXjK+)(JKCwY_G>j`0c zsB687>8(OZr|ZvnqD)epN~J%<`ur9#Yo|7OGQdy6#tV13YX3cf@F}IA$0VW=%eWlzSZ^c1Yv>_$9e)jx*Y^2oB;P&5%zrb z*>T3nx7?J_ceBsFFC(w`0SEvoOMH_zdkvw~Pc))nLKl?)PiJRS006+a0ssI20050$000L7004SPmirx! zjE#qqkco_xij0hlija$skBO9xkdlv*l$M8#J}SuT!kL?}Qz@3jlLo zYJ$l6Yt+a0y!W^AK62N2tO2HXZ(*yy!KP`4VBc08*1~*M%QQ26CgzKNWA4O_rdy(- zQAqI)-KB_=hnaX(JE%&BcrGthoza~H=X}QH(C3z10Z1`R-8ktawY*+4^nw-E0;hip zUSu!$exfMA0a`m;?GoO}9j5qHPxk72RxpN#kw)euOE%d6B(*?J*xIf9Up+0=J6!F3 z^&8hsg@~h4aK|lAjW(uspB>tk_&JjHvLWs5diN)vp3my*vBx}I7zLyUabyqy8i0wvV8;8+dg*Xb(^InG_VgbG+KiUmH) zwS*7T!96Z8hKn_8ZwXCtNs_2*%Z}X8c$1mFL=WCzZJ- z74N!82(BENG_`5R2FkZD+8{=Pl#}i6GT$H85Z9e;_PE_nujKNQ+-|6U$QIOcnjYn` z2rtxkWkzuCorO%*er1p0u;{6dmRvQ~go}Z|%_-EMay|gQ+ReZk%E7a|a5je5u>mYDdW>_#S+PLDB_%tz ztR#26To8uys$JCaGk%Gu1+ha-EoUZ?%LTS4**D0`o3%8xIzQov<0PixSve_jV-qHW z$c!sw9Z2^bkc?*>6?9%I&XFnR6pf4Evx*cW_pYKAI<*WoJR))8#{^se!9)!6xjpZ zdj(^>Hu~k996_x28Yq8)1wP6hL@BHU@3Mk1y*743#&dm0H0uS!%+f9U z>BlqwGhsFt|9dV9bDY$}rYMU%jGLa+o}NW_?jW!C8ghu6MKqSX-+tQY?LO$sDwQBbd=6T2ZryPGSgF*B5oUy|^SM+9JIU#dH&)S1;vL~EyS0-XRYr5)>UP}%jai|vh zX0Hs3HNFqJrT#M=PK9voap{WlaY1vBYCXlj))k)qj2>JSY;vC6?(-~7!B5!gn1;Qe z03PcNXbUsY`TE4!^TVAn(Ti?05Zs$6dx}R+>Mbvh5NC6UqK=%=mGE8srW@`h+KnQWu?Azw3SI@Nms!r3G<40{1nUyiPN_zmSn41883eFNevL~Bod4cB(v%PSQ zxwrN*PdF^S?ioxyH?(owb+r2R{Z>R>Ku4Ui$`vJtXRVIqN$u>VzIdCX!FfAI@BFx- z#e|*chOw01LOvcC07{-qI@#+$UAqy|7z%ZMyX#(e#( zakkc1r5rE6Wh;=9pvCcUPDX=-TMC05xqfO_pMtfE`XjK-M$75(+T3=!4dF!Lmko9~ zW_)W+)*T`L*MT|=(o$+pc{3{PwN~dB?~h{|GHNqpJtyl*;)lOf4vx80lk>&iLOlH8 z97gIs`{ikj_D~OdJir(pUZlIBo>$iZ2rfm!s2*u&+hp8V&aKb1?o+Lfs1Du<`%5LS zTC**R`y;pOvbKA;)|lt8#q-)2PpH&|7yQaGTPbI|yXsG8Pdh7MFp7~gN}mDM9d+Sa zFG{vN^{*1P>}ijNJS%rOlO|{6g%H4Y)y2tuW6jlpL`LV-<^kU7&9ELZoyNPoz!f_AR^@16X5p+!8w@VOXf`!UP!2ZiNMCp{50H)e^W7M@4CFw~-%@(IN`)~t zhZrR)6ss;}<=PmI2}J@Ix#s=^9{W{L3N6_@y}ggd>oiV;nb$!-EMsKdr4FDQWVib8|yt&oX1`5BzTuG6c8!7bfdmyG^$ zu9UCaE^>|}#GhB5$zEMFIN7Pb8-|WSY!rb$*SaqJrykz|oPmor!;%0V+RZ8{H5o6( zik#D3#E7>TS+_AOGNa)j%OB>k1%J~2w5LhGpU2ON^=;5CHX6mQiyjvuN?%5Hgvkq$ z+OFsrG*3N!PwnkjpGW0;nmz7`KF9lgOP#xi+(vMM;Z(lcUA!LZExS>5y)+k)#}&H9 zomGPzH*Sv+ARJIn>8=i5RH$XGBw%s^*#J3FjsgD4wP=ZVL&sRb^J8CPmkFvuq;#13<_lz5`w>cUPr+vjEZtXW@L7)NW z%Fpb7v^{&h3*h++py0P3GYzpFRlB0E_DVQR6|c`9?8gx@Ik!S|J;G_(g1^9|ny2Fp14Hzy$uKb7g?wAdUyo1oKqbp-zP`Gin} zYBY1^^7j5%C-3WloPL){O&?9lo}A7Yl}vi2k3ySsT8R6RHPCU{%WM&NOebGl6aZe^ zC8Un+PV3Q2falklts~1thLIrvNES}QVSi3}v@LC$`nTEtOY+-SX$>gf^uq5GcFkiU z{U|ZhVG|9OIP?2jyS0aWoiH?4?=x&1Xi1ja8~ZYLJ59#8wh({cp4tS`?jk+kofQf7 zFM#^8Vj)(v-DniFE}AQ~l@*olqnhJ&Q!vKjgFKYayF0+QlYZ*u(iYwtwowYRnH(1w z<8|t2W(Af(mzacI=f6i2tqHMJ{pXiQp|ariI?tj&{iVxuZBnTX>GoE5Uc1juasRGX zJZE_Id%Cgi?Ap@ff@9Mp{R%YRiA3V8xpbjCETG)3iafa0g>NsgVds-^?`YP%Rlzw! z_;MsJ)ctyfAzB-Xt=G~`?H7V3Of>c@Hv|&?3x+=Ja+Pi}ToJVxCHDc$2VKaEbIWR%xLrV z+gXU62at2zyXIqpc~@;Hr@L|t>C-1=@ba z8M>iY=gw%vq>)n;uD)?Hl_-7@gbSpj**Ye6Us38HHQ0HZskQ^|FKVs`2$Ot*ik%SX zI<8Gf06r@YSYNtQKe)#V#`I-xr&@sy>8HlwK#2!&;^bz&AP>js`c!gna%5`))@DBIjeCaFz)T3;OQdVB?(5)_;G@{Rs#Ksx z>a|vt4=YM3d`@$Rbkrf3?|14#^eg;*xozE z+9mTM;UM1J&;NJLc1(L5>+I<7Jyi`uan;oGA}X5LwX>MfYa&A-a-kw8dpKzwa+wbb zdd%ukEJvCYoS$Pp-HvUMbj^GfL_7!ibIAS#H^OtfTK?xuJL%mqVO5L?l?n~pAS0(* zLHMRCt+dX@#?YW54p`-hKzD);Ip98<-U9xrwP}gGm0fK;7{d!%hlxxZyTb+mYMmFD zgb|JBZpya5k9VI(d)TJ!wD`;*_>ms_nf267OnAplLVS0*N%7_&q1e2aeqYV9)0$u!KS>XdkWGA#M%;{>oKoj41==1F7c|5p!4-KQ@qMPduQxb>;=loEpnTJy3sOKS0! z;XQ`8ET%>{Hs*cI0QJf3q2ik==GvIibKw7vXp8#mzXU0dD^^8fss%0q6eKsWP=^A( zy0wAJ(1XD!D;UFV)H}BbGSH+jLH73c%l7?Ix7$^o`8mg*(~vn2cB4S%rI)?*y<^T@ zO1`kmhm?!|Y^SxTo{J`%CmH)jr!j*u3rMbe(`qM(FChy};Pa%lHQmyetPZ<1Jha!| zuB`QOJJG?e*KE1Mp7SiPH#NYb?y>MVL$M{YdTd7FGXnrmXJ=CY0KhN<000000F7M$ z00;m80Edy?l^&0ajf;(if{ciih>wknhk=fWiGq-kh>VYhiHL`WzM2hT3NsklbFPLk zhAXqPJ0>DnW@DjAqTbq7=>Lhv2UDzmwOkeEI{TpYyeh>qy<7&=)E^TiJ1;hM13#J3 zJJ7g9A4goxMcoR~N3;x43|v`Z*LgKHHKQ7bCBsbkd`w*)emEf? zWjOQ|hR1k3l8%yfae9wNa%mC6rr>?5Ov3NStw2F9Tim>wXOkdv>ke@|f~kG#Rn7Z` zqJ<#~I-wQMXKLQM4QU%31IG%+a98x;zOUJ_Su;zLgjb&byFcjvtu;<_zW%0o*m<_; zOz3mzt!iL{5`4pbwQ0BrVLU(=eWN@*m8nc3&7vq)gWVDe*4b1017xRMX*IiqvASf@ z*U#H4;q<8-;Xmgh6{HVUznC_0CdLuRpJ}IbcFu&N6LY&sV-8x_Yfc;^AqxQBs?Eq& zO?On^`2x>ZIJ;XsbS9mlTuv~0&%Uoe`}fXNL7uLk-#4yP8x{?F-O<+QH52r!>;)=LhZcA{Ky@ngb1~Nt!3wi zJ)_NaYn~Yd6OY5CG+3UHIR-s&ja{>hMKCXAJ`7~fPe^&Ocd*e*1OP&<7)JFGhlxX4e@EYQ zFa8|Esa`6?opB9@qHIlCln^@aA<&!C zri4c=kQA8K(3}#xZg& z>e48p=ZjZ)iQTC)i1pdo?*lPaa>`QTM~a<|QP9)w^$Pt}?rLQ89D0I-R60DP^AxVb zje}PfqH&ZplaQEj02nqJYP#&~73PTQ0bm4iu8OP*i$+{jyLJS*yZqfQ5DHl4WU9H zH@;xqxG15FW(t_XL^vza^FCIy&ps~$uHXvU%&-eV>s_n54&o*u_j<&Q!U#HJ;tvxO z*@dIH|7h$40YmK$*<+Pwz^H>LfaaxIHvzty&9WBp7-$~0B4c=w+q!c`SXKgn;*vyU z%Z}Z?$9^063~hBJf146J&?`*}7noh^BgTB4ZYLj=`9GvPt^1MA_{eSzwFSls*MUx! z1U9*8u#c`u>QPz;0VP7_|b7j}l;e;#r)Y_&N$zC9jqXGH2 zc3DPlDgnN#&6t+#7&u-bw7Po;G1|5F1OofwqfP8CH%^n<5mnMDEA&!*xC0G_%HaEa|s z<5G4^%e_>hE%z<(<3;;f>C0X5MAfva_3OU`&%`&!UGuYk$ zfRH2!iavH@Vw~olmVFf4=~1G%jU7A&dvOp=23TLgOk~^;_b#(g7_Ll_XMX6CrP2hGDC(bY=XU!CqUI9cu2}vP zU)LPnI<>!elqQxc?1Fz;V?X~4m=f%_)oEDgM~A1f6Z^znX*lRv)wO}CNQHjxOca6_qVTI&qI10TEX$y44pD# z!zx!L(#TML-Lj`}Ta{^5={dDoT6RwMj`z@~ej} z8%O|Vog@jPziZv?i<|kryQw7ewLH{{PzCymFsB4G(mj<*Qyo)|whU;nqr>i*(JgB` zXlZ65QSu?kW+hgO#mb#c-sP|YIf1WW0)^XAT^Q(4Jw$Y>rsgE5d>e=3OFAD-NN+#@ z2emOfFtfT{_CzzEeg68gtC(d8ic_Hp(8{gBSwRRM0EYVgcTYRb@(YV^?RdV2m$Q*oT!f)Vq-+ zz*0HEgzX%X^LXBUKlWwvi~*A>;U2UUYSKSXRj&p{W~$h5!oqS%N|Ko-6-b-}|}Q z*k(VjPd~=zc~%d?ZKmS(vT&w7t)(0!q~7GSTD7NQJF9a#_MN(+0>N3jOA?+Lj=qUM z`-^kt)^Xrvw}n%f5XD^461wvdL?fX;bkvdbzzEPZG}3P1Y%!6#I2scy#NzN;Wk&)Y z%MEEiX{k=0_ag+x@LL~&=}69=ppyisNy0&0GlzekdM16yyXCGjj~S)zE>u>k)xFT# z;(lFlTTWojUJ1RL>o7T6Jt@xMLNG~2F`nbExXFI9e<59$LpC7^1(I{hRO2G%FgN(_ z*f7e)Vx_hU17$+JFtH(H$^Y*DyuN20{UeBm1=2)2O=wJ-t@mLIl(QP(iGW+&KN1UsUPO9{p z`Y^TtQ{z#m+*S60%UV4)dl=|6&gG=2~;HM$2gARVGwP^{FjNWrRh(I2%V1tKUx<;GJoG7om-R)0b zTYC>;ZGAd>9G=~zg36)QaYP$8V2#wPDnnZ@q(VHf?5)$Ba5@?UZ`2M$;iygSaRUAP zgy;H!W4tmES@v>P zK|?V?bv{)&|BqAAHHXTJH`l`PuzS0yLki}!R0X#Xua&@Le0+qfH>^=%KfQ-9ty>0M z1xsUlG|Qa*PwMeTD)&?=H%2kPnYLYha32bPrQ8uA`_cyO5{*bEQeJ1W!(@Hav2k)^ zT-7d+1~xJa@FaRk0A6~{>lAH)&fi$^GbUFK(ut5De$^-;X<|?>^)Vmi_8*}waMpC|G7c-`rOA=BC|pGXUdvT<-}D4} z$0IC^;S!oVyy|Atop4aRd8^wF+vff}yWKzP*Uyf0LFEda!HH|vCHY)mrE%ry=1=IZiBc8Qmz!Vra(fa?&ma zZXyRThS9cVJhQXe+MK`yC7lbxAOlZlXHx(Kx{Ct<00000ja>i$2><{93uPV@7mtXF zjf{njjfsqsj);$bkdBazkdK0WKD#AE9qx(6Xs=M`K;-H5p~p$%gtf8;fZALnV!Y#Y z`+SFe!uhNAb$6Au7g3y6l1Ds;9PcWn{EWpRCu!aAmR*>Ei>rLyLkP3g(KNd+V|7iL z6iioNxH!PHBbF@2a_E3T{XWxWKXEm0l{H7FqXGP#p(CbwijK%&fSx6qK9Do7@slP9 zH287lkf{K^>&3n-rSWj~Bh(~CV|bBJ)^mU~0RUi{3nYn_Hf?WPw4n8T?a;qr)&|-g zT5N^?=e|2^es4(pjJJ+4fU`+9IbRDSx^n$%^*HzYzrNe_O{L|%eyU)dc%Ggr5K9>y)FoOJ9^gp7xrYMYs@%?5F zxXjWUurSOMoSQszl?zg!-_|CI1m3z;MH)$i)*Jh>7I=Qb=1yj360?)K0a(nEFtV%H zHBa2y*#CF$X`Y*!Cx~AP0&20yrx1zr@(r;t@RH-+qGJ?gub?p*oHNN3j#%e~PTXcy z?l@84g?Nk}Cxs4Tu2PL}y&FB$-J9b$DlNVAq0lBoGzE>3)$}zXoc+h_QR9N{l@mZG zF!gIW2LOJ`4T+ZU#NzCWpn84@PF)x}g8%@jSr`*tGS`ahZ(YATkF3M()=yV)sx+2z z|3*l>k@rBT>uIK))tnm{cgyfOXuDEkuPIB7Llu|ExFPZun#w_RH=V8+iq#mm7n-xf zwbf(yo(|i{?e4%Q7WLE)&PsnLjiHh_rwhz$qUSPbQzc>niSI3|oB}?|wNVKbpoNPl z8N-!nb!IMQ5gA+)L@iRCjCDLs`LfO8`&t>dh4-YLYNPE-Cm5+qy^Sf@HPK;J1_#8M z6*m6eg!(^@`jYT2+rE@Np4THRE>e{^Tx1->cf9mUoDV_VJ-Kx!M~^8f+>o*V`T6qz zSm7FI+hH$TQES*HE}?jM9~}VxnkAUIOmBT-Kl{)yhD$^(m3nxw&;(gT@43#mA90ia zdv=leeQBPZ=Gbd)>Tyvi<)@iFtooidYzxYzj#loEzYC4&f6Bv*8M$6fO3kh6(s9fT z=GlfDyQqBme#fePqL-r0c;C@#3J$i{+0r3BeQ09*OTn)_o(p;yN#4@T^_ayOVV-aija^k4-0QOJ840CW(bU~TOQD(x&5^xc zv-QQde%vEnX*c+OvBB}LW$X|6?-8LnR?KJya;_AoZ?!TH8dwhnwN1D41OQ%owP;ER zr@id^Ldeq#f{8hE&PHS-0BC0kGe(%lKacmVcr@)1+H5OLQ7MPIZ098VwSGf8aaO0x zV{nSkEWm0Z57T!bgZ;m2gn;-!vfRZ+(y4Z6BItt^Ik>aa>s3vgNgU*>a@9y-){wx? zo!($B^__ZfTCX>|v-+e>aB9cQHAh9rj-mlRn$6%cyb`^C&lR6BUSaM|U6k~8!KpA| zM7MW0`8j4iUvtgRyfKvbIL0vvoIn>Wmagka4}YNN=@oPPXu0Zw~6G z!eJ3XFOyGQk%HC^{6r^|A~eIrPdHaEcIYcT2c9_-d4YxCNdGn0uv zjhy>_VpqDHZR22|j}Bw*b$tHWHpQ=lhUw{a0UU{cSLIv z03MoEY3V`>i#=BgpW=6R0t=c0WO8{vml>Ra2negSL%+6Q14K6io0KRN9CAOrOTJi zINQp5G^xycr*&$pAJZ-d6mWisvuN$nij0@Sq*@LX8ia;bS6=|$na$8K^ky(DX1y_7 znS(I)=+2mxFk(0?9q)!XzKB`Kl8(DV>9X|v{RI}J1bnXBHEgFEiBzFSmS9&)sDG95?p%|U%CK7Yv7I`5-JJk2k_ zgjPztNdbPTwTUszWima$(-l&Sj36CKnK4nXH5F^$|EGdK+bSuXMy9D8!8AF^!v>+{?P&{zCS*^q_hGlP73i=I#u_+~bd0I$U>T^JsH1((%b}vS zno;gU?^fN19v=s{W~YKRkj;q#W?5KT6b3W^Ua3`ZiCqhd-k7lG7kcgK4jYI70JCKt zOu{1X6YlHBvyao)`>cK&Wij4pTUA2o(lcC+H-}oGE1&>=4OYRqhO2)@Xg!&MlCS#N z86oEQamAQSVO16DsdMDpfUfN8bXqF>)IuhQ>tI{@hDQs^%J{dcvG6tZ7;chjWP`<| zFLrk94^ogA92j^WOAR>zKB`5!KdDMLY5K5a&sX$;h#;tggGpHb-?eSW`1Y^q+I!)? z^5do$c9KLMtLdb+x0Oc|eP>6wk8pa{`4?d*`(}HVyvS(9#QrpYVvc$89j6kLW5HKH zrKmFQkL@|S=i-&U!4RoWwtXTO&dY>OO#>eCzRlr;{jub1UzTj8e}2=OVx7x+pnw!b zFAu(%CH=UvnR+yrS!lXQC`$>jt&>Cyu5NU84dF{$^cIg_|K5i=gm9WNuImYLd`U_m z80-VUPTd2Zb6aEvm$uy>-pHjy#yDFtq}g&A$)QI0vHOcYb%)zh209%3i*0P{o8cVh zM+m{Zh~oH;cYk?Fv+t6UvD-jB9H~o=)Geya6S~V|&bCw><#s>90{|Yn1$8{-zF@RI zeDHFqH?L=U4;$G4m?udL>t=;v!}0IZO3ooirO&R=BjrK+D~J6OqBEEoY_zL(Io{S7 z{A!E|ZE9(9FOei?{XH*oXnE3k>~(B1h{`RcB#m`kw#Sr|g(E2H7&DSa!)n^lSCe4N zro2={)A^iM-VDnLg%r2i@R~84TRt(bWB;cz`+ z%VBQcc4ezA|ExOA<6TvlYDF!=2&=B?F|0jP&3HLB_N7o={3-;I{p~=u$c|?9QOX5V zpazdvRS}ata;&lRve(5%&w%>=c03rz^2V^su}LZ9Y(8qviNk#v_V_iJX9w2i8Fe=j|i8o$7#~KgE_c_t( zk}bT=3y~r|_+*6Mo`+qe9>h^kx&_>47B zeKUS@coYp|(X6@1+Z8rI?2$ui=%R3Y6*g z+}L{Y9uOSNP@7mZ(MOi>Dv~LoI9I)Mza_8$p2(fI+h5v^!&Jcgz@7ugo&x|RNrEa+ zjqTYy>T`}w_u*07CsBdc6>o&b^zk09UI`F)mH+X$}djsA)*4B$zv*CFY zFl+1UHgB@P5zLeFc*W16OYvJP=k27dDV!AG^u+QiEX4pkxV=M8uhIcO=q6wj04J^- A#sB~S literal 0 HcmV?d00001 diff --git a/Resources/Audio/Machines/juicer.ogg b/Resources/Audio/Machines/juicer.ogg new file mode 100644 index 0000000000000000000000000000000000000000..4d6877e7a8238b10acf4cab36f2119af32b288a3 GIT binary patch literal 34955 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ïRM!vQ1wfgH~F7-ec|zpPY#URka4L7nyv^ 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 literal 0 HcmV?d00001 diff --git a/Resources/Prototypes/Entities/Constructible/Specific/Cooking/reagent_grinder.yml b/Resources/Prototypes/Entities/Constructible/Specific/Cooking/reagent_grinder.yml new file mode 100644 index 0000000000..1ae18690ce --- /dev/null +++ b/Resources/Prototypes/Entities/Constructible/Specific/Cooking/reagent_grinder.yml @@ -0,0 +1,35 @@ +- type: entity + id: KitchenReagentGrinder + name: reagent grinder + suffix: grinder/juicer + placement: + mode: SnapgridCenter + components: + - type: SnapGrid + offset: Center + - type: ReagentGrinder + - type: UserInterface + interfaces: + - key: enum.ReagentGrinderUiKey.Key + type: ReagentGrinderBoundUserInterface + - type: Appearance + visuals: + - type: ReagentGrinderVisualizer + - type: Clickable + - type: InteractionOutline + - type: PowerReceiver + - type: LoopingSound + - type: Physics + shapes: + - !type:PhysShapeAabb + bounds: "-0.35,-0.08,0.25,0.15" + layer: + - Opaque + - Impassable + - MobImpassable + - VaultImpassable + - type: Sprite + netsync: false + sprite: Constructible/Power/juicer.rsi + state: juicer0 + drawdepth: Items diff --git a/Resources/Prototypes/Entities/Objects/Consumable/botany.yml b/Resources/Prototypes/Entities/Objects/Consumable/botany.yml index 64905e33a4..def7c602af 100644 --- a/Resources/Prototypes/Entities/Objects/Consumable/botany.yml +++ b/Resources/Prototypes/Entities/Objects/Consumable/botany.yml @@ -27,6 +27,7 @@ Quantity: 5 - type: Produce seed: wheat + - type: Grindable - type: entity name: sugarcane @@ -46,6 +47,7 @@ Quantity: 5 - type: Produce seed: sugarcane + - type: Grindable - type: entity name: tower-cap log @@ -79,6 +81,12 @@ sprite: Objects/Specific/Hydroponics/banana.rsi - type: Produce seed: banana + - type: Grindable + - type: Juiceable + result: + reagents: + - ReagentId: chem.BananaJuice + Quantity: 10 - type: entity name: carrot @@ -96,6 +104,12 @@ sprite: Objects/Specific/Hydroponics/carrot.rsi - type: Produce seed: carrots + - type: Grindable + - type: Juiceable + result: + reagents: + - ReagentId: chem.CarrotJuice + Quantity: 10 - type: entity name: lemon @@ -113,6 +127,12 @@ sprite: Objects/Specific/Hydroponics/lemon.rsi - type: Produce seed: lemon + - type: Grindable + - type: Juiceable + result: + reagents: + - ReagentId: chem.LimeJuice + Quantity: 10 - type: entity name: potato @@ -130,6 +150,12 @@ sprite: Objects/Specific/Hydroponics/potato.rsi - type: Produce seed: potato + - type: Grindable + - type: Juiceable + result: + reagents: + - ReagentId: chem.PotatoJuice + Quantity: 10 - type: entity name: tomato @@ -147,6 +173,12 @@ sprite: Objects/Specific/Hydroponics/tomato.rsi - type: Produce seed: tomato + - type: Grindable + - type: Juiceable + result: + reagents: + - ReagentId: chem.TomatoJuice + Quantity: 10 - type: entity name: eggplant @@ -164,6 +196,7 @@ sprite: Objects/Specific/Hydroponics/eggplant.rsi - type: Produce seed: eggplant + - type: Grindable - type: entity name: apple @@ -181,6 +214,12 @@ sprite: Objects/Specific/Hydroponics/apple.rsi - type: Produce seed: apple + - type: Grindable + - type: Juiceable + result: + reagents: + - ReagentId: chem.AppleJuice + Quantity: 10 - type: entity name: ear of corn @@ -199,6 +238,7 @@ sprite: Objects/Specific/Hydroponics/corn.rsi - type: Produce seed: corn + - type: Grindable - type: entity name: chanterelle cluster @@ -216,3 +256,4 @@ sprite: Objects/Specific/Hydroponics/chanterelle.rsi - type: Produce seed: chanterelle + - type: Grindable diff --git a/Resources/Prototypes/Entities/Objects/Consumable/drinks.yml b/Resources/Prototypes/Entities/Objects/Consumable/drinks.yml index d8255085c6..15a843e3c8 100644 --- a/Resources/Prototypes/Entities/Objects/Consumable/drinks.yml +++ b/Resources/Prototypes/Entities/Objects/Consumable/drinks.yml @@ -165,11 +165,17 @@ - type: entity parent: DrinkGlassBase - id: DrinkBerryjJice + id: DrinkBerryJuice name: berry juice description: A delicious blend of several different kinds of berries. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.BerryJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/berryjuice.rsi @@ -252,6 +258,12 @@ description: Has a uniquely sweet flavour of concentrated carrots. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.CarrotJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/carrotjuice.rsi @@ -564,6 +576,12 @@ description: The sweet-sour juice of limes. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.LimeJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/glass_green.rsi @@ -575,9 +593,31 @@ description: Liquid extract of the orange tree fruit, produced by squeezing or reaming oranges. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.OrangeJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/glass_orange.rsi +- type: entity + parent: DrinkGlassBase + id: DrinkGlassYellow + name: lemon juice + description: Used to make lemonade, soft drinks, and cocktails. + components: + - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.LemonJuice + Quantity: 20 + - type: Sprite + sprite: Objects/Consumable/Drinks/glass_yellow.rsi + - type: entity parent: DrinkGlassBase @@ -586,6 +626,12 @@ description: Juice made from tomatoes, usually used as a beverage, either plain or in cocktails components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.TomatoJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/glass_red.rsi @@ -605,18 +651,6 @@ - type: Sprite sprite: Objects/Consumable/Drinks/glass_white.rsi - -- type: entity - parent: DrinkGlassBase - id: DrinkGlassYellow - name: lemon juice - description: '' - components: - - type: Drink - - type: Sprite - sprite: Objects/Consumable/Drinks/glass_yellow.rsi - - - type: entity parent: DrinkGlassBase id: DrinkGoldschlagerGlass @@ -635,6 +669,12 @@ description: The juice is often sold in stores or fermented and made into wine, brandy, or vinegar. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.GrapeJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/grapejuice.rsi @@ -903,6 +943,12 @@ description: Used to make lemonade, soft drinks, and cocktails. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.LemonJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/lemonjuice.rsi @@ -914,6 +960,14 @@ description: A tangy substance made of lime and lemon. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.LemonJuice + Quantity: 10 + - ReagentId: chem.LimeJuice + Quantity: 10 - type: Sprite sprite: Objects/Consumable/Drinks/lemonlime.rsi @@ -925,6 +979,12 @@ description: The sweet-sour juice of limes. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.LimeJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/limejuice.rsi @@ -1100,6 +1160,12 @@ description: Liquid extract of the orange tree fruit, produced by squeezing or reaming oranges. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.OrangeJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/orangejuice.rsi @@ -1122,6 +1188,12 @@ description: A tasty juice blended from various kinds of very deadly and toxic berries. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.PoisonBerryJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/poisonberryjuice.rsi @@ -1521,9 +1593,15 @@ parent: DrinkGlassBase id: DrinkTomatoJuice name: tomato juice - description: Juice made from tomatoes, usually used as a beverage, either plain or in cocktails + description: Juice made from tomatoes, usually used as a beverage, either plain or in cocktails. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.TomatoJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/tomatojuice.rsi @@ -1612,6 +1690,12 @@ description: Delicious juice made from watermelon. components: - type: Drink + - type: SolutionContainer + maxVol: 20 + contents: + reagents: + - ReagentId: chem.WatermelonJuice + Quantity: 20 - type: Sprite sprite: Objects/Consumable/Drinks/watermelon.rsi diff --git a/Resources/Prototypes/Entities/Objects/Consumable/food.yml b/Resources/Prototypes/Entities/Objects/Consumable/food.yml index 0467526a1e..84197458e6 100644 --- a/Resources/Prototypes/Entities/Objects/Consumable/food.yml +++ b/Resources/Prototypes/Entities/Objects/Consumable/food.yml @@ -35,7 +35,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/4no_raisins.rsi - + - type: Grindable - type: Item sprite: Objects/Consumable/Food/4no_raisins.rsi @@ -53,6 +53,7 @@ trash: TrashSnackBowl - type: Sprite sprite: Objects/Consumable/Food/aesirsalad.rsi + - type: Grindable - type: entity @@ -68,6 +69,7 @@ Quantity: 10 - type: Sprite sprite: Objects/Consumable/Food/amanita_pie.rsi + - type: Grindable - type: entity @@ -85,6 +87,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/amanitajelly.rsi + - type: Grindable #- type: entity @@ -115,6 +118,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/apple_cake_slice.rsi + - type: Grindable - type: entity @@ -130,6 +134,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/apple_pie.rsi + - type: Grindable # TODO: BREADSLICE? @@ -159,6 +164,7 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/badrecipe.rsi + - type: Grindable - type: entity @@ -174,6 +180,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/baguette.rsi + - type: Grindable - type: entity @@ -191,6 +198,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/breadslice.rsi + - type: Grindable - type: entity @@ -208,6 +216,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/bananabreadslice.rsi + - type: Grindable - type: entity @@ -226,6 +235,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/pie.rsi + - type: Grindable #- type: entity @@ -256,6 +266,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/beetsoup.rsi + - type: Grindable - type: entity @@ -273,6 +284,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/berryclafoutis.rsi + - type: Grindable - type: entity @@ -290,6 +302,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/birthday_cake_slice.rsi + - type: Grindable - type: entity @@ -307,6 +320,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/spaghettiboiled.rsi + - type: Grindable - type: entity @@ -324,6 +338,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/brain_cake_slice.rsi + - type: Grindable - type: entity @@ -341,9 +356,9 @@ Quantity: 20 - type: Sprite sprite: Objects/Consumable/Food/candy.rsi - - type: Item sprite: Objects/Consumable/Food/candy.rsi + - type: Grindable - type: entity name: candy corn @@ -358,6 +373,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/candy_corn.rsi + - type: Grindable - type: entity @@ -375,6 +391,7 @@ Quantity: 10 - type: Sprite sprite: Objects/Consumable/Food/carrotcake_slice.rsi + - type: Grindable - type: entity @@ -392,6 +409,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/carrotfries.rsi + - type: Grindable - type: entity @@ -409,6 +427,7 @@ Quantity: 10 - type: Sprite sprite: Objects/Consumable/Food/chawanmushi.rsi + - type: Grindable - type: entity @@ -424,9 +443,9 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/cheeseburger.rsi - - type: Item sprite: Objects/Consumable/Food/cheeseburger.rsi + - type: Grindable - type: entity name: cheesecake (slice) @@ -443,6 +462,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/cheesecake_slice.rsi + - type: Grindable - type: entity @@ -458,6 +478,7 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/cheesewedge.rsi + - type: Grindable - type: entity @@ -475,6 +496,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/cheesie_honkers.rsi + - type: Grindable - type: entity @@ -492,6 +514,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/cheesyfries.rsi + - type: Grindable - type: entity @@ -507,6 +530,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/cherrypie.rsi + - type: Grindable - type: entity @@ -524,9 +548,9 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/chips.rsi - - type: Item sprite: Objects/Consumable/Food/chips.rsi + - type: Grindable - type: entity name: chocolate bar @@ -543,6 +567,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/chocolatebar.rsi + - type: Grindable - type: entity @@ -560,6 +585,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/chocolatecake_slice.rsi + - type: Grindable - type: entity @@ -575,6 +601,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/chocolateegg.rsi + - type: Grindable - type: entity @@ -590,9 +617,9 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/clownburger.rsi - - type: Item sprite: Objects/Consumable/Food/clownburger.rsi + - type: Grindable - type: entity name: clown's tears @@ -607,6 +634,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/clownstears.rsi + - type: Grindable #- type: entity @@ -638,6 +666,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/coldchili.rsi + - type: Grindable #- type: entity @@ -667,6 +696,7 @@ Quantity: 10 - type: Sprite sprite: Objects/Consumable/Food/cookie!!!.rsi + - type: Grindable - type: entity @@ -682,6 +712,7 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/cracker.rsi + - type: Grindable - type: entity @@ -699,6 +730,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/creamcheesebreadslice.rsi + - type: Grindable - type: entity @@ -716,6 +748,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/cubancarp.rsi + - type: Grindable #- type: entity @@ -745,6 +778,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/donkpocket.rsi + - type: Grindable - type: entity @@ -760,9 +794,9 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/donut1.rsi - - type: Item sprite: Objects/Consumable/Food/donut1.rsi + - type: Grindable - type: entity parent: FoodBase @@ -777,9 +811,9 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/donut2.rsi - - type: Item sprite: Objects/Consumable/Food/donut2.rsi.rsi + - type: Grindable - type: entity parent: FoodBase @@ -794,9 +828,9 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/egg-blue.rsi - - type: Item sprite: Objects/Consumable/Food/egg-blue.rsi.rsi + - type: Grindable - type: entity parent: FoodBase @@ -811,9 +845,9 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/egg-green.rsi - - type: Item sprite: Objects/Consumable/Food/egg-green.rsi.rsi + - type: Grindable - type: entity parent: FoodBase @@ -828,9 +862,9 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/egg-mime.rsi - - type: Item sprite: Objects/Consumable/Food/egg-mime.rsi.rsi + - type: Grindable - type: entity parent: FoodBase @@ -845,9 +879,9 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/egg-orange.rsi - - type: Item sprite: Objects/Consumable/Food/egg-orange.rsi.rsi + - type: Grindable - type: entity parent: FoodBase @@ -862,9 +896,9 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/egg-purple.rsi - - type: Item sprite: Objects/Consumable/Food/egg-purple.rsi.rsi + - type: Grindable - type: entity parent: FoodBase @@ -879,9 +913,9 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/egg-rainbow.rsi - - type: Item sprite: Objects/Consumable/Food/egg-rainbow.rsi.rsi + - type: Grindable - type: entity parent: FoodBase @@ -896,9 +930,9 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/egg-red.rsi - - type: Item sprite: Objects/Consumable/Food/egg-red.rsi.rsi + - type: Grindable - type: entity @@ -914,9 +948,9 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/egg-yellow.rsi - - type: Item sprite: Objects/Consumable/Food/egg-yellow.rsi + - type: Grindable - type: entity parent: FoodBase @@ -935,11 +969,12 @@ seed: eggy - type: Item sprite: Objects/Consumable/Food/egg.rsi + - type: Grindable - type: entity parent: FoodBase id: FoodEggplantparm - name: eggplant parmigiana # parma or parmi + name: eggplant parmigiana description: The only good recipe for eggplant. components: - type: Food @@ -951,6 +986,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/eggplantparm.rsi + - type: Grindable #- type: entity @@ -982,6 +1018,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/enchiladas.rsi + - type: Grindable #- type: entity @@ -1025,6 +1062,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/fishandchips.rsi + - type: Grindable - type: entity @@ -1040,9 +1078,9 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/fishburger.rsi - - type: Item sprite: Objects/Consumable/Food/fishburger.rsi + - type: Grindable #- type: entity # parent: FoodBase @@ -1071,6 +1109,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/fishfingers.rsi + - type: Grindable #- type: entity @@ -1100,6 +1139,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/fortune_cookie.rsi + - type: Grindable - type: entity @@ -1115,6 +1155,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/friedegg.rsi + - type: Grindable - type: entity @@ -1132,6 +1173,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/fries.rsi + - type: Grindable - type: entity @@ -1149,6 +1191,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/gappletart.rsi + - type: Grindable - type: entity @@ -1166,6 +1209,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/toastedsandwich.rsi + - type: Grindable - type: entity @@ -1181,9 +1225,9 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/hburger.rsi - - type: Item sprite: Objects/Consumable/Food/hburger.rsi + - type: Grindable - type: entity parent: FoodBase @@ -1200,6 +1244,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/herbsalad.rsi + - type: Grindable #- type: entity @@ -1231,6 +1276,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/hotchili.rsi + - type: Grindable - type: entity @@ -1246,6 +1292,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/hotdog.rsi + - type: Grindable #- type: entity @@ -1275,6 +1322,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/hugemushroomslice.rsi + - type: Grindable - type: entity @@ -1292,6 +1340,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/kabob.rsi + - type: Grindable - type: entity @@ -1307,6 +1356,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/jdonut1.rsi + - type: Grindable - type: entity @@ -1322,6 +1372,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/jdonut2.rsi + - type: Grindable - type: entity @@ -1337,9 +1388,9 @@ Quantity: 10 - type: Sprite sprite: Objects/Consumable/Food/jellyburger.rsi - - type: Item sprite: Objects/Consumable/Food/jellyburger.rsi + - type: Grindable - type: entity parent: FoodBase @@ -1356,6 +1407,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/jellysandwich.rsi + - type: Grindable - type: entity @@ -1373,6 +1425,7 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/jellytoast.rsi + - type: Grindable # TODO: Add more pies. Anything that shares a sprite @@ -1391,6 +1444,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/kabob.rsi + - type: Grindable #- type: entity @@ -1436,6 +1490,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/lemoncake_slice.rsi + - type: Grindable - type: entity @@ -1453,6 +1508,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/limecake_slice.rsi + - type: Grindable - type: entity @@ -1468,6 +1524,7 @@ Quantity: 40 - type: Sprite sprite: Objects/Consumable/Food/liquidfood.rsi + - type: Grindable - type: entity @@ -1483,6 +1540,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/loadedbakedpotato.rsi + - type: Grindable - type: entity @@ -1498,6 +1556,7 @@ Quantity: 5 - type: Sprite sprite: Objects/Consumable/Food/meat.rsi + - type: Grindable - type: entity @@ -1513,9 +1572,9 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/meatball.rsi - - type: Item sprite: Objects/Consumable/Food/meatball.rsi + - type: Grindable - type: entity parent: FoodBase @@ -1532,6 +1591,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/meatballsoup.rsi + - type: Grindable - type: entity @@ -1549,6 +1609,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/meatballspaghetti.rsi + - type: Grindable - type: entity @@ -1566,6 +1627,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/meatbreadslice.rsi + - type: Grindable - type: entity @@ -1583,6 +1645,7 @@ Quantity: 20 - type: Sprite sprite: Objects/Consumable/Food/meatpie.rsi + - type: Grindable - type: entity @@ -1598,6 +1661,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/meatpizzaslice.rsi + - type: Grindable - type: entity @@ -1615,6 +1679,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/meatsteak.rsi + - type: Grindable - type: entity @@ -1632,6 +1697,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/milosoup.rsi + - type: Grindable - type: entity @@ -1647,6 +1713,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/mimeburger.rsi + - type: Grindable - type: entity @@ -1657,11 +1724,12 @@ components: - type: SolutionContainer contents: - reagents: + reagents: # TODO: mint toxin - ReagentId: chem.Nutriment Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/mint.rsi + - type: Grindable #- type: entity @@ -1691,9 +1759,9 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/hburger.rsi - - type: Item sprite: Objects/Consumable/Food/hburger.rsi + - type: Grindable - type: entity parent: FoodBase @@ -1712,6 +1780,7 @@ sprite: Objects/Consumable/Food/monkeycube.rsi - type: Rehydratable target: MonkeyMob_Content + - type: Grindable - type: entity parent: FoodBase @@ -1728,6 +1797,7 @@ Quantity: 30 - type: Sprite sprite: Objects/Consumable/Food/monkeysdelight.rsi + - type: Grindable #- type: entity @@ -1771,6 +1841,7 @@ Quantity: 10 - type: Sprite sprite: Objects/Consumable/Food/mushroompizzaslice.rsi + - type: Grindable - type: entity @@ -1788,6 +1859,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/mushroomsoup.rsi + - type: Grindable # TODO: More in this one @@ -1806,6 +1878,7 @@ Quantity: 1 - type: Sprite sprite: Objects/Consumable/Food/mysterysoup.rsi + - type: Grindable - type: entity @@ -1823,6 +1896,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/nettlesoup.rsi + - type: Grindable #- type: entity @@ -1854,6 +1928,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/omelette.rsi + - type: Grindable - type: entity @@ -1871,6 +1946,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/orangecake_slice.rsi + - type: Grindable - type: entity @@ -1888,6 +1964,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/pastatomato.rsi + - type: Grindable #- type: entity @@ -1917,6 +1994,7 @@ Quantity: 10 - type: Sprite sprite: Objects/Consumable/Food/phelmbiscuit.rsi + - type: Grindable - type: entity @@ -1932,6 +2010,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/pizzamargheritaslice.rsi + - type: Grindable - type: entity @@ -1949,6 +2028,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/plaincake_slice.rsi + - type: Grindable - type: entity @@ -1964,6 +2044,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/plump_pie.rsi + - type: Grindable - type: entity @@ -1982,6 +2063,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/popcorn.rsi + - type: Grindable - type: entity @@ -1997,6 +2079,7 @@ Quantity: 10 - type: Sprite sprite: Objects/Consumable/Food/poppypretzel.rsi + - type: Grindable - type: entity @@ -2014,6 +2097,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/pumpkinpieslice.rsi + - type: Grindable # TODO: Boiled rice? @@ -2044,6 +2128,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/roburger.rsi + - type: Grindable - type: entity @@ -2061,6 +2146,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/rofflewaffles.rsi + - type: Grindable #- type: entity @@ -2106,6 +2192,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/rpudding.rsi + - type: Grindable - type: entity @@ -2123,6 +2210,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/sandwich.rsi + - type: Grindable #- type: entity @@ -2166,6 +2254,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/sausage.rsi + - type: Grindable #- type: entity @@ -2210,9 +2299,9 @@ trash: TrashSOSJerky - type: Sprite sprite: Objects/Consumable/Food/sosjerky.rsi - - type: Item sprite: Objects/Consumable/Food/sosjerky.rsi + - type: Grindable - type: entity parent: FoodBase @@ -2229,6 +2318,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/soydope.rsi + - type: Grindable - type: entity @@ -2246,13 +2336,14 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/soylent_green.rsi + - type: Grindable # why these were named different i have no idea - type: entity parent: FoodBase id: FoodSoylentYellow - name: soylen virdians + name: soylen viridians description: Not made of people. Honest. components: - type: Food @@ -2264,6 +2355,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/soylent_yellow.rsi + - type: Grindable #- type: entity @@ -2293,6 +2385,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/space_twinkie.rsi + - type: Grindable - type: entity @@ -2310,6 +2403,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/spacylibertyduff.rsi + - type: Grindable - type: entity @@ -2325,6 +2419,7 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/spaghetti.rsi + - type: Grindable - type: entity @@ -2340,9 +2435,9 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/spellburger.rsi - - type: Item sprite: Objects/Consumable/Food/spellburger.rsi + - type: Grindable - type: entity parent: FoodBase @@ -2357,6 +2452,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/spesslaw.rsi + - type: Grindable - type: entity @@ -2372,6 +2468,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/stew.rsi + - type: Grindable - type: entity @@ -2389,6 +2486,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/stewedsoymeat.rsi + - type: Grindable - type: entity @@ -2404,6 +2502,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/stuffing.rsi + - type: Grindable #- type: entity @@ -2447,6 +2546,7 @@ Quantity: 40 - type: Sprite sprite: Objects/Consumable/Food/superbiteburger.rsi + - type: Grindable - type: entity @@ -2464,6 +2564,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/syndi_cakes.rsi + - type: Grindable - type: entity @@ -2479,6 +2580,7 @@ Quantity: 8 - type: Sprite sprite: Objects/Consumable/Food/taco.rsi + - type: Grindable - type: entity @@ -2496,6 +2598,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/tastybread.rsi + - type: Grindable - type: entity @@ -2513,6 +2616,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/toastedsandwich.rsi + - type: Grindable - type: entity @@ -2528,6 +2632,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/tofu.rsi + - type: Grindable - type: entity @@ -2545,6 +2650,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/tofubreadslice.rsi + - type: Grindable - type: entity @@ -2560,9 +2666,9 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/tofuburger.rsi - - type: Item sprite: Objects/Consumable/Food/tofuburger.rsi + - type: Grindable - type: entity parent: FoodBase @@ -2579,6 +2685,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/kabob.rsi + - type: Grindable - type: entity @@ -2594,6 +2701,7 @@ Quantity: 24 - type: Sprite sprite: Objects/Consumable/Food/tofurkey.rsi + - type: Grindable - type: entity @@ -2609,6 +2717,7 @@ Quantity: 6 - type: Sprite sprite: Objects/Consumable/Food/tomatomeat.rsi + - type: Grindable - type: entity @@ -2626,6 +2735,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/tomatosoup.rsi + - type: Grindable - type: entity @@ -2641,6 +2751,7 @@ Quantity: 4 - type: Sprite sprite: Objects/Consumable/Food/twobread.rsi + - type: Grindable - type: entity @@ -2658,6 +2769,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/validsalad.rsi + - type: Grindable - type: entity @@ -2673,6 +2785,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/vegetablepizzaslice.rsi + - type: Grindable - type: entity @@ -2690,6 +2803,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/vegetablesoup.rsi + - type: Grindable - type: entity @@ -2707,6 +2821,7 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/waffles.rsi + - type: Grindable - type: entity @@ -2722,6 +2837,7 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/watermelonslice.rsi + - type: Grindable - type: entity @@ -2739,6 +2855,7 @@ Quantity: 12 - type: Sprite sprite: Objects/Consumable/Food/wingfangchu.rsi + - type: Grindable - type: entity @@ -2756,6 +2873,7 @@ Quantity: 2 - type: Sprite sprite: Objects/Consumable/Food/wishsoup.rsi + - type: Grindable - type: entity @@ -2771,9 +2889,9 @@ Quantity: 16 - type: Sprite sprite: Objects/Consumable/Food/xburger.rsi - - type: Item sprite: Objects/Consumable/Food/xburger.rsi + - type: Grindable - type: entity parent: FoodBase @@ -2790,6 +2908,7 @@ Quantity: 20 - type: Sprite sprite: Objects/Consumable/Food/xenobreadslice.rsi + - type: Grindable - type: entity @@ -2805,6 +2924,7 @@ Quantity: 20 - type: Sprite sprite: Objects/Consumable/Food/xenomeat.rsi + - type: Grindable - type: entity @@ -2822,6 +2942,7 @@ Quantity: 20 - type: Sprite sprite: Objects/Consumable/Food/xenomeatpie.rsi + - type: Grindable - type: entity @@ -2839,6 +2960,7 @@ Quantity: 15 - type: Sprite sprite: Objects/Consumable/Food/stew.rsi + - type: Grindable - type: entity @@ -2857,6 +2979,7 @@ Quantity: 20 - type: Sprite sprite: Objects/Consumable/Food/milkape.rsi + - type: Grindable - type: entity name: memory leek @@ -2873,4 +2996,5 @@ - type: Sprite sprite: Objects/Consumable/Food/memoryleek.rsi state: memoryLeek + - type: Grindable diff --git a/Resources/Prototypes/Reagents/drinks.yml b/Resources/Prototypes/Reagents/drinks.yml index bce9438f42..1173cb83d6 100644 --- a/Resources/Prototypes/Reagents/drinks.yml +++ b/Resources/Prototypes/Reagents/drinks.yml @@ -182,7 +182,7 @@ - type: reagent id: chem.Tea name: tea - desc: A made by boiling leaves of the tea tree, Camellia sinensis. + desc: A drink made by boiling leaves of the tea tree, Camellia sinensis. physicalDesc: aromatic color: "#8a5a3a" metabolism: @@ -253,3 +253,152 @@ metabolism: - !type:DefaultDrink rate: 1 + + +#Juices +- type: reagent + id: chem.AppleJuice + name: apple juice + desc: It's a little piece of Eden. + physicalDesc: crisp + color: "#FDAD01" + metabolism: + - !type:DefaultDrink + rate: 1 + +- type: reagent + id: chem.BerryJuice + name: berry juice + desc: A delicious blend of several different kinds of berries. + physicalDesc: sweet + color: "#660099" + metabolism: + - !type:DefaultDrink + rate: 1 + +- type: reagent + id: chem.BananaJuice + name: banana juice + desc: The raw essence of a banana. HONK. + physicalDesc: crisp + color: "#FFE777" + metabolism: + - !type:DefaultDrink + rate: 1 + +#TODO: port on_mob_life: restore eyesight +#if(..()) +#return 1 +# M.eye_blurry = max(M.eye_blurry - 1 , 0) +# M.eye_blind = max(M.eye_blind - 1 , 0) +# switch(data) +# if(21 to INFINITY) +# if(prob(data - 10)) +# M.disabilities &= ~NEARSIGHTED +# data++ + +- type: reagent + id: chem.CarrotJuice + name: carrot juice + desc: It's like a carrot, but less crunchy. + physicalDesc: crisp + color: "#FF8820" + metabolism: + - !type:DefaultDrink + rate: 1 + +- type: reagent + id: chem.LimeJuice + name: lime juice + desc: The sweet-sour juice of limes. + physicalDesc: citric + color: "#99bb43" + metabolism: + - !type:DefaultDrink + rate: 1 + +- type: reagent + id: chem.LemonJuice + name: lemon juice + desc: This juice is VERY sour. + physicalDesc: citric + color: "#fff690" + metabolism: + - !type:DefaultDrink + rate: 1 + +- type: reagent + id: chem.GrapeJuice + name: grape juice + desc: Freshly squeezed juice from red grapes. Quite sweet. + physicalDesc: crisp + color: "#512284" + metabolism: + - !type:DefaultDrink + rate: 1 + + +# /datum/reagent/drink/orangejuice/on_mob_life(var/mob/living/M) + +# if(..()) +# return 1 + +# if(M.getToxLoss() && prob(20)) +# M.adjustToxLoss(-REM) + +- type: reagent + id: chem.OrangeJuice + name: orange juice + desc: Both delicious AND rich in Vitamin C. What more do you need? + physicalDesc: citric + color: "#E78108" + metabolism: + - !type:DefaultDrink + rate: 1 + +- type: reagent + id: chem.TomatoJuice + name: tomato juice + desc: Tomatoes made into juice. What a waste of good tomatoes, huh? + physicalDesc: saucey + color: "#731008" + metabolism: + - !type:DefaultDrink + rate: 1 + +# /datum/reagent/drink/poisonberryjuice/on_mob_life(var/mob/living/M) + +# if(..()) +# return 1 + +# M.adjustToxLoss(1) + +- type: reagent + id: chem.PoisonBerryJuice + name: poison berry juice + desc: A surprisingly tasty juice blended from various kinds of very deadly and toxic berries. + physicalDesc: aromatic #maybe should be 'sickly'? + color: "#6600CC" + metabolism: + - !type:DefaultDrink + rate: 1 + +- type: reagent + id: chem.WatermelonJuice + name: water melon juice + desc: The delicious juice of a watermelon. + physicalDesc: sweet + color: "#EF3520" + metabolism: + - !type:DefaultDrink + rate: 1 + +- type: reagent + id: chem.PotatoJuice + name: potato juice + desc: Juice of the potato. Bleh. + physicalDesc: starchy + color: "#302000" + metabolism: + - !type:DefaultDrink + rate: 1 diff --git a/Resources/Textures/Constructible/Power/juicer.rsi/juicer0.png b/Resources/Textures/Constructible/Power/juicer.rsi/juicer0.png new file mode 100644 index 0000000000000000000000000000000000000000..ea33f756608eb3eae9f6bb3e4d1193eca6dfda6a GIT binary patch literal 579 zcmV-J0=)f+P)`rh`QEVPEde6W-8%kRkV;d%lm8d%hg_j~B+Pst1!K$#1PcJUnRSd|g#Qnx;x? zWq4DCJV}y#Hk%=YpjN8^a5x;uvWz52a-Aw@mCN(IywPaT?REih90$v?0FY9$SS$e8 zZny0Bd#2NAX?|q^p6BJh?=u(-Xti22o6VbXX_^wpF-2^d2<=Z0hT)U@aU7S%R1y$| zA+~L^TrQDP{*^>Z34m?etk>((yjpi)KA-0R$K&zIIKwai7>!1y`L)_GilQ^Y``^F# z_~jFZVO%}C-Hs@V&aq|CHloR7lDFG!K71bWWBQe!Z{J;!Wm$%lk{}3_a#!*JfbZYt zz^N)(mYvsy5C|a%fq&U00hN?o5iSGoNP+@%7~!CeKIruni0 z#^W)b=PC7n0qudLUa#NufX7`Bh9Rrf>V5+WoZPM7?_ZI_$p?zbsDSGKKv_UB1v`$T z6km*IW%HqO8~VO~l~^^t3|bRWr_)hRT%5U^fMV3rfyx=}OQ;jC>x%y-{s4gI=!-D@ RcO(D+002ovPDHLkV1j8x51jx2 literal 0 HcmV?d00001 diff --git a/Resources/Textures/Constructible/Power/juicer.rsi/juicer1.png b/Resources/Textures/Constructible/Power/juicer.rsi/juicer1.png new file mode 100644 index 0000000000000000000000000000000000000000..e588271229d6aae3d44afdf643c99c239959e6fd GIT binary patch literal 598 zcmV-c0;&CpP)E~=C5j?~Ac*t0kjpO9G~-&WMyJyOz%UFnO#?tm z$z(DCV6|GY*=!h%Mw$7Q1(>E8+qO-=->2DZQm@yK^1?90_k9v>mWbT1z;)dlpZmU_ z$tfhjbzO8_XF8oCrTlFXDJ1~9uCrV&GxO%^0n4&tfZc9)Bd=U8127m2GV|y93_Z`= z7x-TPg8k}}a=Dzk*6TH%=k2*!$UTUL!(rTNwV1se@btqa52MGaVo?+!rNnU@rQC() z0Kmmt3;5|u6h-@UAp}AQ9LG`0Q+N^{7Eg)_A@d_hS=wguKew$e=7K_aMxth?nZF;?4 zsyJN#f@fBWt2!5y9Z0rd!!VTi$$FNxA1XUw+jc6kDnARkHllXBt(-WCIhlYWvtA`8 k*H@tWi%p=ql>FQH0mbIyGhrLwlmGw#07*qoM6N<$fTrue True True + True True True True + True True True True