From 6a92564f94131d7de62b92a3ef19de3b8b6bfdb0 Mon Sep 17 00:00:00 2001 From: Meta Vens Date: Sun, 14 Jun 2026 06:02:26 +0100 Subject: [PATCH] Use typed behavior projections in stat modifiers --- .voidbot/state/aetheria.cc | Bin 68616 -> 68793 bytes .../ServerShared/Behaviors/StatModifier.cs | 15 +++++++++++---- docs/aetheria-perfect-machine-map.md | 9 ++++++++- 3 files changed, 19 insertions(+), 5 deletions(-) diff --git a/.voidbot/state/aetheria.cc b/.voidbot/state/aetheria.cc index 25f64bdbeb0d5880c2d86f9ab6e6440e18d6b7f1..c2f628ab8a0a3a87fa3dfa535a95caba0aa6fb6e 100644 GIT binary patch delta 1270 zcmaKs&ui2`6vxfFiv6WM)UH@6qadYdL$~&aTNI&GvCz^|MX)_hliA(aWG0=NbX^aw zpa(sPgi=LB#fqRFDqB!N@#H}eO2x}UJ@iul0r4OneEG4PvX{``+UDMx9=z4 zKS(YwB^vt%yVHZ|UiDC3sACb1 zrNJn21aa|7s-wDVg0m|`^OnSMWMQf04VptTPr|u2zNJbt+|Y9b8B}tnI~vgu!Q2E2 z>I+GzfW4Kk(Fn+Z8IVml(6BJo2=aRYY9`PU(lAY=F^ixqXBIL^4r|3=&+x@@WJmp| zC}^_8xQ7IQTG*h#5QnQLK8wVPEcHp&xd;Tbij_usSg~a@(k^KnWM> zOVB6J_$0}S^&LlVKI0@?8FdfOx4O-b_quoI4wT#0&eUfzo-M~P#W`?3Yz5O-4H6ZL zl=FEYP)NErMkl7HhnQXjZ`lyn7zYzT>iCW7NuK4O0S(E!QW|E4-rqomt&H zRDSsLT4PJ?DH-UWT9P;i;L_#JUn_~G*Ph5$_&}6@{BEdgh$SzqDXHjv>FM^~mxW`> o$5^a4e1~=~?o$*iwlLr=EIv|{QWQLq_JVIuCzMZhv1s4aKheO@*#H0l delta 1080 zcmZvbJ!lj`6vy4mA?5?45RFY_3c-uSy+o4SnIa*2sDWrg6pJ)6*?rj^vpchynZ4v} zPO#A?B8x;T3nPMs3Kt?4el!*qfwX}%b`~NCf}o9W_bzuANHy?2=Dq*#z4!iU`u>yj z+qG23;K$ho{ZoI5}J$T${#Nj+$*+w#$`mhMQjEH}dP`6TR6x+nE-vvN9ZeKl61 zHyg+EB#_JkLLEnfLp2keP;L`Ta67a#D>7Xo5|kDahy%h0ElY%prD&=!e35DJN#Vwn zGGAC8W&ZY$3A9|LoH`&0EC)h?BDxfSO)i6;j!R|YkO{6dw_;)BxWitV+ew0Jwa^|YNRD@Lt;uWDa|~OSX4@eP0xW# ziwsL+w~8q&VnJ4h*q9F_VI}6`Y-N%OO_)NCnv@`;2_+oa7oo;VF+cRG!$3|NNHuTu zXq(Yh{#Fo4;_g&p#RaOVdEKP}hD!V#{KQhlDuLPxg^@Wg1ROVSmSK`hp$>7l4W|`q zMU*Q-&nCXWruOJ6*MuedVKHQZkLa_=z!6znSPP6hF*{V>T!(0}M5SF5coP8usgA79 z7L&vHFJ->M-Ef7RfqAua;MBe666Uujr>V7odlhAhozanJhogs!Cn|rp#@fcmW4-$? zT>>2?{z{)GRh6(K=Q-8pDE*0Ym;?o_CGF9hV=jd diff --git a/Assets/Scripts/ServerShared/Behaviors/StatModifier.cs b/Assets/Scripts/ServerShared/Behaviors/StatModifier.cs index 0a0f86a7a..8462303ae 100644 --- a/Assets/Scripts/ServerShared/Behaviors/StatModifier.cs +++ b/Assets/Scripts/ServerShared/Behaviors/StatModifier.cs @@ -67,15 +67,15 @@ public class StatModifier : Behavior, IInitializableBehavior, IDisposable, IAlwa if (typeof(EquippableItemData).IsAssignableFrom(targetType)) _stats = Entity.Equipment .Select(hp => hp.EquippableItem) - .Where(gear => _data.RequireBehavior == null || ItemManager.GetData(gear).Behaviors.Any(behavior => behavior.GetType() == _data.RequireBehavior)) + .Where(HasRequiredBehavior) .Where(gear => ItemManager.GetData(gear).GetType() == targetType) .Select(gear => statField.GetValue(ItemManager.GetData(gear)) as PerformanceStat) .ToArray(); else _stats = Entity.Equipment .Select(hp => hp.EquippableItem) - .Where(gear => _data.RequireBehavior == null || ItemManager.GetData(gear).Behaviors.Any(behavior => behavior.GetType() == _data.RequireBehavior)) - .SelectMany(gear => ItemManager.GetData(gear).Behaviors) + .Where(HasRequiredBehavior) + .SelectMany(gear => ItemManager.GetRuntimeBehaviorProjections(gear)) .Where(behaviorData => behaviorData.GetType() == targetType) .Select(behaviorData => statField.GetValue(behaviorData) as PerformanceStat) .ToArray(); @@ -83,6 +83,13 @@ public class StatModifier : Behavior, IInitializableBehavior, IDisposable, IAlwa } } + private bool HasRequiredBehavior(EquippableItem gear) + { + return _data.RequireBehavior == null || + ItemManager.GetRuntimeBehaviorProjections(gear) + .Any(behavior => behavior.GetType() == _data.RequireBehavior); + } + private void ApplyModifier() { _applied = true; @@ -135,4 +142,4 @@ public class StatReference [Inspectable, LegacyPayloadKey(2)] public string Stat; -} \ No newline at end of file +} diff --git a/docs/aetheria-perfect-machine-map.md b/docs/aetheria-perfect-machine-map.md index 6bafb18ea..42e219800 100644 --- a/docs/aetheria-perfect-machine-map.md +++ b/docs/aetheria-perfect-machine-map.md @@ -199,7 +199,10 @@ legacy catalog cache, and legacy UI paths should be migration-only or deleted. through the runtime behavior projection bridge before instantiating the current `BehaviorData`-backed behavior classes. `BehaviorData` remains the temporary behavior-class config bridge, not the runtime behavior payload - owner. + owner. `StatModifier` behavior requirements and behavior-stat targets also + read that typed behavior projection bridge instead of hydrating + `EquippableItemData.Behaviors`; item performance stat fields are still a + legacy DTO bridge until those stats move to typed runtime rows. Ship drag, combat/turret shot prediction height, and thruster torque geometry now consume typed hull facets and typed shape masks. The item properties panel also reads typed catalog title names, descriptions, @@ -717,6 +720,10 @@ First Aetheria surfaces to publish: - Done: move `EquippedItem` and `ConsumableItemEffect` behavior construction off `Data.Behaviors` and onto typed runtime behavior payload projection; `BehaviorData` remains only the temporary behavior-class config bridge. + - Done: move `StatModifier` behavior requirements and behavior-stat targets + off `EquippableItemData.Behaviors` and onto typed runtime behavior + projections; equippable item performance stat fields remain a separate DTO + bridge. - Done: move runtime blueprint price aggregation and conductivity restore geometry onto typed runtime item price and hull shape rows; legacy `ItemData.Price` and `HullData.Shape` no longer own those blueprint paths.