diff --git a/docs/output.md b/docs/output.md index 45e432c..cb76f09 100644 --- a/docs/output.md +++ b/docs/output.md @@ -166,11 +166,25 @@ DOM and iframes aren't searched. ## Computed styles (`--computed`) With `--computed`, after the shot renderdiff reads the computed style of every rendered -element on both sides: the properties `dom` compares, plus `outline`, -`text-decoration-line` and `content`, and `::before` and -`::after` wherever they generate content. Masked subtrees and `script`/`style`-like tags +element on both sides, and of `::before` and `::after` wherever they generate content. +Masked subtrees and `script`/`style`-like tags are skipped; a `display: none` element is read, its subtree isn't. Script-driven -animations are finished first. The summary gets one block, after the rows: +animations are finished first. + +It reads a fixed list of properties, not every one, so `0 findings` means none of these +changed: + +- Layout: `display`, `position`, `float`, `flex-direction`, `flex-wrap`, + `justify-content`, `align-items`, `gap`, `grid-template-columns`, `z-index`. +- Box: `margin-*`, `padding-*`, `border-*-width`, `border-top-color`, + `border-top-left-radius`, `outline`, `width`, `height`. +- Text: `font-family`, `font-size`, `font-weight`, `line-height`, `letter-spacing`, + `text-align`, `text-transform`, `text-decoration-line`, `white-space`, `word-break`, + `overflow-wrap`, `hyphens`, `text-wrap-style`, `color`. +- Paint: `background-color`, `background-image`, `box-shadow`, `opacity`, `transform`, + `visibility`, `clip`, `clip-path`, `mask`, `content`. + +The summary gets one block, after the rows: ``` computed: 2 findings; dom identical on 2 of 3 route(s), differs /pricing (1), so findings there are hints @@ -197,7 +211,8 @@ computed: 2 findings; dom identical on 2 of 3 route(s), differs /pricing (1), so style change under it then shows only as `dom differs` and `unmatched`, not as a finding. - One change high in the tree is one finding. An inherited property (`font-*`, - `line-height`, `letter-spacing`, `text-*`, `white-space`, `color`, `visibility`) is + `line-height`, `letter-spacing`, `text-*`, `white-space`, `word-break`, `overflow-wrap`, + `hyphens`, `color`, `visibility`) is dropped where the parent has the same change, so a `body` font change is one line, not one per element. A `width` is dropped inside a parent whose width changed, and a `height` around a child whose height changed, so the box that caused it is what's left. diff --git a/skills/renderdiff/reference.md b/skills/renderdiff/reference.md index 5c92f9f..22dde75 100644 --- a/skills/renderdiff/reference.md +++ b/skills/renderdiff/reference.md @@ -136,9 +136,8 @@ not a route error: the pixel result stands. ## `--computed` -After each shot, reads the computed style (the `dom` properties plus `content`) of every -rendered element and its `::before`/`::after`, on both sides, and compares the markup. One -block after the rows: +After each shot, reads the computed style of every rendered element and its +`::before`/`::after`, on both sides, and compares the markup. One block after the rows: ``` computed: 2 findings; dom identical on 2 of 3 route(s), differs /pricing (1), so findings there are hints @@ -149,6 +148,10 @@ computed: 2 findings; dom identical on 2 of 3 route(s), differs /pricing (1), so unmatched /pricing@1440 -body > main > section.plans:nth-of-type(3) ``` +- The properties are a fixed list, not every one: the `dom` ones plus `outline`, + `text-decoration-line`, `word-break`, `overflow-wrap`, `hyphens`, `text-wrap-style`, + `clip`, `clip-path`, `mask` and `content` (full list: docs/output.md in the renderdiff + repo). `0 findings` means none of those changed, not that no style did. - A finding is `key prop left→right`, then up to three `route@widths` (`+N routes`). One per distinct change across the run, most widespread first, accepted shots included; 20 shown. `--progress` rows say `computed dom identical, N change(s)` or `dom differs (N)`. diff --git a/src/computed.ts b/src/computed.ts index 05a0097..ad7cd6b 100644 --- a/src/computed.ts +++ b/src/computed.ts @@ -60,6 +60,10 @@ const INHERITED = new Set([ "text-align", "text-transform", "white-space", + "word-break", + "overflow-wrap", + "hyphens", + "text-wrap-style", "color", "visibility", ]); diff --git a/src/locate.ts b/src/locate.ts index 8204917..9e377f5 100644 --- a/src/locate.ts +++ b/src/locate.ts @@ -73,7 +73,19 @@ export const PROPS = [ ]; /** `--computed` reads these too; pixel mode's `changed`, and so accepted fingerprints, don't. */ -export const SNAP_PROPS = [...PROPS, "outline", "text-decoration-line", "content"]; +export const SNAP_PROPS = [ + ...PROPS, + "outline", + "text-decoration-line", + "word-break", + "overflow-wrap", + "hyphens", + "text-wrap-style", + "clip", + "clip-path", + "mask", + "content", +]; /** Links and controls forced into each state, per page per side. */ export const MAX_STATES = 500; diff --git a/tests/visual/computed.test.ts b/tests/visual/computed.test.ts index 2c0f61d..3692a0d 100644 --- a/tests/visual/computed.test.ts +++ b/tests/visual/computed.test.ts @@ -192,3 +192,21 @@ test("past 500 links the rest are counted, and the page is left resting", async assert.deepEqual(await snapshot(p, [], BUDGET, null), before); await p.close(); }); + +test("a lint autofix swapping wrapping or clipping keywords is a finding, not inherited down", async () => { + const body = + `
averyveryverylongidentifierwithoutbreaksx
` + + `hidden

Some text.

`; + const h = ".h { position: absolute; width: 1px; height: 1px; overflow: hidden }"; + const { d } = await diff(body, body, [ + `${h} code { overflow-wrap: anywhere } .h { clip-path: inset(50%) }`, + `${h} code { word-break: break-word } .h { clip: rect(0 0 0 0) }`, + ]); + assert.equal(d.dom, 0); + assert.deepEqual(changed(d), [ + ["body > div > code", "word-break"], + ["body > div > code", "overflow-wrap"], + ["body > span.h", "clip"], + ["body > span.h", "clip-path"], + ]); +});