Skip to content

Commit

Permalink
Merge branch 'Lost-Paradise-Project:master' into dbg
Browse files Browse the repository at this point in the history
  • Loading branch information
SpicyDarkFox authored Oct 25, 2024
2 parents fca36ba + 5119e56 commit 1f98318
Show file tree
Hide file tree
Showing 159 changed files with 1,808 additions and 118 deletions.
2 changes: 1 addition & 1 deletion .github/CODEOWNERS
Validating CODEOWNERS rules …
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
**/_LostParadise @Flybik @Evgencheg
. @BL02DL
* @BL02DL
7 changes: 7 additions & 0 deletions Content.Server/Body/Components/StomachComponent.cs
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,13 @@ public sealed partial class StomachComponent : Component
[DataField]
public EntityWhitelist? SpecialDigestible = null;

/// <summary>
/// Добавлено LostParadise.
/// Data responsible to describe what foods this stomach is incapable of processing efficiently.
/// </summary>
[DataField("poorlyDigestibleFood")]
public PoorlyDigestibleFood? LPP_PoorlyDigestibleFood = null;

/// <summary>
/// Used to track how long each reagent has been in the stomach
/// </summary>
Expand Down
74 changes: 37 additions & 37 deletions Content.Server/Chat/Managers/ChatSanitizationManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -14,24 +14,24 @@ public sealed class ChatSanitizationManager : IChatSanitizationManager
// Corvax-Localization-Start
{ "хд", "chatsan-laughs" },
{ "хд.", "chatsan-laughs" },
{ "о-о", "chatsan-wide-eyed" }, // cyrillic о
{ "о.о", "chatsan-wide-eyed" }, // cyrillic о
{ "0_о", "chatsan-wide-eyed" }, // cyrillic о
{ "о-о", "chatsan-wide-eyed" }, // cyrillic о нет
{ "о.о", "chatsan-wide-eyed" }, // cyrillic о нет
{ "0_о", "chatsan-wide-eyed" }, // cyrillic о нет
{ "о/", "chatsan-waves" }, // cyrillic о
{ "о7", "chatsan-salutes" }, // cyrillic о
{ "0_o", "chatsan-wide-eyed" },
{ "0_o", "chatsan-wide-eyed" }, // нет
{ "лмао", "chatsan-laughs" },
{ "лмао.", "chatsan-laughs" },
{ "рофл", "chatsan-laughs" },
{ "рофл.", "chatsan-laughs" },
{ "яхз", "chatsan-shrugs" },
{ "яхз.", "chatsan-shrugs" },
{ ":0", "chatsan-surprised" },
{ ":р", "chatsan-stick-out-tongue" }, // cyrillic р
{ ":р", "chatsan-stick-out-tongue" }, // cyrillic р . в канал гарнитуры
{ "кек", "chatsan-laughs" },
{ "кек.", "chatsan-laughs" },
{ "T_T", "chatsan-cries" },
{ "Т_Т", "chatsan-cries" }, // cyrillic T
{ "T_T", "chatsan-cries" }, // нет
{ "Т_Т", "chatsan-cries" }, // cyrillic T нет
{ "=_(", "chatsan-cries" },
{ "!с", "chatsan-laughs" },
{ "!с.", "chatsan-laughs" },
Expand Down Expand Up @@ -65,60 +65,60 @@ public sealed class ChatSanitizationManager : IChatSanitizationManager
// I could've done this with regex, but felt it wasn't the right idea.
{ ":)", "chatsan-smiles" },
{ ":]", "chatsan-smiles" },
{ "=)", "chatsan-smiles" },
{ "=)", "chatsan-smiles" }, // = + улыбается
{ "=]", "chatsan-smiles" },
{ "(:", "chatsan-smiles" },
{ "[:", "chatsan-smiles" },
{ "[:", "chatsan-smiles" }, // : в ООС
{ "(=", "chatsan-smiles" },
{ "[=", "chatsan-smiles" },
{ "^^", "chatsan-smiles" },
{ "^-^", "chatsan-smiles" },
{ ":(", "chatsan-frowns" },
{ ":[", "chatsan-frowns" },
{ "=(", "chatsan-frowns" },
{ "=(", "chatsan-frowns" }, // = + хмурится
{ "=[", "chatsan-frowns" },
{ "):", "chatsan-frowns" },
{ ")=", "chatsan-frowns" },
{ "]:", "chatsan-frowns" },
{ "]:", "chatsan-frowns" }, // : в админ
{ "]=", "chatsan-frowns" },
{ ":D", "chatsan-smiles-widely" },
{ ":D", "chatsan-smiles-widely" }, //нет канала с ключём , . в шёпот
{ "D:", "chatsan-frowns-deeply" },
{ ":O", "chatsan-surprised" },
{ ":O", "chatsan-surprised" }, // . в безопасность
{ ":3", "chatsan-smiles" }, //nope
{ ":S", "chatsan-uncertain" },
{ ":S", "chatsan-uncertain" }, //нет канала с ключём, . в шёпот
{ ":>", "chatsan-grins" },
{ ":<", "chatsan-pouts" },
{ "xD", "chatsan-laughs" },
{ "xD", "chatsan-laughs" }, // нет
{ ":'(", "chatsan-cries" },
{ ":'[", "chatsan-cries" },
{ "='(", "chatsan-cries" },
{ "='(", "chatsan-cries" }, // =' + хмурится
{ "='[", "chatsan-cries" },
{ ")':", "chatsan-cries" },
{ "]':", "chatsan-cries" },
{ "]':", "chatsan-cries" }, // ': в админ чат
{ ")'=", "chatsan-cries" },
{ "]'=", "chatsan-cries" },
{ "]'=", "chatsan-cries" }, // '= в админ чат
{ ";-;", "chatsan-cries" },
{ ";_;", "chatsan-cries" },
{ "qwq", "chatsan-cries" },
{ ":u", "chatsan-smiles-smugly" },
{ ":v", "chatsan-smiles-smugly" },
{ ">:i", "chatsan-annoyed" },
{ ":i", "chatsan-sighs" },
{ "qwq", "chatsan-cries" }, // нет
{ ":u", "chatsan-smiles-smugly" }, // нет канала с ключём, . в шёпот
{ ":v", "chatsan-smiles-smugly" }, // нет канала с ключём, . в шёпот
{ ">:i", "chatsan-annoyed" }, // :i в чат
{ ":i", "chatsan-sighs" }, // нет канала с ключём, . в шёпот
{ ":|", "chatsan-sighs" },
{ ":p", "chatsan-stick-out-tongue" },
{ ";p", "chatsan-stick-out-tongue" },
{ ":b", "chatsan-stick-out-tongue" },
{ "0-0", "chatsan-wide-eyed" },
{ "o-o", "chatsan-wide-eyed" },
{ "o.o", "chatsan-wide-eyed" },
{ "._.", "chatsan-surprised" },
{ ":p", "chatsan-stick-out-tongue" }, // нет канала с ключём, . в шёпот
{ ";p", "chatsan-stick-out-tongue" }, // Р в общий
{ ":b", "chatsan-stick-out-tongue" }, // нет канала с ключём, . в шёпот
{ "0-0", "chatsan-wide-eyed" }, // нет
{ "o-o", "chatsan-wide-eyed" }, // нет
{ "o.o", "chatsan-wide-eyed" }, // нет
{ "._.", "chatsan-surprised" },
{ ".-.", "chatsan-confused" },
{ "-_-", "chatsan-unimpressed" },
{ "smh", "chatsan-unimpressed" },
{ "smh", "chatsan-unimpressed" }, // нет
{ "o/", "chatsan-waves" },
{ "^^/", "chatsan-waves" },
{ ":/", "chatsan-uncertain" },
{ ":\\", "chatsan-uncertain" },
{ ":\\", "chatsan-uncertain" }, // нет канала с \
{ "lmao", "chatsan-laughs" },
{ "lmao.", "chatsan-laughs" },
{ "lol", "chatsan-laughs" },
Expand All @@ -127,23 +127,23 @@ public sealed class ChatSanitizationManager : IChatSanitizationManager
{ "lel.", "chatsan-laughs" },
{ "kek", "chatsan-laughs" },
{ "kek.", "chatsan-laughs" },
{ "rofl", "chatsan-laughs" },
{ "rofl", "chatsan-laughs" }, // нет
{ "o7", "chatsan-salutes" },
{ ";_;7", "chatsan-tearfully-salutes"},
{ "idk", "chatsan-shrugs" },
{ "idk.", "chatsan-shrugs" },
{ ";)", "chatsan-winks" },
{ ";]", "chatsan-winks" },
{ "(;", "chatsan-winks" },
{ "[;", "chatsan-winks" },
{ "[;", "chatsan-winks" }, // ; в OOC
{ ":')", "chatsan-tearfully-smiles" },
{ ":']", "chatsan-tearfully-smiles" },
{ "=')", "chatsan-tearfully-smiles" },
{ "=')", "chatsan-tearfully-smiles" }, // =' + улыбается
{ "=']", "chatsan-tearfully-smiles" },
{ "(':", "chatsan-tearfully-smiles" },
{ "[':", "chatsan-tearfully-smiles" },
{ "[':", "chatsan-tearfully-smiles" }, // ': в OOC
{ "('=", "chatsan-tearfully-smiles" },
{ "['=", "chatsan-tearfully-smiles" },
{ "['=", "chatsan-tearfully-smiles" }, // '= в админ чат
};

private bool _doSanitize;
Expand Down
5 changes: 5 additions & 0 deletions Content.Server/Nutrition/EntitySystems/FoodSystem.cs
Original file line number Diff line number Diff line change
Expand Up @@ -264,6 +264,11 @@ private void OnDoAfter(Entity<FoodComponent> entity, ref ConsumeDoAfterEvent arg
}

_reaction.DoEntityReaction(args.Target.Value, solution, ReactionMethod.Ingestion);

// Добавлено LostParadise.
if (stomachToUse.LPP_PoorlyDigestibleFood?.AffectsFood(entity, EntityManager) == true)
split = stomachToUse.LPP_PoorlyDigestibleFood.ModifySolution(split);

_stomach.TryTransferSolution(stomachToUse.Owner, split, stomachToUse);

var flavors = args.FlavorMessage;
Expand Down
112 changes: 112 additions & 0 deletions Content.Server/_LostParadise/CarnivoresDiet/AccumulateReagent.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
using Content.Server.Body.Components;
using Content.Shared.Chemistry.Components;
using Content.Shared.Chemistry.Reagent;
using Content.Shared.FixedPoint;
using JetBrains.Annotations;
using Robust.Shared.Prototypes;
using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom.Prototype;

namespace Content.Server.Chemistry.ReagentEffects
{
// This class is basically copied from the sealed class AdjustReagent, but compensates a reagent's metabolism rates when adjusting its levels.
// Was introduced in order to make theobromine accumulate faster than it metabolises.
// While quite kludgy, it is still much safer and cleaner alternative to actively preventing the metabolism system from processing theobromine while it's still in the system.

// TL;DR Это костыль, который тупо добавляет столько же реагента, сколько должно впитаться за данный тик.
// Решение сомнительное, но оно гораздо чище, чем лезть в код метаболирования и добавлять туда группу-исключение с проверкой на наличие реагента в кровеносной системе.

[UsedImplicitly]
public sealed partial class AccumulateReagent : ReagentEffect
{
/// <summary>
/// The reagent ID to accumulate. Only one of this and <see cref="Group"/> should be active.
/// </summary>
[DataField(customTypeSerializer: typeof(PrototypeIdSerializer<ReagentPrototype>), required: true)]
public string? Reagent;

/// <summary>
/// Checks if the target has something that already adds the target reagent
/// </summary>
public bool ContainsPositiveAdjustEffect(IPrototypeManager prototypeMan, Solution solution, List<MetabolismGroupEntry> groups)
{
foreach (var quantity in solution.Contents)
{
var reagent = quantity.Reagent.Prototype;
if (reagent == Reagent)
continue;

if (!prototypeMan.TryIndex(reagent, out ReagentPrototype? reagentProto))
continue;

if (reagentProto?.Metabolisms == null)
continue;

// Ideally we should iterate over the body's MetabolismGroupEntry list.
// But I have no idea why there's no Drink in its .MetabolismGroups property and how to fetch that.
// So it will stay like this for now, but might cause unintended theobromine accumulation in some *very* unlikely and specific scenarios.
foreach (var reagentEffectsEntry in reagentProto.Metabolisms.Values)
{
foreach (var effect in reagentEffectsEntry.Effects)
{
if (effect is not AdjustReagent adjustReagent)
continue;

if (adjustReagent.Reagent == Reagent)
return true;
}
}
}

return false;
}

public override void Effect(ReagentEffectArgs args)
{
// Source is where Theobromine is currently coming from
if (args.Source == null)
return;

if (Reagent == null)
return;

var prototypeMan = IoCManager.Resolve<IPrototypeManager>();
prototypeMan.TryIndex(Reagent, out ReagentPrototype? reagentProto);

args.EntityManager.TryGetComponent(args.OrganEntity, out MetabolizerComponent? metabolizer);

if (metabolizer?.MetabolismGroups is not List<MetabolismGroupEntry> groups)
return;

if (!ContainsPositiveAdjustEffect(prototypeMan, args.Source, groups))
return;

if (reagentProto?.Metabolisms == null)
return;

FixedPoint2 totalCompensationRate = 0;
foreach (var group in groups)
{
// Normally, the rate should only be processed once since a reagent usually only has one group.
if (!reagentProto.Metabolisms.TryGetValue(group.Id, out var reagentEffectsEntry))
continue;

var groupRate = reagentEffectsEntry.MetabolismRate * group.MetabolismRateModifier;
totalCompensationRate += groupRate;
}

// amount *= args.Scale;
args.Source.AddReagent(Reagent, totalCompensationRate);
}

protected override string? ReagentEffectGuidebookText(IPrototypeManager prototype, IEntitySystemManager entSys)
{
if (Reagent != null && prototype.TryIndex(Reagent, out ReagentPrototype? reagentProto))
{
return Loc.GetString("reagent-effect-guidebook-accumulate-reagent-reagent",
("reagent", reagentProto.LocalizedName));
}

throw new NotImplementedException();
}
}
}
92 changes: 92 additions & 0 deletions Content.Server/_LostParadise/CarnivoresDiet/PoorlyDigestible.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
using Content.Server.Nutrition.Components;
using Content.Shared.Chemistry.Components;
using Content.Shared.Chemistry.Reagent;
using Content.Shared.FixedPoint;
using Content.Shared.Tag;
using Content.Shared.Whitelist;
using Robust.Shared.GameObjects;
using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom.Prototype.List;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Content.Server.Body.Components
{
[DataDefinition]
public sealed partial class PoorlyDigestibleFood
{
/// <summary>
/// Reagents that get multiplied by the Factor field.
/// </summary>
[DataField("reducedReagents")]
public List<string>? ReducedReagents = null;

/// <summary>
/// Food containing at least one of these tags is affected as long as it doesn't hit any BlacklistTags.
/// </summary>
[DataField("whitelistTags", customTypeSerializer: typeof(PrototypeIdListSerializer<TagPrototype>))]
public List<string>? WhitelistTags = null;

/// <summary>
/// Food containing any of these tags is not affected.
/// </summary>
[DataField("blacklistTags", customTypeSerializer: typeof(PrototypeIdListSerializer<TagPrototype>))]
public List<string>? BlacklistTags = null;

/// <summary>
/// Factor that the reagent quantities are multiplied by.
/// </summary>
[DataField("factor")]
public FixedPoint2 Factor = 1f;

/// <summary>
/// Reagent that is used to replace the volume taken away by the Factor multiplication.
/// </summary>
[DataField("replacementReagent")]
public string? ReplacementReagentID = null;

public bool AffectsFood(EntityUid foodEnt, IEntityManager entityManager)
{
if (WhitelistTags is null)
return false;

var tagSys = entityManager.System<TagSystem>();

if (BlacklistTags is not null && tagSys.HasAnyTag(foodEnt, BlacklistTags))
return false;

return tagSys.HasAnyTag(foodEnt, WhitelistTags);
}

public Solution ModifySolution(Solution solution)
{
// In case someone forgot to set the reagents being replaced, we do nothing.
if (ReducedReagents is null || Factor <= 0f)
return solution;

// Recreating the list since we can't set quentities in-place.
List<ReagentQuantity> newReagents = new();
FixedPoint2 removedQuantity = 0f;
foreach (var quantity in solution.Contents)
{
if (!ReducedReagents.Contains(quantity.Reagent.Prototype))
{
newReagents.Add(quantity);
continue;
}

removedQuantity += quantity.Quantity;
newReagents.Add(new ReagentQuantity(quantity.Reagent, quantity.Quantity * Factor));
}
removedQuantity *= 1f - Factor;

if (ReplacementReagentID is string reagentId)
newReagents.Add(new ReagentQuantity(new ReagentId(reagentId, null), removedQuantity));

solution.SetContents(newReagents);
return solution;
}
}
}
Binary file added Resources/Audio/Jukebox/Jaya-MalinoviePalmi.ogg
Binary file not shown.
Loading

0 comments on commit 1f98318

Please sign in to comment.