Skip to content

UI/UX Revamped, Code Rafactor #6

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 8 commits into
base: main
Choose a base branch
from
46 changes: 27 additions & 19 deletions src/components/footer.tsx
Original file line number Diff line number Diff line change
@@ -1,41 +1,49 @@
import { ExternalLink, Github, Heart } from "lucide-react";

export function Footer() {
const year = new Date().getFullYear();

return (
<footer className="mt-auto border-t border-slate-200/60 dark:border-slate-700/60 bg-white/70 dark:bg-slate-800/70 backdrop-blur-sm">
<footer className="mt-auto border-t border-slate-200 dark:border-slate-800">
<div className="container mx-auto px-4 py-6 max-w-6xl">
<div className="flex flex-col sm:flex-row items-center justify-between gap-4 text-sm text-slate-600 dark:text-slate-400">
{/* Left side - Author info */}
{/* Left */}
<div className="flex items-center gap-2">
<span>Built with</span>
<Heart className="h-4 w-4 text-red-500 fill-current animate-pulse" />
<span>by</span>
<a
href="https://usmans.me"
target="_blank"
rel="noopener noreferrer"
className="font-medium text-slate-900 dark:text-slate-100 hover:text-blue-600 dark:hover:text-blue-400 transition-colors duration-200 flex items-center gap-1"
>
Usman S.
<ExternalLink className="h-3 w-3" />
</a>
<span>© {year} Whim</span>
<span className="hidden sm:inline text-slate-400">•</span>
<span className="flex items-center gap-1">
Built by
<a
href="https://usmans.me"
target="_blank"
rel="noopener noreferrer"
className="inline-flex items-center gap-1 font-medium text-slate-800 dark:text-slate-200 hover:text-indigo-600 dark:hover:text-indigo-400 transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-indigo-500/30 rounded"
>
Usman S.
<ExternalLink className="h-3.5 w-3.5 opacity-70" aria-hidden="true" />
</a>
<Heart className="h-3.5 w-3.5 text-rose-500/80 ml-1" aria-hidden="true" />
</span>
</div>

{/* Right side - Open source info */}
{/* Right */}
<div className="flex items-center gap-4">
<span className="text-xs">Open Source</span>
<span className="text-xs">Open source</span>
<a
href="https://github.com/max-programming/whim"
target="_blank"
rel="noopener noreferrer"
className="flex items-center gap-2 px-3 py-1.5 rounded-full bg-slate-100/80 dark:bg-slate-700/80 hover:bg-slate-200/80 dark:hover:bg-slate-600/80 transition-all duration-200 text-slate-700 dark:text-slate-300"
aria-label="View Whim on GitHub"
className="inline-flex items-center gap-2 text-slate-700 dark:text-slate-300 hover:text-slate-900 dark:hover:text-white transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-indigo-500/30 rounded"
>
<Github className="h-4 w-4" />
<span className="text-xs font-medium">View on GitHub</span>
<span className="text-xs font-medium underline underline-offset-4 decoration-slate-300/70 hover:decoration-current">
View on GitHub
</span>
</a>
</div>
</div>
</div>
</footer>
);
}
}
109 changes: 35 additions & 74 deletions src/components/landing/landing-hero.tsx
Original file line number Diff line number Diff line change
@@ -1,91 +1,52 @@
import { Clock, Lock, Shield } from "lucide-react";
import { Card, CardContent } from "~/components/ui/card";

export function LandingHero() {
return (
<div className="space-y-9">
{/* Brand Badge with Whim */}
<div className="inline-flex items-center gap-2 bg-indigo-50 dark:bg-indigo-900/30 px-3 py-1.5 rounded-full text-indigo-700 dark:text-indigo-300 font-medium text-sm border border-indigo-100 dark:border-indigo-800">
<img src="/favicon-32x32.png" alt="Whim" className="w-6 h-6" />
Whim
<div className="space-y-8">
<div className="flex justify-center">
<div className="inline-flex items-center gap-2 bg-slate-300 dark:bg-slate-800 px-3 py-1.5 rounded-full">
<img src="/favicon-32x32.png" alt="Whim" className="w-4 h-4" />
<span className="text-sm font-medium text-slate-600 dark:text-slate-400">
Whim
</span>
</div>
</div>

{/* Headline */}
<div className="space-y-3">
<h1 className="text-3xl lg:text-4xl xl:text-5xl font-bold text-slate-900 dark:text-slate-100 leading-tight">
Share Secrets
<span className="text-indigo-600 dark:text-indigo-400 block">
Safely & Securely
<div className="space-y-4 text-center">
<h1 className="text-3xl font-semibold lg:text-4xl xl:text-5xl text-slate-900 dark:text-white capitalize">
Send secrets that
<span className="block text-indigo-600 dark:text-indigo-400">
disappear after they're read
</span>
</h1>

<p className="text-base lg:text-lg text-slate-600 dark:text-slate-300 leading-relaxed max-w-md">
Share sensitive information on a{" "}
<span className="font-medium text-slate-700 dark:text-slate-200">
whim
</span>{" "}
- your secrets automatically self-destruct after being read or when
time expires. Perfect for one-time sharing of API keys, passwords, and
confidential data.
<p className="text-base lg:text-lg text-slate-600 dark:text-slate-400 leading-relaxed max-w-xl mx-auto">
Securely share passwords, API keys, or confidential notes in a single-use,
encrypted message. Once opened, it’s gone forever — private, safe, and simple.
</p>
</div>

{/* Essential Features - Condensed on Mobile */}
<div className="grid grid-cols-3 gap-2 sm:gap-3">
<Card className="py-2 sm:py-4 shadow-sm border-2 border-slate-200 dark:border-slate-700 bg-slate-50 dark:bg-slate-800/50 hover:border-indigo-200 dark:hover:border-indigo-700 transition-colors">
<CardContent className="px-2 sm:px-4 py-0">
<div className="text-center space-y-1 sm:space-y-2">
<div className="flex justify-center">
<Shield className="w-4 h-4 sm:w-6 sm:h-6 text-indigo-600 dark:text-indigo-400" />
</div>
<div>
<div className="font-semibold text-xs sm:text-sm text-slate-900 dark:text-slate-100">
Encrypted
</div>
<div className="text-xs sm:text-xs text-slate-500 dark:text-slate-400 mt-0.5 sm:mt-1">
End-to-end encrypted
</div>
</div>
</div>
</CardContent>
</Card>

<Card className="py-2 sm:py-4 shadow-sm border-2 border-slate-200 dark:border-slate-700 bg-slate-50 dark:bg-slate-800/50 hover:border-indigo-200 dark:hover:border-indigo-700 transition-colors">
<CardContent className="px-2 sm:px-4 py-0">
<div className="text-center space-y-1 sm:space-y-2">
<div className="flex justify-center">
<Clock className="w-4 h-4 sm:w-6 sm:h-6 text-indigo-600 dark:text-indigo-400" />
</div>
<div>
<div className="font-semibold text-xs sm:text-sm text-slate-900 dark:text-slate-100">
Self-Destruct
</div>
<div className="text-xs sm:text-xs text-slate-500 dark:text-slate-400 mt-0.5 sm:mt-1">
Deleted after reading (once or multiple times)
</div>
</div>
</div>
</CardContent>
</Card>
<div className="flex flex-col lg:flex-row items-center justify-center gap-4 lg:gap-8">
<div className="flex items-center gap-2 text-sm text-slate-600 dark:text-slate-400">
<Shield className="w-4 h-4 text-slate-400" />
<span>AES-256 encrypted</span>
</div>
<div className="flex items-center gap-2 text-sm text-slate-600 dark:text-slate-400">
<Clock className="w-4 h-4 text-slate-400" />
<span>Auto-destructs</span>
</div>
<div className="flex items-center gap-2 text-sm text-slate-600 dark:text-slate-400">
<Lock className="w-4 h-4 text-slate-400" />
<span>OTP protected</span>
</div>
</div>

<Card className="py-2 sm:py-4 shadow-sm border-2 border-slate-200 dark:border-slate-700 bg-slate-50 dark:bg-slate-800/50 hover:border-indigo-200 dark:hover:border-indigo-700 transition-colors">
<CardContent className="px-2 sm:px-4 py-0">
<div className="text-center space-y-1 sm:space-y-2">
<div className="flex justify-center">
<Lock className="w-4 h-4 sm:w-6 sm:h-6 text-indigo-600 dark:text-indigo-400" />
</div>
<div>
<div className="font-semibold text-xs sm:text-sm text-slate-900 dark:text-slate-100">
Password Protected
</div>
<div className="text-xs sm:text-xs text-slate-500 dark:text-slate-400 mt-0.5 sm:mt-1">
OTP required
</div>
</div>
</div>
</CardContent>
</Card>
<div className="text-center">
<p className="text-xs text-slate-500 dark:text-slate-500">
Open source • Zero knowledge • No registration required
</p>
</div>
</div>
);
}
}
184 changes: 59 additions & 125 deletions src/components/landing/landing-process-flow.tsx
Original file line number Diff line number Diff line change
@@ -1,137 +1,71 @@
import { Clock, Edit3, Eye, Link2, Shield, Zap } from "lucide-react";
import { Card, CardContent, CardHeader, CardTitle } from "~/components/ui/card";
import { Edit3, Shield, Link2, Eye, Zap } from "lucide-react";

export function LandingProcessFlow() {
return (
<div>
<Card className="shadow-sm border-2 border-slate-200 dark:border-slate-700 bg-slate-50/50 dark:bg-slate-800/30 hover:border-indigo-200 dark:hover:border-indigo-700 transition-colors">
<CardHeader className="pb-4">
<CardTitle className="text-xl text-slate-900 dark:text-slate-100 flex items-center gap-2">
<Shield className="w-5 h-5 text-indigo-600 dark:text-indigo-400" />
How It Works
</CardTitle>
</CardHeader>
<CardContent className="space-y-4">
{/* Step 1 */}
<div className="flex items-start gap-3">
<div className="flex-shrink-0 w-8 h-8 bg-indigo-100 dark:bg-indigo-900/50 rounded-full flex items-center justify-center">
<span className="text-indigo-600 dark:text-indigo-400 font-semibold text-sm">
1
</span>
</div>
<div className="flex-1">
<div className="flex items-center gap-2 mb-1">
<Edit3 className="w-4 h-4 text-indigo-600 dark:text-indigo-400" />
<h3 className="font-semibold text-sm text-slate-900 dark:text-slate-100">
Write Your Secret
</h3>
</div>
<p className="text-sm text-slate-600 dark:text-slate-300">
Type your sensitive information (API keys, passwords, private
notes) into the secure form.
</p>
</div>
</div>

{/* Step 2 */}
<div className="flex items-start gap-3">
<div className="flex-shrink-0 w-8 h-8 bg-indigo-100 dark:bg-indigo-900/50 rounded-full flex items-center justify-center">
<span className="text-indigo-600 dark:text-indigo-400 font-semibold text-sm">
2
</span>
</div>
<div className="flex-1">
<div className="flex items-center gap-2 mb-1">
<Shield className="w-4 h-4 text-indigo-600 dark:text-indigo-400" />
<h3 className="font-semibold text-sm text-slate-900 dark:text-slate-100">
Encrypt & Generate
</h3>
</div>
<p className="text-sm text-slate-600 dark:text-slate-300">
Your secret is encrypted end-to-end and a unique URL + one-time
password (OTP) are generated.
</p>
</div>
</div>
const steps = [
{
icon: Edit3,
title: "Write your secret",
description: "Enter your sensitive information in the secure form",
},
{
icon: Shield,
title: "Encrypt automatically",
description: "Your message is encrypted with AES-256 before leaving your browser",
},
{
icon: Link2,
title: "Share credentials",
description: "Send the unique URL and OTP to your recipient",
},
{
icon: Eye,
title: "Recipient views once",
description: "They access the secret with the OTP for the set number of times",
},
{
icon: Zap,
title: "Auto-destruction",
description: "The secret vanishes forever after viewing",
isLast: true,
},
];

{/* Step 3 */}
<div className="flex items-start gap-3">
<div className="flex-shrink-0 w-8 h-8 bg-indigo-100 dark:bg-indigo-900/50 rounded-full flex items-center justify-center">
<span className="text-indigo-600 dark:text-indigo-400 font-semibold text-sm">
3
</span>
</div>
<div className="flex-1">
<div className="flex items-center gap-2 mb-1">
<Link2 className="w-4 h-4 text-indigo-600 dark:text-indigo-400" />
<h3 className="font-semibold text-sm text-slate-900 dark:text-slate-100">
Share the Link & OTP
</h3>
</div>
<p className="text-sm text-slate-600 dark:text-slate-300">
Send the URL and OTP to your recipient through separate channels
for maximum security.
</p>
</div>
</div>

{/* Step 4 */}
<div className="flex items-start gap-3">
<div className="flex-shrink-0 w-8 h-8 bg-indigo-100 dark:bg-indigo-900/50 rounded-full flex items-center justify-center">
<span className="text-indigo-600 dark:text-indigo-400 font-semibold text-sm">
4
</span>
</div>
<div className="flex-1">
<div className="flex items-center gap-2 mb-1">
<Eye className="w-4 h-4 text-indigo-600 dark:text-indigo-400" />
<h3 className="font-semibold text-sm text-slate-900 dark:text-slate-100">
Limited Access
</h3>
return (
<div className="space-y-4">
<div className="space-y-3">
{steps.map((step, index) => (
<div key={index} className="flex gap-4">
<div className="flex-shrink-0">
<div className={`
w-8 h-8 rounded-full flex items-center justify-center text-sm
${step.isLast
? 'bg-red-50 dark:bg-red-950/20 text-red-600 dark:text-red-400'
: 'bg-slate-100 dark:bg-slate-800 text-slate-600 dark:text-slate-400'
}
`}>
{index + 1}
</div>
<p className="text-sm text-slate-600 dark:text-slate-300">
The recipient opens the link, enters the OTP, and views your
secret for the allowed number of times.
</p>
</div>
</div>

{/* Step 5 */}
<div className="flex items-start gap-3">
<div className="flex-shrink-0 w-8 h-8 bg-red-100 dark:bg-red-900/50 rounded-full flex items-center justify-center">
<span className="text-red-600 dark:text-red-400 font-semibold text-sm">
5
</span>
</div>
<div className="flex-1">
<div className="flex items-center gap-2 mb-1">
<Zap className="w-4 h-4 text-red-600 dark:text-red-400" />
<h3 className="font-semibold text-sm text-slate-900 dark:text-slate-100">
Automatic Destruction
</h3>
<div className="flex-1 space-y-1">
<div className="flex items-center gap-2">
<step.icon className="w-3 h-3 text-slate-400" />
<h4 className="text-sm font-medium text-slate-900 dark:text-white">
{step.title}
</h4>
</div>
<p className="text-sm text-slate-600 dark:text-slate-300">
The secret is permanently deleted from our servers after all
allowed accesses are used.
<p className="text-xs text-slate-500 dark:text-slate-500 leading-relaxed">
{step.description}
</p>
</div>
</div>
))}
</div>

{/* Security Note */}
<div className="bg-indigo-50 dark:bg-indigo-900/20 border border-indigo-200 dark:border-indigo-800 rounded-lg p-3 mt-4">
<div className="flex items-start gap-2">
<Clock className="w-4 h-4 text-indigo-600 dark:text-indigo-400 mt-0.5 flex-shrink-0" />
<div className="text-sm text-indigo-800 dark:text-indigo-200">
<p className="font-medium mb-1">Zero-Knowledge Security</p>
<p className="text-indigo-700 dark:text-indigo-300">
Your secret is encrypted in your browser before being sent to
our servers. We never see your data in plain text.
</p>
</div>
</div>
</div>
</CardContent>
</Card>
<div className="pt-3 border-t border-slate-200 dark:border-slate-800">
<p className="text-xs text-slate-500 dark:text-slate-500">
Zero-knowledge architecture • We never see your unencrypted data
</p>
</div>
</div>
);
}
}
Loading
Loading