useWindowSize
Layout/Viewport
A React hook that tracks the browser window dimensions in real-time, perfect for responsive layouts and dynamic UI adjustments.
Demo
Try resizing your browser window to see the dimensions update in real-time:
Window Width
0px
Window Height
0px
Responsive Breakpoints
Mobile (<640px): Active
Small (≥640px): Inactive
Medium (≥768px): Inactive
Large (≥1024px): Inactive
Extra Large (≥1280px): Inactive
Aspect Ratio
NaN(width / height)
Installation
npm install @thibault.sh/hooks
Usage
import { useWindowSize } from '@thibault.sh/hooks/useWindowSize';
function ResponsiveComponent() {
const { width, height } = useWindowSize();
return (
<div>
<p>Window dimensions: {width}x{height}</p>
{width < 768 ? (
<MobileLayout />
) : (
<DesktopLayout />
)}
</div>
);
}
API
Returns
Object containing current window width and height
Features
- ✓Real-time Updates
Automatically updates when window dimensions change
- ✓SSR Compatible
Safely handles server-side rendering with default dimensions
- ✓Performance Optimized
Uses debounced resize event listener to prevent excessive re-renders
- ✓Type Safe
Full TypeScript support with proper type definitions
Responsive Grid Example
import { useWindowSize } from '@thibault.sh/hooks/useWindowSize';
function ResponsiveGrid({ items }: { items: Array<any> }) {
const { width } = useWindowSize();
// Calculate optimal number of columns based on window width
const columns = Math.max(1, Math.floor(width / 300)); // 300px min column width
const gridStyle = {
display: 'grid',
gridTemplateColumns: `repeat(${columns}, 1fr)`,
gap: '1rem'
};
return (
<div style={gridStyle}>
{items.map((item, index) => (
<div key={index} className="card">
{/* Card content */}
</div>
))}
</div>
);
}
Dynamic Canvas Example
import { useWindowSize } from '@thibault.sh/hooks/useWindowSize';
import { useEffect, useRef } from 'react';
function ResponsiveCanvas() {
const { width, height } = useWindowSize();
const canvasRef = useRef<HTMLCanvasElement>(null);
useEffect(() => {
const canvas = canvasRef.current;
if (!canvas) return;
// Update canvas dimensions
canvas.width = width;
canvas.height = height;
// Get context and draw
const ctx = canvas.getContext('2d');
if (!ctx) return;
// Example: Draw a responsive circle in the center
const centerX = width / 2;
const centerY = height / 2;
const radius = Math.min(width, height) / 4;
ctx.beginPath();
ctx.arc(centerX, centerY, radius, 0, Math.PI * 2);
ctx.fillStyle = '#f97316';
ctx.fill();
}, [width, height]);
return <canvas ref={canvasRef} />;
}
Conditional Rendering Example
import { useWindowSize } from '@thibault.sh/hooks/useWindowSize';
function AdaptiveUI() {
const { width } = useWindowSize();
const isMobile = width < 768;
const isTablet = width >= 768 && width < 1024;
const isDesktop = width >= 1024;
return (
<div>
{isMobile && (
<nav className="mobile-nav">
<HamburgerMenu />
</nav>
)}
{isTablet && (
<nav className="tablet-nav">
<IconMenu />
</nav>
)}
{isDesktop && (
<nav className="desktop-nav">
<FullMenu />
</nav>
)}
<main className={
isDesktop ? 'p-8' :
isTablet ? 'p-6' :
'p-4'
}>
{/* Content */}
</main>
</div>
);
}