Isaiah

BJORK Solar sky panel

Component

About

Solar sky panel is a production-ready cards component from BJORK UI, packaged for shadcn registries.

Built with React and Tailwind. Copy the prompt and paste it into Claude Code, Cursor or Lovable: your agent adds BJORK Solar sky panel to your project and fits it to your theme.

Code

How BJORK Solar sky panel is used: the demo's code. The component's own source comes with a free account.

Usage.tsx

"use client";
import { ThemeProvider as BjorkDemoThemeProvider } from "next-themes";
import { useState } from "react";
import { SolarSkyPanel } from "@/components/ui/bjork-solar-sky-panel";

const PLACES = [
  { label: "Reykjavík", latitude: 64.1466, longitude: -21.9426, timeZone: "Atlantic/Reykjavik" },
  { label: "Austin", latitude: 30.2672, longitude: -97.7431, timeZone: "America/Chicago" },
  { label: "Tokyo", latitude: 35.6762, longitude: 139.6503, timeZone: "Asia/Tokyo" },
];

const PREVIEW_LOCAL = "2026-06-21T19:30";

function zonedInstant(local: string, zone: string): Date {
  const [day, time] = local.split("T");
  const [y, m, d] = day.split("-").map(Number);
  const [hh, mm] = time.split(":").map(Number);
  const asUtc = Date.UTC(y, m - 1, d, hh, mm);
  const formatter = new Intl.DateTimeFormat("en-US", {
    timeZone: zone,
    hourCycle: "h23",
    year: "numeric",
    month: "numeric",
    day: "numeric",
    hour: "numeric",
    minute: "numeric",
  });
  const p: Record<string, number> = {};
  for (const part of formatter.formatToParts(asUtc)) {
    if (part.type !== "literal") p[part.type] = Number(part.value);
  }
  const offset = Date.UTC(p.year, p.month - 1, p.day, p.hour % 24, p.minute) - asUtc;
  return new Date(asUtc - offset);
}
function SourceDemo(){
const isPreview = false;
const [day, setDay] = useState("");
const [returnToNow, setReturnToNow] = useState(true);
const panelDate = (zone: string) => {
    if (isPreview) return zonedInstant(PREVIEW_LOCAL, zone);
    // A chosen day opens at noon in each place's zone. Empty means live: the clock, refreshed every minute.
    return day ? zonedInstant(`${day}T12:00`, zone) : undefined;
  };
const reset = () => {
    setDay("");
    setReturnToNow(true);
  };
return <>

      <div className="flex w-full min-w-0 flex-col items-center gap-5">
        <div className="flex w-full max-w-[920px] flex-wrap justify-center gap-4">
          {PLACES.map((place) => (
            <SolarSkyPanel
              key={place.timeZone}
              latitude={place.latitude}
              longitude={place.longitude}
              locationLabel={place.label}
              timeZone={place.timeZone}
              date={panelDate(place.timeZone)}
              returnToNow={returnToNow}
              className="w-full sm:w-[280px]"
            />
          ))}
        </div>
      </div>
    
</>;
}
export default function BjorkRegistryPreview(){return <BjorkDemoThemeProvider attribute="class" defaultTheme="dark" enableSystem={false} storageKey="bjork-review-demo-theme"><div data-component-demo className="dark flex min-h-screen w-full items-center justify-center bg-[var(--bjork-bg)] p-8 text-[var(--bjork-text)]"><div className="w-full max-w-[850px]"><SourceDemo/></div></div></BjorkDemoThemeProvider>}

Dependencies

More by Isaiah

View all
  • Agent Plan

    Agent Plan

    2.2K
  • Video Scroll Hero

    Video Scroll Hero

    1.4K
  • Voice Powered Orb

    Voice Powered Orb

    1.3K
  • Reveal Text

    Reveal Text

    1.1K
  • Leads Data Table

    Leads Data Table

    935
  • Portfolio Gallery

    Portfolio Gallery

    923
  • Message Dock

    Message Dock

    833
  • Ruler Carousel

    Ruler Carousel

    618