Gods part 3 (#1421)

* apprice action, dead notice

* fix refollowing

* mist lumera action
This commit is contained in:
Red
2025-06-14 02:11:36 +03:00
committed by GitHub
parent b932d56f15
commit fc0beb5ccf
21 changed files with 288 additions and 17 deletions

View File

@@ -25,7 +25,7 @@ public sealed partial class CP14ClientReligionGodSystem : CP14SharedReligionGodS
SubscribeLocalEvent<CP14ReligionVisionComponent, ComponentRemove>(OnOverlayRemove);
}
protected override void SendMessageToGods(ProtoId<CP14ReligionPrototype> religion, string msg, EntityUid source) { }
public override void SendMessageToGods(ProtoId<CP14ReligionPrototype> religion, string msg, EntityUid source) { }
public override void Shutdown()
{

View File

@@ -78,6 +78,6 @@ public sealed partial class CP14ReligionGodSystem
manaPercentage = manaContainerComponent.Energy / manaContainerComponent.MaxEnergy;
}
_userInterface.SetUiState(ent.Owner, CP14ReligionEntityUiKey.Key, new CP14ReligionEntityUiState(altars, followers, followerPercentage, (float)manaPercentage));
_userInterface.SetUiState(ent.Owner, CP14ReligionEntityUiKey.Key, new CP14ReligionEntityUiState(altars, followers, followerPercentage, manaPercentage));
}
}

View File

@@ -7,6 +7,7 @@ using Content.Shared._CP14.Religion.Components;
using Content.Shared._CP14.Religion.Prototypes;
using Content.Shared._CP14.Religion.Systems;
using Content.Shared.Chat;
using Content.Shared.FixedPoint;
using Robust.Server.GameStates;
using Robust.Shared.Network;
using Robust.Shared.Player;
@@ -140,7 +141,7 @@ public sealed partial class CP14ReligionGodSystem : CP14SharedReligionGodSystem
SendMessageToGods(ent.Comp.Religion.Value, wrappedMessage, args.Source);
}
protected override void SendMessageToGods(ProtoId<CP14ReligionPrototype> religion, string msg, EntityUid source)
public override void SendMessageToGods(ProtoId<CP14ReligionPrototype> religion, string msg, EntityUid source)
{
var gods = GetGods(religion);
@@ -156,7 +157,7 @@ public sealed partial class CP14ReligionGodSystem : CP14SharedReligionGodSystem
_chat.ChatMessageToMany(ChatChannel.Notifications, msg, msg, source, false, true, channels, colorOverride: Color.Aqua);
}
public float GetFollowerPercentage(Entity<CP14ReligionEntityComponent> god)
public FixedPoint2 GetFollowerPercentage(Entity<CP14ReligionEntityComponent> god)
{
var total = 0;
var followers = 0;
@@ -177,7 +178,7 @@ public sealed partial class CP14ReligionGodSystem : CP14SharedReligionGodSystem
if (total == 0)
return 0f;
return (float)followers / total;
return followers / total;
}
private void AddPvsOverrides(Entity<CP14ReligionEntityComponent> ent)

View File

@@ -10,6 +10,7 @@ public abstract partial class CP14SharedMagicSystem
{
SubscribeLocalEvent<CP14InstantActionEvent>(OnMagicInstantAction);
SubscribeLocalEvent<CP14EntityWorldTargetActionEvent>(OnMagicEntityWorldTargetAction);
SubscribeLocalEvent<CP14WorldTargetActionEvent>(OnMagicWorldTargetAction);
SubscribeLocalEvent<CP14EntityTargetActionEvent>(OnMagicEntityTargetAction);
}
@@ -47,6 +48,23 @@ public abstract partial class CP14SharedMagicSystem
_action.CP14StartCustomDelay(args.Action, args.Cooldown);
}
private void OnMagicWorldTargetAction(CP14WorldTargetActionEvent args)
{
if (args.Handled)
return;
if (!TryComp<CP14MagicEffectComponent>(args.Action, out var magicEffect))
return;
var spellArgs = new CP14SpellEffectBaseArgs(args.Performer, magicEffect.SpellStorage, null, args.Target);
if (!CanCastSpell((args.Action, magicEffect), spellArgs))
return;
CastSpell((args.Action, magicEffect), spellArgs);
_action.CP14StartCustomDelay(args.Action, args.Cooldown);
}
private void OnMagicEntityTargetAction(CP14EntityTargetActionEvent args)
{
if (args.Handled)

View File

@@ -13,6 +13,12 @@ public sealed partial class CP14EntityWorldTargetActionEvent : EntityWorldTarget
public TimeSpan Cooldown { get; private set; } = TimeSpan.FromSeconds(1f);
}
public sealed partial class CP14WorldTargetActionEvent : WorldTargetActionEvent, ICP14MagicEffect
{
[DataField]
public TimeSpan Cooldown { get; private set; } = TimeSpan.FromSeconds(1f);
}
public sealed partial class CP14EntityTargetActionEvent : EntityTargetActionEvent, ICP14MagicEffect
{
[DataField]

View File

@@ -0,0 +1,25 @@
using Content.Shared._CP14.Religion.Components;
using Content.Shared._CP14.Religion.Systems;
namespace Content.Shared._CP14.MagicSpell.Spells;
public sealed partial class CP14SpellSendMessageToGod : CP14SpellEffect
{
[DataField]
public LocId? Message;
public override void Effect(EntityManager entManager, CP14SpellEffectBaseArgs args)
{
if (!entManager.TryGetComponent<CP14ReligionFollowerComponent>(args.User, out var follower))
return;
if (!entManager.TryGetComponent<MetaDataComponent>(args.User, out var metaData))
return;
if (follower.Religion is null)
return;
var religionSys = entManager.System<CP14SharedReligionGodSystem>();
religionSys.SendMessageToGods(follower.Religion.Value, Loc.GetString("cp14-call-follower-message", ("name", metaData.EntityName)) + " " + Loc.GetString(Message?? ""), args.User.Value);
}
}

View File

@@ -0,0 +1,37 @@
using Content.Shared._CP14.MagicEnergy;
using Content.Shared._CP14.Religion.Components;
using Content.Shared._CP14.Religion.Systems;
using Content.Shared.FixedPoint;
namespace Content.Shared._CP14.MagicSpell.Spells;
public sealed partial class CP14SpellTransferManaToGod : CP14SpellEffect
{
[DataField]
public FixedPoint2 Amount = 10f;
[DataField]
public bool Safe = false;
public override void Effect(EntityManager entManager, CP14SpellEffectBaseArgs args)
{
if (args.User is null)
return;
if (!entManager.TryGetComponent<CP14ReligionFollowerComponent>(args.User, out var follower))
return;
if (follower.Religion is null)
return;
var religionSys = entManager.System<CP14SharedReligionGodSystem>();
var magicEnergySys = entManager.System<SharedCP14MagicEnergySystem>();
var gods = religionSys.GetGods(follower.Religion.Value);
var manaAmount = Amount / gods.Count;
foreach (var god in gods)
{
magicEnergySys.TransferEnergy(args.User.Value, god.Owner, manaAmount, out _, out _, safe: Safe);
}
}
}

View File

@@ -21,9 +21,15 @@ public sealed partial class CP14ReligionFollowerComponent : Component
[DataField]
public EntProtoId RenounceActionProto = "CP14ActionRenounceFromGod";
[DataField]
public EntProtoId AppealToGofProto = "CP14ActionAppealToGod";
[DataField]
public EntityUid? RenounceAction;
[DataField]
public EntityUid? AppealAction;
/// <summary>
/// how much energy does the entity transfer to its god
/// </summary>

View File

@@ -1,4 +1,3 @@
using Content.Shared._CP14.Religion.Components;
using Content.Shared._CP14.Religion.Prototypes;
using Content.Shared.DoAfter;
@@ -13,15 +12,9 @@ public abstract partial class CP14SharedReligionGodSystem
[Dependency] private readonly SharedDoAfterSystem _doAfter = default!;
private void InitializeAltars()
{
SubscribeLocalEvent<CP14ReligionAltarComponent, GetVerbsEvent<ActivationVerb>>(GetBaseVerb);
SubscribeLocalEvent<CP14ReligionAltarComponent, GetVerbsEvent<AlternativeVerb>>(GetAltVerb);
}
private void GetBaseVerb(Entity<CP14ReligionAltarComponent> ent, ref GetVerbsEvent<ActivationVerb> args)
{
}
private void GetAltVerb(Entity<CP14ReligionAltarComponent> ent, ref GetVerbsEvent<AlternativeVerb> args)
{
if (ent.Comp.Religion is null)

View File

@@ -3,7 +3,10 @@ using Content.Shared._CP14.Religion.Components;
using Content.Shared._CP14.Religion.Prototypes;
using Content.Shared.Actions;
using Content.Shared.Alert;
using Content.Shared.Follower;
using Content.Shared.Mind;
using Content.Shared.Mobs;
using Content.Shared.Verbs;
using Robust.Shared.Prototypes;
namespace Content.Shared._CP14.Religion.Systems;
@@ -13,6 +16,8 @@ public abstract partial class CP14SharedReligionGodSystem
[Dependency] private readonly AlertsSystem _alerts = default!;
[Dependency] private readonly SharedActionsSystem _actions = default!;
[Dependency] protected readonly SharedMindSystem Mind = default!;
[Dependency] private readonly FollowerSystem _follower = default!;
private void InitializeFollowers()
{
SubscribeLocalEvent<CP14ReligionPendingFollowerComponent, MapInitEvent>(OnPendingFollowerInit);
@@ -23,6 +28,43 @@ public abstract partial class CP14SharedReligionGodSystem
SubscribeLocalEvent<CP14ReligionAltarComponent, CP14AltarOfferDoAfter>(OnOfferDoAfter);
SubscribeLocalEvent<CP14ReligionFollowerComponent, CP14RenounceFromGodEvent>(OnRenounceFromGod);
SubscribeLocalEvent<CP14ReligionFollowerComponent, GetVerbsEvent<AlternativeVerb>>(OnGetAltVerbs);
SubscribeLocalEvent<CP14ReligionFollowerComponent, MobStateChangedEvent>(OnFollowerStateChange);
}
private void OnFollowerStateChange(Entity<CP14ReligionFollowerComponent> ent, ref MobStateChangedEvent args)
{
if (ent.Comp.Religion is null)
return;
switch (args.NewMobState)
{
case MobState.Critical:
SendMessageToGods(ent.Comp.Religion.Value, Loc.GetString("cp14-critical-follower-message", ("name", MetaData(ent).EntityName)), ent);
break;
case MobState.Dead:
SendMessageToGods(ent.Comp.Religion.Value, Loc.GetString("cp14-dead-follower-message", ("name", MetaData(ent).EntityName)), ent);
break;
}
}
private void OnGetAltVerbs(EntityUid uid, CP14ReligionFollowerComponent component, GetVerbsEvent<AlternativeVerb> args)
{
if (!TryComp<CP14ReligionEntityComponent>(args.User, out var god))
return;
if (god.Religion != component.Religion)
return;
args.Verbs.Add(new AlternativeVerb
{
Text = Loc.GetString("admin-player-actions-follow"),
Act = () =>
{
_follower.StartFollowingEntity(args.User, uid);
},
});
}
private void OnRenounceFromGod(Entity<CP14ReligionFollowerComponent> ent, ref CP14RenounceFromGodEvent args)
@@ -78,6 +120,9 @@ public abstract partial class CP14SharedReligionGodSystem
EnsureComp<CP14ReligionFollowerComponent>(target, out var follower);
if (follower.Religion is not null)
return false;
return !follower.RejectedReligions.Contains(religion);
}
@@ -118,6 +163,7 @@ public abstract partial class CP14SharedReligionGodSystem
SendMessageToGods(pending.Comp.Religion.Value, Loc.GetString("cp14-become-follower-message", ("name", MetaData(pending).EntityName)), pending);
_actions.AddAction(pending, ref follower.RenounceAction, follower.RenounceActionProto);
_actions.AddAction(pending, ref follower.AppealAction, follower.AppealToGofProto);
return true;
}
@@ -146,6 +192,7 @@ public abstract partial class CP14SharedReligionGodSystem
Dirty(target, follower);
_actions.RemoveAction(target, follower.RenounceAction);
_actions.RemoveAction(target, follower.AppealAction);
}
}

View File

@@ -1,3 +1,4 @@
using Content.Shared.FixedPoint;
using Robust.Shared.Serialization;
namespace Content.Shared._CP14.Religion.Systems;
@@ -9,12 +10,12 @@ public enum CP14ReligionEntityUiKey
}
[Serializable, NetSerializable]
public sealed class CP14ReligionEntityUiState(Dictionary<NetEntity, string> altars, Dictionary<NetEntity, string> followers, float followerPercentage, float manaPercentage) : BoundUserInterfaceState
public sealed class CP14ReligionEntityUiState(Dictionary<NetEntity, string> altars, Dictionary<NetEntity, string> followers, FixedPoint2 followerPercentage, FixedPoint2 manaPercentage) : BoundUserInterfaceState
{
public Dictionary<NetEntity, string> Altars = altars;
public Dictionary<NetEntity, string> Followers = followers;
public float FollowerPercentage = followerPercentage;
public float ManaPercentage = manaPercentage;
public FixedPoint2 FollowerPercentage = followerPercentage;
public FixedPoint2 ManaPercentage = manaPercentage;
}
[Serializable, NetSerializable]

View File

@@ -33,7 +33,7 @@ public abstract partial class CP14SharedReligionGodSystem : EntitySystem
return gods;
}
protected abstract void SendMessageToGods(ProtoId<CP14ReligionPrototype> religion, string msg, EntityUid source);
public abstract void SendMessageToGods(ProtoId<CP14ReligionPrototype> religion, string msg, EntityUid source);
}
/// <summary>

View File

@@ -3,6 +3,9 @@ cp14-offer-soul-god-message = [bold]{$name}[/bold] [color=green]wants to become
cp14-unoffer-soul-god-message = [bold]{$name}[/bold] [color=red]has changed his mind about becoming your follower.[/color]
cp14-become-follower-message = [bold]{$name}[/bold] [color=green]becomes your follower[/color]!
cp14-remove-follower-message = [bold]{$name}[/bold] [color=red]rejects you and will never be able to return to you![/color]
cp14-call-follower-message = [bold]{$name}[/bold] appeals to you!
cp14-critical-follower-message = [bold]{$name}[/bold] is falling into critical condition!
cp14-dead-follower-message = [bold]{$name}[/bold] is dead!
cp14-renounce-action-popup = YOU ARE RENOUNCING YOUR PATRON! To confirm, perform the action again.
cp-renounce-action-god-popup = YOU ARE REJECTING YOUR FOLLOWER! To confirm, perform the action again.

View File

@@ -3,6 +3,9 @@ cp14-offer-soul-god-message = [bold]{$name}[/bold] [color=green]хочет ст
cp14-unoffer-soul-god-message = [bold]{$name}[/bold] [color=red]передумал становиться вашим последователем.[/color]
cp14-become-follower-message = [bold]{$name}[/bold] [color=green]становится вашим последователем[/color]!
cp14-remove-follower-message = [bold]{$name}[/bold] [color=red]отвергает вас, и больше никогда не сможет вернться к вам![/color]
cp14-call-follower-message = [bold]{$name}[/bold] взывает к вам!
cp14-critical-follower-message = [bold]{$name}[/bold] падает в критическое состояние!
cp14-dead-follower-message = [bold]{$name}[/bold] погибает!
cp14-renounce-action-popup = ВЫ ОТРЕКАЕТЕСЬ ОТ ПОКРОВИТЕЛЯ! Для подтверждения выполните действие еще раз.
cp-renounce-action-god-popup = ВЫ ОТВЕРГАЕТЕ СВОЕГО ПОСЛЕДОВАТЕЛЯ! Для подтверждения выполните действие еще раз.

View File

@@ -0,0 +1,73 @@
- type: entity
id: CP14ActionSpellGodLumeraDarkmist
name: Impenetrable darkness
description: You summon a thick fog that obscures vision and disorients mortals.
components:
- type: CP14MagicEffectReligionRestricted
- type: CP14MagicEffectManaCost
manaCost: 10
- type: CP14MagicEffect
telegraphyEffects:
- !type:CP14SpellSpawnEntityOnTarget
spawns:
- CP14ImpactEffectFlashLight
effects:
- !type:CP14SpellSpawnEntityOnTarget
spawns:
- CP14LumeraDarkMist
- type: WorldTargetAction
repeat: true
checkCanAccess: false
range: 100
itemIconStyle: BigAction
sound: !type:SoundPathSpecifier
path: /Audio/Magic/Eldritch/voidblink.ogg
icon:
sprite: _CP14/Actions/DemigodSpells/lumera.rsi
state: mist
event: !type:CP14WorldTargetActionEvent
cooldown: 0.15
- type: entity
parent:
- BaseStructure
- BaseShadow
id: CP14LumeraDarkMist
categories: [ HideSpawnMenu ]
components:
- type: SyncSprite
- type: TimedDespawn
lifetime: 60
- type: Occluder
- type: Sprite
drawdepth: Effects
sprite: Effects/spookysmoke.rsi
layers:
- state: spookysmoke
color: "#3266a8"
map: [base]
- type: OptionsVisualizer
visuals:
base:
- options: Default
data: { state: spookysmoke }
- options: ReducedMotion
data: { state: spookysmoke_static }
- type: Physics
bodyType: Static
canCollide: false
- type: Fixtures
fixtures:
fix1:
shape:
!type:PhysShapeAabb
bounds: "-0.5,-0.5,0.5,0.5"
layer:
- SlipLayer
mask:
- ItemMask
density: 1000
hard: false
- type: Tag
tags:
- HideContextMenu

View File

@@ -10,4 +10,30 @@
priority: -8
event: !type:CP14RenounceFromGodEvent
- type: ConfirmableAction
popup: cp14-renounce-action-popup
popup: cp14-renounce-action-popup
- type: entity
id: CP14ActionAppealToGod
name: Appeal to god
description: You call upon your patron! He will hear your call wherever he may be.
components:
- type: CP14MagicEffect
effects:
- !type:CP14SpellSpawnEntityOnTarget
spawns:
- CP14ImpactEffectSphereOfLight
- !type:CP14SpellTransferManaToGod
amount: 20
safe: false
- !type:CP14SpellSendMessageToGod
- type: InstantAction
sound: !type:SoundPathSpecifier
path: /Audio/Magic/rumble.ogg
icon:
sprite: _CP14/Actions/DemigodSpells/generic.rsi
state: appeal
priority: -8
event: !type:CP14DelayedInstantActionEvent
cooldown: 15
castDelay: 1.5
breakOnMove: true

View File

@@ -57,6 +57,21 @@
- !type:GodFollowerPercentage
percentage: 0.3
- type: cp14Skill
id: LumeraDarkMist
skillUiPosition: 6, 3
tree: GodLumera
learnCost: 1.0
icon:
sprite: _CP14/Actions/DemigodSpells/lumera.rsi
state: mist
effects:
- !type:AddAction
action: CP14ActionSpellGodLumeraDarkmist
restrictions:
- !type:NeedPrerequisite
prerequisite: LumeraT2
# T3
- type: cp14Skill

Binary file not shown.

After

Width:  |  Height:  |  Size: 318 B

View File

@@ -0,0 +1,14 @@
{
"version": 1,
"size": {
"x": 32,
"y": 32
},
"license": "All right reserved",
"copyright": "Created by TheShuEd",
"states": [
{
"name": "appeal"
}
]
}

View File

@@ -16,6 +16,9 @@
{
"name": "renounce"
},
{
"name": "mist"
},
{
"name": "t1"
},

Binary file not shown.

After

Width:  |  Height:  |  Size: 554 B