diff --git a/apps/public/src/app/carousel.tsx b/apps/public/src/app/carousel.tsx
index f26569d0..b01e3975 100644
--- a/apps/public/src/app/carousel.tsx
+++ b/apps/public/src/app/carousel.tsx
@@ -34,39 +34,36 @@ const images = [
{ title: 'The classic pie chart', url: '/demo/pie-min.png' },
];
-export function HomeCarousel() {
+export function PreviewCarousel() {
return (
-
-
-
-
-
- {images.map((item) => (
-
-
-
-
-
- ))}
-
-
-
-
-
-
+
+
+ {images.map((item) => (
+
+
+
+ ))}
+
+
+
+
);
}
diff --git a/apps/public/src/app/copy.tsx b/apps/public/src/app/copy.tsx
index 59f8c287..95fd7d82 100644
--- a/apps/public/src/app/copy.tsx
+++ b/apps/public/src/app/copy.tsx
@@ -25,7 +25,9 @@ export function Paragraph({ children, className }: Props) {
export function Heading1({ children, className }: Props) {
return (
-
+
{children}
);
@@ -33,8 +35,20 @@ export function Heading1({ children, className }: Props) {
export function Heading2({ children, className }: Props) {
return (
-
+
{children}
);
}
+
+export function Heading3({ children, className }: Props) {
+ return (
+
+ {children}
+
+ );
+}
diff --git a/apps/public/src/app/hero.tsx b/apps/public/src/app/hero.tsx
new file mode 100644
index 00000000..c04c0e9f
--- /dev/null
+++ b/apps/public/src/app/hero.tsx
@@ -0,0 +1,79 @@
+// background-image: radial-gradient(circle at 1px 1px, black 1px, transparent 0);
+// background-size: 40px 40px;
+
+import { Logo } from '@/components/Logo';
+import {
+ BarChart2Icon,
+ CookieIcon,
+ Globe2Icon,
+ LayoutPanelTopIcon,
+ LockIcon,
+} from 'lucide-react';
+
+import { Heading1, Lead, Lead2 } from './copy';
+import { JoinWaitlist } from './join-waitlist';
+
+const features = [
+ {
+ title: 'Great overview',
+ icon: LayoutPanelTopIcon,
+ },
+ {
+ title: 'Beautiful charts',
+ icon: BarChart2Icon,
+ },
+ {
+ title: 'Privacy focused',
+ icon: LockIcon,
+ },
+ {
+ title: 'Open-source',
+ icon: Globe2Icon,
+ },
+ {
+ title: 'No cookies',
+ icon: CookieIcon,
+ },
+];
+
+export function Hero() {
+ return (
+
+
+
+
+
+
+ A open-source
+
+ alternative to Mixpanel
+
+
+ Combine Mixpanel and Plausible and you get Openpanel. A simple
+ analytics tool that respects privacy.
+
+
+
+ {features.map(({ icon: Icon, title }) => (
+
+
+ {title}
+
+ ))}
+
+
+
+
+ );
+}
diff --git a/apps/public/src/app/join-waitlist.tsx b/apps/public/src/app/join-waitlist.tsx
index 162cd5d8..90ff8051 100644
--- a/apps/public/src/app/join-waitlist.tsx
+++ b/apps/public/src/app/join-waitlist.tsx
@@ -10,8 +10,13 @@ import {
DialogHeader,
DialogTitle,
} from '@/components/ui/dialog';
+import { cn } from '@/utils/cn';
-export function JoinWaitlist() {
+interface JoinWaitlistProps {
+ className?: string;
+}
+
+export function JoinWaitlist({ className }: JoinWaitlistProps) {
const [value, setValue] = useState('');
const [open, setOpen] = useState(false);
@@ -59,7 +64,10 @@ export function JoinWaitlist() {
setValue(e.target.value)}
/>
diff --git a/apps/public/src/app/layout.tsx b/apps/public/src/app/layout.tsx
index e2271db5..9f09c9f5 100644
--- a/apps/public/src/app/layout.tsx
+++ b/apps/public/src/app/layout.tsx
@@ -3,6 +3,7 @@ import { cn } from '@/utils/cn';
import '@/styles/globals.css';
import type { Metadata } from 'next';
+import { Bricolage_Grotesque } from 'next/font/google';
import Script from 'next/script';
import { defaultMeta } from './meta';
@@ -14,6 +15,12 @@ export const metadata: Metadata = {
},
};
+const font = Bricolage_Grotesque({
+ display: 'swap',
+ subsets: ['latin'],
+ weights: [400, 700],
+});
+
export default async function RootLayout({
children,
}: {
@@ -21,7 +28,12 @@ export default async function RootLayout({
}) {
return (
-
+
{children}