115 lines
5.7 KiB
JavaScript
115 lines
5.7 KiB
JavaScript
// Visual check of the Theme Builder, font roles, the Google Fonts browser and Appearance's account /
|
|
// pane themes through the panel harness (/?panel, mocked native commands; the harness fetches Google
|
|
// Fonts itself, like native code would). Needs a Vite dev server (default 127.0.0.1:1437).
|
|
//
|
|
// node scripts/theme-builder-shots.mjs [outDir] [port]
|
|
import { mkdirSync } from 'node:fs';
|
|
import { chromium } from 'playwright';
|
|
|
|
const out = process.argv[2] ?? '../../verification/theme-builder';
|
|
const port = process.argv[3] ?? '1437';
|
|
mkdirSync(out, { recursive: true });
|
|
const browser = await chromium.launch();
|
|
const results = [];
|
|
|
|
async function shot(name, { width = 1440, height = 900, query = '', action } = {}) {
|
|
const page = await browser.newPage({ viewport: { width, height }, deviceScaleFactor: 2, colorScheme: 'dark' });
|
|
const errors = [];
|
|
page.on('pageerror', error => errors.push(error.message));
|
|
page.on('console', message => { if (message.type() === 'error') errors.push(message.text()); });
|
|
await page.goto(`http://127.0.0.1:${port}/?panel${query ? `&${query}` : ''}`);
|
|
await page.waitForTimeout(1000);
|
|
let note = '';
|
|
if (action) note = (await action(page)) ?? '';
|
|
await page.waitForTimeout(500);
|
|
await page.screenshot({ path: `${out}/${name}.png` });
|
|
results.push(`${name}: ${errors.length ? `ERRORS ${errors.join(' | ')}` : 'ok'}${note ? ` (${note})` : ''}`);
|
|
await page.close();
|
|
}
|
|
|
|
// Builder at desktop and split-pane widths.
|
|
await shot('builder-wide', { query: 'section=builder' });
|
|
await shot('builder-narrow', { width: 520, height: 1000, query: 'section=builder' });
|
|
// A light base: palette, contrast report with failures, then auto-fix.
|
|
await shot('builder-contrast', {
|
|
query: 'section=builder',
|
|
action: async page => {
|
|
await page.getByLabel('Background color hex').fill('#fbf8f1'); await page.getByLabel('Background color hex').press('Enter');
|
|
await page.getByLabel('Text color hex').fill('#8a8a8a'); await page.getByLabel('Text color hex').press('Enter');
|
|
await page.getByLabel('Accent color hex').fill('#ffd400'); await page.getByLabel('Accent color hex').press('Enter');
|
|
await page.locator('.wb-card[aria-label="Contrast"]').scrollIntoViewIfNeeded();
|
|
const failing = await page.locator('.wb-contrast li.is-fail').count();
|
|
return `${failing} failing pairs before auto-fix`;
|
|
},
|
|
});
|
|
await shot('builder-autofix', {
|
|
query: 'section=builder',
|
|
action: async page => {
|
|
await page.getByLabel('Text color hex').fill('#8a8a8a'); await page.getByLabel('Text color hex').press('Enter');
|
|
await page.getByRole('button', { name: /Auto-fix/ }).click();
|
|
await page.locator('.wb-card[aria-label="Contrast"]').scrollIntoViewIfNeeded();
|
|
const failing = await page.locator('.wb-contrast li.is-fail').count();
|
|
// Undo brings the failing palette back, redo the fix.
|
|
await page.keyboard.press('Control+z');
|
|
const undone = await page.locator('.wb-contrast li.is-fail').count();
|
|
await page.keyboard.press('Control+Shift+z');
|
|
const redone = await page.locator('.wb-contrast li.is-fail').count();
|
|
return `after fix ${failing} failing; undo ${undone}; redo ${redone}`;
|
|
},
|
|
});
|
|
await shot('builder-fonts', {
|
|
query: 'section=builder',
|
|
action: async page => {
|
|
await page.locator('.wb-card[aria-label="Type"]').scrollIntoViewIfNeeded();
|
|
await page.getByRole('button', { name: 'Fine-tune Numbers' }).click();
|
|
},
|
|
});
|
|
// The font browser: live previews, search, detail with sample text and weights.
|
|
await shot('font-browser', {
|
|
query: 'section=builder',
|
|
action: async page => {
|
|
await page.locator('.wb-card[aria-label="Type"]').scrollIntoViewIfNeeded();
|
|
await page.getByRole('button', { name: /^Post text font/ }).click();
|
|
await page.waitForTimeout(2500);
|
|
},
|
|
});
|
|
await shot('font-browser-detail', {
|
|
query: 'section=builder',
|
|
action: async page => {
|
|
await page.locator('.wb-card[aria-label="Type"]').scrollIntoViewIfNeeded();
|
|
await page.getByRole('button', { name: /^Post text font/ }).click();
|
|
await page.getByLabel('Search Google Fonts').fill('fraunces');
|
|
await page.waitForTimeout(600);
|
|
await page.getByRole('option', { name: /Fraunces/ }).first().click();
|
|
await page.waitForTimeout(2500);
|
|
},
|
|
});
|
|
await shot('font-browser-installed', {
|
|
query: 'section=builder',
|
|
action: async page => {
|
|
await page.locator('.wb-card[aria-label="Type"]').scrollIntoViewIfNeeded();
|
|
await page.getByRole('button', { name: /^Names and headings font/ }).click();
|
|
await page.getByLabel('Search Google Fonts').fill('space grotesk');
|
|
await page.waitForTimeout(500);
|
|
await page.getByRole('option', { name: /Space Grotesk/ }).first().click();
|
|
await page.getByRole('button', { name: /Download and use/ }).click();
|
|
await page.waitForSelector('.wb-sheet', { state: 'detached', timeout: 20000 });
|
|
await page.waitForTimeout(1200);
|
|
return (await page.locator('.wb-role[aria-label="Names and headings"] .wb-role-name').innerText()).replace(/\s+/g, ' ');
|
|
},
|
|
});
|
|
await shot('font-browser-narrow', {
|
|
width: 560, height: 980, query: 'section=builder',
|
|
action: async page => {
|
|
await page.locator('.wb-card[aria-label="Type"]').scrollIntoViewIfNeeded();
|
|
await page.getByRole('button', { name: /^Post text font/ }).click();
|
|
await page.getByRole('radio', { name: 'Serif' }).click();
|
|
await page.waitForTimeout(2500);
|
|
},
|
|
});
|
|
await shot('appearance-fonts', { query: 'section=themes', action: async page => { await page.locator('[aria-label="Interface"]').first().scrollIntoViewIfNeeded(); } });
|
|
await shot('appearance-scopes', { query: 'section=themes', action: async page => { await page.locator('#theme-scopes-h').scrollIntoViewIfNeeded(); } });
|
|
await shot('appearance-light-chrome', { query: 'section=themes&theme=paper' });
|
|
|
|
await browser.close();
|
|
console.log(results.join('\n'));
|