Skip to content

1.31.0 — Drag to place (roadmap 39) - #348

Merged
AlexZ005 merged 10 commits into
mainfrom
feat/39-int
Oct 8, 2026
Merged

AlexZ005 merged 10 commits into
mainfrom
feat/39-int

Conversation

@AlexZ005

@AlexZ005 AlexZ005 commented Oct 8, 2026

Copy link
Copy Markdown
Collaborator

Release 1.31.0 — roadmap 39 "drag to place" (integrator 39-int).

Gates on the union: svelte-check 300/41 (= baseline), vitest 1885/1885, check:tokens, check:storage, scene-lint 0 errors, build. e2e battery (~95 suites, two slots) green except reds identical on pristine v1.30.0 (A/B). Preview https://preview-1-31.theprototype.pages.dev headline proof 16/16 against the real CDN.

🤖 Generated with Claude Code

AlexZ005 and others added 10 commits October 8, 2026 05:55
- placementDims.js (leaf): one Dims shape {size [w,h,d], box, tris, bytes, animated, known,
  source}; read from a pack row / manifest item (a NUMERIC `size` is the old manifest's byte
  count), else what this device measured on first load (ONE idb record `pack:dims-v1`, writes
  debounced), else the 1 m "size unknown" box. Labels W x D x H + cost.
- packs.js normalizes `dims` onto every default-pack item and imported manifest item.
- packRefs.js: loadPackTemplate measures + remembers dims for a row that had none (also for an
  animated file, before it refuses to reference it — AnimatedRefError), keeps the FINISHED
  templates for a sync peek (peekPackTemplate = "decoded in memory"), and reads/writes the
  pack cache in fetchWithProgress and the LOD file fetch.
- packCache.js (leaf): ONE CacheStorage cache `tp-pack-files-v1` with a size index store, so
  downloaded items can be listed, sized and deleted; degrades to plain fetch without caches.
- explorer.js: a new library model records `dims` from the same parse its thumbnail makes.
- static/library/default/default.json: the bundled starter rows carry dims (copied from the
  packs repo's measured rows; identical files).

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…ep spawn (39 P1 + P2)

- placeDrag.js: a POINTER gesture (a native drag delivers no keydown/wheel, so R / the wheel /
  Esc could not work on it). Explorer cancels a TRUSTED dragstart on a placeable card (pack
  object, library model, prefab) and hands over; a touch long-press does the same with the
  Explorer collapsed. Over any non-viewport element the payload is re-dispatched as synthetic
  dragenter/over/leave/drop (+ dragend on the source), flagged x-tp-place-bridge, so every
  existing HTML5 target keeps working and App's window drop ignores it.
  Raycast onto surfaces (ground fallback), the box RESTS on the surface along its normal,
  grid snap on the surface's two axes (Shift = free), R / Shift+R / wheel = 15° steps,
  align-to-surface via snapTargets.alignNormal, Alt = the camera focus point, a row for a
  multi-selection, amber over 50% inside another object, red (no drop) off the world.
- placeGhost.js: scene-root, never saved/sent/picked. BOX tier (wire box + fill + footprint)
  first; the MODEL tier (the template's own geometry, one translucent material, no shadows)
  swaps in on a later frame when decoded + allowed by the preview setting (placementPrefs.js:
  full / within budget (default) / box, 50k tris, 15k on phones and headsets).
  Pending boxes hold a drop's spot while an import path parses.
- explorerDrop.placeFromGhost: a STATIC pack item spawns as a pack STUB through addImported
  (one create entry, the stub element on the wire, Placeholder Style until it fills, peers
  refill with derived uuids); animated / behaviour / over-budget items, library models and
  prefabs take their import paths at the ghost pose (importFile gains `quaternion`). Several
  items share one history batch. Hovering the viewport prefetches (template parse / cache /
  library or prefab decode).
- PlaceDragOverlay.svelte (kit tokens + Icon): the chip, W x D x H / size unknown, tris and
  size, the turn and the keys.
- the two older pack fetches go through the pack cache; importGate.wouldAskFor; debug rows.
- suite place-drag (33, two peers, real mouse, the CDN path served from static/library).

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…, touch drag (39 P3 + P5)

- Settings ▸ Scene ▸ Performance ▸ Placement preview (PlacementSettings.svelte, its own file,
  keywords + settingsIndex rows): Full model / Within budget (default) / Box only, the triangle
  budget (50k desktop, 15k phone/headset) and Show dimensions. LOCAL, safeStorage.
- Explorer ▸ Packs: a Downloaded badge (bottom right, size in its title) on every pack item
  this device holds, a "Downloaded" axis in the filter menu inside the Packs, the item menu's
  Delete -> "Delete cache (size)" (disabled when nothing is held; the item stays in the pack),
  and the pack row's "Delete downloads (size)".
- Storage: a "Pack downloads" category (one row per pack, CacheStorage — reclaimed through
  packCache) + "Clear all pack downloads"; the measured-sizes key is claimed there too.
- placing a pack item re-downloads it when its cache was deleted (a file still parsed in memory).
- touch: the place drag blocks the browser's pan with a non-passive touchmove (touch-action is
  decided at touchstart, before the long-press) — without it every finger drag ended in a
  pointercancel (measured).
- suites: place-drag 39 (+ release over chrome places nothing — proven red with App's
  bridge guard removed, 0 -> 1 —, a library model's import-time size, and the HTML5 bridge
  still moving a card into a folder), place-drag-cache 33 (downloads, filter, Delete cache,
  Storage, the preview tiers, the Settings rows, a long-press drag at 390 x 844).

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…me (39 P2/P3)

- builds a 200340-tri sphere in the page, serves it as a pack item, warms it into the
  pack cache + memory, then samples rAF intervals 4 s idle vs 4 s mid-drag (pointer moving
  every 16 ms): 16.67 vs 16.67 ms, no long tasks; the ghost is the box over the 50k budget.
- run under e2e-slot --exclusive; writes after-39/39-place/perf-drag.json.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…s (39 P1/P4)

- the chip under a finger says 'Lift to place · back to the Explorer to cancel' instead of
  the keyboard hints.
- PACKS.md: size [w,h,d] / box / tris / bytes / animated on item rows, what writes them
  (kit-build dims) and the legacy numeric size = bytes reading.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…uites (39 P6)

- Alt while dropping: the orbit focus point is usually in the air, so it is projected down
  onto the first surface below it (explorerDrop.surfaceBelow; ground plane fallback).
- suite place-drag-extras: a multi-selection drags as one gesture with a ghost per item in a
  row and drops as ONE undo step (one Ctrl+Z removes both); Alt = focus point on the ground;
  aiming above the horizon is red ('No place to put it here') and the release places nothing.
- vitest placementDims (13): row dims incl. the legacy numeric size = bytes, the ghost tier
  rule, an item's download urls.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…39-int)

Settings ▸ Scene ▸ Performance gained Placement preview, Preview triangle budget and Show
dimensions (roadmap 39 P3). The run-1 lock found 10 queries whose result sets grew by exactly
those rows (no row or section lost); re-recorded on the union c4eaf25.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
… before you let go (39-int)

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@AlexZ005
AlexZ005 merged commit 371d7ca into main Oct 8, 2026
7 checks passed
@AlexZ005
AlexZ005 deleted the feat/39-int branch October 8, 2026 06:15
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant