docs(04-00): add WandAssetSpike documentation artifact

Documentation-only class capturing the 04-00 spike conclusions. Not wired
into GravityFlipPlugin. Private constructor prevents instantiation.

Records the locked VANILLA_COPY decision:
- Do NOT register a new Item asset store (unproven pattern).
- Subclass SimpleInstantInteraction and register via
  getCodecRegistry(Interaction.CODEC).register("GravityFlipWand", ...).
- Plan 04-02 will runtime-identify a vanilla hatchet/axe itemID for
  /gravityflip wand to hand out.

Delete this class at the start of Plan 04-01.
This commit is contained in:
2026-04-23 18:46:38 +02:00
parent 5b2484be3b
commit 66536628ad
@@ -0,0 +1,71 @@
package com.mythlane.gravityflip.wand.spike;
/**
* <h2>04-00 Spike artifact — NOT WIRED INTO THE PLUGIN.</h2>
*
* <p>This class is intentionally <strong>not referenced</strong> from
* {@code GravityFlipPlugin}. It exists purely as an executable-looking
* documentation of the empirical investigation that produced
* {@code .planning/phases/04-wand-commands/04-00-SPIKE-RESULT.md}.
*
* <p><b>Locked decision (see SPIKE-RESULT.md):</b> we will <em>not</em> register
* a brand-new {@code Item} asset store from a plugin — no decompiled builtin
* plugin does that, and it risks duplicating the core's Item store. Instead,
* Plan 04-01 will:
*
* <ol>
* <li>Subclass {@link com.hypixel.hytale.server.core.modules.interaction.interaction.config.SimpleInstantInteraction}
* as {@code GravityFlipWandInteraction} with its own {@code BuilderCodec}.</li>
* <li>In {@code GravityFlipPlugin.setup()}, call:
* <pre>{@code
* getCodecRegistry(Interaction.CODEC)
* .register("GravityFlipWand",
* GravityFlipWandInteraction.class,
* GravityFlipWandInteraction.CODEC);
* }</pre>
* This is the pattern used by PortalsPlugin:74, CreativeHubPlugin:149,
* InstancesPlugin:158, CraftingPlugin:130, TeleporterPlugin:73,
* ObjectivePlugin:210-211 — 8+ builtin precedents.</li>
* <li>Plan 04-02 will identify the concrete vanilla itemID to hand out in
* {@code /gravityflip wand} by iterating
* {@code Item.getAssetStore().getAssetMap()} at runtime (disposable
* probe), then hardcode the chosen itemID (likely a hatchet/axe variant
* that already exposes Primary + Secondary interactions).</li>
* </ol>
*
* <p>The code below is illustrative only. It compiles against stubs in
* javadoc and is <strong>not invoked</strong>. Delete this class at the start
* of Plan 04-01.
*
* <h3>Why VANILLA_COPY and not a brand-new Item JSON?</h3>
*
* <p>Hypothesised pattern (rejected):
* <pre>{@code
* // UNPROVEN: no builtin plugin does this for Item.class.
* getAssetRegistry().register(
* HytaleAssetStore.builder(Item.class, Item.ASSET_MAP)
* .setPath("Items")
* .build());
* }</pre>
*
* <p>User-confirmed pattern (adopted):
* <blockquote>
* « On peut copier un item vanilla genre la hache et changer des propriétés
* genre couleur etc. » — 2026-04-23
* </blockquote>
*
* <p>Copy an existing vanilla item (hatchet / pickaxe / sword — anything
* exposing {@code Primary} + {@code Secondary}) and hijack the click
* behaviour via the {@code Interaction.CODEC} registry. Visual polish
* (custom colour / display name) can be layered later without blocking v1.
*/
public final class WandAssetSpike {
/** Not callable. Not invoked. Documentation-only. */
private WandAssetSpike() {
throw new UnsupportedOperationException(
"WandAssetSpike is a 04-00 documentation artifact. "
+ "See .planning/phases/04-wand-commands/04-00-SPIKE-RESULT.md. "
+ "Delete this class at the start of Plan 04-01.");
}
}