Skip to content

Commit

Permalink
I mean, it freakin works :P
Browse files Browse the repository at this point in the history
What else can ya ask for.

There needs to be a proper way to specify skill requirements in YAML, likely a serializable struct. There's a basis for that commented out in the main System at the moment but I wanted to test if it actually worked.
Other than that, I suppose it's just a matter of refining, helper functions, and of course, implementation.
  • Loading branch information
Pspritechologist committed Mar 24, 2024
1 parent 66175f0 commit 9744437
Show file tree
Hide file tree
Showing 11 changed files with 440 additions and 308 deletions.
27 changes: 27 additions & 0 deletions Content.Server/SimpleStation14/Skills/RoleSkillsSpecial.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
using Content.Shared.Roles;
using Content.Shared.SimpleStation14.Skills.Prototypes;
using Content.Shared.SimpleStation14.Skills.Systems;
using JetBrains.Annotations;
using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom.Prototype.Dictionary;

namespace Content.Server.SimpleStation14.Skills;

/// <summary>
/// Adds to an Entity's skills on equip.
/// </summary>
[UsedImplicitly]
public sealed class RoleSkillsSpecial : JobSpecial
{

[DataField("skills", customTypeSerializer: typeof(PrototypeIdDictionarySerializer<int, SkillPrototype>))]
public Dictionary<string, int> Skills { get; } = new();

public override void AfterEquip(EntityUid mob)
{
var entMan = IoCManager.Resolve<IEntityManager>();
var skillSystem = entMan.System<SharedSkillsSystem>();

foreach (var skill in Skills)
skillSystem.TryModifySkillLevel(mob, skill.Key, skill.Value);
}
}
225 changes: 40 additions & 185 deletions Content.Server/SimpleStation14/Skills/SkillsCommands.cs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
using Content.Server.Administration;
using Content.Shared.Administration;
using Content.Shared.Borgs;
using Robust.Shared.Console;
using Content.Server.Players;
using Robust.Server.Player;
Expand All @@ -9,106 +8,17 @@

namespace Content.Server.SimpleStation14.Skills;

[AdminCommand(AdminFlags.Logs)]
public sealed class SkillUiCommand : IConsoleCommand
{
public string Command => "skillui";
public string Description => Loc.GetString("command-skillui-description");
public string Help => Loc.GetString("command-skillui-help");

public async void Execute(IConsoleShell shell, string argStr, string[] args)
{
var entityManager = IoCManager.Resolve<IEntityManager>();
var uiSystem = IoCManager.Resolve<UserInterfaceSystem>();
var player = shell.Player as IPlayerSession;
EntityUid? entity = null;

if (args.Length == 0 && player != null)
{
entity = player.ContentData()?.Mind?.CurrentEntity;
}
else if (IoCManager.Resolve<IPlayerManager>().TryGetPlayerDataByUsername(args[0], out var data))
{
entity = data.ContentData()?.Mind?.CurrentEntity;
}
else if (EntityUid.TryParse(args[0], out var foundEntity))
{
entity = foundEntity;
}

if (entity == null)
{
shell.WriteLine("Can't find entity.");
return;
}

if (!uiSystem.TryGetUi(entity.Value, SkillsUiKey.Key, out _))
return;

uiSystem.TryOpen(entity.Value, SkillsUiKey.Key, player!);
}
}

// [AdminCommand(AdminFlags.Logs)]
// public sealed class ListSkillsCommand : IConsoleCommand
// public sealed class SkillUiCommand : IConsoleCommand
// {
// public string Command => "skillsls";
// public string Description => Loc.GetString("command-skillsls-description");
// public string Help => Loc.GetString("command-skillsls-help");

// public async void Execute(IConsoleShell shell, string argStr, string[] args)
// {
// var entityManager = IoCManager.Resolve<IEntityManager>();
// var player = shell.Player as IPlayerSession;
// EntityUid? entity = null;

// if (args.Length == 0 && player != null)
// {
// entity = player.ContentData()?.Mind?.CurrentEntity;
// }
// else if (IoCManager.Resolve<IPlayerManager>().TryGetPlayerDataByUsername(args[0], out var data))
// {
// entity = data.ContentData()?.Mind?.CurrentEntity;
// }
// else if (EntityUid.TryParse(args[0], out var foundEntity))
// {
// entity = foundEntity;
// }
// public string Command => "skillui";
// public string Description => Loc.GetString("command-skillui-description");
// public string Help => Loc.GetString("command-skillui-help");

// if (entity == null)
// {
// shell.WriteLine("Can't find entity.");
// return;
// }

// if (!entityManager.TryGetComponent<SkillsComponent>(entity, out var skills))
// {
// shell.WriteLine("Entity has no skills.");
// return;
// }

// // Parkstation-Skills-Start
// shell.WriteLine($"Name: {Loc.GetString($"skillset-name-{skills.SkillsID}")}");
// shell.WriteLine($"Description: {Loc.GetString($"skillset-description-{skills.SkillsID}")}");
// // Parkstation-Skills-End

// shell.WriteLine($"Skills for {entityManager.ToPrettyString(entity.Value)}:");
// foreach (var skills in skills.Skills)
// {
// shell.WriteLine(skills);
// }
// }
// }

// [AdminCommand(AdminFlags.Fun)]
// public sealed class ClearSkillsCommand : IConsoleCommand
// {
// public string Command => "skillsclear";
// public string Description => Loc.GetString("command-skillsclear-description");
// public string Help => Loc.GetString("command-skillsclear-help");
// public async void Execute(IConsoleShell shell, string argStr, string[] args)
// {
// var entityManager = IoCManager.Resolve<IEntityManager>();
// var uiSystem = IoCManager.Resolve<UserInterfaceSystem>();
// var player = shell.Player as IPlayerSession;
// EntityUid? entity = null;

Expand All @@ -131,102 +41,47 @@ public async void Execute(IConsoleShell shell, string argStr, string[] args)
// return;
// }

// if (!entityManager.TryGetComponent<SkillsComponent>(entity.Value, out var skills))
// {
// shell.WriteLine("Entity has no skills component to clear");
// if (!uiSystem.TryGetUi(entity.Value, SkillsUiKey.Key, out _))
// return;
// }

// entityManager.EntitySysManager.GetEntitySystem<SkillsSystem>().ClearSkills(entity.Value, skills);
// uiSystem.TryOpen(entity.Value, SkillsUiKey.Key, player!);
// }
// }

// [AdminCommand(AdminFlags.Fun)]
// public sealed class AddSkillsCommand : IConsoleCommand
// {
// public string Command => "skillsadd";
// public string Description => Loc.GetString("command-skillsadd-description");
// public string Help => Loc.GetString("command-skillsadd-help");
// public async void Execute(IConsoleShell shell, string argStr, string[] args)
// {
// var entityManager = IoCManager.Resolve<IEntityManager>();
// var player = shell.Player as IPlayerSession;
// EntityUid? entity = null;

// if (args.Length < 2 || args.Length > 3)
// {
// shell.WriteLine("Wrong number of arguments.");
// return;
// }

// if (IoCManager.Resolve<IPlayerManager>().TryGetPlayerDataByUsername(args[0], out var data))
// {
// entity = data.ContentData()?.Mind?.CurrentEntity;
// }
// else if (EntityUid.TryParse(args[0], out var foundEntity))
// {
// entity = foundEntity;
// }

// if (entity == null)
// {
// shell.WriteLine("Can't find entity.");
// return;
// }

// var skills = entityManager.EnsureComponent<SkillsComponent>(entity.Value);

// if (args.Length == 2)
// entityManager.EntitySysManager.GetEntitySystem<SkillsSystem>().AddSkills(entity.Value, args[1], component: skills);
// else if (args.Length == 3 && int.TryParse(args[2], out var index))
// entityManager.EntitySysManager.GetEntitySystem<SkillsSystem>().AddSkills(entity.Value, args[1], index, skills);
// else
// shell.WriteLine("Third argument must be an integer.");
// }
// }

// [AdminCommand(AdminFlags.Fun)]
// public sealed class RemoveSkillsCommand : IConsoleCommand
// {
// public string Command => "skillsrm";
// public string Description => Loc.GetString("command-skillsrm-description");
// public string Help => Loc.GetString("command-skillsrm-help");
// public async void Execute(IConsoleShell shell, string argStr, string[] args)
// {
// var entityManager = IoCManager.Resolve<IEntityManager>();
// var player = shell.Player as IPlayerSession;
// EntityUid? entity = null;

// if (args.Length < 1 || args.Length > 2)
// {
// shell.WriteLine("Wrong number of arguments.");
// return;
// }
[AdminCommand(AdminFlags.Logs)]
public sealed class SkillModifyCommand : IConsoleCommand
{
public string Command => "skillmodify";
public string Description => Loc.GetString("command-skillmodify-description");
public string Help => Loc.GetString("command-skillmodify-help");

// if (IoCManager.Resolve<IPlayerManager>().TryGetPlayerDataByUsername(args[0], out var data))
// {
// entity = data.ContentData()?.Mind?.CurrentEntity;
// }
// else if (EntityUid.TryParse(args[0], out var foundEntity))
// {
// entity = foundEntity;
// }
public async void Execute(IConsoleShell shell, string argStr, string[] args)
{
var entityManager = IoCManager.Resolve<IEntityManager>();
var player = shell.Player as IPlayerSession;
EntityUid? entity = null;
var skillSystem = entityManager.EntitySysManager.GetEntitySystem<SharedSkillsSystem>();

// if (entity == null)
// {
// shell.WriteLine("Can't find entity.");
// return;
// }
if (args.Length < 3 && player != null)
{
entity = player.ContentData()?.Mind?.CurrentEntity;
}
else if (IoCManager.Resolve<IPlayerManager>().TryGetPlayerDataByUsername(args[2], out var data))
{
entity = data.ContentData()?.Mind?.CurrentEntity;
}
else if (EntityUid.TryParse(args[2], out var foundEntity))
{
entity = foundEntity;
}

// if (!entityManager.TryGetComponent<SkillsComponent>(entity, out var skills))
// {
// shell.WriteLine("Entity has no skills to remove!");
// return;
// }
if (entity == null)
{
shell.WriteLine("Can't find entity.");
return;
}

// if (args[1] == null || !int.TryParse(args[1], out var index))
// entityManager.EntitySysManager.GetEntitySystem<SkillsSystem>().RemoveSkills(entity.Value);
// else
// entityManager.EntitySysManager.GetEntitySystem<SkillsSystem>().RemoveSkills(entity.Value, index);
// }
// }
if (!skillSystem.TryModifySkillLevel(entity.Value, args[0], int.Parse(args[1])))
shell.WriteLine("Failed to modify skill.");
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -7,18 +7,22 @@

namespace Content.Shared.SimpleStation14.Skills.Components
{
/// <summary>
/// This holds all the data on an entity's skills.
/// It should generally never be accessed directly, and instead accessed through <see cref="SharedSkillsSystem"/>.
/// No, not event just to get a single value. I worked hard on those functions ;~;.
/// </summary>
[RegisterComponent]
[NetworkedComponent]
[AutoGenerateComponentState]
[Serializable]
[NetSerializable]
public sealed partial class SkillsComponent : Component
{
/// <summary>
/// This holds all the data on an entity's skills.
/// If you're using this- don't. Use <see cref="SharedSkillsSystem"/> to access it.
/// </summary>
[AutoNetworkedField]
[ViewVariables(VVAccess.ReadOnly)]
public Dictionary<string, int> Skills = new();

/// <summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,20 +16,20 @@ public sealed class SkillCategoryPrototype : IPrototype
// [DataField("icon")]
// public SpriteSpecifier Icon = default!;

/// <summary>
/// A whitelist to determine what Entities are allowed to use this category of skills.
/// </summary>
[DataField("whitelist")]
public EntityWhitelist? Whitelist = null;
// /// <summary>
// /// A whitelist to determine what Entities are allowed to use this category of skills.
// /// </summary>
// [DataField("whitelist")]
// public EntityWhitelist? Whitelist = null;

/// <summary>
/// A whitelist to determine what Entities are NOT allowed to use this category of skills.
/// </summary>
/// <remarks>
/// A blacklist is just a whitelist you deny.
/// </remarks>
[DataField("blacklist")]
public EntityWhitelist? Blacklist = null;
// /// <summary>
// /// A whitelist to determine what Entities are NOT allowed to use this category of skills.
// /// </summary>
// /// <remarks>
// /// A blacklist is just a whitelist you deny.
// /// </remarks>
// [DataField("blacklist")]
// public EntityWhitelist? Blacklist = null;

/// <summary>
/// Whether or not this category is viewable in the character menu.
Expand Down
22 changes: 13 additions & 9 deletions Content.Shared/SimpleStation14/Skills/Prototypes/SkillPrototype.cs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
using Content.Shared.SimpleStation14.Skills.Systems;
using Content.Shared.Whitelist;
using Robust.Shared.Prototypes;
using Robust.Shared.Serialization.TypeSerializers.Implementations;
Expand All @@ -21,6 +22,9 @@ public sealed class SkillPrototype : IPrototype
[DataField("subCategory", required: true, customTypeSerializer: typeof(PrototypeIdSerializer<SkillSubCategoryPrototype>))]
public string SubCategory = default!;

[DataField("maxValue")]
public int MaxValue = 5;

/// <summary>
/// If true, this skill's icon won't be colored by the sub category's color.
/// </summary>
Expand All @@ -39,16 +43,16 @@ public sealed class SkillPrototype : IPrototype
/// Skills lower will make less of an impact.
/// </summary>
[DataField("weight")]
public int Weight = 1;
public float Weight = 1;

/// <summary>
/// Optional override for the Sprite Specifier for the icon for this skill.
/// </summary>
/// <remarks>
/// If null, the state will be generated from the skill's name, and the RSI will be inherited from the sub category.
/// </remarks>
[DataField("icon", customTypeSerializer: typeof(SpriteSpecifierSerializer))]
public SpriteSpecifier? Icon = null;
// /// <summary>
// /// Optional override for the Sprite Specifier for the icon for this skill.
// /// </summary>
// /// <remarks>
// /// If null, the state will be generated from the skill's name, and the RSI will be inherited from the sub category.
// /// </remarks>
// [DataField("icon", customTypeSerializer: typeof(SpriteSpecifierSerializer))]
// public SpriteSpecifier? Icon = null;

/// <summary>
/// A whitelist to determine what Entities are allowed to use this skill, in addition to the sub categories list.
Expand Down
Loading

0 comments on commit 9744437

Please sign in to comment.