Design language Accessibility
Accessibility
We build zeronesecurity.com to WCAG 2.2 level AA, in English and Turkish, and we check it on every change. This page sets out the rules the site follows, the test that holds each one and the places no test reaches yet.
WCAG 2.2 AA, on every change.
#WCAG 2.2 level AA is the floor for every page in both languages, and a change that fails an accessibility check does not reach the site.
- 0 axe violations allowed on a page, of any impact
- 63 axe rules run on each scanned page, from 5 WCAG tag sets
- 320 CSS pixels wide, and no page may scroll sideways
- 100 desktop Lighthouse accessibility score required on 21 pages
axe-core judges what a machine can judge. Several criteria it cannot judge have scripted browser tests of their own, among them reflow, focus hidden under the sticky header and a pause control for moving content. The checks run on every merge request and every push, and the next section lists each one with the exact name its test has in the code.
Every built page is scanned, the 404 page included.
WhyThe test takes its list of pages from the built site itself: every HTML file the build writes, in English and in Turkish, including the 404 page that a visitor sees at any address that does not exist. A new page is checked without anyone adding it.
TestEnforced by a test on every change.
A change that fails a check does not reach the site.
WhyDeployment of the site waits for the build gates, the browser tests and the desktop Lighthouse run. If one fails, the site is not deployed. In CI a browser test that fails is run once more, and it stops the deployment only if it fails again.
BuildEnforced by the build pipeline on every change.
What is tested and how.
#Each row is a check that runs on every change. When this page is built, every row is matched to the test that runs it, so a renamed, deleted or skipped test breaks the build of this page instead of leaving a stale claim behind.
| Criterion or check | How it is checked |
|---|---|
| WCAG 2.2 A and AA, automated | axe-core 4.13.0 runs on every built page, the 404 page included, with the tags wcag2a, wcag2aa, wcag21a, wcag21aa, wcag22aa. axe leaves out its experimental and deprecated rules, so 63 rules run. The page is first scrolled from top to bottom so that visuals are judged in their final state, and the test expects an empty list of violations. |
| 1.4.10 Reflow | One browser window 320 × 640 CSS px opens every built page, the 404 page included. No page may be wider than the window, not even by one pixel. |
| 2.4.11 Focus not obscured | 60 presses of Tab, then 40 of Shift+Tab, on /, /zero-door and /tr/contact: once in a desktop window 1280 × 800 and once in a narrow window 390 × 844. After each press the test waits for scrolling to stop and fails if the sticky header covers the centre and all four corners of the focused element. |
| 2.2.2 Pause, stop, hide | On every scanned page: if a loop has started, a visible pause control must be on the page as well, or the page fails. Every loop sets the mark data-ambient when it starts. The shared motion lifecycle sets it for the loops it runs; the noise canvas, the hold motion of the two scroll scenes and the scroll cue in the home page hero set it themselves. The build of this page stops if a component loops without setting it. |
| 2.2.2 The decision persists | Pausing on the home page pauses the site. On the Zero Door page the control still reads paused, and back on the home page the noise canvas reports itself paused. |
| 2.2.2 and 2.5.8 on the Zero Door page | Every looping visual has its own control; the first is at least 24 × 24 px and labelled as a pause. One click pauses every control and the moving rows stop, and the decision survives a reload. |
| 2.5.8 Target size (minimum) | The axe rule target-size, part of the wcag22aa tag set, runs on every scanned page. |
| 1.4.13 Content on hover or focus | On a wide screen a rule on the home page opens when keyboard focus reaches its title. Escape closes it while focus stays, focus on its proof link opens it again and focus moving on to the next rule closes it. On a narrow screen the rules are an accordion: opening one closes the one that was open, and a closed rule keeps its link hidden. |
| 2.1.1 Keyboard | In the evidence scene on the home page the arrow keys move between steps, take focus with them and stop at the first and the last step. |
| 1.1.1 and 4.1.2 The label follows the step | Choosing a step changes the role=img label of the scene to the sentence for that step, taken from the dictionary. |
| 1.3.1 Info and relationships: heading order | In every built HTML file, heading levels inside <main> never skip. axe treats heading order as good practice rather than a WCAG rule, so a build gate holds it. |
| 3.1.2 Language of parts | In the hero of the Turkish home page, the framework names in the trust line and the kicker carry lang=en. On the Turkish sector pages, a proof line quoted from the product’s English output carries lang=en, and a proof line written in Turkish carries none. |
| Reduced motion, site-wide | Every built page except the 404 page opens with reduced motion requested. No revealed element is left with a transform, every labelled visual in the main content is drawn, not hidden or clipped away, the motion class is not set and no loop starts. |
| Reduced motion, home page | On the home page, with reduced motion requested, every revealed element stands in its final place with no transform, fully opaque and not hidden, and the motion class is never set. |
| Without JavaScript, site-wide | Every built page except the 404 page opens with scripts off. Every revealed element stands in its final place with no transform, and every labelled visual in the main content is drawn, not hidden or clipped away. |
| Without JavaScript, home page | With scripts off, the evidence scene on the home page stacks its four cards, the stage stands still and the pause control stays hidden. |
| 1.4.3 Contrast (minimum): text colour tokens | ink, ink-muted, ink-subtle and accent-deep are computed against paper and paper-2 and must reach 4.5:1 on both. |
| 1.4.11 Non-text contrast: focus ring and field border | From the colour tokens, the accent focus ring is computed against paper, paper-2, accent-tint and ink, and the ink-subtle border of form fields against paper, paper-2 and accent-tint; each must reach 3:1. The test also checks that the contact form, the call-to-action band and the glossary filter draw their fields with that border, and that the global focus rule is a 2px solid accent outline. |
| Lighthouse accessibility | Desktop Lighthouse opens 21 pages, 2 runs each, and every run on each page must score 100 for accessibility. |
WCAG 2.2 A and AA, automated
How it is checkedaxe-core 4.13.0 runs on every built page, the 404 page included, with the tags
wcag2a,wcag2aa,wcag21a,wcag21aa,wcag22aa. axe leaves out its experimental and deprecated rules, so 63 rules run. The page is first scrolled from top to bottom so that visuals are judged in their final state, and the test expects an empty list of violations.1.4.10 Reflow
How it is checkedOne browser window 320 × 640 CSS px opens every built page, the 404 page included. No page may be wider than the window, not even by one pixel.
2.4.11 Focus not obscured
How it is checked60 presses of Tab, then 40 of Shift+Tab, on /, /zero-door and /tr/contact: once in a desktop window 1280 × 800 and once in a narrow window 390 × 844. After each press the test waits for scrolling to stop and fails if the sticky header covers the centre and all four corners of the focused element.
2.2.2 Pause, stop, hide
How it is checkedOn every scanned page: if a loop has started, a visible pause control must be on the page as well, or the page fails. Every loop sets the mark
data-ambientwhen it starts. The shared motion lifecycle sets it for the loops it runs; the noise canvas, the hold motion of the two scroll scenes and the scroll cue in the home page hero set it themselves. The build of this page stops if a component loops without setting it.2.2.2 The decision persists
How it is checkedPausing on the home page pauses the site. On the Zero Door page the control still reads paused, and back on the home page the noise canvas reports itself paused.
2.2.2 and 2.5.8 on the Zero Door page
How it is checkedEvery looping visual has its own control; the first is at least 24 × 24 px and labelled as a pause. One click pauses every control and the moving rows stop, and the decision survives a reload.
2.5.8 Target size (minimum)
How it is checkedThe axe rule
target-size, part of thewcag22aatag set, runs on every scanned page.1.4.13 Content on hover or focus
How it is checkedOn a wide screen a rule on the home page opens when keyboard focus reaches its title. Escape closes it while focus stays, focus on its proof link opens it again and focus moving on to the next rule closes it. On a narrow screen the rules are an accordion: opening one closes the one that was open, and a closed rule keeps its link hidden.
2.1.1 Keyboard
How it is checkedIn the evidence scene on the home page the arrow keys move between steps, take focus with them and stop at the first and the last step.
1.1.1 and 4.1.2 The label follows the step
How it is checkedChoosing a step changes the
role=imglabel of the scene to the sentence for that step, taken from the dictionary.1.3.1 Info and relationships: heading order
How it is checkedIn every built HTML file, heading levels inside
<main>never skip. axe treats heading order as good practice rather than a WCAG rule, so a build gate holds it.3.1.2 Language of parts
How it is checkedIn the hero of the Turkish home page, the framework names in the trust line and the kicker carry
lang=en. On the Turkish sector pages, a proof line quoted from the product’s English output carrieslang=en, and a proof line written in Turkish carries none.Reduced motion, site-wide
How it is checkedEvery built page except the 404 page opens with reduced motion requested. No revealed element is left with a transform, every labelled visual in the main content is drawn, not hidden or clipped away, the motion class is not set and no loop starts.
Reduced motion, home page
How it is checkedOn the home page, with reduced motion requested, every revealed element stands in its final place with no transform, fully opaque and not hidden, and the motion class is never set.
Without JavaScript, site-wide
How it is checkedEvery built page except the 404 page opens with scripts off. Every revealed element stands in its final place with no transform, and every labelled visual in the main content is drawn, not hidden or clipped away.
Without JavaScript, home page
How it is checkedWith scripts off, the evidence scene on the home page stacks its four cards, the stage stands still and the pause control stays hidden.
1.4.3 Contrast (minimum): text colour tokens
How it is checkedink, ink-muted, ink-subtle and accent-deep are computed against paper and paper-2 and must reach 4.5:1 on both.
1.4.11 Non-text contrast: focus ring and field border
How it is checkedFrom the colour tokens, the accent focus ring is computed against paper, paper-2, accent-tint and ink, and the ink-subtle border of form fields against paper, paper-2 and accent-tint; each must reach 3:1. The test also checks that the contact form, the call-to-action band and the glossary filter draw their fields with that border, and that the global focus rule is a 2px solid accent outline.
Lighthouse accessibility
How it is checkedDesktop Lighthouse opens 21 pages, 2 runs each, and every run on each page must score 100 for accessibility.
Focus is always visible.
#Keyboard focus looks the same everywhere: a solid 2px outline in the accent colour. It is drawn when the browser decides focus should show, so a mouse click on a button or link leaves no ring behind. Components may change the offset. They never change the width or the colour.
Try it with the keyboard.
Press Tab to move through these controls. They use the site’s own button and link classes and a plain text field, under the one global focus rule. The buttons are samples and do nothing.
.btn, .btn-ghost, .btn-ink, .link and a text field. Every ring here comes from the global rule: 2px, offset 3px.The ring on four surfaces
The ring is not text, so it needs 3:1 against the colour behind it. The accent meets that on each of the four surfaces below: the two page surfaces, the accent tint and the ink of the code panels.
- paper4.38:1 meets 3:1
- paper-24.12:1 meets 3:1
- accent-tint3.97:1 meets 3:1
- ink3.78:1 meets 3:1
Offsets in use
Offsets in use run from 3px to -2px. The default ring stands clear of the element, the pause control and fields sit closer, step buttons are hugged by their ring and code panels draw it inside.
- Default3px
- Pause control2px
- Glossary field1px
- Step button0px
- Code panel-2px
.btn.| Selector | Offset |
|---|---|
| :focus-visible | 3px |
| .fd:focus-visible | 2px |
| li:focus-within | -2px |
| .v:focus-visible | none, see :focus-within |
| .tw:focus-visible | 2px |
| pre:focus-visible | -2px |
| .tw:focus-visible | 2px |
| .t:focus-visible | none, see :focus-within |
| .row:focus-within | -2px |
| .tw:focus-visible | 2px |
| .tw:focus-visible | 2px |
| .tw:focus-visible | 2px |
| .tw:focus-visible | 2px |
| .tw:focus-visible | 2px |
| .b:focus-visible | 2px |
| .tg:focus-visible | 2px |
| .chip:focus-visible, .play:focus-visible | 2px |
| .b:focus-visible, .card:focus-visible | 2px |
| .in:focus-visible | 1px |
| .tw:focus-visible | 2px |
| .dots button:focus-visible | 0 |
| .mb:focus-visible | 2px |
| .integ summary:focus-visible | 3px |
| .errs .err:focus-visible | 2px |
| input:focus-visible, select:focus-visible, textarea:focus-visible | 2px |
| input:focus-visible | 1px |
| .card:focus-within | 2px |
| .title a:focus-visible | none, see :focus-within |
| .file pre:focus-visible | -2px |
| .dots button:focus-visible | 0 |
Sticky header and scroll margin
The header stays at the top of the window and is 67px tall. Links, buttons, form fields, summaries and anything with a tabindex carry a scroll margin of 84px at the top and 16px at the bottom, so when focus scrolls one of them into view it stops below the header with 17px to spare. Section anchors carry margins of their own.
- Sticky header · 67px
- 17px clear
- scroll-margin-top: 84px
- scroll-margin-bottom: 16px
:focus-visible { outline: 2px solid var(--color-accent); outline-offset: 3px; }
:where(a[href], button, input, select, textarea, summary, [tabindex]) { scroll-margin-top: 84px; scroll-margin-bottom: 16px; }Focus is a solid 2px accent outline. Only the offset changes.
WhyOne sign for focus everywhere, so nobody has to learn a second one. When this page is built it reads every focus rule in the components, layouts, pages and global CSS, and stops the build if one draws a different width or colour, or sets the ring through
outlinelonghands orbox-shadow.BuildEnforced by the build pipeline on every change.
Focus is never hidden entirely under the sticky header.
WhyWCAG 2.4.11. Keyboard users move through the page with focus, and a header that covers the focused element hides where they are. The test walks 3 pages at desktop width, and a second test walks them again in a window 390 px wide.
TestEnforced by a test on every change.
An outline is removed only where the ring moves to the container.
WhyOn a whole-card link the ring goes to the card through
:focus-within, so it still outlines the whole target. The build of this page stops if a component removes an outline in a file with no:focus-withinrule.BuildEnforced by the build pipeline on every change.
Colour is never the only signal.
#Text reaches 4.5:1 on both page surfaces, and meaning never rests on colour alone. Links are underlined, the pause control changes shape and the do and do not marks on these pages carry a word as well as a symbol.
The full palette and the computed text contrast of every token are on the Colour page. This section keeps what accessibility adds to it.
Contrast for what is not text
Focus rings, icons and the borders that mark out a control need 3:1 against the colour behind them (WCAG 1.4.11). The accent, ink-muted and ink-subtle tokens meet it, and form fields draw their border in ink-subtle. The two hair tokens do not: the site draws separators and frames with them, and also the borders of the pause control, the ghost button and the menu button.
| Token | On paper | On paper-2 |
|---|---|---|
| accent | 4.38:1 · meets 3:1 | 4.12:1 · meets 3:1 |
| ink-muted | 6.85:1 · meets 3:1 | 6.44:1 · meets 3:1 |
| ink-subtle | 4.89:1 · meets 3:1 | 4.60:1 · meets 3:1 |
| hair-2 | 1.56:1 · below 3:1 | 1.47:1 · below 3:1 |
| hair | 1.27:1 · below 3:1 | 1.19:1 · below 3:1 |
Computed from the tokens in tokens.css with the WCAG 2.x formula when this page is built, and rounded down. Whether the pause control, the ghost button or the menu button needs its border to be recognised has not been audited; it is listed under the gaps below.
Links in running text
In running text a link is marked by its underline. The colour supports the underline; it never replaces it.
Check the contrast table before you pick a colour pair.
Check the contrast table before you pick a colour pair.
Shape and words carry state.
The pause control shows two bars while things move and a triangle once they stop, and its label switches between “Pause animations” and “Play animations”. The do and do not marks on these pages pair a tick or a cross with a word.
- Pause animations
- Play animations
Small text never falls below 4.5:1.
WhyWCAG 1.4.3. axe measures the text on every scanned page, and a unit test pins the text tokens against both surfaces.
TestEnforced by a test on every change.
Plain accent is for non-text: rings, underlines, rules and dots.
WhyOn paper it measures 4.38:1, under the 4.5:1 that small text needs. Filled buttons use
accent-deepinstead; paper text on it measures 6.65:1.ReviewKept by review, not by a test.
A link in running text never stands out by colour alone.
WhyWCAG 1.4.1. axe fails a link in running text whose colour differs from the text around it by less than 3:1 and that has no other mark, such as an underline.
TestEnforced by a test on every change.
Every loop can be stopped.
#Motion is added on top of content that is already there. One control stops every loop, loops rest when nobody can see them and nothing moves for people who ask their system for less motion.
How motion is built, from the curve to the scroll scenes, is on the Motion page. This section keeps what accessibility asks of it.
Live state of the diagram
- Lifecycle
data-state - not set
- Loop
data-ambient - not set
- Paused site-wide
html.paused - no
Live: the diagram from the architecture page with its real pause control. Pausing here pauses every loop on the site and is remembered on the next page you open.
The pause control
A round 28px icon button labelled “Pause animations” or “Play animations”: one click stops every loop on the page, and the choice is stored in the browser under the key zs-motion, so the next page opens paused as well.
Loops rest when nobody is watching.
A loop pauses when its visual leaves the screen or the tab is hidden, and it obeys the site-wide pause.
Reduced motion
When the system asks for reduced motion, the block below turns off smooth scrolling, cuts transitions to almost nothing and removes CSS animations, and visuals go straight to their final state.
@media (prefers-reduced-motion: reduce) {
html { scroll-behavior: auto; }
*, *::before, *::after { transition-duration: 0.01ms !important; animation: none !important; }
}No loop runs without a visible pause control on the page.
WhyWCAG 2.2.2. A browser cannot tell whether a page moves, so every loop sets
data-ambientwhen it starts, and the 2.2.2 check in the axe test then looks for a visible control. The shared lifecycle sets the mark for the loops it runs; the noise canvas, the hold motion of the two scroll scenes and the hero scroll cue set it themselves. The build of this page stops if a component loops without the mark.TestEnforced by a test on every change.
One decision pauses every loop on every page.
WhyStopping motion should not be a task to repeat on each page. The test pauses on the home page and finds the next page paused.
TestEnforced by a test on every change.
A loop stops when its visual leaves the screen.
WhyMotion that nobody sees still costs battery and processing. The test scrolls the dam illustration on the Zero Door page away and checks that its cards stand still.
TestEnforced by a test on every change.
With reduced motion, visuals rest in their final state and the control is hidden.
WhyWhat was asked for is less motion, not a button to press. The test checks the visuals of the Zero Door page.
TestEnforced by a test on every change.
A one-time animation shorter than five seconds needs no control.
WhyWCAG 2.2.2 asks for a control only when motion lasts longer than five seconds. A block that rises into place as it scrolls into view moves once, for 0.8 seconds, and stops.
ReviewKept by review, not by a test.
Motion never animates
opacity.WhyText that fades through half transparency fails contrast on the way, and the automated contrast checks once failed for that reason. Elements enter by
transform,clip-pathor stroke drawing instead.ReviewKept by review, not by a test.
Content arrives before scripts.
#The server sends every page in its final, readable state. Scripts add motion on top; only the second block of the home hero waits for a script, and a CSS rescue opens it if the script is late.
Each page starts with the class no-js on its root element. A script removes it and, unless reduced motion is requested, adds the class motion. Every state that hides something before it animates is written under that motion class, except the second block of the home hero, which a CSS rescue opens if the hero script is late; without the script no content is hidden.
If the script runs but the observer never sees an element, a safety net reveals every reveal element after 3 seconds.
Without JavaScript the scroll scenes stack their cards, the pause controls stay hidden, the glossary shows its full list and the contact form posts as a plain HTML form.
Content is complete without JavaScript.
WhyA script can fail to load, be blocked or break. What a page says must not depend on it. A browser test opens every built page except the 404 page with scripts off: every revealed element must stand in its final place, and every labelled visual in the main content must be drawn, not hidden or clipped away. A second test checks the evidence scene on the home page in detail.
TestEnforced by a test on every change.
The contact form works without JavaScript.
WhyIt is a real HTML form with native validation, and it posts to the same address with or without a script.
TestEnforced by a test on every change.
Reduced motion never leaves an element half revealed.
WhySomeone who asks for less motion still sees all of the content, whatever the scripts do. A browser test opens every built page except the 404 page with reduced motion requested: no revealed element is left out of place, every labelled visual in the main content is drawn, the motion class is not set and no loop starts. A second test checks on the home page that every revealed element is also fully opaque and not hidden.
TestEnforced by a test on every change.
A visual that makes a point has a sentence.
#A visual that makes a point is an image with a sentence: role=img and a label from the dictionary, written in both languages. A visual that only decorates is hidden from assistive technology.
A host runs the agent; the agent opens the connection outwards to the platform, which holds the stores. Nothing dials in to your hosts.
<figure class="fd" data-flow role="img" aria-label={d.label} tabindex="0">
<svg viewBox="0 0 760 260" preserveAspectRatio="xMidYMid meet"><span class="lbl"><svg viewBox="0 0 16 16" aria-hidden="true"><path d="M3.5 8.5 6.5 11.5 12.5 4.5"></path></svg>{c.do}</span>The label follows the scene.
The scroll scenes on the home page and the Zero Door page are one image whose meaning changes step by step, and the label changes with it. These are the four sentences of the home page scene in this language.
- Scene 1: two curves cross. Thousands of raw changes on one server narrow to a single alert.
- Scene 2: a calendar grid. An illustrative fourteen days of evidence hunting, with a two day target scenario over the first two.
- Scene 3: signal pills merging into one verdict pill.
- Scene 4: a row of memory regions with one gap, the region with no file behind it.
How labels are written
Many labels in use begin with “Illustration:” or “Scene N:” and then say what is drawn and what it shows. Icons, glyphs, canvases, separators and arrows that only decorate carry aria-hidden=true. Numbers that count up on screen do so inside such an image, so a screen reader hears its sentence and not the count.
A
role=imgvisual never ships without a label.WhyWCAG 1.1.1. axe fails an image role that has no name. The labels come from the dictionary, so the English and Turkish sentences sit side by side.
TestEnforced by a test on every change.
When a scene changes step, its label changes with it.
WhyA screen reader user hears what a sighted reader sees at that step.
TestEnforced by a test on every change.
Counting numbers are not read out on their way up.
WhyReading every value is noise. The counters in the Zero Door illustrations climb inside an image with a sentence, so a screen reader hears that sentence instead. The commitment figures in the Trust centre do not count at all: on its way up a counter showed values that were never promised.
ReviewKept by review, not by a test.
Decoration is
aria-hidden.WhyA shape that carries no meaning only takes up time in a screen reader.
ReviewKept by review, not by a test.
Wide content scrolls in its own box.
#The reflow test opens every built page, the 404 page included, at 320 CSS px, and none scrolls sideways. Tables, code and diagrams that cannot shrink scroll inside their own box, and the box takes keyboard focus so it can be scrolled without a mouse.
| Page | Runs | Accessibility score required |
|---|---|---|
| /solutions/banking-and-finance | 2 | 100 |
| /research/inside-symbiote-malware-deep-dive | 2 | 100 |
| /legal/terms-of-use | 2 | 100 |
| /tr/legal/terms-of-use | 2 | 100 |
| /design/motion | 2 | 100 |
16 more pages in the run
Boxes that scroll on their own
- Markdown tables, wrapped in a focusable box when the site is built
- Markdown code blocks, made focusable when the site is built
- The tables and code panels on these pages
- The architecture diagram below 760px wide, which keeps its drawing 620px wide and scrolls instead of shrinking
Nothing scrolls the page sideways at 320 CSS px.
WhyWCAG 1.4.10. On a narrow screen or at high zoom, nobody should have to scroll in two directions to read a line.
TestEnforced by a test on every change.
A box that scrolls can take keyboard focus.
WhyWCAG 2.1.1. A keyboard user can only scroll a box that takes focus, and axe fails one that cannot.
TestEnforced by a test on every change.
Targets are large enough to hit.
#WCAG 2.2 asks for targets of at least 24 by 24 CSS px, or enough space around a smaller one. The custom controls on the site meet that size or go beyond it.
- 24 × 24Step buttons, home page scene
- 24 × 24Step buttons, Zero Door scene
- 28 × 28Pause control
- 28 × 28Icon link in the footer
- 40 × 40Menu button on narrow screens
- 24 × 24The # link beside each section heading on these pages
target-size.Smaller targets that rely on an exception
Links in running text fall under the inline exception: the line of text sets their size. axe target-size does not measure them.
Custom controls meet the target size of WCAG 2.5.8.
WhyWCAG 2.5.8. axe runs its
target-sizerule on every scanned page, and the Zero Door test measures the first pause control as well.TestEnforced by a test on every change.
What is not tested yet.
#Automated checks do not cover everything. These are the gaps we know of, listed so that this page is never read as a larger claim than the tests behind it.
Not tested
- Non-text contrast of icons and controls (1.4.11)axe does not measure it. A unit test computes, from the tokens, the focus ring against the four surfaces it lands on and the form-field border against the surfaces it sits on, and checks that the site’s three forms draw that border; no test checks icons or rendered controls. hair-2, which draws the borders of the pause control, the ghost button and the menu button, measures 1.56:1 against paper; whether those controls need the border to be recognised has not been audited. Form fields draw theirs in ink-subtle, at 4.89:1.
- A second cue beside colourIn diagrams, accent and raw differ by 1.30:1 in luminance and read as different mainly by hue. The rule that a direction, a mark shape or a word says the same thing is a convention held by review; no test checks that every scene keeps that second cue.
- Visible focus (2.4.7)The ring is defined in one global rule that components restate with an offset of their own. Only the live controls on this page are checked for a drawn ring; no test checks it across the site. The header test for 2.4.11 runs on 3 pages, not on all of them.
- Text spacing, resize and orientationaxe checks only that zoom is not disabled (1.4.4) and that inline styles do not lock text spacing (1.4.12). No test renders a page at 200 percent or with wider spacing, and orientation (1.3.4) is not checked: the axe rule for it is experimental and does not run.
- Forced coloursThe site has no styles for forced colours or high contrast modes, and none are tested.
- Skip linkIt is the first element on every page, and no test uses it.
- Assistive technologyNobody has recorded a test with a screen reader or other assistive technology. Of the criteria a scanner cannot judge, three have scripted browser tests that walk many pages: reflow (1.4.10) on every built page, focus under the sticky header (2.4.11) on 3 pages and the pause control (2.2.2) on every scanned page. Others, such as keyboard use (2.1.1), are tested on a single component or not at all, and no person checks them.
- PhonesOn the phone profile, axe skips every page under /legal/ and /research/ but still scans the index page of each, and the mobile Lighthouse run is advisory. The reflow test runs in a desktop browser narrowed to 320 px, and the header test for 2.4.11 in a desktop browser at 1280 × 800 and narrowed to 390 × 844; neither runs in the phone profile.
- Where the pause control sitsThe 2.2.2 check looks for a visible control on the page while a loop runs, not for one beside each loop.
- Text inside illustrationsThe smallest size set in the site’s components is 5.4px, in Plate. SVG text also shrinks with its drawing on narrow screens. No rule sets a minimum and no test measures it.
- Changing the motion setting mid-visitScripts read the setting when a page loads, so loops and reveals follow a change on the next page; the CSS rules follow it at once.
- Lighthouse coverageLighthouse runs on a fixed list of 21 pages.
Not defined yet
- Allowed colour pairsNo rule forbids ink-subtle text on accent-tint, which measures 4.44:1, under 4.5:1. axe would flag it on any page that used it.
- A conformance reportNo accessibility conformance report for the site has been published.
- A contrast preferenceThe site does not respond to a request for more contrast (prefers-contrast).
Statement and reports
#The short public statement is in the Trust centre, and this page is the working detail behind it: it lists the tests in full.
If something on the site does not work with your keyboard, your browser settings or your assistive technology, tell us through the contact form. Name the page and what you were trying to do, and we will reply.