From bbd3e32c3595695985d631a52cef492e5fe4bed7 Mon Sep 17 00:00:00 2001 From: Alem Tuzlak Date: Thu, 6 Feb 2025 10:48:19 +0100 Subject: [PATCH 1/6] Client hints added to base-stack --- app/root.tsx | 8 +++++--- app/services/client-hints.tsx | 37 +++++++++++++++++++++++++++++++++++ package.json | 3 ++- pnpm-lock.yaml | 8 ++++++++ 4 files changed, 52 insertions(+), 4 deletions(-) create mode 100644 app/services/client-hints.tsx diff --git a/app/root.tsx b/app/root.tsx index b560c11d8..96e39865b 100644 --- a/app/root.tsx +++ b/app/root.tsx @@ -4,11 +4,13 @@ import type { LinksFunction } from "react-router" import { useChangeLanguage } from "remix-i18next/react" import type { Route } from "./+types/root" import { LanguageSwitcher } from "./library/language-switcher" +import { ClientHintCheck, getHints } from "./services/client-hints" import tailwindcss from "./tailwind.css?url" -export async function loader({ context }: Route.LoaderArgs) { +export async function loader({ context, request }: Route.LoaderArgs) { const { lang, clientEnv } = context - return { lang, clientEnv } + const hints = getHints(request) + return { lang, clientEnv, hints } } export const links: LinksFunction = () => [{ rel: "stylesheet", href: tailwindcss }] @@ -20,7 +22,6 @@ export const handle = { export default function App({ loaderData }: Route.ComponentProps) { const { lang, clientEnv } = loaderData useChangeLanguage(lang) - return ( <> @@ -44,6 +45,7 @@ export const Layout = ({ children }: { children: React.ReactNode }) => { {children} + diff --git a/app/services/client-hints.tsx b/app/services/client-hints.tsx new file mode 100644 index 000000000..865d153fc --- /dev/null +++ b/app/services/client-hints.tsx @@ -0,0 +1,37 @@ +import { getHintUtils } from "@epic-web/client-hints" +import { clientHint as colorSchemeHint, subscribeToSchemeChange } from "@epic-web/client-hints/color-scheme" +import { clientHint as reducedMotionHint, subscribeToMotionChange } from "@epic-web/client-hints/reduced-motion" +import { clientHint as timeZoneHint } from "@epic-web/client-hints/time-zone" +import { useEffect } from "react" +import { useRevalidator, useRouteLoaderData } from "react-router" +import type { Route } from "../+types/root" + +export const { getHints, getClientHintCheckScript } = getHintUtils({ + theme: colorSchemeHint, + timeZone: timeZoneHint, + reducedMotion: reducedMotionHint, + // add other hints here +}) + +export const getTimeZone = (request?: Request) => getHints(request).timeZone + +export function useHints() { + const requestInfo = useRouteLoaderData("root") + return requestInfo?.hints +} + +export function ClientHintCheck({ nonce }: { nonce?: string }) { + const { revalidate } = useRevalidator() + useEffect(() => subscribeToSchemeChange(() => revalidate()), [revalidate]) + useEffect(() => subscribeToMotionChange(() => revalidate()), [revalidate]) + + return ( +