Web source: crop capture to actual content bounds (anchor 0,0); slider click-to-position; web URI X clears; tab order

This commit is contained in:
2026-08-28 11:10:49 -07:00
parent 23874c2dd6
commit f39ebd96ce
6 changed files with 98 additions and 30 deletions
+20 -14
View File
@@ -6,26 +6,32 @@
working). **NOT pushed — user rule: never push without explicit instruction (2026-08-24).** No feature
branches pre-1.0: all work lands on `main` per work unit.
## The web-source rendering work (2026-08-28) — CURRENT MODEL: stable viewport + Fill
## The web-source rendering work (2026-08-28) — CURRENT MODEL: stable viewport + content-bounds crop
**Background:** viewport==box made dragging the box reflow the page (truncation, scrollbars,
unrecoverable image, "janky at stressful geometries"). Fixed-viewport + `Uniform` left letterbox
dead space. CSS reset enlarged the gap. Scrollbars were called "super fail".
dead space. CSS reset enlarged the gap. Scrollbars were called "super fail". The right/bottom
dead-space + "not anchored at (0,0)" report persisted across every model — dead space was
page-internal (widget content smaller than the viewport), which is now cropped out.
**The model that satisfies invariants (implemented, needs visual verification):**
- `Services/WebView2Manager.cs` — the page renders ONCE at the viewport size the element was
created at (snapshot in `Register`, never tracked → no reflow, no truncation during resize).
`overflow:hidden` (html+body) + transparent-bg injection on every nav — nothing else, no
layout/CSS meddling. Immediate capture on `NavigationCompleted`. `FramePump` unchanged.
- `MainWindow.xaml` — web `<Image>` uses `Stretch="Fill"`: any box the user draws is covered
edge-to-edge, zero dead space, zero crop (OBS free-transform: fixed browser resolution,
scene-item scales the texture). Aspect distortion only when the box aspect ≠ viewport aspect.
- Invariants: **page viewport is stable; display Fill-scales texture to the box.**
**The model that satisfies invariants (implemented, visual verification pending):**
- `Services/WebView2Manager.cs` — stable viewport = the element's size at `Register` (snapshot,
never tracked → no reflow/truncation during resize). `overflow:hidden` (html+body) +
transparent-bg injection on every nav (nothing else). After each navigation,
`QueryContentBoundsAsync` reads the page's real content rect
(`scrollWidth/scrollHeight` vs `innerWidth/innerHeight` via `ExecuteScriptAsync` + JSON) and
`CaptureFrame` **crops the capture to the actual content bounds, anchored at (0,0)** — dead
space inside the viewport no longer reaches the box. Immediate capture on `NavigationCompleted`.
- `MainWindow.xaml` — web `<Image>` uses `Stretch="Fill"`: the cropped frame maps edge-to-edge,
so the selection box always bounds the real widget. `FramePump` unchanged.
- Invariants: **page viewport stable; display Fill-crops to content and fills the box.**
Build: 0 warnings; tests 4/4 (snapshot at register, no tracking after, min 1, transparent bg).
**Property panel / sliders (2026-08-28):** web URI ✕ clears the textbox; web ✓/✕ icon buttons
`IsTabStop="False"` so Tab walks X→Y→W→H→URI; Slider style `IsMoveToPointEnabled="True"`
restores click-anywhere-on-bar.
**Rejected for the record:** fixed 1920×1080+`Uniform` (letterbox), CSS margin/100% reset
(enlarged gap), viewport==box (reflow/truncation/scrollbars).
Build: 0 warnings; tests 4/4. Rejected for the record: fixed 1920×1080+`Uniform` (letterbox),
CSS margin/100% reset (enlarged gap), viewport==box (reflow/truncation/scrollbars).
## Key facts / landmines