Game guide · source of truth
Production

AAA detail catalog (polish standards)

The small details that make Zoen feel finished — hit feel, camera, animation, effects, sound, world, enemies, loot, interface, optimisation, comfort and, since round 2, network feel, input feel, look and rendering and session flow — each with a starting standard, the stage it is due in and its proof. Rendered from polish-standards.json. 127 accepted on 2026-10-06 (ADR-028) and 90 more on 2026-10-07 (ADR-031); none implemented.

Accepted by the owner on 2026-10-06 as the polish standard (ADR-028). Not implemented yet. Every number is a starting value to tune in the Combat Lab. The tables on this page are rendered from polish-standards.json, so the data file is the only place to change them. Every item is presentation or optimisation: none changes a server outcome.

Round 2, accepted by the owner on 2026-10-07 (ADR-031): 90 more details, four new areas and a fourth stage, alpha. Each keeps its added date. Why: Development review, round 2.

The older docs give the big systems: the hit-feel stack, the effect layers, the 4-layer hit sound and the budgets. This page adds the small details those systems need before they feel finished, and says when each one is due.

217 details in 15 areas · adopted stage by stage

Round 2 added 90 details, four areas and the alpha stage on 2026-10-07 (review, accepted in ADR-031).

core 44 details

G2 · one polished skill (M2)

Needed before the owner judges the first skill. Without these the feel cannot be judged fairly.

slice 115 details

G3 · battle slice (M4)

Needed for a small real fight: enemies, loot, the mix, traversal.

alpha 27 details

M8 · content alpha (first closed playtest)

Needed before outside players: online feel, session flow, onboarding, full menus and comfort options. Keeps the G3 battle slice small.

polish 31 details

M10 · art, audio and polish

Adds richness once the systems are stable.

◆How to use this page

  • Task cards name detail ids. "Implements HIT-02, SFX-05, CAM-03" is a testable scope. Each id has a proof.
  • Agents load one slice, not the page. node tools/ctx.mjs polish SFX prints one area, polish SFX-05 one item and polish core one stage. See Speed and token efficiency.
  • Existing rules win. Hitstop lengths stay in combat-states.json, tiers in feel-quality.json, limits in Performance. A data test fails if this catalog redefines them.
  • Stages keep development fast. Only the core details gate the first polished skill (G2). The slice details arrive with the battle slice (G3) and the polish details in M10. Do not build a later stage early. The alpha stage (M8, the first closed playtest) holds online feel, onboarding and full menus, so G3 stays small.

◆Three rules that cut across every area

  1. One swing is one event. A cleave that lands on twelve targets gives one attacker freeze, one camera impulse and one merged impact sound, not twelve. Without this rule, pack combat stutters, the camera rattles and the voice cap is spent in a single frame. Values: crowdCoalescing in the data file (HIT-02, CAM-03, SFX-05, HIT-10).
  2. Predicted is attacker-side, confirmed is target-side. The wind-up, swish and trail start on input. Everything on the target (flash, material burst, impact sound, number, haptic) waits for the server Hit event (HIT-04). This settles the gap between "contact sparks may play predicted" in Netcode and "misses never produce hit feedback" in the development guide. Online that layer arrives a round trip late, so a predicted-contact mode is built beside it and the owner picks one at G2 (ADR-031).
  3. Name the platform. Several techniques in the older docs do not exist on every target. The browser build has no mixer effects, no dynamic resolution, no compute shaders and one managed thread. A technique is accepted only with its fallback.
What each platform can do · checked 2026-10-06
TechniquewindowsandroidioswebFallback where it is missing
dynamic resolutionDirectX 12 onlyVulkan only✓✗fixed render scale from the capability probe, stepped only at safe moments
gpu resident drawerForward+ onlyVulkan and Forward+ onlyForward+ only✗SRP Batcher and GPU instancing; Mesh Renderers only either way
stp upscaler✓Vulkan only✓✗bilinear or FSR 1.0 upscaling filter
vfx graph✓needs compute shaders; verify on the Low reference✓✗Particle System definitions with the same timing and footprint (docs/production/VFX.md)
audio mixer effects and snapshots✓✓✓✗bus-gain automation in code; gain staging instead of a limiter
streamed audio clips✓✓✓✗compressed-in-memory clips
managed threads✓✓✓✗main-thread budget; only native code and Burst-compiled jobs can use threads

◆Hit feel and combat feedback

The existing stack defines hitstop, shake, flash and numbers for one hit on one target. These details cover crowds, kills, breaks, rejected inputs and the player being hit.

HIT · 17 details · starting values

Each hit reads as one clear event, even when a swing lands on twelve targets.

IDDetailStandard (starting values)StageProof
HIT-01Hitstop releaseFreeze lengths stay in combat-states.json. Release ramps the pose speed from 0 to 1 over 2 frames. The attacker's weapon trail freezes with the pose; world particles, numbers and sound keep running.coreFrame capture: trail static during the freeze, sparks advance; damage log identical with feel off.
HIT-02One hitstop per swingA swing that lands on several targets in one tick gives the attacker one freeze of the highest impact class, plus 10% per extra target up to +30%, never over 150 ms. Attacker freeze time is at most 25% of any rolling second. Struck targets freeze individually.
crowdCoalescing.hitstop: freezesPerSwing 1 · extraTargetBonus 0.1 · maxBonus 0.3 · maxAttackerFreezeMs 150 · attackerFreezeShareMaxPerSecond 0.25 · releaseRampFrames 2 · killMultiplier 1.25 · killCapMs 140 · bossDeathCapMs 200
core100-dummy cleave: attacker freeze inside the cap; chain cadence unchanged in the replay.
HIT-03Hit shakeA struck target's mesh (never its capsule) jitters along the hit axis during its freeze and decays to zero: 3 / 4 / 6 / 8 cm for light / medium / heavy / massive.
crowdCoalescing.hitShakeCm: light 3 · medium 4 · heavy 6 · massive 8
coreCapsule position identical in the replay; jitter visible in a side capture.
HIT-04Predicted and confirmed layersPredicted on input: wind-up pose, weapon swish, trail and cast cue only. Target flash, material burst, impact sound, numbers and hit haptics play only on the server Hit event. A miss shows none of them. ADR-031: a predicted-contact mode (attacker freeze, spark and first impact transient on the client's own hit test; numbers, health, reactions, status and kill confirm still on the server event) is built behind a Combat Lab switch, and the owner picks the mode at G2 after judging both at 80 ms.coreForced-miss replay shows zero target-side cues.
HIT-05No-stagger readWhen the rule gives flash only, or the target has superarmour or is a boss, play the armoured impact variant of its material (duller sound, pale spark, no flinch), so the player can read that this hit will not stagger.
hitMaterials: blood none · items [id:fur, burst:tufts and dust, armoured:dull thud, no tufts, id:carapace, burst:chitin chips and a hard spark, armoured:clank and a pale spark, id:scale, burst:scale flecks and grit, armoured:scrape and a pale spark, id:cloth_leather, burst:dust and loose threads, armoured:padded thump, id:shell, burst:shell chips and stone dust, armoured:knock and a pale spark, id:feather, burst:feathers and down, armoured:soft thump, few feathers]
coreReaction-matrix capture includes the armoured variant for every material.
HIT-06Kill confirmThe killing blow gets freeze x1.25 (at most 140 ms), a kill sweetener layer and a styled number. The death style still comes from combat-states.json.
crowdCoalescing.hitstop: freezesPerSwing 1 · extraTargetBonus 0.1 · maxBonus 0.3 · maxAttackerFreezeMs 150 · attackerFreezeShareMaxPerSecond 0.25 · releaseRampFrames 2 · killMultiplier 1.25 · killCapMs 140 · bossDeathCapMs 200
sliceClip of kill and non-kill with the same skill, side by side.
HIT-07Break momentA poise break or boss break gets one unmistakable cue set: the break sting (sfx-break), a radial dust ring, a camera punch one class above the hit and a distinct broken pose held for the break window.sliceOwner review clip; cue fires exactly once per break in the event log.
HIT-08Being hitDamage to the player shows a direction arc toward the source for 0.6 s, an edge pulse scaled by the health lost (a thin edge line when Reduce flashing is on), a rumble pattern different from dealing damage, and a hurt vocal at most every 0.8 s.sliceCapture from four hit directions; rate limit shown in the cue log.
HIT-09Delayed health barTarget, boss and party bars show lost health as a pale chunk for 0.5 s, then drain it over 0.3 s, so burst damage is readable.sliceHUD capture of a 3-hit burst.
HIT-10Damage number mannersOwn numbers only by default (others are a setting). Live cap 12 / 20 / 32 / 48 by tier. Numbers drift alternately left and right so they do not stack; crits overshoot for 80 ms; a merged number keeps counting up instead of spawning new ones.
crowdCoalescing.numbers: liveCapByTier low:12, mid:20, high:32, ultra:48 · othersVisibleByDefault false
sliceS1 perf scene: live numbers never over the cap; zero allocations.
HIT-11Input acknowledgementEvery accepted press shows a response on the next presentation frame. Every rejected press says why: a mana orb pulse with a soft blip (at most every 0.5 s), a slot shake on cooldown, 'No opening' on finishers.coreC4 and C8 control tests record the feedback event for each rejection reason.
HIT-12Chain escalationEach step of an unbroken chain raises the swish pitch by one semitone, up to +3, and resets with the chain, so a full chain sounds like it is building.polishAudio capture of an 8-slot chain.
HIT-13Low health stateBelow 25% health: the vitals pulse, a quiet heartbeat loop plays and ambience drops 6 dB. Each part can be switched off. Never a screen tint that hides telegraphs.sliceTelegraph contrast check passes while the state is active.
HIT-14Ticks are not hits
added 2026-10-07
Channel ticks, damage over time and auras never trigger hitstop, shake or the full impact layers. The first and last tick of a channel get the full hit; ticks between play a light tick sound at most every 0.25 s per target and merge their numbers (HIT-10).slice10 s channel on the 25-dummy field: no attacker freeze between the first and the last tick; voices inside the cap.
HIT-15Critical read
added 2026-10-07
A critical hit adds one bright sweetener layer and a white-hot core to the impact (VFX-01 still holds), never extra hitstop or shake beyond its impact class. Critical hits on other players' targets add nothing.sliceA/B capture of a normal and a critical hit; freeze lengths are equal in the replay.
HIT-16Projectile impacts
added 2026-10-07
A projectile's target burst plays on the server Hit event where the projectile is drawn, not at the server's resolved point. A terrain hit plays the surface response (WLD-01) and never a target flash. A projectile always ends with its end effect, never a mid-air pop.sliceLatency test at 120 ms: the burst sits on the drawn projectile; terrain hits show no flash.
HIT-17Finisher signature
added 2026-10-07
On top of its impact class from combat-states.json, a finisher contact adds a low sub-drop, a radial ring and, in the close view, a field-of-view push of at most 2°. Local presentation only: no global slow motion.polishOwner review clip per finisher family; the replay shows the freeze inside its class.

◆Camera

Shake needs different rules in the two views: positional shake reads well from above, but in the close view it must be rotational and smaller to stay comfortable.

CAM · 12 details · starting values

The camera adds weight to your own hits and never costs you sight of a threat.

IDDetailStandard (starting values)StageProof
CAM-01Shake by viewTactical view shakes position. Close view shakes rotation (pitch and yaw at most 1.5°, roll at most 0.8°) at 60% scale. Shake is smooth noise on the existing trauma curve, never a new random offset every frame.
crowdCoalescing.camera: impulsesPerSwing 1 · extraTargetBonus 0.1 · maxBonus 0.3 · closeViewScale 0.6 · closeViewMaxPitchYawDeg 1.5 · closeViewMaxRollDeg 0.8 · reducedMotionMaxScale 0.3
coreBoth-camera clip of a massive hit; shake values logged.
CAM-02Whose hits shakeOnly your hits, hits on you, and boss or world events inside their radius add trauma, scaled by distance. Other players' impacts never shake your camera.coreTwo-client test: client B's camera transform is unchanged by client A's hits.
CAM-03One impulse per swingA multi-target swing adds one trauma impulse of the highest class, plus 10% per extra target up to +30%.
crowdCoalescing.camera: impulsesPerSwing 1 · extraTargetBonus 0.1 · maxBonus 0.3 · closeViewScale 0.6 · closeViewMaxPitchYawDeg 1.5 · closeViewMaxRollDeg 0.8 · reducedMotionMaxScale 0.3
core100-dummy cleave: one impulse in the camera log.
CAM-04Follow and look-aheadPosition damping 0.12–0.18 s. The tactical view leads 0.8 m toward movement, eased over 0.4 s, and holds still during attacks. No lead in the close view.sliceRun, stop and reverse clip; no overshoot wobble.
CAM-05Collision mannersPush in fast (0.1 s or less) and ease out slowly (0.4–0.6 s) so the camera does not pump near walls. In the close view the character dithers out under 0.8 m and effects fade under 1.0 m from the lens.sliceCorner and narrow-passage captures (C12, C17).
CAM-06Always findableWhen the player or the current target is hidden by something that cannot fade, draw a flat tinted silhouette. Telegraphs draw over terrain decoration on every tier.
Tiers: High and Ultra: outline. Low and Mid: flat tint for the player and the current target only.
sliceCapture behind a wall and in tall reeds on Low.
CAM-07Speed and field of viewSprinting and mounts widen the view by 3–5° over 0.3 s. Hit punches follow feel-quality.json.polishMount sprint clip.
CAM-08Reduce camera motionOne comfort switch: no directional kick, no field-of-view punch, no look-ahead, and shake at most 30%.
crowdCoalescing.camera: impulsesPerSwing 1 · extraTargetBonus 0.1 · maxBonus 0.3 · closeViewScale 0.6 · closeViewMaxPitchYawDeg 1.5 · closeViewMaxRollDeg 0.8 · reducedMotionMaxScale 0.3
sliceSettings test: values clamp when the switch is on.
CAM-09Lock-on framingThe optional close-view lock-on keeps the player in the lower third and the boss upper-middle, turns at most 220° per second on its own and never moves the capsule.sliceBoss circle-strafe capture; capsule path equals the input path.
CAM-10Fit the fight
added 2026-10-07
When an elite or a boss is engaged, the tactical view eases its distance out by up to 15% over 1 s so the largest active telegraph fits on screen, and eases back 3 s after combat ends. The close view never zooms by itself.sliceS3 boss scene at 16:9 and 19.5:9: every boss telegraph is fully on screen in the tactical view.
CAM-11View switch
added 2026-10-07
The view switch (R3 or V) blends in 0.25–0.35 s along a path that cannot pass through geometry, keeps movement and aim live during the blend and keeps the current target.sliceSwitch spam during a chain in a narrow passage: no clipping frame, no lost input.
CAM-12Rooms and ceilings
added 2026-10-07
Interiors (the Kiln Depths, ruins) use camera volumes that cap height and distance, so the tactical view never sits above a ceiling. Moving between volumes blends over 0.5 s.alphaDungeon fly-through: no frame with the camera inside or above geometry.

◆Animation and character motion

These add to the mannequin and review standard. ANM-04 resolves a conflict in the older docs: magnetism may slide the body up to 1.5 m, while a planted foot may slide less than 2 cm.

ANM · 19 details · starting values

Bodies carry weight, answer input at once and stay cheap in a crowd.

IDDetailStandard (starting values)StageProof
ANM-01Starts, stops and pivotsThe capsule keeps its 0.08 s stop. The stop clip is chosen by which foot is down and settles with under 2 cm of slide. Add 180° pivots, 90° and 180° turns in place, and eight-direction strafing for the close view.coreFoot-slide test on stop and pivot clips; both-camera capture.
ANM-02Lean and lookAdditive lean into turns from the turn rate (at most 8°). Head and eyes track the target or cursor (at most 60° of yaw, 0.2 s damping), switched off while an attack clip authors the head.sliceFigure-eight run clip; no neck flip in the joint-limit check.
ANM-03Foot contactTwo-bone foot IK with a pelvis offset of at most 12 cm on slopes and stairs. IK fades out in the air and during travel skills.
Tiers: Low: own character only.
coreSlope and stair captures; ground penetration under 1 cm.
ANM-04Magnet windowEach melee clip marks the frames where magnetism may move the body (a step or lunge). The slide of up to 1.5 m happens only there, never while a foot is planted, so magnetism and the 2 cm slide limit both hold.coreFoot-slide test with magnetism at High against a target 1.5 m away.
ANM-05Cancel blendA movement cancel shows displacement on the next frame and blends from a snapshot of the current pose in 0.06–0.10 s. It never cross-fades from the attack clip while that clip keeps swinging.coreC1–C3 interruption snapshots: no extra swing after the cancel frame.
ANM-06Contact poseThe contact frame is a strong, readable pose, because local hitstop holds exactly that frame. Review it as a still in both cameras.coreContact stills in the eight-view sheet.
ANM-07Reaction priorityA new reaction interrupts the current one only if it is stronger. The same reaction re-triggers at most every 0.15 s. Direction comes from the hit vector in four quadrants.sliceMulti-hit test: no reaction jitter; the table test covers priority.
ANM-08Reaction detail by distanceTier A characters play full reactions, tier B flinch and stagger, tier C only death and knockback displacement. Deaths and telegraph poses always play.sliceS1 perf scene with tiers visualised.
ANM-09Secondary motionCapes, hair and tails settle in 0.3–0.6 s, reset on teleports and long dashes so they never explode, and update at the character's animation rate.
Tiers: Tier A 60 Hz, tier B 30 Hz, tier C off.
sliceDash and blink captures; no stretched chain in any frame.
ANM-10Idle lifeBreathing plus two or three weapon-specific fidgets after 8–15 s of idle. None within 4 s of combat.polish60 s idle clip per grip.
ANM-11Smooth trailsSample weapon sockets at 120 Hz, or interpolate between frames, so arcs from 30 fps clips are curved and not polygonal.sliceSlow-motion capture of the fastest basic attack.
ANM-12Bodies on the groundCorpse cap 8 / 16 / 24 / 40 by tier. When the cap is reached the oldest dissolves early (1 s). Loot never depends on a corpse. Bosses are exempt.
crowdCoalescing.corpses: capByTier low:8, mid:16, high:24, ultra:40 · earlyDissolveS 1
sliceS1 perf scene: corpse count never over the cap.
ANM-13MountsMount and dismount within 0.6 s, interrupted by damage. Gallop sway at most 0.5°. Hoof dust and sound come from the surface table.polishMount clip on three surfaces.
ANM-14Cues come from the cast clock
added 2026-10-07
Effect and sound cues are scheduled from the cast's phase timeline (the server-synced cast clock), not fired by animation events, so they fire exactly once at 30 fps, through blends and hitstop, and stop on a cancel. Animation events carry only presentation details such as footsteps.core1,000 casts at 20, 30 and 60 fps with random cancels: every cue fired once or was cancelled, none later than one frame.
ANM-15Draw and sheathe
added 2026-10-07
The first attack draws the weapon inside its own windup on the upper-body layer and never adds delay. Weapons sheathe 6–8 s after combat ends, on the move, without stopping the legs. Mounting sheathes at once.sliceReplay: the first attack's contact time equals that of an attack with the weapon already drawn.
ANM-16Landing weight
added 2026-10-07
Jumps and falls pick a light, medium or heavy landing by fall speed. Heavy landings dip the pelvis and raise the surface burst (VFX-09). A landing never holds the player longer than the recovery in the gem's or the fall's data.sliceDrop test from 1, 3 and 6 m: the right variant, and input accepted at the authored frame.
ANM-17Hit while moving
added 2026-10-07
A player hit while running plays an additive upper-body flinch and keeps the legs' gait, unless the reaction rule says stagger or knockdown.sliceRun through a 10-hit volley: the gait stays continuous, no skating.
ANM-18No lockstep crowds
added 2026-10-07
Monsters of one type start their idle and locomotion cycles at random offsets and pick between two or three idle variants. Idle playback varies by ±5%; locomotion stays matched to speed. Packs never move in step.sliceS1 capture: no two neighbouring monsters of one type in phase.
ANM-19Faces and eyes
added 2026-10-07
Where the rig has face bones: blinks every 2–6 s, eye saccades toward the look target (ANM-02) and an effort expression on heavy and signature attacks. Off beyond 10 m and on Low.polishClose-view capture at idle and during a signature.

◆Visual effects

VFX-04 matters most. The HUD contract describes telegraphs as decals, and the effect pipeline recycles decals at a cap of 64. A telegraph must never be recycled, so telegraphs get a renderer and a pool of their own.

VFX · 21 details · starting values

Rich to look at, cheap to draw, and never in the way of a warning.

IDDetailStandard (starting values)StageProof
VFX-01One focal pointEach effect has one brightest element. Only cores cross the bloom threshold; secondary elements stay under 60% of that value and lingering elements under 30%. Check it in greyscale.coreGreyscale capture in the visual checklist.
VFX-02Fast in, slow outImpact flash 1–3 frames. Sparks 0.2–0.4 s. Dust and smoke 0.6–1.5 s. Decals follow feel-quality.json.coreEffect timeline against the phase bar.
VFX-03Impact placementSpawn the impact at the hit point on the target (its hit_center socket plus an offset along the swing), turned to the hit direction. Never at the target's feet or root.coreCapture from four attack directions on a small and a large target.
VFX-04Telegraphs have their own rendererTelegraphs and player ground previews use a dedicated pooled, terrain-following mesh and shader, sized for the worst encounter. They never share the capped decal pool, are never recycled early and look the same on every tier and platform. The fill follows server time.core100 dummies and a boss with the decal pool exhausted: every telegraph is visible every frame.
VFX-05Near the lens and the groundParticles fade inside 1.0 m of the camera. Depth-fade (soft) particles are used only where a depth texture exists; elsewhere billboards are lifted 3 cm and meshes are aligned to their velocity.
Tiers: Soft particles on High and Ultra. Low, Mid and Web use the offset rule.
coreClose-view capture of a ground burst on Low and High.
VFX-06Overdraw disciplineOne premultiplied-alpha material covers additive and blended sprites. Flipbook quads are trimmed to the sprite. No full-screen quads except the single Ultra shockwave. An own effect may cover at most 35% of the screen in the tactical view and 50% in the close view, for at most 0.3 s.coreOverdraw capture and screen-coverage metric in the budget JSON.
VFX-07Fields stay see-throughLasting ground areas keep a strong edge (60% opacity or more) and a faint interior (25% or less), so enemies and telegraphs inside stay readable.sliceTelegraph inside a field on bright and dark terrain.
VFX-08Status signaturesEach ailment has its own shape, colour and motion (burn rises and flickers, chill rims and drips, shock crawls). Show at most three overlays per target; nameplate icons carry the rest.sliceSix-ailment line-up in greyscale.
VFX-09Surface responseDashes, landings and heavy impacts spawn the puff, splash or chips of the surface under them.
Tiers: Low: one shared puff tinted by surface.
sliceDash clip across three surfaces.
VFX-10Prewarmed effectsEvery effect definition is spawned once off-screen and its shaders are warmed during loading, so the first cast never hitches.corePerf scene S5: no frame over twice the budget.
VFX-11Lobbed projectilesArcing projectiles carry a ground shadow. Player mortars show a jade landing marker and enemy ones a telegraph.sliceCapture from the tactical view.
VFX-12Smooth flipbooksBlend between flipbook frames so 8×8 sheets can play at 15–20 fps without visible stepping.sliceSlow-motion capture of a smoke flipbook.
VFX-13Area atmosphereOne ambient emitter per area: ember drift in the Cinder Kilns, salt glitter on the Saltway, falling ash in Ashroot Grove, dew sparkle in Dewgrass Meadow.
Tiers: High and Ultra only.
polishStory-camera screenshot per area.
VFX-14Bending plantsGrass and reeds bend away from nearby actors and shockwaves.
Tiers: High and Ultra: displacement texture. Mid: nearest 4 actors. Low: off.
polishDash through reeds clip.
VFX-15WaterRipples on steps and dashes, a splash on landing, wet footprints for 2 s after leaving water.
Tiers: Ripples from Mid; footprints from High.
polishReedwater Banks clip.
VFX-16What gives way firstWhen a pool is full, drop the oldest decoration of other players first, then your own decoration. Never drop telegraphs, your own hit confirms or party utility footprints.slicePool-exhaustion test in perf scene S3.
VFX-17Spawn and despawn
added 2026-10-07
Monsters never pop in or out. In view they emerge (burrow, step out of shadow, gather from dust) over 0.6–1.0 s and leave with a dissolve. Server spawn rules are unchanged.sliceSpawn 50 monsters in view: no single-frame appearance or disappearance.
VFX-18Decals stay on the ground
added 2026-10-07
Impact marks, scorches and lasting fields project only onto terrain and static kits through decal layers, never onto characters, moving props or water. Overlapping marks fade the oldest first. Telegraphs keep their own renderer (VFX-04).sliceField cast on a crowd: no decal on any character in the capture.
VFX-19Far effects simplify
added 2026-10-07
Other players' effects beyond 25 m drop to their core and footprint. Your own and your party's effects keep full detail to 40 m. Telegraphs never simplify.alphaS2 town crowd: particles by distance band in perf.json.
VFX-20One texture library
added 2026-10-07
Effects draw from one shared set of masks, noises, gradients and flipbooks packed into a few atlases per tier. A new texture needs a reason in the effect's data, so the style stays consistent, memory stays flat and effects batch.sliceAsset validator: textures per effect and atlas use.
VFX-21Element on the weapon
added 2026-10-07
Buffs that imbue an element tint the trail and the impact core in that element's palette (VFX.md) and add one small emitter on the weapon, never a screen effect.polishCapture with the buff on and off.

◆Sound

Two facts shape this area. The listener cannot sit on a camera that is 9–16 m above the player (SFX-01). And the Web build's mixer supports volume only, so every duck and state mix must work as plain gain changes (SFX-03).

SFX · 29 details · starting values

Weight comes from timing and contrast, and the mix works on all four platforms.

IDDetailStandard (starting values)StageProof
SFX-01Listener at the playerThe listener sits at the player's head and uses the camera's yaw: fully at the player in the tactical view, a 70/30 player/camera blend in the close view. Distances are measured from the player, not from a camera up to 16 m away.
audioMix.listener: tactical player:1, camera:0 · close player:0.7, camera:0.3 · orientation camera yaw
coreA hit at the player's feet measures the same level in both views.
SFX-02Transient on timeA one-shot's first transient starts within 10 ms of the file start (checked by the audio validator). The swish stores its peak time and is scheduled on the audio clock so the peak lands on contact. The impact fires on the server Hit event.coreValidator report; cue timestamp within 16.7 ms of contact.
SFX-03Portable mix coreAll ducking and state mixing is bus-gain automation in code, because the mixer in the Web build supports volume only. Limiter, compressor, low-pass and reverb are native extras and must never be needed for a correct mix.
Platform: Web: no mixer effects or snapshots, no streamed clips.
coreThe same mix test passes on the Web build with every mixer effect removed.
SFX-04No machine-gun repeatsTakes shuffle and never repeat either of the last two. Pitch ±6% (existing) and volume ±1.5 dB. Telegraph cues stay fixed.
audioMix.variation: avoidRepeatLast 2 · pitchPct 6 · volumeDb 1.5
core1,000-trigger log: no repeat inside the window.
SFX-05Crowd coalescingIdentical impact cues inside 50 ms merge into one instance that is 1.5 dB louder per doubling (at most +6 dB), with up to two material layers. At most two instances of one cue start per 50 ms.
crowdCoalescing.audio: mergeWindowMs 50 · gainPerDoublingDb 1.5 · maxGainDb 6 · maxInstancesPerCuePerWindow 2 · maxMaterialLayers 2 · stealFadeMs 8
core12-target cleave: voices inside the cap, no phasing in the capture.
SFX-06Clean voice stealingA stolen voice fades out over 8 ms. Loops go virtual and resume. Own hits, telegraph cues and boss cues are never stolen.
crowdCoalescing.audio: mergeWindowMs 50 · gainPerDoublingDb 1.5 · maxGainDb 6 · maxInstancesPerCuePerWindow 2 · maxMaterialLayers 2 · stealFadeMs 8
coreVoice-cap test with a click detector on the capture.
SFX-07Distance classesFootsteps 1–18 m, hits 2–35 m, skills 3–45 m, boss and telegraph cues 5–90 m. The curve is logarithmic near the source and linear at the tail.
audioMix.attenuationM: footsteps [1, 18] · hits [2, 35] · skills [3, 45] · bossAndTelegraph [5, 90]
sliceLevel against distance plot per class.
SFX-08Ducking tableBoss or telegraph warning: music −6 dB (existing) and other players −4 dB for the length of the cue. Own massive hit: ambience −3 dB for 250 ms. Menu open: world buses −6 dB.sliceBus gain log for each trigger.
SFX-09Loudness of the whole mixMeasure a scripted 30-minute session: −18 LUFS for phones and the browser, −23 LUFS for the desktop wide preset, true peak at most −1 dBTP.
audioMix.loudness: measure integrated loudness of the whole mix over a scripted 30-minute session · phoneAndWebLufs -18 · desktopWideLufs -23 · truePeakDbtp -1 · reference Sony ASWG-R001: -24 LKFS for home systems, -18 LKFS for portable systems, true peak -1 dBTP
sliceLoudness report of the session capture.
SFX-10Headroom without a limiterBus gains are staged so the worst-case sum stays under −1 dBFS on Web, where no limiter exists.
Platform: Web.
sliceOffline render of the worst-case cue set: peak at most −1 dBFS.
SFX-11FootstepsSurface × gait (walk, run, sprint, land) plus an armour layer (cloth, leather, plate), fired from animation foot contacts. Other players' steps play only inside 12 m, on at most 2 voices.sliceWalk across three surfaces; step events line up with foot plants.
SFX-12Telegraph cue shapeA riser as long as the telegraph that ends in a strike transient on the damage frame. Three danger timbres (normal, heavy, lethal). Placed at the telegraph centre. Never ducked and never randomised.sliceRiser end within 16.7 ms of the server strike at 200 ms round trip.
SFX-13Pre-impact dipFor massive hits, ambience and music dip 3 dB from 80 ms before contact (the time is known from the wind-up) and recover over 400 ms. Weight comes from contrast, not volume.sliceBus gain log around a finisher.
SFX-14State mixesTown, explore, combat, boss, low health, dead and menu are gain tables applied in code. Native builds may add mixer snapshots on top.sliceState-change test logs the gain table applied.
SFX-15Creature voicesIdle, aggro, effort, pain and death per monster. Pain at most every 0.6 s per monster, and at most three pain voices per 250 ms in a crowd.
audioMix.rateLimits: hoverTickMs 60 · manaBlipMs 500 · hurtVocalMs 800 · monsterPainMs 600 · crowdPainVoicesPer250Ms 3
sliceCrowd fight capture; rate limits in the cue log.
SFX-16Interface sound mannersHover ticks at most every 60 ms. Rapid pickups and allocations climb one semitone per event inside 0.4 s, up to +7.
audioMix.pitchLadder: semitonesPerEvent 1 · windowMs 400 · maxSemitones 7 · chainMaxSemitones 3
sliceFast-hover and 10-item pickup captures.
SFX-17Output presetsHeadphones or speakers (wide), laptop or TV (medium), phone speaker or night (narrow: ambience and interface +3 dB, peaks −3 dB, and a mid-range knock layer carries weight on small speakers).polishLoudness range report per preset.
SFX-18SpaceA reverb send per area: open desert is dry, ruins and courts have a stone slap.
Platform: Native only. Web: none.
polishListening review per area.
SFX-19OcclusionOne ray per audible emitter every 200 ms. A blocked source drops 4 dB.
Platform: Native adds a 2.5 kHz low-pass. Web is volume only.
polishWalk behind a wall near an emitter.
SFX-20Memory and loadingHit and interface one-shots are decompressed and preloaded with the combat bank. Beds and emitters stay compressed in memory. Music streams on native and is compressed in memory on Web.
Platform: Web supports only compressed-in-memory and decompress-on-load clips.
sliceAudio memory in perf.json; no load hitch on the first hit.
SFX-21Foley setWeapon draw and sheath, cloth on dash, landing by surface, hooves by surface, pickup by item class.sliceCoverage test: every listed action has a cue.
SFX-22Sound you can seeEvery critical sound has a visual twin (telegraph, off-screen arrow, HUD pulse). Mono switch. Separate sliders for master, music, ambience, effects and interface.sliceMuted playthrough of the boss slice.
SFX-23Borders blend
added 2026-10-07
Area beds cross-fade over 20–40 m at area borders, and the night and weather layers over 5–10 s at a phase change (WLD-08). Never a hard switch or a gap.alphaWalk across three borders: no gap and no doubled bed in the loudness trace.
SFX-24Big sources sound big
added 2026-10-07
Rivers, campfires, crowds and large monsters play from the nearest point on their shape (a line or an area) with some spread, so they never pinpoint or jump.alphaWalk along the river: level steady within 2 dB.
SFX-25No Doppler wobble
added 2026-10-07
Doppler is off on every source except fast fly-bys (projectiles, passing mounts), so camera turns never bend pitch.sliceFast camera spin in a loud scene: no pitch change in the capture.
SFX-26Focus and interruptions
added 2026-10-07
Losing focus lowers the game to a level set in the options (proposed −12 dB on desktop). Calls and other system interruptions pause sound and resume it cleanly. On iOS the silent switch mutes the game unless the player turns that off.
Platform: iOS: the audio session category decides the silent switch. Web: the browser decides autoplay and focus.
sliceInterruption test on the iPhone SE and the Galaxy A07; focus test on Windows and in the browser.
SFX-27Player efforts
added 2026-10-07
Heavy and signature attacks, dodges, jumps and hard landings may play a short vocal effort, at most one per 1.2 s and never on light chain steps. Each lineage and gender has its own set. Non-verbal efforts from the local audio generator (ADR-031); no spoken lines.polishChain and gem spam: effort rate inside the limit.
SFX-28After the fight
added 2026-10-07
Combat ends 4 s after the last hit. The combat mix then releases over 2 s and the area's quiet accents return, the first after at least 3 s, so the end of a fight sounds like relief.sliceFight-end capture: release time and first accent in the trace.
SFX-29Swish by weight
added 2026-10-07
Swishes are picked by the weapon's weight class and swing speed: light blades whistle, heavy weapons push air, and pitch falls as the weapon grows.sliceCapture across the 18 weapon families.

◆World and traversal

Time of day and weather are in from day one (ADR-030); their contract is time-weather.json, summarised in the development guide.

WLD · 12 details · starting values

The ground answers the player, and the world never pops or misleads.

IDDetailStandard (starting values)StageProof
WLD-01Surface tableOne table maps each surface to its footstep cue, step puff, dash trail, landing burst and impact mark. Terrain splat layers and kit materials carry a surface id.coreData test: every surface resolves to a cue or a fallback.
WLD-02Zone surfacesEach zone lists its surfaces, so audio and effects load only what the area needs.
zoneSurfaces: amber_gate [stone, sand, wood] · dewgrass_meadow [grass, wood, earth] · old_orchard [earth, grass, wood] · reedwater_banks [mud, water, stone] · clay_cut [earth, stone, water] · cinder_kilns [ash, stone] · saltway_flats [salt, water, wood] · bellshade_court [stone, sand] · stormquill_ridge [stone] · ashroot_grove [ash, earth, wood] · jade_seal_ruins [stone] · caravan_crown_arena [earth, sand]
sliceData test: every zone in world.json has a list.
WLD-03No pop-in near the playerNo visible detail-level or impostor switch inside 60 m. Switch distances use 10% hysteresis.
Tiers: High and Ultra: 0.3 s dithered cross-fade.
sliceMount ride capture along the road.
WLD-04Ambient lifeBirds lift when a player sprints within 6 m, insects gather near water, dust devils cross the flats. Client-only, instanced and tier-culled; never blocks or misleads.polishStory-camera clips.
WLD-05BeaconsEvery landmark is visible from its waypoint and is marked by a sky cue (smoke column, banner, glow) as well as its sound emitter.sliceScreenshot from each waypoint.
WLD-06Silhouettes in dark areasCharacters get a rim-light lift in dark or hazy areas so they still read at 64 px.slice64 px crops in Ashroot Grove and the Cinder Kilns.
WLD-07Town lifeIdle variety for townsfolk, lantern flicker in the shader (no real lights), awnings and banners in the wind.polishAmber Gate fly-through.
WLD-08Time of day and weatherIn from day one (ADR-030). A server clock drives four lighting phases and each area has a weather state, all defined in time-weather.json. Look and sound only. Every contrast, readability and performance check runs across its review matrix, and the GM arena can set the time and the weather.coreFour-phase capture strip from the first scene; telegraph contrast check across the review matrix on Low.
WLD-09One wind
added 2026-10-07
One wind vector from the weather state drives grass, trees, cloth, banners, smoke, dust and weather particles, so all of them agree. Gusts cross the terrain as a slow wave.sliceSandstorm capture: every wind-driven element moves the same way.
WLD-10NPCs notice you
added 2026-10-07
NPCs turn their head to a player within 4 m, turn to face them within 0.3 s when spoken to, and greet with a bark at most once per 10 minutes per player.alphaTown walk capture.
WLD-11Things you can use
added 2026-10-07
NPCs, waypoints, chests and quest objects share one proximity highlight and cursor (UI-14); on phones a context button appears near the thumb. It never looks like loot or an enemy.alphaHighlight capture of every interactable kind.
WLD-12Footprints
added 2026-10-07
Soft surfaces in the surface table keep footprints and dash scrapes for 4–8 s from a pooled set. Low has none.polishDash capture on the Saltway Flats.

◆Surface table

One table drives footsteps, puffs, dash trails and landing bursts. Four surfaces have no footstep recording yet and use a fallback until a request is added to the audio generator.

Surface table · one source for footsteps and ground effects
SurfaceFootstep cueStep puffDashLandingImpact markUsed in
sandsfx-foley-step-sandpale dust puffsand streakdust ringscuffamber gate, bellshade court, caravan crown arena
stonesfx-foley-step-stonethin gritgrit linegrit burstchip and crackamber gate, reedwater banks, clay cut, cinder kilns, bellshade court, stormquill ridge, jade seal ruins
woodsfx-foley-step-woodnonedust from the boardsboard dustnoneamber gate, dewgrass meadow, old orchard, saltway flats, ashroot grove
grasssfx-foley-step-grassblade flecksparting streakflecks and dewflattened patchdewgrass meadow, old orchard
watersfx-foley-step-watersmall splashwakesplash ringripplesreedwater banks, clay cut, saltway flats
earthsfx-foley-step-sand request neededochre dustdust streakdust burstscuffdewgrass meadow, old orchard, clay cut, ashroot grove, caravan crown arena
mudsfx-foley-step-water request neededmud fleckwet streakmud splatfootprintreedwater banks
ashsfx-foley-step-sand request neededgrey ash puffash plumeash ringscuffcinder kilns, ashroot grove
saltsfx-foley-step-stone request neededsalt crystalscrystal spraycrust crackcracksaltway flats

◆Enemies, telegraphs and bosses

ENM · 10 details · starting values

Every threat announces itself the same way, in picture and in sound.

IDDetailStandard (starting values)StageProof
ENM-01Telegraph anatomyA constant outline, a progress fill, a border that brightens over the last 20% (never a screen flash), then the strike frame. Fill progress is computed from the server start time, so the strike matches the server at 200 ms round trip.coreLatency test at 0 and 200 ms: strike frame within one frame of the server event.
ENM-02More than a decalEach ability also changes the silhouette in its wind-up and shows a short weapon or eye glint 0.2 s before the strike, together with the riser cue.sliceClip with the ground decal hidden: the attack is still readable.
ENM-03Off-screen warningsTelegraphs and elite or boss attacks aimed at you from outside the view show an edge arrow in the danger colour. At most four, in both cameras.sliceClose-view capture with a caster behind the player.
ENM-04Aggro and leashAggro: a bark and a nameplate flash. Leash: a grey nameplate and a heal-back effect, so a reset never looks like a bug.sliceAggro and leash clip.
ENM-05Waiting enemies actEnemies without an attack token pace, circle or taunt. They never stand idle next to the player.slicePack fight clip; engagement-token log.
ENM-06Elite identityThe existing aura and ★, plus a spawn sting and vocals two semitones lower.polishElite spawn clip.
ENM-07Boss beatsAn intro of 1.5–2.5 s that never takes control away. A phase change authored inside the server's transition time, with a shockwave and a music boundary. A break window with a broken pose and a lit weak point. A death with a longer freeze (at most 200 ms), a slow dissolve and a loot fountain.
crowdCoalescing.hitstop: freezesPerSwing 1 · extraTargetBonus 0.1 · maxBonus 0.3 · maxAttackerFreezeMs 150 · attackerFreezeShareMaxPerSecond 0.25 · releaseRampFrames 2 · killMultiplier 1.25 · killCapMs 140 · bossDeathCapMs 200
sliceOwner review of the boss slice.
ENM-08Nameplate mannersThe existing cap of 40. Health shows when damaged or targeted; elites and bosses always show it; the delayed health chunk follows HIT-09.sliceS2 perf scene screenshot.
ENM-09Dead means untargeted
added 2026-10-07
On the Death event the nameplate and the target ring clear within one frame, so nobody keeps swinging at a corpse. The next target follows the existing targeting rules.sliceKill test in a pack: no frame with a ring on a corpse.
ENM-10Boss presence
added 2026-10-07
Bosses have heavy footsteps on the boss distance class (SFX-07), dust on big steps and an idle breath, without shaking other players' cameras (CAM-02).polishBoss idle and walk capture.

◆Loot and rewards

The economy docs define what drops. Nothing defined how a drop looks, sounds and is picked up.

LOOT · 8 details · starting values

Rewards feel generous without covering the fight.

IDDetailStandard (starting values)StageProof
LOOT-01The dropItems leave the corpse on a 0.35 s arc, bounce once and settle. Several drops are staggered 40 ms apart.sliceMulti-drop clip.
LOOT-02Rarity signalsBeam height, ground glow and drop sound scale with the five rarities in items.json. Rare and above ping the minimap.sliceLine-up of the five rarities.
LOOT-03LabelsLabels never overlap; the nearest and rarest sit on top. A client-only filter hides rarities below a chosen level.slice30-drop pile screenshot.
LOOT-04PickupA picked item flies to the player in 0.2 s with the climbing tick of SFX-16. A full bag gives a clear refusal.slice10-item pickup clip.
LOOT-05Level upA pillar of light, a ring that pushes nothing, a fanfare under 1.5 s and a refill sweep. Other players see a reduced version.sliceLevel-up clip from own and other view.
LOOT-06Three sizes of celebrationMinor (pickup, quest step), major (quest done, rank up), milestone (level, keystone, first Legend). Only milestones may use the screen.polishOne clip per size.
LOOT-07Crafting tensionRefinement and orbs build a short anticipation, then a clear success or failure sting that grows with the stakes.polishRefinement +1, +9 and +15 clips.
LOOT-08New and better
added 2026-10-07
New items carry a badge until hovered. An item that beats the equipped one for the current build shows an up arrow on its tile and label (a client-side comparison).alphaInventory screenshot with new and upgrade markers.

◆Interface feel

UI · 17 details · starting values

The interface answers within a frame and prepares the game while the player waits.

IDDetailStandard (starting values)StageProof
UI-01Instant responseInput to visible change within one frame. Hover highlight within 50 ms. Windows open and close in 120–160 ms and never block input while animating.coreInput-to-paint timing in the UI test.
UI-02Cooldown readA radial sweep, a 0.15 s ready flash, and a soft ready tick for Q E Z X C only.coreHUD capture of a cooldown ending.
UI-03Expiring effectsBuffs blink in their last 3 s. Dangerous debuffs are drawn larger.sliceBuff bar capture.
UI-04Tooltip intentA 200 ms delay, and no delay when moving between neighbouring slots within 0.5 s.sliceInventory sweep capture.
UI-05Phone fitSafe-area insets, the HUD's 48 px minimum touch targets (hud.json), and thumb zones clear of the camera drag area.sliceScreenshots at 360 and 390 px wide with a notch.
UI-06Settings apply liveEvery setting applies at once, without a restart or reload.sliceSettings test toggles each option in play.
UI-07Text ready for other languagesAll text lives in tables, fonts have a fallback, and layouts leave 30% room for longer strings.polishPseudo-localised screenshot pass.
UI-08Interface hapticsA light tick on confirm and on tab change on phones, behind the Haptics slider.polishDevice check.
UI-09Loading that preparesThe loading phase warms shaders, pools and the combat sound bank, and the bar reports real steps.slicePerf scene S5 after a cold start.
UI-10Device glyphs
added 2026-10-07
Button prompts follow the last device used (keyboard and mouse, Xbox, PlayStation, touch) within one frame and never mix on one screen.sliceDevice swap test with screenshots.
UI-11Every window works on a gamepad
added 2026-10-07
Visible focus, a logical D-pad order, shoulder buttons switch tabs, one button always backs out, and no step needs the cursor.alphaGamepad navigation test across every window in ui-windows.json.
UI-12Steady numbers
added 2026-10-07
Timers, counters and stats use tabular figures so digits do not jitter. Combat text abbreviates large values (12.3k); tooltips never do.sliceScreenshot strip of a 10 s countdown.
UI-13Errors that help
added 2026-10-07
Every failure message says what happened, why, and what to do next, in plain words. Codes appear only as a small reference for bug reports.alphaReview of the message table.
UI-14Cursor
added 2026-10-07
Custom cursors for attack, talk, loot, use and invalid. The cursor hides while a gamepad drives and can be confined to the window in full-screen play (a setting).sliceCursor state capture.
UI-15Drag and drop
added 2026-10-07
Dragging shows a ghost and lights valid targets; an invalid drop snaps back in 0.15 s. Phones use a 0.3 s long press with a haptic tick (UI-08).alphaInventory drag test on desktop and phone.
UI-16Counters roll
added 2026-10-07
Gold, XP and currency counters roll to the new value in 0.3–0.6 s with the climbing tick (SFX-16). Spending updates at once.alphaCapture of a pickup burst and a purchase.
UI-17Quiet HUD
added 2026-10-07
An optional setting fades HUD parts that carry no news (full bars, idle chat, an unused skill bar) after 10 s out of combat and brings them back on any input or damage.polishSettings capture with the option on.

◆Optimisation

The budgets stay in Performance. These details say how to hold them on each platform and how to prove it with the same five scenes every time.

OPT · 25 details · starting values

Smooth beats fast, and every technique names what it does on each platform.

IDDetailStandard (starting values)StageProof
OPT-01Capability tableEvery technique names what it does on each platform. Dynamic resolution, the GPU Resident Drawer, STP upscaling, VFX Graph, mixer effects, streamed audio and managed threads are not available everywhere.
platformCapabilities: checked 2026-10-06 · platforms [windows, android, ios, web] · features [id:dynamic_resolution, windows:DirectX 12 only, android:Vulkan only, ios:true, web:false, fallback:fixed render scale from the capability probe, stepped only at safe moments, source:https://docs.unity3d.com/6000.2/Documentation/Manual/DynamicResolution-introduction.html, id:gpu_resident_drawer, windows:Forward+ only, android:Vulkan and Forward+ only, ios:Forward+ only, web:false, fallback:SRP Batcher and GPU instancing; Mesh Renderers only either way, source:https://docs.unity3d.com/6000.0/Documentation/Manual/urp/gpu-resident-drawer.html, id:stp_upscaler, windows:true, android:Vulkan only, ios:true, web:false, fallback:bilinear or FSR 1.0 upscaling filter, source:https://docs.unity3d.com/6000.3/Documentation/Manual/urp/stp/stp-upscaler.html, id:vfx_graph, windows:true, android:needs compute shaders; verify on the Low reference, ios:true, web:false, fallback:Particle System definitions with the same timing and footprint (docs/production/VFX.md), source:docs/production/VFX.md, id:audio_mixer_effects_and_snapshots, windows:true, android:true, ios:true, web:false, fallback:bus-gain automation in code; gain staging instead of a limiter, source:https://docs.unity3d.com/6000.1/Documentation/Manual/webgl-audio.html, id:streamed_audio_clips, windows:true, android:true, ios:true, web:false, fallback:compressed-in-memory clips, source:https://docs.unity3d.com/6000.1/Documentation/Manual/webgl-audio.html, id:managed_threads, windows:true, android:true, ios:true, web:false, fallback:main-thread budget; only native code and Burst-compiled jobs can use threads, source:https://docs.unity3d.com/6000.0/Documentation/Manual/webgl-technical-overview.html]
coreData test: every limited feature has a fallback.
OPT-02Resolution controlMetal, Vulkan and DirectX 12 use dynamic resolution inside the tier's range. Web and OpenGL ES pick a fixed render scale from the capability probe and change it only at safe moments (loading, zone change), one step at a time.
Platform: Dynamic resolution is not available on Web or OpenGL ES.
coreProbe JSON records the path taken per device.
OPT-03Frame pacingSet the target frame rate explicitly (30 on Low and on phones by default, 60 on High) with Android frame pacing on. Judge smoothness by spread: p99 minus p50 at most 8 ms on Low.
perfTargets: managedBytesPerFrameInCombat 0 · frameSpreadLowMs 8 · firstCastMaxFrameFactor 2 · regressionFailPct 10 · flashesPerSecondMax 3
coreperf.json p50, p95 and p99 per scene.
OPT-04Zero garbage in combat0 B of managed allocation per frame in the combat scenes after warm-up, measured with a profiler counter. Incremental collection on.
perfTargets: managedBytesPerFrameInCombat 0 · frameSpreadLowMs 8 · firstCastMaxFrameFactor 2 · regressionFailPct 10 · flashesPerSecondMax 3
corePerf scene S1: allocation counter is zero for 60 s.
OPT-05Shader and pipeline prewarmTrace pipeline states in development builds for each platform and warm them while loading; on Web warm a shader variant collection. The first cast of every skill adds no frame over twice the budget.
perfTargets: managedBytesPerFrameInCombat 0 · frameSpreadLowMs 8 · firstCastMaxFrameFactor 2 · regressionFailPct 10 · flashesPerSecondMax 3
corePerf scene S5 on each platform.
OPT-06Pools sized from worst casesPool sizes come from the perf scenes, are prewarmed while loading and never grow in combat.slicePool high-water marks in perf.json.
OPT-07HeatAndroid reads the thermal state through Adaptive Performance and iOS through the system thermal state. On a warning, step down in this order: other players' particles, shadows, render scale, frame cap. Log the state in perf.json.slice30-minute session on each phone reference.
OPT-08MemoryMip streaming on native inside the tier's texture budget. Low loads half-resolution texture variants. Meshes are not readable at run time. Audio follows SFX-20.sliceMemory snapshot per tier against the budget.
OPT-09Render path by tierHigh and Ultra on native use Forward+ (needed for the GPU Resident Drawer). Low, Mid and Web use Forward with at most one extra light and no depth or opaque texture copies. Low aims for zero full-screen passes.sliceFrame debugger pass list per tier.
OPT-10SkinningLow uses two skin weights. On higher tiers, detail levels below the first are authored with at most two influences and without finger and face bones. GPU skinning on.sliceAsset validator report.
OPT-11Perf scenesFive named scenes with fixed seeds. Every performance task names the scene it ran.sliceScene ids in perf.json.
OPT-12Regression gateClient tasks that touch a hot path run scene S1 on the development Mac and fail on a 10% regression. Reference devices run all scenes at milestone gates.
perfTargets: managedBytesPerFrameInCombat 0 · frameSpreadLowMs 8 · firstCastMaxFrameFactor 2 · regressionFailPct 10 · flashesPerSecondMax 3
sliceTrend file in logs/evidence.
OPT-13Quality auto-pickThe probe picks the tier. During the first 60 s it may step down if p95 is over budget. It never steps up mid-session and never overrides the player's choice.sliceProbe test on each reference.
OPT-14Loading without hitchesUploads are time-sliced (2–4 ms per frame on Low). Zone content is preloaded before entry. The existing streaming limit of 8 ms p99 holds.slicePerf scene S4.
OPT-15Battery30 fps by default on phones with an optional 60. Full-screen menus may render at half rate.polish30-minute battery and heat log.
OPT-16Network on the clientSnapshot decoding and interpolation allocate nothing per packet.sliceAllocation counter during a 1,000-bot session.
OPT-17Interface costWorld-space numbers and nameplates are instanced meshes, not interface elements. No full-screen transparent panel sits behind a window.sliceDraw-call count with the HUD on and off.
OPT-18One thread in the browserManaged code runs on one thread in the Web build. That build must hold its frame budget with jobs on the main thread unless a measurement shows otherwise.
Platform: Web.
sliceWeb perf run of scene S1 on Mid.
OPT-19Per-character effects keep batching
added 2026-10-07
Hit flash, dissolve, rim and tint use per-character material instances or instance data, never MaterialPropertyBlocks: a renderer with a property block drops out of the SRP Batcher.coreFrame Debugger with 50 flashing dummies: no renderer leaves the SRP Batcher.
OPT-20Animation by distance
added 2026-10-07
Animators update every frame inside 15 m, at half rate to 40 m and at a quarter rate beyond. Off-screen monsters stop animating except for deaths and telegraph poses (ANM-08). Baked crowds take over past the tier limit (M1-01).sliceS1 and S2: animation time per distance band in perf.json.
OPT-21Client physics is cosmetic
added 2026-10-07
Movement and hits come from the shared simulation; the client runs no gameplay rigid bodies. Physics simulates only cosmetic debris, on High and Ultra, inside a cap.sliceS1 on Low: physics time near zero in perf.json.
OPT-22Texture formats by platform
added 2026-10-07
ASTC on Android and iOS, BC formats on Windows. The browser gets two builds, DXT for desktops and ASTC for phones, picked by the loader page, because an unsupported format is decompressed in software and costs memory.
Platform: Web: one texture compression format per build.
sliceBuild report per platform: no uncompressed texture over 64 KB.
OPT-23Per-system timings
added 2026-10-07
Every system (simulation, animation, effects, audio, network, interface, rendering) has a profiler marker. perf.json records each one's p50 and p95 in milliseconds and the frames over twice the budget per 10 minutes, so a regression names its system without screenshots.sliceperf.json schema test; S1 output lists every system.
OPT-24Shader keywords
added 2026-10-07
Effect and character shaders use local keywords and shader_feature for options, not multi_compile, and the build strips variants by tier and platform. The build report lists variants per shader against the variant budget in PERFORMANCE.md.sliceBuild report per platform inside the variant budget.
OPT-25Redraw only on change
added 2026-10-07
The minimap, far nameplates and HUD text that did not change redraw at most ten times a second.polishInterface time in perf.json, scene S2.

◆Perf scenes

Perf scenes · every performance task names the one it ran
IDSceneSetupWatch
S1Chain spam in a pack100 dummies in the Combat Lab, the 8-slot chain held for 60 s, both camerasframe p50/p95/p99 · managed bytes per frame · live particles · draw calls · audio voices · attacker freeze share
S2Crowded town150 visible players across tiers A, B and C idling and walking in Amber Gateframe p50/p95/p99 · nameplates · memory · bandwidth
S3World boss100 players casting with Reduced effects while the boss telegraphs every 4–6 stelegraph visible every frame · frame p99 · audio voices · pool high-water marks
S4Dash traversalReed Rush at its reuse limit across 8 chunk borders, then a mount sprintstreaming hitch p99 · missing ground · memory growth
S5First castcold start, then every skill in the build cast onceframes over twice the budget · shader compile events

◆Comfort and accessibility

ACC · 10 details · starting values

Nothing in the feel stack hurts, and nothing important lives in one sense only.

IDDetailStandard (starting values)StageProof
ACC-01Flash limitNo effect flashes more than three times in any one second, with or without Reduce flashing.coreFlash counter on the capture of the brightest skill.
ACC-02Two channelsEvery critical cue exists as both picture and sound (see SFX-22).sliceMuted and greyscale playthroughs of the boss slice.
ACC-03Comfort switchesReduce camera motion (CAM-08), Reduce flashing, the hitstop toggle and the haptics slider (all three existing) sit together in one settings group.sliceSettings screenshot.
ACC-04Colour is never aloneHostile, friendly and rarity signals also differ by shape, pattern or icon. Check with three colour-blind simulations.sliceSimulated captures in the visual checklist.
ACC-05Text size
added 2026-10-07
A text size step (100, 115 and 130%) separate from the 80–130% interface scale. Body text stays at least 12 px on a 390×844 phone and 14 px at 1080p.alphaScreenshot matrix at every step.
ACC-06Captions
added 2026-10-07
Barks and critical sounds without a picture can be captioned with their source and direction ('Boss roars, left'). Voices are non-verbal (ADR-031) and NPC dialogue is text, so there are no spoken lines to subtitle. Size and background options.alphaCaption screenshot; every critical cue in SFX-22 has a caption.
ACC-07Hold or toggle
added 2026-10-07
Every held input (chain, charge, aim, sprint) offers a toggle, and every binding is remappable on keyboard, gamepad and the touch layout.sliceSettings test plays a chain in toggle mode.
ACC-08High-contrast threats
added 2026-10-07
One switch draws telegraph edges 50% thicker and brighter, gives enemy projectiles a dark outline and dims other players' effects to 30%.sliceS3 capture with the switch off and on; the contrast check passes on Low.
ACC-09Field of view
added 2026-10-07
The close view has a field-of-view slider (proposed ±10° around its default). The tactical view keeps its presets.sliceSettings capture at both ends of the slider.
ACC-10Menu narration
added 2026-10-07
Menus can be read aloud by the platform screen reader or text to speech where the platform supports it.polishNarration test on one platform.

◆Network feel

Added in round 2 (ADR-031). Netcode sets the prediction, interpolation and correction numbers; these details make them invisible. NET-01 and NET-02 come first: the first skill is judged at a realistic round trip, and the delay of confirmed hits is measured before G2 (finding D1).

NET · 10 details · starting values

Online play feels local: corrections, other players and confirmations never read as lag.

IDDetailStandard (starting values)StageProof
NET-01Judge feel at real latency
added 2026-10-07
The Combat Lab and every feel review run with a simulated 80 ms round trip and 10 ms of jitter by default, with a 0 ms switch for comparison. The G2 owner clip is recorded at 80 ms.coreReview clips state their simulated latency; the debug HUD shows it.
NET-02Confirm delay is measured
added 2026-10-07
The debug HUD and perf.json record the time from the local contact frame to the confirmed impact (HIT-04) at 0, 60, 120 and 200 ms round trip. Both impact modes of ADR-031 (strict confirmed layers and predicted contact) are built behind a Combat Lab switch and judged side by side at 80 ms before G2; the delay numbers go with the clips.coreDelay histogram in the task evidence.
NET-03Others move like locals
added 2026-10-07
Other players' gait comes from their interpolated velocity with foot locking. They turn in place when they rotate on the spot and use the same start, stop and pivot clips, so they never moonwalk between 20 Hz snapshots.alphaTwo-client capture at 120 ms: planted-foot slide inside the 2 cm limit.
NET-04Elastic buffer
added 2026-10-07
The 100 ms interpolation delay (NETCODE_1000.md) absorbs jitter by playing up to 5% faster or slower instead of snapping or stalling.alphaJitter test at ±30 ms: no visible snap; buffer underruns counted in perf.json.
NET-05Remote effects line up
added 2026-10-07
Other players' casts and hits play their effects at the event's time on the interpolated timeline, so effects match their animation, not the packet arrival.alphaTwo-client capture: the remote impact lands on the remote contact frame, within one frame.
NET-06Rejected actions end cleanly
added 2026-10-07
When the server rejects a predicted cast or movement, its cue and trail fade within 0.1 s, the resource display returns, the player sees the reason (HIT-11) and the position correction follows the existing thresholds. No ghost hit.sliceForced-rejection test: no confirmed-layer cue; one reason message.
NET-07One smooth clock
added 2026-10-07
Cooldowns, buffs, telegraph fills and the day clock read a smoothed server clock that never steps backwards; corrections ease in over 0.25 s.sliceClock-skew test at ±50 ms: no cooldown or fill runs backwards.
NET-08Connection honesty
added 2026-10-07
A small indicator appears only while the connection is degraded (round trip over 150 ms or loss over 2% for 5 s), says so in plain words and leaves when it recovers.alphaGM network lab at the thresholds.
NET-09Reconnect
added 2026-10-07
A dropped connection shows a reconnect overlay within 1 s and keeps the last frame, dimmed, with input paused. The player returns to the world without the login screen whenever the server allows it.alphaDisconnect test in the GM network lab.
NET-10Lag spikes stay calm
added 2026-10-07
When snapshots stop, other characters extrapolate for at most the existing 150 ms and then hold; they never cross collision or run off a ledge.alpha1 s blackout test: no remote character crosses collision.

◆Input feel

Added in round 2 (ADR-031). Bindings stay in controls.json and the movement-first rules in the development guide; these details shape how each device feels in the hand.

INP · 8 details · starting values

Every device feels precise and forgiving, and the game always answers the hand that is playing.

IDDetailStandard (starting values)StageProof
INP-01Stick shaping
added 2026-10-07
A radial dead zone of 0.12–0.18 with the rest of the range rescaled, so diagonals and slow walks stay true; an outer dead zone of 0.05–0.08; walk or run chosen by stick magnitude with 0.05 hysteresis. No axial dead zone.coreStick sweep test: continuous output, no dead cross, no walk/run flicker.
INP-02Camera input
added 2026-10-07
Sensitivity per view and per device, invert X and Y, raw mouse input without acceleration, and a gamepad turn that ramps to full speed over 0.15–0.25 s.sliceSettings test; the turn ramp in the input log.
INP-03Touch stick manners
added 2026-10-07
The floating joystick (controls.json) starts after 8–12 px of drag, follows the thumb when it leaves the stick's radius and stops within one frame of release.sliceTouch replay on the phone references.
INP-04Touch aiming
added 2026-10-07
A dragged skill shows its ground preview at once, a tap uses the automatic target, and the cancel gesture (drag back to centre, controls.json) greys the preview before release.sliceTouch replay: a cancelled aim costs nothing and casts nothing.
INP-05Device hot-swap
added 2026-10-07
The last device used owns input and glyphs (UI-10) from its first input. A resting mouse or a drifting stick never steals control: the mouse must move 6 px and the stick must leave its dead zone.sliceSwap test with a drifting pad.
INP-06Haptics vocabulary
added 2026-10-07
One table of at most six rumble patterns (deal, take, break, kill, warning, interface) used everywhere, scaled by the Haptics slider and inside the existing pulse limit (feel-quality.json).sliceEvery haptic call names a pattern from the table.
INP-07Click to move
added 2026-10-07
A click shows a ground marker that expands over 0.4 s, holding shows the path, and an unreachable click shows a small cross with a soft blip. WASD cancels at once (existing rule).sliceClick test on open and blocked ground.
INP-08Cursor aim on slopes
added 2026-10-07
In the tactical view, facing uses the cursor's intersection with a plane at the character's height; only ground-targeted skills use the terrain point. Facing never jumps when the cursor crosses a cliff.sliceAim sweep over a cliff edge: facing changes smoothly.

◆Look and rendering

Added in round 2 (ADR-031). LOOK-01 comes first, because bloom thresholds, effect palettes and every contrast check depend on one colour pipeline. Shadow and texture budgets stay in Performance.

LOOK · 12 details · starting values

One colour pipeline and measurable material rules make every asset, effect and area look like one game.

IDDetailStandard (starting values)StageProof
LOOK-01One colour pipeline
added 2026-10-07
Linear colour space; one tone mapper chosen once in the Combat Lab (Neutral or ACES); fixed exposure per lighting phase, with no automatic exposure in combat; one grading table per area and phase. Bloom thresholds and effect palettes are tuned under this pipeline only.
Platform: Low and Web may render without HDR; their grade is baked into the same tables.
coreCombat Lab capture with the pipeline settings recorded in the evidence.
LOOK-02Material sanity
added 2026-10-07
Non-metal albedo between 30 and 240 sRGB, metal reflectance between 180 and 255, roughness never exactly 0 or 1, and one normal-map convention everywhere. The asset validator flags outliers.alphaValidator report per asset batch.
LOOK-03Texel density
added 2026-10-07
One density per asset class at High (proposed: characters 1,024 px/m, kits 512 px/m), checked by the asset validator within ±25%. Low uses the half-resolution variants (OPT-08).alphaValidator report.
LOOK-04Characters stand out
added 2026-10-07
The player, enemies and telegraphs pass the same greyscale contrast check against their background in every state of the time and weather review matrix (WLD-08), using WLD-06's rim lift where needed.sliceContrast report across the matrix.
LOOK-05Light where characters stand
added 2026-10-07
Moving characters take light from light probes (adaptive probe volumes where supported), so they darken in caves, under trees and at night and never glow in shade.sliceWalk from sun into a cave: character brightness follows the scene.
LOOK-06Anti-aliasing by tier
added 2026-10-07
Low and Web use 2× MSAA where it is cheap on the GPU, otherwise FXAA; Mid uses SMAA. High uses TAA or STP only if fast effects and damage numbers pass a ghosting check; otherwise SMAA.sliceFast-chain capture per tier: no ghost trails.
LOOK-07No banding
added 2026-10-07
The final pass adds dither so skies, fog and soft glows never band on 8-bit and phone screens.sliceSky gradient capture on the phone references.
LOOK-08Baked occlusion
added 2026-10-07
Kits and characters carry baked ambient occlusion on every tier, so Low never looks flat. Screen-space occlusion is High and Ultra only.alphaLow and High capture of one camp.
LOOK-09A sky that moves
added 2026-10-07
Clouds drift with the wind (WLD-09), the sun and moon follow the server clock and set the shadow direction, and stars show at night. The sky never jumps at a phase change.sliceTime-lapse at 120× in the GM arena.
LOOK-10Shadows without seams
added 2026-10-07
Cascades follow PERFORMANCE.md. Cascade borders blend, the shadow distance shortens in the close view, and far crowds use blob shadows on every tier.sliceWalk capture: no visible cascade line.
LOOK-11Skin and eyes up close
added 2026-10-07
In the close view on High, skin uses wrap or pre-integrated lighting and eyes get a catch-light; Low uses the standard lit shader.polishClose-view capture on High and Low.
LOOK-12Reflections
added 2026-10-07
One reflection probe per area and box-projected probes inside buildings; Low uses one baked probe per area.polishMetal weapon capture in town and in the Kiln Depths.

◆Session flow

Added in round 2 (ADR-031). What the player meets between fights: starting the game, the first minute, learning, dying, travelling and coming back.

FLOW · 7 details · starting values

From the first launch to logging off, the player always knows what is happening and what to do next.

IDDetailStandard (starting values)StageProof
FLOW-01Boot to play
added 2026-10-07
Native Low: start to the login screen within 10 s and login to the playable town within 20 s, measured on the device. The browser keeps the download targets in PERFORMANCE.md. Loading shows real steps (UI-09).alphaTimings in perf.json on the reference devices.
FLOW-02First minute
added 2026-10-07
A new character can move, attack and defeat a first monster within 60 s of entering the world, with no blocking text box.alphaFirst-session capture with a timer.
FLOW-03Taught by doing
added 2026-10-07
Each core action (move, chain, movement gem, view switch, skill, buff) is introduced when a situation needs it, with one prompt that shows the binding of the device in use. At most one prompt at a time; doing the action dismisses it; it returns only if the action goes unused.alphaTutorial log: every prompt shown and cleared by its action.
FLOW-04Death and return
added 2026-10-07
On death the camera eases back, the world loses half its colour, one line names the cause ('Sand Burst, Dune Beetle') and the respawn choices appear after 1.5 s with their consequences in plain words.alphaDeath capture in both views.
FLOW-05Arrivals
added 2026-10-07
Waypoints, teleports and respawns fade out in 0.25 s and fade back in only when ground, collision and nearby monsters are ready. Others see an arrival burst.alphaWaypoint test at the highest travel speed: no missing ground on arrival.
FLOW-06Welcome back
added 2026-10-07
After a break of a day or more, login shows a three-line recap (current quest, next step, Auto-Hunt results) and points to the next objective.polishRecap screenshot after a simulated day away.
FLOW-07Offline results
added 2026-10-07
The offline Auto-Hunt summary lists XP, gold and items with the highlights first and uses the major celebration (LOOT-06) for upgrades.polishSummary screenshot.

◆What this page corrects in the older docs

Older statementProblemStandard here
Telegraphs are decals; decals are capped at 64 and recycled oldest firstA crowd fight could recycle a boss telegraph, which breaks the "never cull telegraphs" ruleVFX-04: own renderer and pool
"Dynamic resolution holds the frame budget before any visual feature is dropped"Unity supports dynamic resolution on Metal, Vulkan and DirectX 12 only; not on Web or OpenGL ESOPT-02: fixed, stepped render scale there
Ducking uses mixer snapshots; a limiter protects the master busThe Web build's mixer supports volume onlySFX-03, SFX-10: gain automation and headroom by staging
Music streamsWeb clips are compressed in memory or decompressed on loadSFX-20
Camera shake default 70% in controls.json, 100% in feel-quality.jsonTwo defaults for one settingDecided 2026-10-06: 70% in both files, and it stays a setting (ADR-028)
UI-05: "the kit's 44 px touch targets"44 px is the wiki kit's control height; the game HUD's minimum touch target is 48 px (hud.json)UI-05 cites hud.json (corrected 2026-10-07)

The VFX page listed "decal only" for the Low tier's aftermath layer while feel-quality.json gives Low no decals. That line was corrected with this task, because data decides.

◆Owner decisions of 2026-10-06

  1. The catalog is the polish standard, adopted stage by stage (ADR-028).
  2. Camera shake defaults to 70% and is a setting.
  3. No blood.
  4. Other players' damage numbers are hidden by default; a setting shows them.
  5. Day/night and weather are in from day one, with toggles in the GM arena (ADR-030). WLD-08 moved to the core stage.

◆Owner decisions of 2026-10-07

ADR-031, answering the round-2 review:

  1. Round 2 is accepted: 90 details, the four new areas and the alpha stage. 44 core details now gate G2.
  2. Hits online: both impact modes (the strict layers of HIT-04 and predicted contact) are built behind a Combat Lab switch and judged at a simulated 80 ms round trip; the owner picks one at G2 (NET-01, NET-02).
  3. Voices are non-verbal and come from the local audio generator; there are no spoken lines (SFX-27, ACC-06).
  4. The agents build the action to this catalog; the owner reviews it and gives feedback later.

◆Sources

Checked 2026-10-06. Each source supports only the fact beside it; Zoen's numbers are design proposals.

Source: zoen/docs/production/POLISH.md · 1,554 words · edit the Markdown, not this page.