Skip to content

v2.5.0

Latest

Choose a tag to compare

@github-actions github-actions released this 05 Sep 03:47
6d773b6

Headline: the toolbar and lecture typography now match the existing Sphinx builds — an icon-only search trigger, PT Serif headings on the Sphinx scale, and QuantEcon-blue content links — and every toolbar control gets a proper accessible name in place of a nested button. The notebook launcher collapses to a direct Colab link, dropping the Private JupyterHub option no lecture site ever configured. The "back to top" button no longer fades out of the page margin on load, and the WebKit FOUC guard is hardened against the hydration race that could turn it red for reasons unrelated to the critical CSS.

Changed

  • The toolbar search trigger is now a plain magnifier icon, matching the search affordance on the existing lecture sites and the styling of the neighbouring toolbar icons, in place of the boxed "Search ⌘K" placeholder. The ⌘K / Ctrl K keyboard hint moves into the search dialog, overlaid on the right edge of the text input. Because @myst-theme/site exports only the top-level Search component, Search.tsx is forked verbatim from @myst-theme/site@1.3.0 into app/components/toolbar/ apart from the trigger and hint placement; search behaviour, keyboard navigation and platform detection are unchanged (#165).
  • Lecture headings now follow the Sphinx builds' typography. h1h3 are set in PT Serif with h4/h5 kept in the sans face, sized on the Sphinx scale (h1 2em, h2 1.7em, h3 1.4em, h4 1.2em of the content size, so the scale tracks the font-scale controls), with every level at line-height 1.15 and h4/h5 at weight 900 to match the Sphinx build's measured values. All of it is mirrored into the critical CSS so the first WebKit paint on static-build navigations is already serif at the final sizes rather than painting the title small and swapping (#166).
  • Content links are coloured to match the Sphinx lecture builds: #0072bc (5.05:1 on white, WCAG AA) with #004979 on hover, and white in both states in dark mode as the Sphinx dark theme does. Both of myst-to-react's anchor classes are covered — .link for plain links and .hover-link for cross-references, citations and footnotes — via --qe-link-color / --qe-link-hover-color tokens in styles/quantecon.css, overriding the upstream blue-700/blue-400 at matched specificity, with the underline drawn in currentColor so it always follows the text. Colour only: the Sphinx builds' hover-only underline and :visited colour are deliberately not matched here. Site chrome (footer badge, back-to-top) keeps its own rules (#167).

Removed

  • The Private JupyterHub launch option. The toolbar's Launch control is now a direct link to Google Colab instead of a popover with a radio group and a hand-typed service URL. The demand signal this was gated on came back empty: the book-theme only renders its hub button when jupyterhub_url is set in _config.yml, and an org-wide search finds that key in no lecture repo at all — every flagship series configures colab_url alone — so the button has never appeared on a live QuantEcon site. The MyST version was also not the same feature: it had no config key, rendered unconditionally, and asked the reader to type a hub URL into a box whose value was React.useState('') and so was discarded when the popover closed. Verified against a live build, it also hardcoded a /jupyter/hub/ path segment the Sphinx theme leaves to the configured URL, so it only ever addressed hubs at <host>/jupyter/hub/ and could not reach a stock JupyterHub, let alone a local Jupyter server. Removing it drops buildJupyterHubUrl, the Radix popover and radio group, and the launch-open.png visual baseline; launch-colab now asserts the anchor's href, which also pins that the control is a link rather than a chooser. Re-adding hub, Binder and local-server targets is tracked as future work (#87).

Fixed

  • Every toolbar control was nesting a second <button> inside its real button or link, because the Radix tooltip trigger renders its own element by default: invalid HTML and a duplicate tab and screen-reader stop on each control. Tooltips now merge onto the real interactive element (asChild), icon-only triggers that had no accessible name get an aria-label (the mobile "more actions" menu no longer announces itself as "Downloads"), two stray tabIndex attributes on decorative icons are dropped, and tooltips open on keyboard focus of the actual control. Closing the search dialog no longer leaves its tooltip open over the trigger (#165).
  • The "back to top" button no longer fades out of the page margin on load. It is hidden by opacity-0 and carries a transition-opacity, so on any frame where the stylesheet is absent it painted at full opacity and then animated away once the sheet landed. That frame is not the first paint alone: the React hydration recovery (#126) re-renders the head and briefly drops the stylesheet after the component has mounted, which is why gating the transition on mount cannot stop it. The critical CSS now pins the button to opacity: 0 on the same zero-specificity terms as the toggle's close icon, and the WebKit FOUC guard asserts it — with the rule the button never paints, without it the control sees it at full opacity. Measured with the stylesheet delayed: 17–18 animating frames before, none after. Supersedes the useMounted approach in #141.
  • The WebKit FOUC guard no longer goes red for reasons unrelated to the critical CSS. Hydration currently fails on every page load (React #418/#423), and the recovery re-render restores the inlined critical <style> 150–240ms after DOMContentLoaded — after the control test has deliberately stripped it from the served HTML to prove the guard is meaningful. The measurement used to run from the test after domcontentloaded, so on a loaded runner every control assertion flipped at once. It now samples from an init script that fires in-page on DOMContentLoaded, before hydration is even scheduled. Both cases also assert their own preconditions — that the strip actually matched, and whether the inline block is present as sampled — so a reshaped CRITICAL_CSS reports as a stale strip pattern instead of as a run of confusing failures about grid layout. The underlying hydration failure remains open in #126; carried over from #141.

Dependencies

  • @fontsource/pt-serif 5.3.0 self-hosts the PT Serif heading face (400/700, upright and italic), routed through the same Remix/esbuild pipeline as Source Sans 3, so no Google Fonts request (#166).