feat(D-01/E): resistance & lock system rework (E1-E7)

E1: Initialize currentResistance in NBT at equip time from
    ResistanceComponent — eliminates MAX-scan fallback bug

E2: BuiltInLockComponent for organic items (already committed)

E3: canStruggle refactor — new model:
    - ARMS: always struggle-able (no lock gating)
    - Non-ARMS: only if locked OR built-in lock
    - Removed dead isItemLocked() from StruggleState + overrides

E4: canUnequip already handled by BuiltInLockComponent.blocksUnequip()
    via ComponentHolder delegation

E5: Help/assist mechanic deferred (needs UI design)

E6: Removed lock resistance from ILockable (5 methods + NBT key deleted)
    - GenericKnife: new knifeCutProgress NBT for cutting locks
    - StruggleAccessory: accessoryStruggleResistance NBT replaces lock resistance
    - PacketV2StruggleStart: uses config-based padlock resistance
    - All lock/unlock packets cleaned of initializeLockResistance/clearLockResistance

E7: Fixed 3 pre-existing bugs:
    - B2: DataDrivenItemRegistry.clear() synchronized on RELOAD_LOCK
    - B3: V2TyingPlayerTask validates heldStack before equip (prevents duplication)
    - B5: EntityKidnapperMerchant.remove() cleans playerToMerchant map (memory leak)
This commit is contained in:
NotEvil
2026-04-15 03:23:49 +02:00
parent 199bf00aef
commit d6bb030ad7
17 changed files with 76 additions and 228 deletions

View File

@@ -356,6 +356,16 @@ public class DataDrivenBondageItem extends AbstractV2BondageItem {
holder.onEquipped(stack, entity);
}
// Initialize currentResistance in NBT from ResistanceComponent at equip time.
// This avoids the MAX-scan fallback in getBaseResistance(entity) which returns
// the highest resistance across ALL equipped data-driven items.
ResistanceComponent resistComp = getComponent(stack, ComponentType.RESISTANCE, ResistanceComponent.class);
if (resistComp != null) {
com.tiedup.remake.items.base.IHasResistance resistanceItem =
(com.tiedup.remake.items.base.IHasResistance) stack.getItem();
resistanceItem.setCurrentResistance(stack, resistComp.getBaseResistance());
}
// NPC speed reduction (players use MovementStyleManager, not this legacy path)
if (!(entity instanceof Player)) {
Set<BodyRegionV2> regions = getOccupiedRegions(stack);

View File

@@ -139,7 +139,9 @@ public final class DataDrivenItemRegistry {
* Clear all definitions. Called on world unload or for testing.
*/
public static void clear() {
SNAPSHOT = RegistrySnapshot.EMPTY;
synchronized (RELOAD_LOCK) {
SNAPSHOT = RegistrySnapshot.EMPTY;
}
}
// ===== COMPONENT HOLDERS =====