commit 5eb002e67a8b5370e57299767b3f691a1e01e360 Author: iisaev Date: Sun Oct 18 12:41:39 2026 +0300 init mod diff --git a/locale/en.properties b/locale/en.properties new file mode 100644 index 0000000..9c7f611 --- /dev/null +++ b/locale/en.properties @@ -0,0 +1,2 @@ +mod_skills_base_name = Skills Engine +mod_skills_base_desc = Engine skills subsystem: card-based skill definitions, the grant service (skill + granted action pairing), the skills panel UI and the collection effect plate. diff --git a/locale/ru.properties b/locale/ru.properties new file mode 100644 index 0000000..24a75dc --- /dev/null +++ b/locale/ru.properties @@ -0,0 +1,2 @@ +mod_skills_base_name = Движок умений +mod_skills_base_desc = Подсистема умений движка: карточные определения умений, сервис выдачи (умение + связанное действие), панель умений и плашка эффекта коллекции. diff --git a/manifest.json b/manifest.json new file mode 100644 index 0000000..5f5f5dd --- /dev/null +++ b/manifest.json @@ -0,0 +1,13 @@ +{ + "id": "skills_base", + "name": "Skills Engine", + "version": "1.0.0", + "author": "ct", + "description": "Engine skills subsystem: card-based skill definitions, the grant service (skill + granted action pairing), the skills panel UI and the collection effect plate. Replaces the former Core/Skills implementations and Core/Factories/Impls/SkillFactory.", + "category": "engine, library", + "sources": [ + "src/**/*.cs" + ], + "depends": ["interface>=1"], + "ui": [] +} diff --git a/src/RareType.cs b/src/RareType.cs new file mode 100644 index 0000000..d40f060 --- /dev/null +++ b/src/RareType.cs @@ -0,0 +1,21 @@ +namespace Cthangover.Mods.Skills +{ + /// + /// Represents the rarity tier of a skill card, determining its drop probability, + /// visual frame treatment, and relative power budget. Higher tiers correspond to + /// more potent effects and rarer acquisition chances. + /// + public enum RareType + { + /// Standard skill with the highest drop rate and baseline power. + Common, + /// Slightly improved stats and a lower drop rate than Common. + Uncommon, + /// Notably stronger, appearing infrequently in loot pools. + Rare, + /// Powerful skill with significant gameplay impact; very low drop chance. + Epic, + /// The highest tier — game-changing abilities with extremely rare availability. + Legendary + } +} diff --git a/src/SkillCardBehaviour.cs b/src/SkillCardBehaviour.cs new file mode 100644 index 0000000..ef4eee0 --- /dev/null +++ b/src/SkillCardBehaviour.cs @@ -0,0 +1,205 @@ +using Cthangover.Mods.Interface.Base.Lists; +using Cthangover.Core.UI.Theming; +using Godot; + +using Cthangover.Mods.Interface.Theming; +namespace Cthangover.Mods.Skills +{ + /// + /// Grid card of one collected skill. Pure presentation: the panel binds a + /// through and toggles + /// selection through , while every colour comes + /// from so the same rarity reads identically on + /// the card, the study plate and the rarity filter tabs. + /// + /// Clicking is intentionally not handled here: the panel subscribes to + /// GuiInput, so the card keeps a single responsibility and can be + /// hosted by any list without knowing its owner. Hover is handled inside + /// because it only repaints the card itself. + /// + public partial class SkillCardBehaviour : ListItem + { + [Export] private Panel bg; + [Export] private Panel accent; + [Export] private PanelContainer art; + [Export] private TextureRect imgCard; + [Export] private Label txtName; + [Export] private Label txtGems; + [Export] private PanelContainer badgeBox; + [Export] private Label badgeLabel; + [Export] private HBoxContainer effectRow; + [Export] private Label effectValue; + [Export] private Label effectLabel; + + private bool _selected; + private bool _hover; + + /// Configures the card to accept mouse input for hover/selection feedback. + public override void _Ready() + { + MouseFilter = MouseFilterEnum.Stop; + MouseEntered += OnMouseEntered; + MouseExited += OnMouseExited; + } + + /// + /// Binds the skill definition to the card: artwork, translated name, + /// rarity gems (one diamond per tier), the type badge and the first + /// numeric effect as the card's short line. Skills without effects hide + /// the effect row instead of leaving an empty band; a skill without + /// artwork keeps the empty well, which is a valid authored state. + /// + public override void Construct(SkillInfo skillInfo) + { + base.Construct(skillInfo); + ResolveNodes(); + + if (art != null) + art.AddThemeStyleboxOverride("panel", UiKit.Frame(UiTokens.RadiusSm, UiTokens.Well, UiTokens.Line)); + + if (skillInfo == null) + return; + + if (imgCard != null) + imgCard.Texture = skillInfo.Sprite; + + if (txtName != null) + { + txtName.Text = TranslationServer.Translate(skillInfo.Name); + txtName.AddThemeFontSizeOverride("font_size", UiTokens.FontBodySmall); + txtName.AddThemeColorOverride("font_color", UiTokens.InkBright); + } + + if (txtGems != null) + { + txtGems.Text = new string('◆', Mathf.Clamp((int)skillInfo.RareType + 1, 1, 5)); + txtGems.AddThemeFontSizeOverride("font_size", UiTokens.FontMicro); + txtGems.AddThemeColorOverride("font_color", SkillPalette.RarityColor(skillInfo.RareType)); + } + + ApplyTypeBadge(skillInfo); + ApplyEffect(skillInfo); + RefreshStyle(); + } + + /// + /// Applies the panel-owned selection state: the selected card gets the + /// golden surface, rarity border and a soft rarity glow, while hover + /// only lifts the border. Both are repainted from scratch so the card + /// can never end up half-styled after a filter rebuild. + /// + public void SetSelected(bool selected) + { + _selected = selected; + RefreshStyle(); + } + + /// Frees the node; the panel owns the card's lifetime and rebuilds the grid. + public override void Destruct() + { + QueueFree(); + } + + private void ResolveNodes() + { + bg ??= GetNodeOrNull("Bg"); + accent ??= GetNodeOrNull("Accent"); + art ??= GetNodeOrNull("Art"); + imgCard ??= GetNodeOrNull("Art/ImgCard"); + txtName ??= GetNodeOrNull