float-pigment-forest 0.10.4

A node tree implementation for float-pigment-layout.
Documentation

float-pigment-forest

A node tree implementation for float-pigment-layout.

This is a crate of the float-pigment project. See its documentation for details.

Testing

The test suite uses an HTML-based imperative codegen framework. You author declarative HTML test cases; build.rs compiles each into a self-contained imperative Rust #[test] at build time (no hand-written test code).

Run tests

cargo test -p float-pigment-forest

Add a test case

  1. Create tests/cases/<topic>/<name>.html:
<div style="display: flex; width: 200px; height: 100px;">
  <div style="width: 80px; height: 40px;" data-expect-width="80" data-expect-left="0"></div>
  <div style="width: 120px; height: 40px;" data-expect-width="120" data-expect-left="80"></div>
</div>
  1. Run cargo test -p float-pigment-forest. build.rs auto-generates tests/generated/<topic>/<name>.rs (imperative) and runs it.

  2. Inspect the generated code:

cat tests/generated/<topic>/<name>.rs

Assertion attributes

Write data-expect-* on the element(s) you want to assert. Values are numbers (pixels); only write the axes you check.

HTML attribute Generated assertion
data-expect-width="V" assert_eq!(ctx.width(n).round(), V.0)
data-expect-height="V" assert_eq!(ctx.height(n).round(), V.0)
data-expect-left="V" assert_eq!(ctx.left(n).round(), V.0)
data-expect-top="V" assert_eq!(ctx.top(n).round(), V.0)
data-expect-margin-top/right/bottom/left="V" assert_eq!(ctx.margin_<side>(n).round(), V.0)
data-ignore="true" marks the #[test] as #[ignore]

Text nodes (>text<) compile to ctx.create_text("text").

Generated code shape

Each case compiles to an imperative test under tests/generated/ (gitignored, regenerated every build):

// AUTO-GENERATED from tests/cases/<topic>/<name>.html. Do not edit.
use crate::TestCtx;

#[test]
fn html_<topic>_<name>() {
    let mut ctx = TestCtx::new();
    let n0 = ctx.create_node("div");
    ctx.set_style(n0, "display: flex; width: 200px; ...");
    let n1 = ctx.create_node("div");
    ctx.append(n0, n1);
    ctx.layout_imperative();
    assert_eq!(ctx.width(n1).round(), 80.0);
}
  • Test fn name: html_<topic>_<name> (path separators and -_). Filter with cargo test html_<keyword>.
  • Edit a casecargo test regenerates automatically (rerun-if-changed=tests/cases).
  • tests/generated/ is gitignored — HTML cases are the source of truth, generated code is a build artifact.

Chrome cross-check (optional)

scripts/chrome-cross-check.mjs opens each case whose data-chrome != "false" in headless Chrome and compares getBoundingClientRect against data-expect-* — useful for catching cases where float-pigment's layout diverges from a real browser. Run from the repo root:

cd scripts && pnpm install && node chrome-cross-check.mjs

Set data-chrome="false" on the root element of a case that intentionally diverges from Chrome (e.g. float-pigment-specific behavior) to exclude it.