Skip to content

Instantly share code, notes, and snippets.

@nathanaelphilip
Created July 14, 2026 19:00
Show Gist options
  • Select an option

  • Save nathanaelphilip/bc91fe358e5589c5c5c914a981a855ab to your computer and use it in GitHub Desktop.

Select an option

Save nathanaelphilip/bc91fe358e5589c5c5c914a981a855ab to your computer and use it in GitHub Desktop.
clock.tsx
"use client";
import { useEffect, useRef, useState } from "react";
export default function Clock() {
const reftime = useRef(new Date());
const [time, setTime] = useState(new Date());
useEffect(() => {
const id = setInterval(() => (reftime.current = new Date()), 16);
return () => clearInterval(id);
}, []);
useEffect(() => {
const id = setInterval(() => setTime(reftime.current), 1000);
return () => clearInterval(id);
}, []);
const hours = time.getHours() % 12;
const minutes = time.getMinutes();
const seconds = time.getSeconds();
const secondDeg = seconds * 6; // 360 / 60
const minuteDeg = minutes * 6 + seconds * 0.1; // + carry from seconds
const hourDeg = hours * 30 + minutes * 0.5; // 360 / 12, + carry from minutes
return (
<div className="relative rounded-full border-b border-2 w-40 h-40 mx-auto bg-gray-50 shadow-2xl">
<div className="absolute top-[50%] left-[50%] -translate-x-1/2 -translate-y-1/2">
<div
id="hour"
className={`w-0.5 h-8 absolute left-[50%] -translate-y-1 bottom-0 bg-gray-900 -translate-x-1/2 rotate-0 origin-[50%_100%]`}
style={{ rotate: `${hourDeg}deg` }}
/>
<div
id="minute"
className="w-0.5 h-12 absolute left-[50%] -translate-y-1 bottom-0 bg-gray-900 -translate-x-1/2 rotate-0 origin-[50%_100%]"
style={{ rotate: `${minuteDeg}deg` }}
/>
<div
id="second"
className="w-px h-16 transition-all duration-75 absolute left-[50%] -translate-y-1 bottom-0 bg-gray-900 -translate-x-1/2 rotate-0 origin-[50%_100%]"
style={{ rotate: `${secondDeg}deg` }}
/>
<div className="bg-gray-900 w-2 h-2 rounded-full" />
</div>
</div>
);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment