diff --git a/tools/trace_replay/render_retrace_summary.mjs b/tools/trace_replay/render_retrace_summary.mjs index 2d8a989e..2869ee8e 100644 --- a/tools/trace_replay/render_retrace_summary.mjs +++ b/tools/trace_replay/render_retrace_summary.mjs @@ -1,6 +1,7 @@ #!/usr/bin/env node -import { mkdir, readdir, readFile, stat, writeFile } from "node:fs/promises"; +import { createWriteStream } from "node:fs"; +import { mkdir, readdir, readFile, stat } from "node:fs/promises"; import path from "node:path"; import { fileURLToPath } from "node:url"; @@ -393,37 +394,16 @@ async function renderHtml(rows, groupLabels, outputDir, title, groupLabel, htmlN `; }; - const groupSections = groups.map((group) => { - const displayGroup = groupLabels.get(group) ?? group; - const groupCells = CASES.flatMap((caseName) => BACKENDS.map((backend) => cellFor(group, backend, caseName))); - const passed = groupCells.filter((row) => effectiveStatus(row) === "PASS").length; - const failed = groupCells.filter((row) => effectiveStatus(row) === "FAIL").length; - const noResult = groupCells.filter((row) => effectiveStatus(row) === "NO_RESULT").length; - const passRateDenominator = passed + failed; - const passRate = passRateDenominator === 0 ? "0.0%" : `${(passed * 100 / passRateDenominator).toFixed(1)}%`; - return ` -
-

${htmlEscape(title)} - ${htmlEscape(displayGroup)}

-

Each backend cell shows actual / golden / diff. Failed cases are red; absent results are orange; incomplete image sets get an orange notch.
PASS ${passed}, FAIL ${failed}, NO RESULT ${noResult}, PASS RATE ${passRate}.

-
-
case
-
DirectGLES
-
DirectVulkan
-
- ${CASES.map((caseName, index) => ` -
- - ${backendCell(group, "DirectGLES", caseName)} - ${backendCell(group, "DirectVulkan", caseName)} -
`).join("")} -
`; - }).join(""); + const output = path.join(outputDir, htmlName); + const stream = createWriteStream(output, { encoding: "utf8" }); + const write = (chunk) => new Promise((resolve, reject) => { + stream.write(chunk, (error) => error ? reject(error) : resolve()); + }); + const finish = () => new Promise((resolve, reject) => { + stream.end((error) => error ? reject(error) : resolve()); + }); - const html = ` + await write(` @@ -452,9 +432,8 @@ async function renderHtml(rows, groupLabels, outputDir, title, groupLabel, htmlN font-family: Arial, Helvetica, sans-serif; font-size: 12px; } - main { width: 1170px; margin: 0 auto; padding: 14px 10px 24px; } - .group { break-after: page; margin-bottom: 28px; } - .group:last-child { break-after: auto; } + main { width: 1170px; margin: 0 auto; padding: 14px 10px 96px; } + .group { margin-bottom: 28px; } h1 { margin: 0; font-size: 24px; line-height: 1.2; } p { margin: 4px 0 12px; color: var(--muted); } .grid { @@ -576,17 +555,62 @@ async function renderHtml(rows, groupLabels, outputDir, title, groupLabel, htmlN object-fit: contain; box-shadow: 0 18px 70px rgb(0 0 0 / 70%); } + .summary-footer { + margin-top: 24px; + padding: 18px 0 8px; + color: var(--muted); + border-top: 1px solid var(--line); + } @page { size: 1170px 2380px; margin: 0; } @media print { main { padding: 10px; } - .group { margin-bottom: 0; } + .group { break-after: page; margin-bottom: 0; } + .group:last-child { break-after: auto; } + .summary-footer { display: none; } .lightbox { display: none; } }
-${groupSections} +`); + + for (const group of groups) { + const displayGroup = groupLabels.get(group) ?? group; + const groupCells = CASES.flatMap((caseName) => BACKENDS.map((backend) => cellFor(group, backend, caseName))); + const passed = groupCells.filter((row) => effectiveStatus(row) === "PASS").length; + const failed = groupCells.filter((row) => effectiveStatus(row) === "FAIL").length; + const noResult = groupCells.filter((row) => effectiveStatus(row) === "NO_RESULT").length; + const passRateDenominator = passed + failed; + const passRate = passRateDenominator === 0 ? "0.0%" : `${(passed * 100 / passRateDenominator).toFixed(1)}%`; + await write(` +
+

${htmlEscape(title)} - ${htmlEscape(displayGroup)}

+

Each backend cell shows actual / golden / diff. Failed cases are red; absent results are orange; incomplete image sets get an orange notch.
PASS ${passed}, FAIL ${failed}, NO RESULT ${noResult}, PASS RATE ${passRate}.

+
+
case
+
DirectGLES
+
DirectVulkan
+
+`); + for (const [index, caseName] of CASES.entries()) { + await write(` +
+ + ${backendCell(group, "DirectGLES", caseName)} + ${backendCell(group, "DirectVulkan", caseName)} +
`); + } + await write(` +
`); + } + + await write(` +