Hooks
useMediaQuery
A React hook that tracks a CSS media query and returns a boolean that updates reactively as the viewport changes.
Pass any valid CSS media query string and get back a boolean that is true when the query matches. The value updates automatically whenever the viewport (or any other tracked media feature) changes.
SSR-safe — uses useIsomorphicLayoutEffect internally to avoid hydration warnings.
Installation
npx shadcn@latest add https://mksingh.dev/r/use-media-query-hook.jsonUsage
import { useMediaQuery } from '@/hooks/use-media-query'
export function MyComponent() {
const isMobile = useMediaQuery('(max-width: 768px)')
return <p>{isMobile ? 'Mobile' : 'Desktop'}</p>
}API
useMediaQuery(query: string, options?: UseMediaQueryOptions): booleanParameters
| Parameter | Type | Default | Description |
|---|---|---|---|
query | string | — | Any valid CSS media query, e.g. "(max-width: 768px)" |
options.defaultValue | boolean | false | Value returned on the server (no window) and as the initial state when initializeWithValue is false |
options.initializeWithValue | boolean | true | When true, the initial state is set by evaluating the query immediately on mount instead of waiting for the first effect |
Returns
boolean — true when the media query matches, false otherwise.
Examples
Responsive rendering
const isDesktop = useMediaQuery('(min-width: 1024px)')
return isDesktop ? <DesktopLayout /> : <MobileLayout />Dark mode preference
const prefersDark = useMediaQuery('(prefers-color-scheme: dark)')SSR-safe with a custom default
// Returns `false` on the server, then re-evaluates on the client.
const isLarge = useMediaQuery('(min-width: 1280px)', { defaultValue: false })Notes
- Supports Safari < 14 via the deprecated
addListener/removeListenerAPI with a graceful fallback toaddEventListener. - The query string is re-evaluated whenever it changes, so you can pass a dynamic query safely.