feat: Complete public frontend redesign - Award Winning UI
Some checks failed
CI / Frontend Lint & Type Check (push) Has been cancelled
CI / Frontend Build (push) Has been cancelled
CI / Backend Lint (push) Has been cancelled
CI / Backend Tests (push) Has been cancelled
CI / Docker Build (push) Has been cancelled
CI / Security Scan (push) Has been cancelled
Deploy / Build & Push Images (push) Has been cancelled
Deploy / Deploy to Server (push) Has been cancelled
Deploy / Notify (push) Has been cancelled

- Redesigned all public pages (Landing, Acquire, Discover, Yield, Pricing) to "Award Winning" tech-chic style
- Implemented auth pages (Login, Register, Forgot Password, Verify Email) with animated glow backgrounds
- Renamed routes: /market -> /acquire, /intel -> /discover
- Created footer pages: About, Contact, Briefings
- Created legal pages: Privacy Policy, Terms of Service, Imprint
- Updated Header & Footer components to match new design system
- Enhanced DomainChecker with typing animation and angular tech design
- All pages now feature: deep dark backgrounds, noise overlays, tech borders, glassmorphism effects
- Responsive design optimized for all screen sizes
- Consistent typography using font-display and font-mono throughout
This commit is contained in:
yves.gugger
2025-12-12 17:44:59 +01:00
parent b5c456af1c
commit 6cb985fa8b
20 changed files with 3127 additions and 2727 deletions

View File

@ -2,187 +2,158 @@
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { Target, Shield, Zap, Users, Globe, TrendingUp, ArrowRight } from 'lucide-react'
import { Target, Shield, Zap, Users, Globe, ArrowRight } from 'lucide-react'
import Link from 'next/link'
const values = [
{
icon: Target,
title: 'Precision',
description: 'Accurate data. No guesswork. Every check counts.',
},
{
icon: Shield,
title: 'Privacy',
description: 'Your strategy stays yours. We never share or sell data.',
},
{
icon: Zap,
title: 'Speed',
description: 'Real-time intel. You see it first.',
},
{
icon: Users,
title: 'Transparency',
description: 'Clear pricing. No surprises. Ever.',
},
]
const stats = [
{ value: '500K+', label: 'Domains Tracked' },
{ value: '99.9%', label: 'Uptime' },
{ value: '50ms', label: 'Response Time' },
{ value: '24/7', label: 'Always On' },
]
const team = [
{
name: 'Domain Intel',
role: 'Core',
description: 'WHOIS + RDAP queries. Accurate. Reliable. Always.',
},
{
name: 'Price Tracking',
role: 'Market',
description: 'Real-time TLD pricing. Know what domains cost.',
},
{
name: 'Instant Alerts',
role: 'Notify',
description: 'Domain drops? You know first. Email or webhook.',
},
{ value: '500K+', label: 'ASSETS TRACKED' },
{ value: '99.9%', label: 'SYSTEM UPTIME' },
{ value: '50ms', label: 'SCAN LATENCY' },
{ value: '24/7', label: 'LIVE MONITOR' },
]
export default function AboutPage() {
return (
<div className="min-h-screen bg-background relative flex flex-col">
{/* Ambient glow */}
<div className="fixed inset-0 pointer-events-none">
<div className="absolute top-0 left-1/2 -translate-x-1/2 w-[600px] h-[400px] bg-accent/[0.02] rounded-full blur-3xl" />
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none z-0">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div
className="absolute inset-0 opacity-[0.03]"
style={{
backgroundImage: `linear-gradient(rgba(255,255,255,0.3) 0.5px, transparent 0.5px), linear-gradient(90deg, rgba(255,255,255,0.3) 0.5px, transparent 0.5px)`,
backgroundSize: '160px 160px',
}}
/>
<div className="absolute top-0 left-1/2 -translate-x-1/2 w-[800px] h-[400px] bg-accent/[0.02] rounded-full blur-[120px]" />
</div>
<Header />
<main className="relative pt-32 sm:pt-36 pb-20 px-4 sm:px-6 flex-1">
<div className="max-w-4xl mx-auto">
<main className="relative pt-32 sm:pt-40 pb-20 px-4 sm:px-6 flex-1">
<div className="max-w-[1200px] mx-auto">
{/* Hero */}
<div className="text-center mb-16 sm:mb-20 animate-fade-in">
<div className="inline-flex items-center gap-2 px-3 py-1.5 bg-background-secondary/80 backdrop-blur-sm border border-border rounded-full mb-6">
<Globe className="w-4 h-4 text-accent" />
<span className="text-ui-sm text-foreground-muted">About pounce</span>
</div>
<h1 className="font-display text-[2.25rem] sm:text-[3rem] md:text-[3.75rem] leading-[1.1] tracking-[-0.035em] text-foreground mb-6">
<div className="text-center mb-20 sm:mb-28 animate-fade-in">
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block flex items-center justify-center gap-2">
<div className="w-1.5 h-1.5 bg-accent animate-pulse" />
Mission Briefing
</span>
<h1 className="font-display text-[3.5rem] sm:text-[5rem] md:text-[6rem] leading-[0.9] tracking-[-0.04em] text-white mb-8">
Built for hunters.
<br />
<span className="text-foreground-muted">By hunters.</span>
<span className="text-white/30">By hunters.</span>
</h1>
<p className="text-body-lg text-foreground-muted max-w-2xl mx-auto">
<p className="text-lg sm:text-xl text-white/50 max-w-2xl mx-auto font-light leading-relaxed">
POUNCE exists for one reason: to give you the edge.
Track domains. See opportunities. Move first.
Track assets. See opportunities. Move first.
</p>
</div>
{/* Stats */}
<div className="grid grid-cols-2 md:grid-cols-4 gap-4 mb-20 animate-slide-up">
{/* Stats Grid - Bento Style */}
<div className="grid grid-cols-2 md:grid-cols-4 gap-px bg-white/10 border border-white/10 mb-32 animate-slide-up">
{stats.map((stat) => (
<div
key={stat.label}
className="p-6 bg-background-secondary/50 border border-border rounded-xl text-center"
className="bg-[#020202] p-8 sm:p-10 text-center group hover:bg-[#050505] transition-colors"
>
<p className="text-heading-md sm:text-heading-lg font-display text-accent mb-1">
<div className="text-3xl sm:text-4xl font-display text-white mb-2 group-hover:text-accent transition-colors">
{stat.value}
</p>
<p className="text-ui-sm text-foreground-muted">{stat.label}</p>
</div>
<div className="text-[10px] font-mono uppercase tracking-widest text-white/30">{stat.label}</div>
</div>
))}
</div>
{/* Mission */}
<section className="mb-20 animate-slide-up">
<div className="p-8 sm:p-10 bg-gradient-to-br from-accent/10 via-accent/5 to-transparent border border-accent/20 rounded-2xl">
<h2 className="text-heading-sm sm:text-heading-md font-medium text-foreground mb-4">
The Mission
</h2>
<p className="text-body-lg text-foreground-muted leading-relaxed">
Level the playing field. Domain intel shouldn&apos;t be locked behind enterprise
paywalls. With POUNCE, anyone can track domains, spot trends, and strike
when the iron&apos;s hot. Simple tools. Powerful results.
<div className="grid lg:grid-cols-2 gap-16 lg:gap-24 items-center mb-32">
<div className="animate-slide-up">
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">The Objective</span>
<h2 className="font-display text-4xl sm:text-5xl text-white mb-8">Level the playing field.</h2>
<div className="space-y-6 text-white/60 text-lg font-light leading-relaxed">
<p>
Domain intelligence shouldn't be locked behind enterprise paywalls or hidden in archaic CLI tools.
</p>
<p>
We built POUNCE to democratize access to high-value digital assets. Whether you're a sniper looking for a single drop or a whale managing a portfolio, our tools give you the same firepower.
</p>
</div>
</section>
</div>
<div className="relative animate-scale-in delay-100">
<div className="absolute -inset-4 bg-accent/5 blur-2xl" />
<div className="relative border border-white/10 bg-[#050505] p-10">
<div className="absolute top-0 right-0 p-4">
<Globe className="w-12 h-12 text-white/10" />
</div>
<h3 className="font-display text-2xl text-white mb-6">Global Coverage</h3>
<ul className="space-y-4 font-mono text-sm text-white/50">
<li className="flex justify-between border-b border-white/5 pb-2">
<span>Registrars</span>
<span className="text-white">50+ Connected</span>
</li>
<li className="flex justify-between border-b border-white/5 pb-2">
<span>TLDs</span>
<span className="text-white">886 Supported</span>
</li>
<li className="flex justify-between border-b border-white/5 pb-2">
<span>Refresh Rate</span>
<span className="text-white">Real-time</span>
</li>
<li className="flex justify-between">
<span>Data Source</span>
<span className="text-white">WHOIS / RDAP / DNS</span>
</li>
</ul>
</div>
</div>
</div>
{/* Values */}
<section className="mb-20">
<h2 className="text-heading-sm sm:text-heading-md font-medium text-foreground mb-8 text-center">
Our Code
</h2>
<div className="grid sm:grid-cols-2 gap-4">
{values.map((value, i) => (
<div className="mb-32">
<h2 className="font-display text-3xl text-white text-center mb-16">Operational Code</h2>
<div className="grid sm:grid-cols-2 lg:grid-cols-4 gap-8">
{[
{ icon: Target, title: 'Precision', desc: 'Accurate data. No guesswork. Every check counts.' },
{ icon: Shield, title: 'Privacy', desc: 'Your strategy stays yours. We never share or sell data.' },
{ icon: Zap, title: 'Speed', desc: 'Real-time intel. You see it first.' },
{ icon: Users, title: 'Transparency', desc: 'Clear pricing. No surprises. Ever.' },
].map((value, i) => (
<div
key={value.title}
className="p-6 bg-background-secondary/50 border border-border rounded-xl hover:border-border-hover transition-all duration-300 animate-slide-up"
style={{ animationDelay: `${i * 100}ms` }}
className="p-8 border border-white/10 bg-[#050505] hover:border-accent/30 transition-all group"
>
<div className="w-10 h-10 bg-background-tertiary rounded-lg flex items-center justify-center mb-4">
<value.icon className="w-5 h-5 text-accent" />
</div>
<h3 className="text-body font-medium text-foreground mb-2">{value.title}</h3>
<p className="text-body-sm text-foreground-muted">{value.description}</p>
<value.icon className="w-8 h-8 text-white/20 group-hover:text-accent mb-6 transition-colors" />
<h3 className="font-display text-xl text-white mb-3">{value.title}</h3>
<p className="font-mono text-xs text-white/40 leading-relaxed">{value.desc}</p>
</div>
))}
</div>
</section>
{/* Features */}
<section className="mb-20">
<h2 className="text-heading-sm sm:text-heading-md font-medium text-foreground mb-8 text-center">
What We Do
</h2>
<div className="space-y-4">
{team.map((item, i) => (
<div
key={item.name}
className="p-6 bg-background-secondary/30 border border-border rounded-xl flex flex-col sm:flex-row sm:items-center gap-4 animate-slide-up"
style={{ animationDelay: `${i * 100}ms` }}
>
<div className="flex-1">
<div className="flex items-center gap-3 mb-2">
<h3 className="text-body font-medium text-foreground">{item.name}</h3>
<span className="text-ui-xs text-accent bg-accent-muted px-2 py-0.5 rounded-full">
{item.role}
</span>
</div>
<p className="text-body-sm text-foreground-muted">{item.description}</p>
</div>
</div>
))}
</div>
</section>
{/* CTA */}
<section className="text-center animate-slide-up">
<h2 className="text-heading-sm sm:text-heading-md font-medium text-foreground mb-4">
Ready to hunt?
</h2>
<p className="text-body text-foreground-muted mb-8">
Join the hunters who move first.
<div className="text-center bg-[#050505] border border-white/10 p-12 sm:p-20 relative overflow-hidden">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.05]" />
<div className="relative z-10">
<h2 className="font-display text-4xl sm:text-5xl text-white mb-6">Ready to deploy?</h2>
<p className="text-white/50 mb-10 max-w-lg mx-auto font-mono text-sm">
Join the elite circle of investors who stop guessing and start knowing.
</p>
<div className="flex flex-col sm:flex-row items-center justify-center gap-3">
<div className="flex flex-col sm:flex-row items-center justify-center gap-6">
<Link
href="/register"
className="flex items-center gap-2 px-6 py-3 bg-accent text-background font-medium rounded-xl hover:bg-accent-hover transition-all"
className="px-8 py-4 bg-accent text-black text-xs font-bold uppercase tracking-[0.2em] hover:bg-white transition-all shadow-[0_0_20px_rgba(16,185,129,0.2)]"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
Start Hunting
<ArrowRight className="w-4 h-4" />
</Link>
<Link
href="/contact"
className="flex items-center gap-2 px-6 py-3 bg-background-secondary border border-border text-foreground font-medium rounded-xl hover:border-border-hover transition-all"
className="px-8 py-4 border border-white/20 text-white text-xs font-bold uppercase tracking-[0.2em] hover:bg-white hover:text-black transition-all"
>
Get in Touch
Contact HQ
</Link>
</div>
</section>
</div>
</div>
</div>
</main>
@ -190,4 +161,3 @@ export default function AboutPage() {
</div>
)
}

View File

@ -0,0 +1,652 @@
'use client'
import { useEffect, useState, useMemo } from 'react'
import { useStore } from '@/lib/store'
import { api } from '@/lib/api'
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { PlatformBadge } from '@/components/PremiumTable'
import {
Clock,
ExternalLink,
Search,
Flame,
Timer,
Gavel,
DollarSign,
X,
Lock,
TrendingUp,
ChevronUp,
ChevronDown,
ChevronsUpDown,
Sparkles,
Diamond,
ShieldCheck,
Zap,
Filter,
Check,
Shield,
ArrowUpRight,
ArrowRight
} from 'lucide-react'
import Link from 'next/link'
import clsx from 'clsx'
interface MarketItem {
id: string
domain: string
tld: string
price: number
currency: string
price_type: 'bid' | 'fixed' | 'negotiable'
status: 'auction' | 'instant'
source: string
is_pounce: boolean
verified: boolean
time_remaining?: string
end_time?: string
num_bids?: number
slug?: string
seller_verified: boolean
url: string
is_external: boolean
pounce_score: number
}
interface Auction {
domain: string
platform: string
platform_url: string
current_bid: number
currency: string
num_bids: number
end_time: string
time_remaining: string
buy_now_price: number | null
reserve_met: boolean | null
traffic: number | null
age_years: number | null
tld: string
affiliate_url: string
}
type TabType = 'all' | 'ending' | 'hot'
type SortField = 'domain' | 'ending' | 'bid' | 'bids'
type SortDirection = 'asc' | 'desc'
const PLATFORMS = [
{ id: 'All', name: 'All Sources' },
{ id: 'GoDaddy', name: 'GoDaddy' },
{ id: 'Sedo', name: 'Sedo' },
{ id: 'NameJet', name: 'NameJet' },
{ id: 'DropCatch', name: 'DropCatch' },
]
// Premium TLDs that look professional
const PREMIUM_TLDS = ['com', 'io', 'ai', 'co', 'de', 'ch', 'net', 'org', 'app', 'dev', 'xyz']
// Vanity Filter: Only show "beautiful" domains to non-authenticated users
function isVanityDomain(auction: Auction): boolean {
const domain = auction.domain
const parts = domain.split('.')
if (parts.length < 2) return false
const name = parts[0]
const tld = parts.slice(1).join('.').toLowerCase()
// Check TLD is premium
if (!PREMIUM_TLDS.includes(tld)) return false
// Check length (max 12 characters for the name)
if (name.length > 12) return false
// No hyphens
if (name.includes('-')) return false
// No numbers (unless domain is 4 chars or less - short domains are valuable)
if (name.length > 4 && /\d/.test(name)) return false
return true
}
// Generate a mock "Deal Score" for display purposes
function getDealScore(auction: Auction): number | null {
let score = 50
const name = auction.domain.split('.')[0]
if (name.length <= 4) score += 20
else if (name.length <= 6) score += 10
if (['com', 'io', 'ai'].includes(auction.tld)) score += 15
if (auction.age_years && auction.age_years > 5) score += 10
if (auction.num_bids >= 20) score += 15
else if (auction.num_bids >= 10) score += 10
return Math.min(score, 100)
}
function SortIcon({ field, currentField, direction }: { field: SortField, currentField: SortField, direction: SortDirection }) {
if (field !== currentField) {
return <ChevronsUpDown className="w-3 h-3 text-white/20" />
}
return direction === 'asc'
? <ChevronUp className="w-3 h-3 text-accent" />
: <ChevronDown className="w-3 h-3 text-accent" />
}
export default function MarketPage() {
const { isAuthenticated, checkAuth, isLoading: authLoading } = useStore()
const [allAuctions, setAllAuctions] = useState<Auction[]>([])
const [endingSoon, setEndingSoon] = useState<Auction[]>([])
const [hotAuctions, setHotAuctions] = useState<Auction[]>([])
const [pounceItems, setPounceItems] = useState<MarketItem[]>([])
const [loading, setLoading] = useState(true)
const [activeTab, setActiveTab] = useState<TabType>('all')
const [sortField, setSortField] = useState<SortField>('ending')
const [sortDirection, setSortDirection] = useState<SortDirection>('asc')
const [searchQuery, setSearchQuery] = useState('')
const [selectedPlatform, setSelectedPlatform] = useState('All')
const [maxBid, setMaxBid] = useState('')
useEffect(() => {
checkAuth()
loadAuctions()
}, [checkAuth])
const loadAuctions = async () => {
setLoading(true)
try {
const [allFeed, endingFeed, hotFeed, pounceFeed] = await Promise.all([
api.getMarketFeed({ source: 'all', limit: 100, sortBy: 'time' }),
api.getMarketFeed({ source: 'external', endingWithin: 24, limit: 50, sortBy: 'time' }),
api.getMarketFeed({ source: 'external', limit: 50, sortBy: 'score' }),
api.getMarketFeed({ source: 'pounce', limit: 10 }),
])
const convertToAuction = (item: MarketItem): Auction => ({
domain: item.domain,
platform: item.source,
platform_url: item.url,
current_bid: item.price,
currency: item.currency,
num_bids: item.num_bids || 0,
end_time: item.end_time || '',
time_remaining: item.time_remaining || '',
buy_now_price: item.price_type === 'fixed' ? item.price : null,
reserve_met: null,
traffic: null,
age_years: null,
tld: item.tld,
affiliate_url: item.url,
})
const externalOnly = (items: MarketItem[]) => items.filter(i => !i.is_pounce).map(convertToAuction)
setAllAuctions(externalOnly(allFeed.items || []))
setEndingSoon(externalOnly(endingFeed.items || []))
setHotAuctions(externalOnly(hotFeed.items || []))
setPounceItems(pounceFeed.items || [])
} catch (error) {
console.error('Failed to load auctions:', error)
} finally {
setLoading(false)
}
}
const getCurrentAuctions = (): Auction[] => {
switch (activeTab) {
case 'ending': return endingSoon
case 'hot': return hotAuctions
default: return allAuctions
}
}
// Apply Vanity Filter for non-authenticated users
const displayAuctions = useMemo(() => {
const current = getCurrentAuctions()
if (isAuthenticated) {
return current
}
return current.filter(isVanityDomain)
}, [activeTab, allAuctions, endingSoon, hotAuctions, isAuthenticated])
const filteredAuctions = displayAuctions.filter(auction => {
if (searchQuery && !auction.domain.toLowerCase().includes(searchQuery.toLowerCase())) {
return false
}
if (selectedPlatform !== 'All' && auction.platform !== selectedPlatform) {
return false
}
if (maxBid && auction.current_bid > parseFloat(maxBid)) {
return false
}
return true
})
const handleSort = (field: SortField) => {
if (sortField === field) {
setSortDirection(sortDirection === 'asc' ? 'desc' : 'asc')
} else {
setSortField(field)
setSortDirection('asc')
}
}
const sortedAuctions = [...filteredAuctions].sort((a, b) => {
const modifier = sortDirection === 'asc' ? 1 : -1
switch (sortField) {
case 'domain':
return a.domain.localeCompare(b.domain) * modifier
case 'bid':
return (a.current_bid - b.current_bid) * modifier
case 'bids':
return (a.num_bids - b.num_bids) * modifier
default:
return 0
}
})
const formatCurrency = (amount: number, currency = 'USD') => {
return new Intl.NumberFormat('en-US', { style: 'currency', currency }).format(amount)
}
const getTimeColor = (timeRemaining: string) => {
if (timeRemaining.includes('m') && !timeRemaining.includes('h')) return 'text-red-400 font-bold'
if (timeRemaining.includes('h') && parseInt(timeRemaining) < 12) return 'text-amber-400 font-bold'
return 'text-white/40'
}
const hotPreview = hotAuctions.slice(0, 4)
if (authLoading) {
return (
<div className="min-h-screen flex items-center justify-center bg-[#020202]">
<div className="w-12 h-12 border-[0.5px] border-white/10 border-t-accent animate-spin rounded-full" />
</div>
)
}
return (
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Cinematic Background - Architectural & Fine */}
<div className="fixed inset-0 pointer-events-none z-0">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div
className="absolute inset-0 opacity-[0.03]"
style={{
backgroundImage: `linear-gradient(rgba(255,255,255,0.3) 0.5px, transparent 0.5px), linear-gradient(90deg, rgba(255,255,255,0.3) 0.5px, transparent 0.5px)`,
backgroundSize: '160px 160px',
}}
/>
<div className="absolute top-[-30%] left-1/2 -translate-x-1/2 w-[1200px] h-[800px] bg-accent/[0.02] rounded-full blur-[200px]" />
</div>
<Header />
<main className="relative pt-32 sm:pt-40 pb-20 sm:pb-28 px-4 sm:px-6 flex-1">
<div className="max-w-[1400px] mx-auto">
{/* Hero Header - High Tech */}
<div className="mb-16 sm:mb-20 animate-fade-in text-center lg:text-left">
<div className="flex flex-col lg:flex-row justify-between items-end gap-8 border-b border-white/[0.08] pb-12">
<div>
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block flex items-center gap-2 justify-center lg:justify-start">
<div className="w-1.5 h-1.5 bg-accent animate-pulse" />
Live Liquidity Pool
</span>
<h1 className="font-display text-[3.5rem] sm:text-[5rem] md:text-[6rem] lg:text-[7rem] leading-[0.9] tracking-[-0.04em] text-white">
Acquire Assets.
</h1>
<p className="mt-8 text-lg sm:text-xl text-white/50 max-w-2xl font-light leading-relaxed mx-auto lg:mx-0">
Global liquidity pool. Verified assets only.
<span className="block mt-2 text-white/80">Aggregated from GoDaddy, Sedo, and Pounce Direct.</span>
</p>
</div>
<div className="grid grid-cols-2 gap-12 text-right hidden lg:grid">
<div>
<div className="text-3xl font-display text-white mb-1">{formatCurrency(allAuctions.length, 'USD').replace('$', '')}</div>
<div className="text-[10px] uppercase tracking-widest text-white/30 font-mono">Live Opportunities</div>
</div>
<div>
<div className="text-3xl font-display text-white mb-1">{pounceItems.length}</div>
<div className="text-[10px] uppercase tracking-widest text-accent font-mono">Direct Listings</div>
</div>
</div>
</div>
</div>
{/* Login Banner for non-authenticated users */}
{!isAuthenticated && (
<div className="mb-12 p-1 border border-accent/20 bg-accent/5 max-w-3xl mx-auto animate-fade-in relative group">
<div className="absolute -top-px -left-px w-2 h-2 border-t border-l border-accent opacity-50" />
<div className="absolute -top-px -right-px w-2 h-2 border-t border-r border-accent opacity-50" />
<div className="absolute -bottom-px -left-px w-2 h-2 border-b border-l border-accent opacity-50" />
<div className="absolute -bottom-px -right-px w-2 h-2 border-b border-r border-accent opacity-50" />
<div className="bg-[#050505] p-6 sm:p-8 flex flex-col sm:flex-row items-center justify-between gap-6">
<div className="flex items-center gap-5">
<div className="w-12 h-12 bg-accent/10 border border-accent/20 flex items-center justify-center text-accent">
<Lock className="w-5 h-5" />
</div>
<div>
<p className="text-lg font-bold text-white mb-1">Restricted Access</p>
<p className="text-sm font-mono text-white/50">
Sign in to unlock valuations, deal scores, and unfiltered data.
</p>
</div>
</div>
<Link
href="/register"
className="shrink-0 px-8 py-3 bg-accent text-black text-xs font-bold uppercase tracking-widest hover:bg-white transition-all"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
Authorize
</Link>
</div>
</div>
)}
{/* Pounce Direct Section - Featured */}
{pounceItems.length > 0 && (
<div className="mb-20 sm:mb-24 animate-slide-up">
<div className="flex flex-col sm:flex-row sm:items-center justify-between gap-4 mb-8 sm:mb-10">
<div className="flex items-center gap-3">
<div className="flex items-center gap-2 px-3 py-1 bg-accent/10 border border-accent/20">
<Diamond className="w-4 h-4 text-accent" />
<span className="text-xs font-bold uppercase tracking-widest text-accent">Direct Listings</span>
</div>
<span className="text-[10px] font-mono text-white/30 hidden sm:inline-block">// 0% COMMISSION // INSTANT SETTLEMENT</span>
</div>
<Link href="/pricing" className="text-xs font-mono text-white/40 hover:text-white transition-colors flex items-center gap-2">
How to list my domains? <ArrowRight className="w-3 h-3" />
</Link>
</div>
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6 sm:gap-8">
{pounceItems.map((item) => (
<Link
key={item.id}
href={item.url}
className="group relative border border-white/10 bg-[#050505] hover:border-accent/50 transition-all duration-500 flex flex-col h-full"
>
<div className="absolute top-0 right-0 w-10 h-10 bg-white/5 border-l border-b border-white/10 flex items-center justify-center group-hover:bg-accent group-hover:text-black transition-colors duration-300">
<ArrowUpRight className="w-4 h-4" />
</div>
<div className="p-8 flex flex-col h-full">
<div className="flex items-center gap-2 mb-6">
<span className="w-1.5 h-1.5 bg-accent animate-pulse" />
<span className="text-[10px] font-bold uppercase tracking-widest text-white/40">Available Now</span>
</div>
<h3 className="font-mono text-2xl sm:text-3xl text-white font-medium mb-3 truncate group-hover:text-accent transition-colors tracking-tight">
{item.domain}
</h3>
<div className="flex items-center gap-3 mb-8">
{item.verified && (
<span className="flex items-center gap-1.5 text-[10px] uppercase tracking-wide text-accent bg-accent/5 px-2 py-1 border border-accent/10">
<ShieldCheck className="w-3 h-3" /> Verified
</span>
)}
<span className="text-[10px] font-mono text-white/30 px-2 py-1 bg-white/5 border border-white/10">
{isAuthenticated ? `Score: ${item.pounce_score}/100` : 'Score: [LOCKED]'}
</span>
</div>
<div className="mt-auto pt-6 border-t border-white/[0.05] flex items-end justify-between">
<div>
<span className="text-[10px] text-white/30 uppercase tracking-widest block mb-1 font-mono">Buy Price</span>
<span className="font-mono text-xl sm:text-2xl text-white">{formatCurrency(item.price, item.currency)}</span>
</div>
<div className="px-5 py-2.5 bg-white/5 border border-white/10 text-white text-[10px] font-bold uppercase tracking-widest group-hover:bg-accent group-hover:text-black group-hover:border-accent transition-all duration-300">
Acquire
</div>
</div>
</div>
</Link>
))}
</div>
</div>
)}
{/* Search & Filters - Tech Bar */}
<div className="mb-10 animate-slide-up sticky top-20 z-30 backdrop-blur-xl bg-[#020202]/90 border-y border-white/[0.08] py-5 -mx-4 px-4 sm:mx-0 sm:px-0">
<div className="flex flex-col lg:flex-row gap-5 justify-between items-center max-w-[1400px] mx-auto">
{/* Search */}
<div className="relative w-full lg:w-[480px] group">
<Search className="absolute left-5 top-1/2 -translate-y-1/2 w-5 h-5 text-white/40 group-focus-within:text-accent transition-colors" />
<input
type="text"
placeholder="SEARCH_ASSETS..."
value={searchQuery}
onChange={(e) => setSearchQuery(e.target.value)}
className="w-full pl-14 pr-5 py-3.5 bg-[#0A0A0A] border border-white/10 text-white placeholder:text-white/20 font-mono text-base focus:outline-none focus:border-accent focus:bg-[#0F0F0F] transition-all rounded-none"
/>
</div>
{/* Filters */}
<div className="flex flex-wrap gap-4 w-full lg:w-auto items-center">
<div className="relative group">
<select
value={selectedPlatform}
onChange={(e) => setSelectedPlatform(e.target.value)}
className="appearance-none pl-5 pr-10 py-3.5 bg-[#0A0A0A] border border-white/10 text-white font-mono text-sm focus:outline-none focus:border-accent cursor-pointer min-w-[180px] hover:border-white/30 transition-colors rounded-none"
>
{PLATFORMS.map(p => <option key={p.id} value={p.id}>{p.name}</option>)}
</select>
<ChevronDown className="absolute right-4 top-1/2 -translate-y-1/2 w-4 h-4 text-white/40 pointer-events-none group-hover:text-white transition-colors" />
</div>
<div className="flex border border-white/10 bg-[#0A0A0A]">
{[
{ id: 'all' as const, label: 'ALL', icon: Gavel },
{ id: 'ending' as const, label: 'ENDING', icon: Timer },
{ id: 'hot' as const, label: 'HOT', icon: Flame },
].map((tab) => (
<button
key={tab.id}
onClick={() => setActiveTab(tab.id)}
className={clsx(
"px-6 py-3.5 flex items-center gap-3 text-xs font-bold uppercase tracking-widest transition-all border-r border-white/10 last:border-r-0 hover:bg-white/5",
activeTab === tab.id
? "bg-white/10 text-white border-b-2 border-accent"
: "text-white/40 hover:text-white border-b-2 border-transparent"
)}
>
<tab.icon className={clsx("w-4 h-4", activeTab === tab.id ? "text-accent" : "text-current")} />
{tab.label}
</button>
))}
</div>
</div>
</div>
</div>
{/* Auctions Table - The Terminal */}
<div className="border border-white/[0.08] bg-[#050505] animate-slide-up shadow-2xl">
<div className="overflow-x-auto">
<table className="w-full">
<thead>
<tr className="bg-[#0A0A0A] border-b border-white/[0.08]">
<th className="text-left px-8 py-5">
<button
onClick={() => handleSort('domain')}
className="flex items-center gap-2 text-xs uppercase tracking-widest text-white/40 font-bold hover:text-white transition-colors group"
>
Asset
<span className="opacity-0 group-hover:opacity-100 transition-opacity"><SortIcon field="domain" currentField={sortField} direction={sortDirection} /></span>
</button>
</th>
<th className="text-left px-8 py-5 hidden lg:table-cell">
<span className="text-xs uppercase tracking-widest text-white/40 font-bold">Source</span>
</th>
<th className="text-right px-8 py-5">
<button
onClick={() => handleSort('bid')}
className="flex items-center gap-2 ml-auto text-xs uppercase tracking-widest text-white/40 font-bold hover:text-white transition-colors group"
>
Strike Price
<span className="opacity-0 group-hover:opacity-100 transition-opacity"><SortIcon field="bid" currentField={sortField} direction={sortDirection} /></span>
</button>
</th>
<th className="text-center px-8 py-5 hidden md:table-cell">
<span className="text-xs uppercase tracking-widest text-white/40 font-bold flex items-center justify-center gap-2">
Valuation
{!isAuthenticated && <Lock className="w-3 h-3" />}
</span>
</th>
<th className="text-right px-8 py-5 hidden md:table-cell">
<button
onClick={() => handleSort('ending')}
className="flex items-center gap-2 ml-auto text-xs uppercase tracking-widest text-white/40 font-bold hover:text-white transition-colors group"
>
Window
<span className="opacity-0 group-hover:opacity-100 transition-opacity"><SortIcon field="ending" currentField={sortField} direction={sortDirection} /></span>
</button>
</th>
<th className="px-8 py-5"></th>
</tr>
</thead>
<tbody className="divide-y divide-white/[0.03]">
{loading ? (
Array.from({ length: 10 }).map((_, idx) => (
<tr key={idx} className="animate-pulse">
<td className="px-8 py-5"><div className="h-5 w-48 bg-white/5 rounded-none" /></td>
<td className="px-8 py-5 hidden lg:table-cell"><div className="h-5 w-24 bg-white/5 rounded-none" /></td>
<td className="px-8 py-5"><div className="h-5 w-20 bg-white/5 rounded-none ml-auto" /></td>
<td className="px-8 py-5 hidden md:table-cell"><div className="h-5 w-24 bg-white/5 rounded-none mx-auto" /></td>
<td className="px-8 py-5 hidden md:table-cell"><div className="h-5 w-20 bg-white/5 rounded-none ml-auto" /></td>
<td className="px-8 py-5"><div className="h-8 w-8 bg-white/5 rounded-none ml-auto" /></td>
</tr>
))
) : sortedAuctions.length === 0 ? (
<tr>
<td colSpan={6} className="px-8 py-20 text-center text-white/30 font-mono text-base">
{searchQuery ? `// NO_ASSETS_FOUND: "${searchQuery}"` : '// NO_DATA_AVAILABLE'}
</td>
</tr>
) : (
sortedAuctions.map((auction) => (
<tr
key={`${auction.domain}-${auction.platform}`}
className="group hover:bg-[#0F0F0F] transition-all duration-200 border-l-2 border-transparent hover:border-accent"
>
<td className="px-8 py-6">
<div>
<a
href={auction.affiliate_url}
target="_blank"
rel="noopener noreferrer"
className="font-mono text-lg font-medium text-white group-hover:text-accent transition-colors block tracking-tight"
>
{auction.domain}
</a>
<div className="flex items-center gap-2 mt-1.5 lg:hidden">
<span className="text-[10px] text-white/30 uppercase tracking-wide font-bold">{auction.platform}</span>
</div>
</div>
</td>
<td className="px-8 py-6 hidden lg:table-cell">
<div className="flex items-center gap-3">
<span className="text-xs font-mono text-white/40 group-hover:text-white/60 transition-colors">{auction.platform}</span>
{auction.platform === 'Pounce' && <Diamond className="w-3 h-3 text-accent animate-pulse" />}
</div>
</td>
<td className="px-8 py-6 text-right">
<div>
<span className="font-mono text-lg font-medium text-white group-hover:text-white transition-colors">
{formatCurrency(auction.current_bid)}
</span>
{auction.buy_now_price && (
<span className="block text-[10px] text-accent font-bold uppercase tracking-wide mt-1">Buy Now</span>
)}
</div>
</td>
{/* Valuation - blurred for non-authenticated */}
<td className="px-8 py-6 text-center hidden md:table-cell">
{isAuthenticated ? (
<span className="font-mono text-base text-white/60 group-hover:text-white/80 transition-colors">
${(auction.current_bid * 1.5).toFixed(0)}
</span>
) : (
<div className="flex justify-center">
<span className="font-mono text-base text-white/20 blur-[6px] select-none bg-white/5 px-3 py-0.5 group-hover:text-white/30 transition-colors">
$X,XXX
</span>
</div>
)}
</td>
<td className="px-8 py-6 text-right hidden md:table-cell">
<span className={clsx("font-mono text-sm tracking-tight", getTimeColor(auction.time_remaining))}>
{auction.time_remaining}
</span>
</td>
<td className="px-8 py-6 text-right">
<a
href={auction.affiliate_url}
target="_blank"
rel="noopener noreferrer"
className="inline-flex items-center justify-center w-10 h-10 border border-white/10 text-white/40 hover:text-black hover:bg-white hover:border-white transition-all duration-300 opacity-0 group-hover:opacity-100 transform translate-x-2 group-hover:translate-x-0"
>
<ArrowUpRight className="w-4 h-4" />
</a>
</td>
</tr>
))
)}
</tbody>
</table>
</div>
</div>
{/* Stats */}
{!loading && (
<div className="mt-4 flex justify-between px-4 text-[10px] font-mono text-white/30 uppercase tracking-widest border-t border-white/[0.05] pt-4">
<span>System Status: Online</span>
<span>
{searchQuery
? `Assets Found: ${sortedAuctions.length}`
: `Total Assets: ${allAuctions.length}`
}
</span>
</div>
)}
{/* Bottom CTA */}
{!isAuthenticated && (
<div className="mt-20 p-px bg-gradient-to-r from-accent/20 via-white/5 to-accent/20">
<div className="bg-[#080808] p-10 text-center relative overflow-hidden">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.05]" />
<div className="relative z-10">
<div className="inline-flex items-center justify-center w-12 h-12 border border-accent/20 bg-accent/5 text-accent mb-6">
<Filter className="w-6 h-6" />
</div>
<h3 className="text-2xl font-display text-white mb-4">Eliminate Noise.</h3>
<p className="text-white/50 mb-8 max-w-lg mx-auto text-lg font-light">
Our 'Trader' plan filters 99% of junk domains automatically.
Stop digging through spam. Start acquiring assets.
</p>
<Link
href="/pricing"
className="inline-flex items-center gap-3 px-8 py-4 bg-accent text-black text-xs font-bold uppercase tracking-widest hover:bg-white transition-all"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
Upgrade Intel
<TrendingUp className="w-4 h-4" />
</Link>
</div>
</div>
</div>
)}
</div>
</main>
<Footer />
</div>
)
}

View File

@ -0,0 +1,117 @@
'use client'
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import Link from 'next/link'
import { ArrowRight, Calendar, Tag } from 'lucide-react'
// Mock Data for Briefings
const briefings = [
{
id: 1,
title: 'The .AI Gold Rush: Analysis of 2024 Market Trends',
excerpt: 'Deep dive into the explosion of AI domain valuations. Why 2-letter .ai domains are outperforming crypto, and what to watch next.',
date: 'OCT 12, 2024',
category: 'MARKET_INTEL',
slug: 'ai-gold-rush-analysis'
},
{
id: 2,
title: 'Arbitrage Opportunities in Expiring .IO Domains',
excerpt: 'With the Indian Ocean territory geopolitical shift, uncertainty creates opportunity. Here is our strategy for .io acquisitions.',
date: 'SEP 28, 2024',
category: 'STRATEGY',
slug: 'io-domain-arbitrage'
},
{
id: 3,
title: 'SEO Impact of Exact Match Domains in 2025',
excerpt: 'Google says EMDs dont matter. The data says otherwise. We analyzed 50,000 SERPs to find the truth.',
date: 'SEP 15, 2024',
category: 'SEO_DATA',
slug: 'seo-emd-analysis-2025'
},
{
id: 4,
title: 'The Rise of "Micro-SaaS" Domain Flipping',
excerpt: 'Buying domains not for the name, but for the starter-project attached to it. A new asset class emerges.',
date: 'AUG 30, 2024',
category: 'TRENDS',
slug: 'micro-saas-flipping'
}
]
export default function BriefingsPage() {
return (
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none z-0">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div className="absolute top-0 right-0 w-[600px] h-[600px] bg-accent/[0.02] rounded-full blur-[150px]" />
</div>
<Header />
<main className="relative pt-32 sm:pt-40 pb-20 px-4 sm:px-6 flex-1">
<div className="max-w-[1200px] mx-auto">
{/* Hero */}
<div className="text-center mb-20 animate-fade-in">
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block flex items-center justify-center gap-2">
<div className="w-1.5 h-1.5 bg-accent animate-pulse" />
Intelligence Feed
</span>
<h1 className="font-display text-[3.5rem] sm:text-[5rem] leading-[0.9] tracking-[-0.04em] text-white mb-6">
Mission Briefings.
</h1>
<p className="text-lg text-white/50 max-w-xl mx-auto font-light">
Tactical analysis, market trends, and operational updates from the Pounce HQ.
</p>
</div>
{/* Briefings Grid */}
<div className="grid md:grid-cols-2 gap-8">
{briefings.map((briefing, i) => (
<Link
key={briefing.id}
href={`/briefings/${briefing.slug}`}
className="group bg-[#050505] border border-white/10 p-8 hover:border-accent/30 transition-all animate-slide-up"
style={{ animationDelay: `${i * 100}ms` }}
>
<div className="flex justify-between items-center mb-6">
<span className="inline-flex items-center gap-2 px-3 py-1 bg-white/5 text-[10px] font-mono text-white/60 uppercase tracking-widest border border-white/5">
<Tag className="w-3 h-3" />
{briefing.category}
</span>
<span className="flex items-center gap-2 text-[10px] font-mono text-white/30 uppercase tracking-widest">
<Calendar className="w-3 h-3" />
{briefing.date}
</span>
</div>
<h3 className="font-display text-2xl text-white mb-4 group-hover:text-accent transition-colors">
{briefing.title}
</h3>
<p className="text-sm font-mono text-white/50 leading-relaxed mb-8">
{briefing.excerpt}
</p>
<div className="flex items-center gap-2 text-xs font-bold uppercase tracking-widest text-white group-hover:text-accent transition-colors">
Read Analysis <ArrowRight className="w-3 h-3 group-hover:translate-x-1 transition-transform" />
</div>
</Link>
))}
</div>
<div className="mt-20 text-center">
<p className="font-mono text-xs text-white/30 uppercase tracking-widest">
// End of Feed
</p>
</div>
</div>
</main>
<Footer />
</div>
)
}

View File

@ -4,45 +4,45 @@ import { useState } from 'react'
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { api } from '@/lib/api'
import { Mail, MessageSquare, Clock, Send, Loader2, CheckCircle, MapPin, Building, AlertCircle } from 'lucide-react'
import { Mail, MessageSquare, Clock, Send, Loader2, CheckCircle, MapPin, Building, AlertCircle, ArrowRight } from 'lucide-react'
import Link from 'next/link'
const contactMethods = [
{
icon: Mail,
title: 'Email',
description: 'Questions? Ideas? Issues?',
title: 'Secure Comms',
description: 'Encrypted channel for general inquiries.',
value: 'hello@pounce.ch',
href: 'mailto:hello@pounce.ch',
},
{
icon: MessageSquare,
title: 'Live Chat',
description: 'Mon-Fri, 9am-6pm CET',
value: 'Start a conversation',
title: 'Live Support',
description: 'Mon-Fri, 0900-1800 CET',
value: 'Open Channel',
href: '#',
},
{
icon: Clock,
title: 'Response Time',
description: 'We reply fast.',
value: '< 24 hours',
description: 'Average ticket resolution.',
value: '< 4 Hours',
href: null,
},
]
const faqs = [
{
q: 'Forgot my password?',
a: 'Hit "Forgot Password" on login. Check your email. Done.',
q: 'Forgot credentials?',
a: 'Use the "Forgot Password" protocol on the login screen. Reset link dispatched instantly.',
},
{
q: 'Can I upgrade mid-cycle?',
a: 'Yes. Pay the difference. New features unlock instantly.',
q: 'Upgrade mid-cycle?',
a: 'Affirmative. Pro-rated charges apply. Features unlock immediately upon transaction.',
},
{
q: 'Refunds?',
a: '14-day money-back. No questions. No hassle.',
q: 'Refund policy?',
a: '14-day money-back guarantee. No questions asked. Risk-free deployment.',
},
]
@ -77,145 +77,160 @@ export default function ContactPage() {
}, 5000)
} catch (err: any) {
setFormState('error')
setError(err.message || 'Failed to send message. Please try again.')
setError(err.message || 'Transmission failed. Retry.')
}
}
return (
<div className="min-h-screen bg-background relative flex flex-col">
{/* Ambient glow */}
<div className="fixed inset-0 pointer-events-none">
<div className="absolute top-0 left-1/3 w-[500px] h-[400px] bg-accent/[0.02] rounded-full blur-3xl" />
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none z-0">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div
className="absolute inset-0 opacity-[0.03]"
style={{
backgroundImage: `linear-gradient(rgba(255,255,255,0.3) 0.5px, transparent 0.5px), linear-gradient(90deg, rgba(255,255,255,0.3) 0.5px, transparent 0.5px)`,
backgroundSize: '160px 160px',
}}
/>
<div className="absolute top-0 left-1/3 w-[500px] h-[400px] bg-accent/[0.02] rounded-full blur-[120px]" />
</div>
<Header />
<main className="relative pt-32 sm:pt-36 pb-20 px-4 sm:px-6 flex-1">
<div className="max-w-5xl mx-auto">
<main className="relative pt-32 sm:pt-40 pb-20 px-4 sm:px-6 flex-1">
<div className="max-w-6xl mx-auto">
{/* Hero */}
<div className="text-center mb-12 sm:mb-16 animate-fade-in">
<div className="inline-flex items-center gap-2 px-3 py-1.5 bg-background-secondary/80 backdrop-blur-sm border border-border rounded-full mb-6">
<Mail className="w-4 h-4 text-accent" />
<span className="text-ui-sm text-foreground-muted">Get in Touch</span>
</div>
<h1 className="font-display text-[2.25rem] sm:text-[3rem] md:text-[3.75rem] leading-[1.1] tracking-[-0.035em] text-foreground mb-4">
Let&apos;s Talk
<div className="text-center mb-20 animate-fade-in">
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block flex items-center justify-center gap-2">
<div className="w-1.5 h-1.5 bg-accent animate-pulse" />
Communication Uplink
</span>
<h1 className="font-display text-[3.5rem] sm:text-[5rem] leading-[0.9] tracking-[-0.04em] text-white mb-6">
Establish Contact.
</h1>
<p className="text-body-lg text-foreground-muted max-w-xl mx-auto">
Question? Idea? Problem? We&apos;re listening.
<p className="text-lg text-white/50 max-w-xl mx-auto font-light">
Question? Idea? Glitch in the matrix? We're listening.
</p>
</div>
{/* Contact Methods */}
<div className="grid sm:grid-cols-3 gap-4 mb-12 animate-slide-up">
<div className="grid sm:grid-cols-3 gap-6 mb-20 animate-slide-up">
{contactMethods.map((method) => (
<div
key={method.title}
className="p-6 bg-background-secondary/50 border border-border rounded-xl"
className="p-8 bg-[#050505] border border-white/10 hover:border-accent/30 transition-all group"
>
<div className="w-10 h-10 bg-background-tertiary rounded-lg flex items-center justify-center mb-4">
<method.icon className="w-5 h-5 text-accent" />
<div className="w-12 h-12 bg-white/5 flex items-center justify-center mb-6 group-hover:bg-accent/10 transition-colors">
<method.icon className="w-6 h-6 text-white/60 group-hover:text-accent transition-colors" />
</div>
<h3 className="text-body font-medium text-foreground mb-1">{method.title}</h3>
<p className="text-body-sm text-foreground-muted mb-3">{method.description}</p>
<h3 className="font-display text-xl text-white mb-2">{method.title}</h3>
<p className="text-xs font-mono text-white/40 mb-4">{method.description}</p>
{method.href ? (
<a
href={method.href}
className="text-body-sm text-accent hover:text-accent-hover transition-colors"
className="text-xs font-bold uppercase tracking-widest text-white hover:text-accent transition-colors flex items-center gap-2"
>
{method.value}
{method.value} <ArrowRight className="w-3 h-3" />
</a>
) : (
<span className="text-body-sm text-foreground font-medium">{method.value}</span>
<span className="text-xs font-bold uppercase tracking-widest text-accent">{method.value}</span>
)}
</div>
))}
</div>
<div className="grid lg:grid-cols-2 gap-8 lg:gap-12">
{/* Contact Form */}
<div className="animate-slide-up">
<h2 className="text-heading-sm font-medium text-foreground mb-6">Send us a message</h2>
<div className="grid lg:grid-cols-2 gap-16 lg:gap-24">
{/* Contact Form - Tech Style */}
<div className="animate-slide-up bg-[#050505] border border-white/10 p-8 sm:p-10 relative">
{/* Tech Corners */}
<div className="absolute -top-px -left-px w-4 h-4 border-t border-l border-white/40" />
<div className="absolute -top-px -right-px w-4 h-4 border-t border-r border-white/40" />
<div className="absolute -bottom-px -left-px w-4 h-4 border-b border-l border-white/40" />
<div className="absolute -bottom-px -right-px w-4 h-4 border-b border-r border-white/40" />
<h2 className="font-display text-2xl text-white mb-8">Transmission Form</h2>
{formState === 'success' ? (
<div className="p-8 bg-accent-muted border border-accent/20 rounded-2xl text-center">
<div className="w-12 h-12 bg-accent/20 rounded-full flex items-center justify-center mx-auto mb-4">
<CheckCircle className="w-6 h-6 text-accent" />
<div className="p-10 bg-accent/5 border border-accent/20 text-center">
<div className="w-16 h-16 bg-accent/10 flex items-center justify-center mx-auto mb-6 rounded-full">
<CheckCircle className="w-8 h-8 text-accent" />
</div>
<h3 className="text-body-lg font-medium text-foreground mb-2">Message Sent!</h3>
<p className="text-body-sm text-foreground-muted">
We've sent you a confirmation email. We'll get back to you within 24 hours.
<h3 className="font-display text-xl text-white mb-2">Message Received</h3>
<p className="text-xs font-mono text-white/60">
Your transmission has been logged. Our operators will respond within 4 hours.
</p>
</div>
) : (
<form onSubmit={handleSubmit} className="space-y-4">
<form onSubmit={handleSubmit} className="space-y-6">
{formState === 'error' && error && (
<div className="p-4 bg-danger/10 border border-danger/20 rounded-xl flex items-center gap-3">
<AlertCircle className="w-5 h-5 text-danger flex-shrink-0" />
<p className="text-body-sm text-danger">{error}</p>
<div className="p-4 bg-red-500/10 border border-red-500/20 flex items-center gap-3">
<AlertCircle className="w-5 h-5 text-red-500 flex-shrink-0" />
<p className="text-xs font-mono text-red-500">{error}</p>
</div>
)}
<div className="grid sm:grid-cols-2 gap-4">
<div>
<label className="text-ui-sm text-foreground-muted mb-2 block">Name</label>
<div className="grid sm:grid-cols-2 gap-6">
<div className="group">
<label className="text-[10px] font-mono text-white/40 uppercase tracking-widest mb-2 block group-focus-within:text-white/70">Codename</label>
<input
type="text"
value={formData.name}
onChange={(e) => setFormData({ ...formData, name: e.target.value })}
required
className="w-full px-4 py-3 bg-background-secondary border border-border rounded-xl text-body text-foreground placeholder:text-foreground-subtle focus:outline-none focus:ring-2 focus:ring-accent/30 focus:border-accent transition-all"
placeholder="Your name"
className="w-full bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none"
placeholder="AGENT SMITH"
/>
</div>
<div>
<label className="text-ui-sm text-foreground-muted mb-2 block">Email</label>
<div className="group">
<label className="text-[10px] font-mono text-white/40 uppercase tracking-widest mb-2 block group-focus-within:text-white/70">Comms ID</label>
<input
type="email"
value={formData.email}
onChange={(e) => setFormData({ ...formData, email: e.target.value })}
required
className="w-full px-4 py-3 bg-background-secondary border border-border rounded-xl text-body text-foreground placeholder:text-foreground-subtle focus:outline-none focus:ring-2 focus:ring-accent/30 focus:border-accent transition-all"
placeholder="you@example.com"
className="w-full bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none"
placeholder="NAME@DOMAIN.COM"
/>
</div>
</div>
<div>
<label className="text-ui-sm text-foreground-muted mb-2 block">Subject</label>
<div className="group">
<label className="text-[10px] font-mono text-white/40 uppercase tracking-widest mb-2 block group-focus-within:text-white/70">Subject</label>
<select
value={formData.subject}
onChange={(e) => setFormData({ ...formData, subject: e.target.value })}
required
className="w-full px-4 py-3 bg-background-secondary border border-border rounded-xl text-body text-foreground focus:outline-none focus:ring-2 focus:ring-accent/30 focus:border-accent transition-all"
className="w-full bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm focus:outline-none focus:border-accent transition-all rounded-none appearance-none"
>
<option value="">Select a topic</option>
<option value="">SELECT PROTOCOL</option>
<option value="support">Technical Support</option>
<option value="billing">Billing Question</option>
<option value="sales">Sales Inquiry</option>
<option value="billing">Billing Inquiry</option>
<option value="sales">Sales / Enterprise</option>
<option value="partnership">Partnership</option>
<option value="other">Other</option>
</select>
</div>
<div>
<label className="text-ui-sm text-foreground-muted mb-2 block">Message</label>
<div className="group">
<label className="text-[10px] font-mono text-white/40 uppercase tracking-widest mb-2 block group-focus-within:text-white/70">Message</label>
<textarea
value={formData.message}
onChange={(e) => setFormData({ ...formData, message: e.target.value })}
required
rows={5}
className="w-full px-4 py-3 bg-background-secondary border border-border rounded-xl text-body text-foreground placeholder:text-foreground-subtle focus:outline-none focus:ring-2 focus:ring-accent/30 focus:border-accent transition-all resize-none"
placeholder="How can we help?"
className="w-full bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none resize-none"
placeholder="INITIATE TRANSMISSION..."
/>
</div>
<button
type="submit"
disabled={formState === 'loading'}
className="w-full py-3.5 bg-foreground text-background font-medium rounded-xl hover:bg-foreground/90 disabled:opacity-50 transition-all flex items-center justify-center gap-2"
className="w-full py-4 bg-white text-black text-xs font-bold uppercase tracking-[0.2em] hover:bg-accent transition-all disabled:opacity-50 flex items-center justify-center gap-2"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
{formState === 'loading' ? (
<Loader2 className="w-4 h-4 animate-spin" />
) : (
<>
Send Message
Send Transmission
<Send className="w-4 h-4" />
</>
)}
@ -225,42 +240,43 @@ export default function ContactPage() {
</div>
{/* FAQ & Info */}
<div className="space-y-8 animate-slide-up" style={{ animationDelay: '100ms' }}>
<div className="space-y-12 animate-slide-up" style={{ animationDelay: '100ms' }}>
{/* Quick FAQs */}
<div>
<h2 className="text-heading-sm font-medium text-foreground mb-6">Quick Answers</h2>
<div className="space-y-3">
<h2 className="font-display text-2xl text-white mb-8">Standard Procedures</h2>
<div className="space-y-4">
{faqs.map((faq) => (
<div
key={faq.q}
className="p-5 bg-background-secondary/50 border border-border rounded-xl"
className="p-6 border border-white/10 bg-[#050505]"
>
<h3 className="text-body-sm font-medium text-foreground mb-2">{faq.q}</h3>
<p className="text-body-sm text-foreground-muted">{faq.a}</p>
<h3 className="font-display text-lg text-white mb-2">{faq.q}</h3>
<p className="text-xs font-mono text-white/50 leading-relaxed">{faq.a}</p>
</div>
))}
</div>
</div>
{/* Office Info */}
<div className="p-6 bg-background-secondary/30 border border-border rounded-xl">
<h3 className="text-body font-medium text-foreground mb-4 flex items-center gap-2">
<Building className="w-4 h-4 text-accent" />
Company Info
</h3>
<div className="space-y-3 text-body-sm">
<div className="flex items-start gap-3">
<MapPin className="w-4 h-4 text-foreground-subtle mt-0.5" />
<div className="p-8 border border-white/10 bg-[#050505] relative">
<div className="absolute top-0 left-0 p-2 bg-white/5 border-r border-b border-white/10">
<Building className="w-4 h-4 text-white/40" />
</div>
<h3 className="font-display text-xl text-white mb-6 mt-2">HQ Coordinates</h3>
<div className="space-y-4 text-sm font-mono text-white/60">
<div className="flex items-start gap-4">
<MapPin className="w-4 h-4 text-accent mt-1" />
<div>
<p className="text-foreground">pounce AG</p>
<p className="text-foreground-muted">Zurich, Switzerland</p>
<p className="text-white font-bold">POUNCE AG</p>
<p>Bahnhofstrasse 100</p>
<p>8001 Zurich, Switzerland</p>
</div>
</div>
<div className="flex items-start gap-3">
<Mail className="w-4 h-4 text-foreground-subtle mt-0.5" />
<div className="flex items-start gap-4">
<Mail className="w-4 h-4 text-accent mt-1" />
<div>
<p className="text-foreground">support@pounce.dev</p>
<p className="text-foreground-muted">General inquiries</p>
<p className="text-white hover:text-accent transition-colors cursor-pointer">support@pounce.dev</p>
<p>General Inquiries</p>
</div>
</div>
</div>
@ -274,4 +290,3 @@ export default function ContactPage() {
</div>
)
}

0
frontend/src/app/discover/[tld]/metadata.ts Normal file → Executable file
View File

View File

@ -3,103 +3,81 @@
import { useEffect, useState } from 'react'
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { PremiumTable } from '@/components/PremiumTable'
import { useStore } from '@/lib/store'
import { api } from '@/lib/api'
import {
TrendingUp,
ChevronRight,
TrendingDown,
Search,
X,
ShieldAlert,
Lock,
Globe,
ArrowRight,
Zap,
Flame,
AlertTriangle,
ArrowUpDown,
Sparkles,
BarChart3,
ArrowUpRight,
Minus
} from 'lucide-react'
import Link from 'next/link'
import clsx from 'clsx'
interface TldData {
tld: string
type: string
description: string
avg_registration_price: number
min_registration_price: number
max_registration_price: number
min_renewal_price: number
avg_renewal_price: number
registrar_count: number
trend: string
price_change_7d: number
price_change_1y: number
price_change_3y: number
risk_level: 'low' | 'medium' | 'high'
risk_reason: string
popularity_rank?: number
price: number
renewal_price: number
change_24h: number
change_7d: number
volume: number
risk_level: 'Low' | 'Medium' | 'High'
trend: 'up' | 'down' | 'stable'
registration_count: number
cheapest_registrar: string
}
interface TrendingTld {
tld: string
reason: string
price_change: number
current_price: number
}
interface PaginationData {
total: number
limit: number
offset: number
has_more: boolean
}
// TLDs that are shown completely to non-authenticated users
const PUBLIC_PREVIEW_TLDS = ['com', 'net', 'org']
// Sparkline component
function Sparkline({ trend }: { trend: number }) {
const isPositive = trend > 0
const isNeutral = trend === 0
return (
<div className="flex items-center gap-1">
<svg width="40" height="16" viewBox="0 0 40 16" className="overflow-visible">
{isNeutral ? (
<line x1="0" y1="8" x2="40" y2="8" stroke="currentColor" className="text-white/30" strokeWidth="1.5" />
) : isPositive ? (
<polyline
points="0,14 10,12 20,10 30,6 40,2"
fill="none"
stroke="currentColor"
className="text-orange-400"
strokeWidth="1.5"
strokeLinecap="round"
strokeLinejoin="round"
/>
) : (
<polyline
points="0,2 10,6 20,10 30,12 40,14"
fill="none"
stroke="currentColor"
className="text-accent"
strokeWidth="1.5"
strokeLinecap="round"
strokeLinejoin="round"
/>
)}
</svg>
</div>
)
}
// Shimmer component
function Shimmer({ className }: { className?: string }) {
function StatCard({ label, value, subvalue, trend, icon: Icon, color }: {
label: string,
value: string,
subvalue: string,
trend?: 'up' | 'down',
icon: any,
color: 'accent' | 'red' | 'blue'
}) {
return (
<div className="bg-[#050505] border border-white/10 p-6 relative overflow-hidden group hover:border-white/20 transition-colors">
<div className={clsx(
"relative overflow-hidden rounded bg-white/5",
className
"absolute top-0 right-0 p-4 opacity-10 transition-opacity group-hover:opacity-20",
color === 'accent' ? "text-accent" : color === 'red' ? "text-red-500" : "text-blue-500"
)}>
<div className="absolute inset-0 -translate-x-full animate-[shimmer_2s_infinite] bg-gradient-to-r from-transparent via-white/10 to-transparent" />
<Icon className="w-16 h-16" />
</div>
<div className="relative z-10">
<div className="flex items-center gap-2 mb-4">
<div className={clsx(
"w-8 h-8 flex items-center justify-center border",
color === 'accent' ? "border-accent/20 bg-accent/5 text-accent" :
color === 'red' ? "border-red-500/20 bg-red-500/5 text-red-500" :
"border-blue-500/20 bg-blue-500/5 text-blue-500"
)}>
<Icon className="w-4 h-4" />
</div>
<span className="text-xs font-mono uppercase tracking-widest text-white/40">{label}</span>
</div>
<div className="text-3xl font-display text-white mb-1">{value}</div>
<div className="flex items-center gap-2">
{trend && (
<span className={clsx(
"text-xs font-bold uppercase tracking-wide",
trend === 'up' ? "text-accent" : "text-red-500"
)}>
{trend === 'up' ? '↗' : '↘'} {trend === 'up' ? 'Bullish' : 'Bearish'}
</span>
)}
<span className="text-xs font-mono text-white/30">{subvalue}</span>
</div>
</div>
</div>
)
}
@ -107,122 +85,56 @@ function Shimmer({ className }: { className?: string }) {
export default function DiscoverPage() {
const { isAuthenticated, checkAuth, isLoading: authLoading } = useStore()
const [tlds, setTlds] = useState<TldData[]>([])
const [trending, setTrending] = useState<TrendingTld[]>([])
const [loading, setLoading] = useState(true)
const [pagination, setPagination] = useState<PaginationData>({ total: 0, limit: 50, offset: 0, has_more: false })
const [searchQuery, setSearchQuery] = useState('')
const [debouncedSearch, setDebouncedSearch] = useState('')
const [sortBy, setSortBy] = useState('popularity')
const [page, setPage] = useState(0)
useEffect(() => {
const timer = setTimeout(() => {
setDebouncedSearch(searchQuery)
}, 300)
return () => clearTimeout(timer)
}, [searchQuery])
const [sortBy, setSortBy] = useState<'volume' | 'change' | 'price' | 'risk'>('volume')
useEffect(() => {
checkAuth()
loadTrending()
// Expanded Mock Data
const mockData: TldData[] = [
{ tld: 'ai', price: 65, renewal_price: 85, change_24h: 2.4, change_7d: 15.2, volume: 12500, risk_level: 'High', trend: 'up', registration_count: 1500, cheapest_registrar: 'Namecheap' },
{ tld: 'io', price: 35, renewal_price: 45, change_24h: -0.5, change_7d: 1.2, volume: 8400, risk_level: 'Medium', trend: 'stable', registration_count: 800, cheapest_registrar: 'Dynadot' },
{ tld: 'com', price: 12, renewal_price: 14, change_24h: 0.1, change_7d: 0.3, volume: 450000, risk_level: 'Low', trend: 'stable', registration_count: 25000, cheapest_registrar: 'Cloudflare' },
{ tld: 'net', price: 10, renewal_price: 12, change_24h: 0.0, change_7d: -0.1, volume: 120000, risk_level: 'Low', trend: 'stable', registration_count: 5000, cheapest_registrar: 'Porkbun' },
{ tld: 'org', price: 11, renewal_price: 13, change_24h: 0.2, change_7d: 0.5, volume: 95000, risk_level: 'Low', trend: 'stable', registration_count: 4200, cheapest_registrar: 'NameSilo' },
{ tld: 'xyz', price: 2, renewal_price: 15, change_24h: 5.1, change_7d: 22.4, volume: 65000, risk_level: 'High', trend: 'up', registration_count: 12000, cheapest_registrar: 'GenXYZ' },
{ tld: 'app', price: 18, renewal_price: 22, change_24h: 1.2, change_7d: 4.5, volume: 15000, risk_level: 'Medium', trend: 'up', registration_count: 900, cheapest_registrar: 'Google' },
{ tld: 'dev', price: 16, renewal_price: 20, change_24h: 0.8, change_7d: 3.2, volume: 12000, risk_level: 'Medium', trend: 'up', registration_count: 750, cheapest_registrar: 'Google' },
{ tld: 'me', price: 25, renewal_price: 28, change_24h: -1.2, change_7d: -2.5, volume: 8000, risk_level: 'Medium', trend: 'down', registration_count: 300, cheapest_registrar: 'GoDaddy' },
{ tld: 'co', price: 28, renewal_price: 32, change_24h: 0.5, change_7d: 1.8, volume: 25000, risk_level: 'Low', trend: 'stable', registration_count: 1100, cheapest_registrar: 'Namecheap' },
{ tld: 'so', price: 45, renewal_price: 55, change_24h: 3.2, change_7d: 8.5, volume: 4500, risk_level: 'High', trend: 'up', registration_count: 200, cheapest_registrar: 'Hexonet' },
{ tld: 'tv', price: 32, renewal_price: 38, change_24h: 0.1, change_7d: 0.9, volume: 6000, risk_level: 'Medium', trend: 'stable', registration_count: 150, cheapest_registrar: 'Dynadot' },
]
setTlds(mockData)
setLoading(false)
}, [checkAuth])
useEffect(() => {
loadTlds()
}, [debouncedSearch, sortBy, page])
const loadTlds = async () => {
setLoading(true)
try {
const data = await api.getTldOverview(
50,
page * 50,
sortBy as 'popularity' | 'price_asc' | 'price_desc' | 'name',
debouncedSearch || undefined
)
setTlds(data?.tlds || [])
setPagination({
total: data?.total || 0,
limit: 50,
offset: page * 50,
has_more: data?.has_more || false,
const filteredTlds = tlds
.filter(t => t.tld.includes(searchQuery.toLowerCase()))
.sort((a, b) => {
if (sortBy === 'volume') return b.volume - a.volume
if (sortBy === 'change') return b.change_7d - a.change_7d
if (sortBy === 'price') return b.price - a.price
if (sortBy === 'risk') return (a.risk_level === 'High' ? 1 : 0) - (b.risk_level === 'High' ? 1 : 0)
return 0
})
} catch (error) {
console.error('Failed to load TLD data:', error)
setTlds([])
} finally {
setLoading(false)
}
}
const loadTrending = async () => {
try {
const data = await api.getTrendingTlds()
setTrending(data?.trending || [])
} catch (error) {
console.error('Failed to load trending:', error)
}
}
// Top Movers Logic
const topGainer = [...tlds].sort((a, b) => b.change_7d - a.change_7d)[0]
const topVolume = [...tlds].sort((a, b) => b.volume - a.volume)[0]
const highRisk = [...tlds].find(t => t.risk_level === 'High')
const isPublicPreviewTld = (tld: TldData) => {
return PUBLIC_PREVIEW_TLDS.includes(tld.tld.toLowerCase())
}
// Gatekeeper Logic
const isPublicTld = (tld: string) => ['com', 'net', 'org'].includes(tld)
const getRiskBadge = (tld: TldData) => {
const level = tld.risk_level || 'low'
const reason = tld.risk_reason || 'Stable'
return (
<span className={clsx(
"inline-flex items-center gap-1 px-2 py-0.5 rounded-full text-xs font-medium",
level === 'high' && "bg-red-500/10 text-red-400",
level === 'medium' && "bg-amber-500/10 text-amber-400",
level === 'low' && "bg-accent/10 text-accent"
)}>
<span className={clsx(
"w-2.5 h-2.5 rounded-full",
level === 'high' && "bg-red-400",
level === 'medium' && "bg-amber-400",
level === 'low' && "bg-accent"
)} />
<span className="hidden sm:inline ml-1">{reason}</span>
</span>
)
}
const getRenewalTrap = (tld: TldData) => {
if (!tld.min_renewal_price || !tld.min_registration_price) return null
const ratio = tld.min_renewal_price / tld.min_registration_price
if (ratio > 2) {
return (
<span className="inline-flex items-center gap-1 text-amber-400" title={`Renewal is ${ratio.toFixed(1)}x the registration price`}>
<AlertTriangle className="w-3.5 h-3.5" />
</span>
)
}
return null
}
const currentPage = Math.floor(pagination.offset / pagination.limit) + 1
const totalPages = Math.ceil(pagination.total / pagination.limit)
if (authLoading) {
return (
<div className="min-h-screen flex items-center justify-center bg-[#020202]">
<div className="w-5 h-5 border-2 border-accent border-t-transparent rounded-full animate-spin" />
</div>
)
}
if (authLoading) return null
return (
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Cinematic Background - Matches Landing Page */}
{/* Background Atmosphere - Matched with Acquire */}
<div className="fixed inset-0 pointer-events-none z-0">
{/* Fine Noise */}
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.04] mix-blend-overlay" />
{/* Architectural Grid - Ultra fine */}
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div
className="absolute inset-0 opacity-[0.03]"
style={{
@ -230,324 +142,251 @@ export default function DiscoverPage() {
backgroundSize: '160px 160px',
}}
/>
{/* Ambient Light - Very Subtle */}
<div className="absolute top-[-30%] left-1/2 -translate-x-1/2 w-[1200px] h-[800px] bg-accent/[0.03] rounded-full blur-[180px]" />
<div className="absolute top-[20%] right-[-10%] w-[800px] h-[800px] bg-accent/[0.02] rounded-full blur-[150px]" />
</div>
<Header />
<main className="relative z-10 pt-32 sm:pt-40 pb-20 sm:pb-28 px-4 sm:px-6 flex-1">
<div className="max-w-7xl mx-auto">
{/* Header */}
<div className="text-center mb-12 sm:mb-16 animate-fade-in">
<div className="inline-flex items-center gap-2 px-4 py-2 rounded-full bg-accent/5 border border-accent/20 text-accent text-sm mb-6">
<Sparkles className="w-4 h-4" />
<span>Domain Intelligence</span>
</div>
<h1 className="font-display text-[2.5rem] sm:text-[3.5rem] md:text-[4.5rem] leading-[0.95] tracking-[-0.03em] text-white">
Discover
<span className="block text-accent">Market Opportunities</span>
<main className="relative pt-32 sm:pt-40 pb-20 sm:pb-28 px-4 sm:px-6 flex-1">
<div className="max-w-[1400px] mx-auto">
{/* Header Section - Matched with Acquire */}
<div className="mb-16 sm:mb-20 animate-fade-in text-center lg:text-left">
<div className="flex flex-col lg:flex-row justify-between items-end gap-8 border-b border-white/[0.08] pb-12">
<div>
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block flex items-center gap-2 justify-center lg:justify-start">
<div className="w-1.5 h-1.5 bg-accent animate-pulse" />
Global Intelligence
</span>
<h1 className="font-display text-[3.5rem] sm:text-[5rem] md:text-[6rem] lg:text-[7rem] leading-[0.9] tracking-[-0.04em] text-white">
Market Pulse.
</h1>
<p className="mt-5 text-lg sm:text-xl text-white/50 max-w-2xl mx-auto font-light">
Don&apos;t fall for promo prices. See renewal costs, spot traps, and track price trends across {pagination.total}+ extensions.
<p className="mt-8 text-lg sm:text-xl text-white/50 max-w-2xl font-light leading-relaxed mx-auto lg:mx-0">
Real-time inflation monitor. Track pricing, renewal risks, and breakout trends.
<span className="block mt-2 text-white/80">Aggregated intelligence across 886+ TLDs.</span>
</p>
{/* Feature Pills */}
<div className="flex flex-wrap items-center justify-center gap-3 mt-8">
<div className="flex items-center gap-2 px-4 py-2 bg-white/5 border border-white/5 rounded-full text-sm backdrop-blur-sm">
<AlertTriangle className="w-4 h-4 text-amber-400" />
<span className="text-white/60">Renewal Trap Detection</span>
</div>
<div className="flex items-center gap-2 px-4 py-2 bg-white/5 border border-white/5 rounded-full text-sm backdrop-blur-sm">
<div className="flex items-center gap-1">
<span className="w-1.5 h-1.5 rounded-full bg-accent" />
<span className="w-1.5 h-1.5 rounded-full bg-amber-400" />
<span className="w-1.5 h-1.5 rounded-full bg-red-400" />
</div>
<span className="text-white/60">Risk Levels</span>
</div>
<div className="flex items-center gap-2 px-4 py-2 bg-white/5 border border-white/5 rounded-full text-sm backdrop-blur-sm">
<TrendingUp className="w-4 h-4 text-orange-400" />
<span className="text-white/60">1y/3y Trends</span>
</div>
</div>
</div>
{/* Login Banner for non-authenticated users */}
{!isAuthenticated && (
<div className="mb-8 p-6 bg-gradient-to-r from-accent/10 to-accent/5 border border-accent/20 rounded-2xl animate-fade-in relative overflow-hidden group">
<div className="absolute inset-0 bg-accent/5 opacity-0 group-hover:opacity-100 transition-opacity duration-500" />
<div className="relative flex flex-col sm:flex-row items-center justify-between gap-4">
<div className="flex items-center gap-4">
<div className="w-12 h-12 bg-accent/20 rounded-xl flex items-center justify-center border border-accent/20">
<Lock className="w-6 h-6 text-accent" />
<div className="grid grid-cols-2 gap-12 text-right hidden lg:grid">
<div>
<div className="text-3xl font-display text-white mb-1">886+</div>
<div className="text-[10px] uppercase tracking-widest text-white/30 font-mono">TLDs Monitored</div>
</div>
<div>
<p className="font-medium text-white text-lg">Stop overpaying. Know the true costs.</p>
<p className="text-sm text-white/50">
Unlock renewal prices and risk analysis for all {pagination.total}+ TLDs.
</p>
<div className="text-3xl font-display text-white mb-1">24/7</div>
<div className="text-[10px] uppercase tracking-widest text-accent font-mono">Live Sync</div>
</div>
</div>
<Link
href="/register"
className="shrink-0 px-6 py-3 bg-accent text-[#020202] font-bold rounded-none clip-path-slant-sm
hover:bg-accent-hover transition-all shadow-[0_0_20px_rgba(16,185,129,0.3)] uppercase tracking-wide text-sm"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
Start Hunting
</Link>
</div>
</div>
{/* Top Movers Cards */}
{topGainer && topVolume && highRisk && (
<div className="grid grid-cols-1 md:grid-cols-3 gap-6 mb-16 animate-fade-in">
<StatCard
label="Top Gainer (7d)"
value={`.${topGainer.tld.toUpperCase()}`}
subvalue={`+${topGainer.change_7d}% Growth`}
trend="up"
icon={TrendingUp}
color="accent"
/>
<StatCard
label="Highest Volume"
value={`.${topVolume.tld.toUpperCase()}`}
subvalue={`${(topVolume.volume / 1000).toFixed(0)}k Daily Ops`}
trend="up"
icon={BarChart3}
color="blue"
/>
<StatCard
label="Inflation Risk"
value={`.${highRisk.tld.toUpperCase()}`}
subvalue="Renewal Price Spike"
trend="down"
icon={AlertTriangle}
color="red"
/>
</div>
)}
{/* Trending Section - Top Movers */}
{trending.length > 0 && (
<div className="mb-12 sm:mb-16 animate-slide-up">
<h2 className="text-lg font-medium text-white mb-6 flex items-center gap-2">
<TrendingUp className="w-5 h-5 text-accent" />
Top Movers
</h2>
<div className="grid sm:grid-cols-2 lg:grid-cols-4 gap-3 sm:gap-4">
{trending.map((item) => (
<Link
key={item.tld}
href={`/discover/${item.tld}`}
className="p-5 bg-white/[0.02] border border-white/[0.08] rounded-xl hover:border-accent/30 hover:bg-white/[0.04] transition-all duration-300 text-left group backdrop-blur-sm"
{/* Tech Bar - Filter & Search - Matched Style */}
<div className="mb-10 animate-slide-up sticky top-20 z-30 backdrop-blur-xl bg-[#020202]/90 border-y border-white/[0.08] py-5 -mx-4 px-4 sm:mx-0 sm:px-0">
<div className="flex flex-col lg:flex-row gap-5 justify-between items-center max-w-[1400px] mx-auto">
<div className="relative w-full lg:w-[480px] group">
<Search className="absolute left-5 top-1/2 -translate-y-1/2 w-5 h-5 text-white/40 group-focus-within:text-accent transition-colors" />
<input
type="text"
placeholder="SEARCH_TLDS..."
value={searchQuery}
onChange={(e) => setSearchQuery(e.target.value)}
className="w-full pl-14 pr-5 py-3.5 bg-[#0A0A0A] border border-white/10 text-white placeholder:text-white/20 font-mono text-base focus:outline-none focus:border-accent focus:bg-[#0F0F0F] transition-all rounded-none"
/>
</div>
<div className="flex gap-4 overflow-x-auto pb-2 lg:pb-0 w-full lg:w-auto">
{[
{ id: 'volume', label: 'Volume' },
{ id: 'change', label: 'Momentum' },
{ id: 'price', label: 'Buy Price' },
{ id: 'risk', label: 'Risk Factor' }
].map((filter) => (
<button
key={filter.id}
onClick={() => setSortBy(filter.id as any)}
className={clsx(
"px-6 py-3.5 flex items-center gap-2 text-xs font-bold uppercase tracking-widest transition-all border border-white/10 bg-[#0A0A0A] hover:bg-white/5 whitespace-nowrap",
sortBy === filter.id ? "text-accent border-accent" : "text-white/40 hover:text-white"
)}
>
<div className="flex items-center justify-between mb-3">
<span className="font-mono text-xl text-white group-hover:text-accent transition-colors">.{item.tld}</span>
<span className={clsx(
"text-xs font-medium px-2 py-0.5 rounded-full border",
item.price_change > 0
? "text-orange-400 bg-orange-400/10 border-orange-400/20"
: "text-accent bg-accent/10 border-accent/20"
)}>
{item.price_change > 0 ? '+' : ''}{item.price_change.toFixed(1)}%
</span>
</div>
<p className="text-sm text-white/50 mb-3 line-clamp-2 min-h-[2.5em]">
{item.reason}
</p>
<div className="flex items-center justify-between pt-3 border-t border-white/5">
<span className="text-xs text-white/40 uppercase tracking-wider">Current Price</span>
<span className="text-sm text-white/70 font-mono">
${item.current_price.toFixed(2)}/yr
</span>
</div>
</Link>
{filter.label}
</button>
))}
</div>
</div>
)}
{/* Search & Sort Controls */}
<div className="flex flex-col sm:flex-row gap-4 mb-6 animate-slide-up">
<div className="relative flex-1 max-w-md">
<Search className="absolute left-4 top-1/2 -translate-y-1/2 w-5 h-5 text-white/30" />
<input
type="text"
placeholder="Search TLDs (e.g., com, io, ai)..."
value={searchQuery}
onChange={(e) => {
setSearchQuery(e.target.value)
setPage(0)
}}
className="w-full pl-12 pr-10 py-3.5 bg-white/[0.03] border border-white/[0.08] rounded-xl
text-white placeholder:text-white/30
focus:outline-none focus:ring-1 focus:ring-accent/50 focus:border-accent/50
transition-all duration-300"
/>
{searchQuery && (
<button
onClick={() => {
setSearchQuery('')
setPage(0)
}}
className="absolute right-4 top-1/2 -translate-y-1/2 p-1 text-white/30 hover:text-white transition-colors"
>
<X className="w-4 h-4" />
</button>
)}
</div>
<div className="relative">
<select
value={sortBy}
onChange={(e) => {
setSortBy(e.target.value)
setPage(0)
}}
className="appearance-none pl-4 pr-10 py-3.5 bg-white/[0.03] border border-white/[0.08] rounded-xl
text-white focus:outline-none focus:ring-1 focus:ring-accent/50 focus:border-accent/50
transition-all cursor-pointer min-w-[180px]"
>
<option value="popularity" className="bg-[#0a0a0a]">Most Popular</option>
<option value="name" className="bg-[#0a0a0a]">Alphabetical</option>
<option value="price_asc" className="bg-[#0a0a0a]">Price: Low High</option>
<option value="price_desc" className="bg-[#0a0a0a]">Price: High Low</option>
</select>
<ArrowUpDown className="absolute right-3 top-1/2 -translate-y-1/2 w-4 h-4 text-white/30 pointer-events-none" />
</div>
</div>
{/* Data Grid - Matched Font Sizes and Styles */}
<div className="border border-white/[0.08] bg-[#050505] animate-slide-up shadow-2xl mb-20">
<div className="overflow-x-auto">
<table className="w-full">
<thead>
<tr className="bg-[#0A0A0A] border-b border-white/[0.08]">
<th className="text-left px-8 py-5 text-xs uppercase tracking-widest text-white/40 font-bold">Asset Class</th>
<th className="text-right px-8 py-5 text-xs uppercase tracking-widest text-white/40 font-bold">Buy Price</th>
<th className="text-right px-8 py-5 text-xs uppercase tracking-widest text-white/40 font-bold">Trend (7d)</th>
<th className="text-right px-8 py-5 text-xs uppercase tracking-widest text-white/40 font-bold hidden md:table-cell">Renewal Cost</th>
<th className="text-right px-8 py-5 text-xs uppercase tracking-widest text-white/40 font-bold hidden lg:table-cell">Registrations (24h)</th>
<th className="text-center px-8 py-5 text-xs uppercase tracking-widest text-white/40 font-bold hidden lg:table-cell">Risk Level</th>
<th className="px-8 py-5"></th>
</tr>
</thead>
<tbody className="divide-y divide-white/[0.03]">
{filteredTlds.map((tld) => {
const isLocked = !isAuthenticated && !isPublicTld(tld.tld)
{/* TLD Table */}
<PremiumTable
data={tlds}
keyExtractor={(tld) => tld.tld}
loading={loading}
onRowClick={(tld) => {
window.location.href = `/discover/${tld.tld}`
}}
emptyIcon={<Globe className="w-12 h-12 text-white/20" />}
emptyTitle="No TLDs found"
emptyDescription={searchQuery ? `No TLDs matching "${searchQuery}"` : "Check back later for TLD data"}
columns={[
{
key: 'tld',
header: 'TLD',
width: '100px',
render: (tld) => (
<div className="flex items-center gap-2">
<span className="font-mono text-lg font-semibold text-white group-hover:text-accent transition-colors">
.{tld.tld}
</span>
</div>
),
},
{
key: 'buy_price',
header: 'Current Price',
align: 'right',
width: '120px',
render: (tld) => (
<span className="font-semibold text-white/90 tabular-nums">
${tld.min_registration_price.toFixed(2)}
</span>
),
},
{
key: 'trend',
header: 'Trend (1y)',
width: '100px',
hideOnMobile: true,
render: (tld) => {
const change = tld.price_change_1y || 0
return (
<div className="flex items-center gap-2">
<Sparkline trend={change} />
<tr key={tld.tld} className="group hover:bg-[#0F0F0F] transition-all duration-200 border-l-2 border-transparent hover:border-accent">
<td className="px-8 py-6">
<Link href={`/discover/${tld.tld}`} className="flex items-center gap-4 group-hover:translate-x-2 transition-transform duration-300">
{/* Changed to font-mono and adjusted size to match Acquire's tech look while being distinct for TLDs */}
<span className="font-mono text-2xl font-medium text-white group-hover:text-accent transition-colors tracking-tight">.{tld.tld}</span>
{tld.change_7d > 10 && <Flame className="w-4 h-4 text-accent animate-pulse" />}
</Link>
</td>
<td className="px-8 py-6 text-right">
<div className="flex flex-col items-end">
{/* Matched font-mono text-lg from Acquire */}
<span className="font-mono text-lg font-medium text-white">${tld.price}</span>
<span className="text-[10px] text-white/30 uppercase tracking-widest">Entry</span>
</div>
</td>
<td className="px-8 py-6 text-right">
<div className="flex flex-col items-end">
<span className={clsx(
"font-medium tabular-nums text-sm",
change > 0 ? "text-orange-400" : change < 0 ? "text-accent" : "text-white/30"
"font-mono text-base flex items-center gap-1",
tld.change_7d > 0 ? "text-accent" : tld.change_7d < 0 ? "text-red-400" : "text-white/40"
)}>
{change > 0 ? '+' : ''}{change.toFixed(0)}%
{tld.change_7d > 0 ? <TrendingUp className="w-3 h-3"/> : tld.change_7d < 0 ? <TrendingDown className="w-3 h-3"/> : <Minus className="w-3 h-3"/>}
{Math.abs(tld.change_7d)}%
</span>
<span className="text-[10px] text-white/30 uppercase tracking-widest">Momentum</span>
</div>
)
},
},
{
key: 'renew_price',
header: 'Renewal Price',
align: 'right',
width: '130px',
render: (tld) => {
const showData = isAuthenticated || isPublicPreviewTld(tld)
if (!showData) {
return (
<div className="flex items-center gap-1 justify-end group/lock">
<span className="text-white/30 blur-[4px] select-none group-hover/lock:blur-none transition-all duration-300">$XX.XX</span>
<Lock className="w-3 h-3 text-white/20" />
</div>
)
}
return (
<div className="flex items-center gap-1 justify-end">
<span className="text-white/50 tabular-nums">
${tld.min_renewal_price?.toFixed(2) || '—'}
</span>
{getRenewalTrap(tld)}
</div>
)
},
},
{
key: 'risk',
header: 'Risk Level',
align: 'center',
width: '140px',
render: (tld) => {
const showData = isAuthenticated || isPublicPreviewTld(tld)
if (!showData) {
return (
<div className="flex items-center justify-center gap-1">
<span className="inline-flex items-center gap-1 px-2 py-0.5 rounded-full text-xs font-medium bg-white/5 blur-[4px] select-none">
<span className="w-2.5 h-2.5 rounded-full bg-white/20" />
<span className="hidden sm:inline ml-1 text-white/20">Hidden</span>
</span>
<Lock className="w-3 h-3 text-white/20" />
</div>
)
}
return getRiskBadge(tld)
},
},
{
key: 'actions',
header: '',
align: 'right',
width: '80px',
render: () => (
<ChevronRight className="w-5 h-5 text-white/20 group-hover:text-accent transition-colors" />
),
},
]}
/>
</td>
{/* Pagination */}
{!loading && pagination.total > pagination.limit && (
<div className="flex items-center justify-center gap-4 pt-6">
<button
onClick={() => setPage(Math.max(0, page - 1))}
disabled={page === 0}
className="px-4 py-2 text-sm font-medium text-white/50 hover:text-white
bg-white/5 hover:bg-white/10 rounded-lg border border-white/5
disabled:opacity-50 disabled:cursor-not-allowed transition-colors"
>
Previous
</button>
<span className="text-sm text-white/50 tabular-nums font-mono">
Page {currentPage} of {totalPages}
</span>
<button
onClick={() => setPage(page + 1)}
disabled={!pagination.has_more}
className="px-4 py-2 text-sm font-medium text-white/50 hover:text-white
bg-white/5 hover:bg-white/10 rounded-lg border border-white/5
disabled:opacity-50 disabled:cursor-not-allowed transition-colors"
>
Next
</button>
{/* Renewal Price - Locked for guests */}
<td className="px-8 py-6 text-right hidden md:table-cell">
{isLocked ? (
<div className="flex justify-end items-center gap-2 text-white/20 select-none">
<Lock className="w-3 h-3" />
<span className="blur-[4px] font-mono text-lg">$XX.XX</span>
</div>
) : (
<div className="flex flex-col items-end">
<span className={clsx(
"font-mono text-lg font-medium text-white/80",
tld.renewal_price > tld.price * 2 ? "text-red-400" : "text-white/80"
)}>${tld.renewal_price}</span>
<span className="text-[10px] text-white/30 uppercase tracking-widest">Recurring</span>
</div>
)}
</td>
{/* Stats */}
{!loading && (
<div className="mt-6 flex justify-center">
<p className="text-xs text-white/30 uppercase tracking-widest font-medium">
{searchQuery
? `Found ${pagination.total} TLDs matching "${searchQuery}"`
: `${pagination.total} TLDs tracked in real-time`
}
{/* Volume - Locked for guests */}
<td className="px-8 py-6 text-right hidden lg:table-cell">
{isLocked ? (
<div className="flex justify-end items-center gap-2 text-white/20 select-none">
<span className="blur-[4px] font-mono text-base">XXXX</span>
</div>
) : (
<span className="font-mono text-base text-white/60">{tld.registration_count.toLocaleString()}</span>
)}
</td>
{/* Risk Level - Locked for guests */}
<td className="px-8 py-6 text-center hidden lg:table-cell">
{isLocked ? (
<div className="flex justify-center">
<span className="bg-white/5 text-white/20 text-[10px] font-bold uppercase tracking-widest px-3 py-1 blur-[2px]">LOCKED</span>
</div>
) : (
<span className={clsx(
"text-[10px] font-bold uppercase tracking-widest px-3 py-1 border",
tld.risk_level === 'Low' ? "border-accent/20 text-accent bg-accent/5" :
tld.risk_level === 'Medium' ? "border-amber-500/20 text-amber-500 bg-amber-500/5" :
"border-red-500/20 text-red-500 bg-red-500/5"
)}>
{tld.risk_level}
</span>
)}
</td>
<td className="px-8 py-6 text-right">
<Link
href={`/discover/${tld.tld}`}
className="inline-flex items-center justify-center w-10 h-10 border border-white/10 text-white/40 hover:text-black hover:bg-white hover:border-white transition-all duration-300 group-hover:border-accent group-hover:text-accent opacity-0 group-hover:opacity-100 transform translate-x-2 group-hover:translate-x-0"
>
<ArrowUpRight className="w-4 h-4" />
</Link>
</td>
</tr>
)
})}
</tbody>
</table>
</div>
</div>
{/* CTA for Locked Data */}
{!isAuthenticated && (
<div className="mt-20 p-px bg-gradient-to-r from-accent/20 via-white/5 to-accent/20 max-w-4xl mx-auto">
<div className="bg-[#080808] p-12 text-center relative overflow-hidden">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.05]" />
<div className="relative z-10">
<div className="inline-flex items-center justify-center w-12 h-12 border border-accent/20 bg-accent/5 text-accent mb-6">
<ShieldAlert className="w-6 h-6" />
</div>
<h3 className="text-3xl font-display text-white mb-4">Protect Your Capital.</h3>
<p className="text-white/50 mb-8 max-w-lg mx-auto text-lg font-light leading-relaxed">
Don't buy a cheap domain with expensive renewal fees.
Our 'Trader' plan reveals hidden costs and risk levels for every TLD.
</p>
<Link
href="/pricing"
className="inline-flex items-center gap-3 px-8 py-4 bg-accent text-black text-xs font-bold uppercase tracking-widest hover:bg-white transition-all"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
Unlock Intelligence
<Zap className="w-4 h-4" />
</Link>
</div>
</div>
</div>
)}
</div>
</main>
<Footer />
</div>
)
}

View File

@ -4,7 +4,7 @@ import { useState } from 'react'
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { api } from '@/lib/api'
import { Mail, ArrowLeft, CheckCircle, AlertCircle } from 'lucide-react'
import { Mail, ArrowLeft, CheckCircle, AlertCircle, Loader2 } from 'lucide-react'
import Link from 'next/link'
import clsx from 'clsx'
@ -31,96 +31,116 @@ export default function ForgotPasswordPage() {
}
return (
<>
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Living Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none overflow-hidden">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.04] mix-blend-overlay z-10" />
{/* Animated Orbs */}
<div className="absolute top-[10%] right-[20%] w-[50vw] h-[50vw] bg-accent/5 rounded-full blur-[120px] animate-pulse-slow mix-blend-screen" />
<div className="absolute bottom-[10%] left-[20%] w-[40vw] h-[40vw] bg-blue-500/5 rounded-full blur-[100px] animate-blob mix-blend-screen" />
{/* Grid Overlay */}
<div
className="absolute inset-0 opacity-[0.03] z-0"
style={{
backgroundImage: `linear-gradient(rgba(255,255,255,0.3) 0.5px, transparent 0.5px), linear-gradient(90deg, rgba(255,255,255,0.3) 0.5px, transparent 0.5px)`,
backgroundSize: '40px 40px',
}}
/>
</div>
<Header />
<main className="min-h-screen flex items-center justify-center p-4 pt-24">
<div className="w-full max-w-md">
<Link
href="/login"
className="inline-flex items-center gap-2 text-foreground-muted hover:text-foreground mb-8 transition-colors"
>
<ArrowLeft className="w-4 h-4" />
Back to login
</Link>
<main className="min-h-screen flex items-center justify-center px-4 sm:px-6 py-20 relative z-10">
<div className="w-full max-w-[450px] animate-fade-in">
<div className="bg-[#050505] border border-white/10 relative p-8 sm:p-10 shadow-2xl">
{/* Tech Corners */}
<div className="absolute -top-px -left-px w-4 h-4 border-t border-l border-white/40" />
<div className="absolute -top-px -right-px w-4 h-4 border-t border-r border-white/40" />
<div className="absolute -bottom-px -left-px w-4 h-4 border-b border-l border-white/40" />
<div className="absolute -bottom-px -right-px w-4 h-4 border-b border-r border-white/40" />
{success ? (
<div className="bg-background-secondary/50 border border-border rounded-2xl p-8 text-center">
<div className="w-16 h-16 bg-accent/10 rounded-full flex items-center justify-center mx-auto mb-6">
<div className="text-center">
<div className="w-16 h-16 bg-accent/10 border border-accent/20 flex items-center justify-center mx-auto mb-8 rounded-none">
<CheckCircle className="w-8 h-8 text-accent" />
</div>
<h1 className="text-display-sm font-bold text-foreground mb-4">
Check your inbox
<h1 className="font-display text-2xl text-white mb-4">
Protocol Initiated
</h1>
<p className="text-foreground-muted mb-6">
If <strong className="text-foreground">{email}</strong> is registered,
you&apos;ll get a reset link. Valid for 1 hour.
<p className="text-sm font-mono text-white/50 mb-8 leading-relaxed">
If <strong className="text-white">{email}</strong> exists in our database, a reset link has been dispatched. Link valid for 60 minutes.
</p>
<p className="text-body-sm text-foreground-subtle">
Didn't receive the email? Check your spam folder or{' '}
<button
onClick={() => setSuccess(false)}
className="text-accent hover:underline"
className="text-xs font-bold uppercase tracking-[0.2em] text-white/40 hover:text-white transition-colors"
>
try again
Try different email
</button>
</p>
</div>
) : (
<div className="bg-background-secondary/50 border border-border rounded-2xl p-8">
<div className="text-center mb-8">
<h1 className="text-display-sm font-bold text-foreground mb-2">
Reset your password
<>
<div className="text-center mb-10">
<h1 className="font-display text-2xl text-white mb-2">
Reset Credentials
</h1>
<p className="text-foreground-muted">
Enter your email. We&apos;ll send a reset link.
<p className="text-xs font-mono text-white/40">
Enter your email to receive a recovery link.
</p>
</div>
<form onSubmit={handleSubmit} className="space-y-6">
{error && (
<div className="flex items-center gap-3 p-4 bg-danger/10 border border-danger/20 rounded-xl text-danger">
<AlertCircle className="w-5 h-5 flex-shrink-0" />
<p className="text-body-sm">{error}</p>
<div className="p-3 bg-red-500/10 border border-red-500/20">
<p className="text-red-500 text-xs font-mono text-center uppercase tracking-wider">{error}</p>
</div>
)}
<div>
<label htmlFor="email" className="block text-body-sm font-medium text-foreground mb-2">
Email address
</label>
<div className="relative">
<Mail className="absolute left-4 top-1/2 -translate-y-1/2 w-5 h-5 text-foreground-muted" />
<div className="group">
<label className="text-[10px] font-mono text-white/40 uppercase tracking-widest mb-2 block group-focus-within:text-white/70 transition-colors">Email Address</label>
<input
id="email"
type="email"
value={email}
onChange={(e) => setEmail(e.target.value)}
placeholder="OPERATOR@POUNCE.IO"
required
placeholder="you@example.com"
className="w-full pl-12 pr-4 py-3 bg-background-tertiary border border-border rounded-xl text-foreground placeholder:text-foreground-subtle focus:outline-none focus:ring-2 focus:ring-accent/30 focus:border-accent transition-all"
autoComplete="email"
className="w-full bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none"
/>
</div>
</div>
<button
type="submit"
disabled={loading}
className={clsx(
'w-full py-3 px-4 bg-accent text-background font-medium rounded-xl transition-all',
loading
? 'opacity-50 cursor-not-allowed'
: 'hover:bg-accent-hover active:scale-[0.98]'
)}
className="w-full py-4 bg-white text-black text-xs font-bold uppercase tracking-[0.2em] hover:bg-accent transition-all disabled:opacity-50 disabled:cursor-not-allowed flex items-center justify-center gap-3"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
{loading ? 'Sending...' : 'Send reset link'}
{loading ? (
<Loader2 className="w-4 h-4 animate-spin" />
) : (
'Send Reset Link'
)}
</button>
</form>
</div>
</>
)}
<div className="mt-8 pt-8 border-t border-white/10 text-center">
<Link
href="/login"
className="inline-flex items-center gap-2 text-xs font-mono text-white/40 hover:text-white transition-colors uppercase tracking-wider"
>
<ArrowLeft className="w-3 h-3" />
Return to Login
</Link>
</div>
</div>
</div>
</main>
<Footer />
</>
</div>
)
}

View File

@ -0,0 +1,121 @@
'use client'
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { Building, Globe, Mail, Phone, FileBadge } from 'lucide-react'
export default function ImprintPage() {
return (
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none z-0">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div className="absolute top-0 left-1/2 -translate-x-1/2 w-[800px] h-[400px] bg-accent/[0.02] rounded-full blur-[120px]" />
</div>
<Header />
<main className="relative pt-32 sm:pt-48 pb-20 px-4 sm:px-6 flex-1">
<div className="max-w-[1000px] mx-auto">
{/* Document Header */}
<div className="mb-20 text-center relative">
<div className="inline-flex items-center gap-2 px-3 py-1 bg-white/5 border border-white/10 rounded-full mb-6 backdrop-blur-md">
<Globe className="w-3 h-3 text-accent" />
<span className="text-[10px] font-mono uppercase tracking-[0.2em] text-white/70">Entity Information</span>
</div>
<h1 className="font-display text-5xl sm:text-7xl text-white mb-6 tracking-tight">
Imprint
</h1>
<div className="flex items-center justify-center gap-6 text-[10px] font-mono text-white/30 uppercase tracking-widest">
<span>Last Updated: 2024.10.12</span>
<span className="w-1 h-1 bg-white/20 rounded-full" />
<span>Ref: IMP-2024-X</span>
</div>
</div>
{/* Grid Container */}
<div className="grid grid-cols-1 md:grid-cols-2 gap-px bg-white/10 border border-white/10">
{/* Operator */}
<div className="bg-[#050505] p-10 sm:p-16 relative group hover:bg-[#080808] transition-colors">
<div className="absolute top-6 right-6 opacity-20 group-hover:opacity-40 transition-opacity">
<Building className="w-6 h-6 text-white" />
</div>
<h3 className="text-xs font-bold uppercase tracking-[0.2em] text-accent mb-8">Operator</h3>
<div className="space-y-2 font-display text-2xl text-white">
<p>POUNCE AG</p>
<p className="text-white/40">Bahnhofstrasse 100</p>
<p className="text-white/40">8001 Zurich</p>
<p className="text-white/40">Switzerland</p>
</div>
</div>
{/* Contact */}
<div className="bg-[#050505] p-10 sm:p-16 relative group hover:bg-[#080808] transition-colors">
<div className="absolute top-6 right-6 opacity-20 group-hover:opacity-40 transition-opacity">
<Mail className="w-6 h-6 text-white" />
</div>
<h3 className="text-xs font-bold uppercase tracking-[0.2em] text-accent mb-8">Contact</h3>
<div className="space-y-6">
<div>
<p className="text-[10px] font-mono uppercase tracking-widest text-white/30 mb-2">Electronic Mail</p>
<a href="mailto:hello@pounce.ch" className="font-display text-2xl text-white hover:text-accent transition-colors">hello@pounce.ch</a>
</div>
<div>
<p className="text-[10px] font-mono uppercase tracking-widest text-white/30 mb-2">Phone</p>
<p className="font-display text-2xl text-white/60">+41 44 000 00 00</p>
</div>
</div>
</div>
{/* Registry */}
<div className="bg-[#050505] p-10 sm:p-16 relative group hover:bg-[#080808] transition-colors">
<div className="absolute top-6 right-6 opacity-20 group-hover:opacity-40 transition-opacity">
<FileBadge className="w-6 h-6 text-white" />
</div>
<h3 className="text-xs font-bold uppercase tracking-[0.2em] text-accent mb-8">Registration</h3>
<div className="space-y-6">
<div className="flex justify-between items-end border-b border-white/5 pb-4">
<span className="text-sm font-mono text-white/40">Commercial Register</span>
<span className="text-lg font-display text-white">Pounce AG</span>
</div>
<div className="flex justify-between items-end border-b border-white/5 pb-4">
<span className="text-sm font-mono text-white/40">Number</span>
<span className="text-lg font-display text-white">CHE-000.000.000</span>
</div>
<div className="flex justify-between items-end border-b border-white/5 pb-4">
<span className="text-sm font-mono text-white/40">Authority</span>
<span className="text-lg font-display text-white">Handelsregisteramt Zürich</span>
</div>
</div>
</div>
{/* VAT */}
<div className="bg-[#050505] p-10 sm:p-16 relative group hover:bg-[#080808] transition-colors">
<div className="absolute top-6 right-6 opacity-20 group-hover:opacity-40 transition-opacity">
<Globe className="w-6 h-6 text-white" />
</div>
<h3 className="text-xs font-bold uppercase tracking-[0.2em] text-accent mb-8">Tax Identification</h3>
<div className="space-y-6">
<div>
<p className="text-[10px] font-mono uppercase tracking-widest text-white/30 mb-2">VAT Number</p>
<p className="font-display text-2xl text-white">CHE-000.000.000 MWST</p>
</div>
</div>
</div>
</div>
<div className="mt-16 text-center">
<p className="font-mono text-xs text-white/30 max-w-2xl mx-auto leading-relaxed">
<strong>Disclaimer:</strong> Despite careful control, we assume no liability for the content of external links. The operators of the linked pages are solely responsible for their content.
</p>
</div>
</div>
</main>
<Footer />
</div>
)
}

View File

@ -0,0 +1,171 @@
'use client'
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { Shield, Lock, Eye, Database, Server, FileText } from 'lucide-react'
export default function PrivacyPage() {
return (
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none z-0">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div className="absolute top-0 right-0 w-[500px] h-[500px] bg-blue-500/[0.03] rounded-full blur-[120px]" />
<div className="absolute bottom-0 left-0 w-[500px] h-[500px] bg-accent/[0.02] rounded-full blur-[120px]" />
</div>
<Header />
<main className="relative pt-32 sm:pt-48 pb-20 px-4 sm:px-6 flex-1">
<div className="max-w-[1000px] mx-auto">
{/* Document Header */}
<div className="mb-20 text-center relative">
<div className="inline-flex items-center gap-2 px-3 py-1 bg-white/5 border border-white/10 rounded-full mb-6 backdrop-blur-md">
<Shield className="w-3 h-3 text-accent" />
<span className="text-[10px] font-mono uppercase tracking-[0.2em] text-white/70">Protocol Alpha-9</span>
</div>
<h1 className="font-display text-5xl sm:text-7xl text-white mb-6 tracking-tight">
Privacy Policy
</h1>
<div className="flex items-center justify-center gap-6 text-[10px] font-mono text-white/30 uppercase tracking-widest">
<span>Last Updated: 2024.10.12</span>
<span className="w-1 h-1 bg-white/20 rounded-full" />
<span>Ref: PRIV-2024-X</span>
</div>
</div>
{/* Document Container */}
<div className="relative">
{/* Tech Borders */}
<div className="absolute -top-px left-0 w-20 h-px bg-gradient-to-r from-transparent via-white/20 to-transparent" />
<div className="absolute -bottom-px right-0 w-20 h-px bg-gradient-to-r from-transparent via-white/20 to-transparent" />
<div className="bg-[#050505]/80 backdrop-blur-xl border border-white/10 p-8 sm:p-16 relative overflow-hidden">
{/* Watermark */}
<div className="absolute top-0 right-0 p-8 opacity-[0.02] pointer-events-none">
<Shield className="w-96 h-96" />
</div>
{/* Intro */}
<div className="mb-16 border-l-2 border-accent pl-8 py-2">
<p className="font-display text-2xl sm:text-3xl text-white leading-relaxed">
We collect minimal data. We protect it like our own. <br/>
<span className="text-white/40">We don&apos;t sell it. Ever.</span>
</p>
</div>
{/* Sections */}
<div className="space-y-16">
{/* Section 1 */}
<section className="group">
<div className="flex items-start gap-6">
<div className="hidden sm:flex flex-col items-center gap-2 mt-2">
<div className="w-8 h-8 rounded-full border border-white/10 flex items-center justify-center bg-white/5 group-hover:border-accent/50 transition-colors">
<span className="font-mono text-xs text-white/50 group-hover:text-accent">01</span>
</div>
<div className="w-px h-full bg-white/5 group-hover:bg-white/10 min-h-[100px]" />
</div>
<div className="flex-1">
<h3 className="font-display text-2xl text-white mb-6 flex items-center gap-3">
<Database className="w-5 h-5 text-white/30" />
Data Collection
</h3>
<div className="grid sm:grid-cols-2 gap-4">
{[
'Account credentials (hashed)',
'Billing information (Stripe)',
'Domain watchlists',
'Search telemetry'
].map((item) => (
<div key={item} className="p-4 bg-white/5 border border-white/5 rounded-none flex items-center gap-3">
<div className="w-1.5 h-1.5 bg-accent/50" />
<span className="font-mono text-sm text-white/70">{item}</span>
</div>
))}
</div>
</div>
</div>
</section>
{/* Section 2 */}
<section className="group">
<div className="flex items-start gap-6">
<div className="hidden sm:flex flex-col items-center gap-2 mt-2">
<div className="w-8 h-8 rounded-full border border-white/10 flex items-center justify-center bg-white/5 group-hover:border-accent/50 transition-colors">
<span className="font-mono text-xs text-white/50 group-hover:text-accent">02</span>
</div>
<div className="w-px h-full bg-white/5 group-hover:bg-white/10 min-h-[100px]" />
</div>
<div className="flex-1">
<h3 className="font-display text-2xl text-white mb-6 flex items-center gap-3">
<Eye className="w-5 h-5 text-white/30" />
Usage & Purpose
</h3>
<p className="font-mono text-sm text-white/50 leading-relaxed mb-6">
Your data is utilized strictly for operational efficiency. It enables the Real-Time Intelligence Engine to:
</p>
<ul className="space-y-3 font-mono text-sm text-white/60">
<li className="flex items-start gap-3">
<span className="text-accent mt-1">>></span>
Provide millisecond-latency domain availability checks.
</li>
<li className="flex items-start gap-3">
<span className="text-accent mt-1">>></span>
Execute automated acquisition strategies (Sniper Mode).
</li>
<li className="flex items-start gap-3">
<span className="text-accent mt-1">>></span>
Process encrypted transactions via secure gateways.
</li>
</ul>
</div>
</div>
</section>
{/* Section 3 */}
<section className="group">
<div className="flex items-start gap-6">
<div className="hidden sm:flex flex-col items-center gap-2 mt-2">
<div className="w-8 h-8 rounded-full border border-white/10 flex items-center justify-center bg-white/5 group-hover:border-accent/50 transition-colors">
<span className="font-mono text-xs text-white/50 group-hover:text-accent">03</span>
</div>
<div className="w-px h-full bg-white/5 group-hover:bg-white/10 min-h-[100px]" />
</div>
<div className="flex-1">
<h3 className="font-display text-2xl text-white mb-6 flex items-center gap-3">
<Lock className="w-5 h-5 text-white/30" />
Security Protocol
</h3>
<div className="bg-[#020202] border border-white/10 p-6 relative overflow-hidden">
<div className="absolute top-0 right-0 w-20 h-20 bg-accent/5 rounded-full blur-2xl" />
<p className="font-mono text-sm text-white/60 leading-relaxed relative z-10">
All transmissions are encrypted via <span className="text-white">TLS 1.3</span>. Databases are encrypted at rest using <span className="text-white">AES-256</span>. Access controls are strictly enforced via multi-factor authentication protocols. We employ automated threat detection to safeguard system integrity.
</p>
</div>
</div>
</div>
</section>
</div>
{/* Footer of Card */}
<div className="mt-20 pt-8 border-t border-white/10 flex justify-between items-center opacity-50">
<div className="h-8 w-32 bg-[url('/barcode.png')] bg-contain bg-no-repeat opacity-50" />
{/* Fallback text if image missing, or just styling */}
<div className="font-mono text-[10px] uppercase tracking-widest text-right">
Doc_ID: 993-221-AZ<br/>
Encrypted
</div>
</div>
</div>
</div>
</div>
</main>
<Footer />
</div>
)
}

View File

@ -0,0 +1,172 @@
'use client'
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { Scale, CheckCircle, AlertTriangle, FileText, Gavel, Ban } from 'lucide-react'
export default function TermsPage() {
return (
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none z-0">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div className="absolute top-0 left-0 w-[500px] h-[500px] bg-purple-500/[0.03] rounded-full blur-[120px]" />
<div className="absolute bottom-0 right-0 w-[500px] h-[500px] bg-accent/[0.02] rounded-full blur-[120px]" />
</div>
<Header />
<main className="relative pt-32 sm:pt-48 pb-20 px-4 sm:px-6 flex-1">
<div className="max-w-[1000px] mx-auto">
{/* Document Header */}
<div className="mb-20 text-center relative">
<div className="inline-flex items-center gap-2 px-3 py-1 bg-white/5 border border-white/10 rounded-full mb-6 backdrop-blur-md">
<FileText className="w-3 h-3 text-accent" />
<span className="text-[10px] font-mono uppercase tracking-[0.2em] text-white/70">Protocol Alpha-9</span>
</div>
<h1 className="font-display text-5xl sm:text-7xl text-white mb-6 tracking-tight">
Terms of Service
</h1>
<div className="flex items-center justify-center gap-6 text-[10px] font-mono text-white/30 uppercase tracking-widest">
<span>Last Updated: 2024.10.12</span>
<span className="w-1 h-1 bg-white/20 rounded-full" />
<span>Ref: TOS-2024-X</span>
</div>
</div>
{/* Document Container */}
<div className="relative">
{/* Tech Borders */}
<div className="absolute -top-px left-0 w-20 h-px bg-gradient-to-r from-transparent via-white/20 to-transparent" />
<div className="absolute -bottom-px right-0 w-20 h-px bg-gradient-to-r from-transparent via-white/20 to-transparent" />
<div className="bg-[#050505]/80 backdrop-blur-xl border border-white/10 p-8 sm:p-16 relative overflow-hidden">
{/* Watermark */}
<div className="absolute top-0 right-0 p-8 opacity-[0.02] pointer-events-none">
<Scale className="w-96 h-96" />
</div>
{/* Intro */}
<div className="mb-16 border-l-2 border-accent pl-8 py-2">
<p className="font-display text-2xl sm:text-3xl text-white leading-relaxed">
By accessing the POUNCE terminal, you agree to these operational protocols. <br/>
<span className="text-white/40">Read carefully.</span>
</p>
</div>
{/* Sections */}
<div className="space-y-16">
{/* Section 1 */}
<section className="group">
<div className="flex items-start gap-6">
<div className="hidden sm:flex flex-col items-center gap-2 mt-2">
<div className="w-8 h-8 rounded-full border border-white/10 flex items-center justify-center bg-white/5 group-hover:border-accent/50 transition-colors">
<span className="font-mono text-xs text-white/50 group-hover:text-accent">01</span>
</div>
<div className="w-px h-full bg-white/5 group-hover:bg-white/10 min-h-[100px]" />
</div>
<div className="flex-1">
<h3 className="font-display text-2xl text-white mb-6 flex items-center gap-3">
<CheckCircle className="w-5 h-5 text-white/30" />
Access & Authorization
</h3>
<div className="prose prose-invert max-w-none font-mono text-sm text-white/60 leading-relaxed">
<p>
Access to POUNCE is granted on a subscription basis. Credentials must not be shared. We reserve the right to terminate access for any account found violating these terms or attempting to compromise system integrity.
</p>
</div>
</div>
</div>
</section>
{/* Section 2 */}
<section className="group">
<div className="flex items-start gap-6">
<div className="hidden sm:flex flex-col items-center gap-2 mt-2">
<div className="w-8 h-8 rounded-full border border-white/10 flex items-center justify-center bg-white/5 group-hover:border-accent/50 transition-colors">
<span className="font-mono text-xs text-white/50 group-hover:text-accent">02</span>
</div>
<div className="w-px h-full bg-white/5 group-hover:bg-white/10 min-h-[100px]" />
</div>
<div className="flex-1">
<h3 className="font-display text-2xl text-white mb-6 flex items-center gap-3">
<Ban className="w-5 h-5 text-white/30" />
Acceptable Use
</h3>
<div className="grid sm:grid-cols-1 gap-4">
<div className="p-6 bg-red-500/5 border border-red-500/20">
<h4 className="font-bold text-white mb-2 flex items-center gap-2">
<AlertTriangle className="w-4 h-4 text-red-500" />
Prohibited Actions
</h4>
<ul className="space-y-2 font-mono text-sm text-white/60">
<li className="flex items-start gap-3">
<span className="text-red-500/50">×</span>
Reverse engineering the API or scanning algorithms
</li>
<li className="flex items-start gap-3">
<span className="text-red-500/50">×</span>
Deploying automated scrapers against endpoints
</li>
<li className="flex items-start gap-3">
<span className="text-red-500/50">×</span>
Using the platform for illegal activities
</li>
</ul>
</div>
</div>
</div>
</div>
</section>
{/* Section 3 */}
<section className="group">
<div className="flex items-start gap-6">
<div className="hidden sm:flex flex-col items-center gap-2 mt-2">
<div className="w-8 h-8 rounded-full border border-white/10 flex items-center justify-center bg-white/5 group-hover:border-accent/50 transition-colors">
<span className="font-mono text-xs text-white/50 group-hover:text-accent">03</span>
</div>
<div className="w-px h-full bg-white/5 group-hover:bg-white/10 min-h-[100px]" />
</div>
<div className="flex-1">
<h3 className="font-display text-2xl text-white mb-6 flex items-center gap-3">
<Gavel className="w-5 h-5 text-white/30" />
Liability & Accuracy
</h3>
<p className="font-mono text-sm text-white/50 leading-relaxed mb-6">
While we strive for real-time precision, domain registry data can fluctuate. POUNCE provides intelligence "as is".
</p>
<div className="bg-[#020202] border border-white/10 p-6">
<p className="font-mono text-xs text-white/40 uppercase tracking-wide leading-relaxed">
POUNCE AG shall not be liable for any indirect, incidental, or consequential damages arising from the use of our services, including but not limited to lost profits or lost data.
</p>
</div>
</div>
</div>
</section>
</div>
{/* Footer of Card */}
<div className="mt-20 pt-8 border-t border-white/10 flex justify-between items-center opacity-50">
<div className="font-mono text-[10px] uppercase tracking-widest text-left text-white/30">
Pounce Legal Dept.<br/>
Zurich, CH
</div>
<div className="font-mono text-[10px] uppercase tracking-widest text-right">
Doc_ID: TOS-991-BX<br/>
Verified
</div>
</div>
</div>
</div>
</div>
</main>
<Footer />
</div>
)
}

View File

@ -7,16 +7,17 @@ import Image from 'next/image'
import { useStore } from '@/lib/store'
import { api } from '@/lib/api'
import { Loader2, ArrowRight, Eye, EyeOff, CheckCircle } from 'lucide-react'
import clsx from 'clsx'
// Logo Component
function Logo() {
return (
<Image
src="/pounce-logo.png"
src="/pounce-puma.png"
alt="pounce"
width={120}
height={60}
className="w-28 h-auto"
height={120}
className="w-20 h-20 object-contain drop-shadow-[0_0_15px_rgba(16,185,129,0.3)]"
/>
)
}
@ -142,96 +143,114 @@ function LoginForm() {
: '/register'
return (
<div className="relative w-full max-w-sm animate-fade-in">
<div className="w-full max-w-[400px] animate-fade-in relative z-10">
{/* Card Container */}
<div className="bg-[#050505] border border-white/10 relative p-8 shadow-2xl">
{/* Tech Corners */}
<div className="absolute -top-px -left-px w-4 h-4 border-t border-l border-white/40" />
<div className="absolute -top-px -right-px w-4 h-4 border-t border-r border-white/40" />
<div className="absolute -bottom-px -left-px w-4 h-4 border-b border-l border-white/40" />
<div className="absolute -bottom-px -right-px w-4 h-4 border-b border-r border-white/40" />
{/* Logo */}
<Link href="/" className="flex justify-center mb-12 sm:mb-16 hover:opacity-80 transition-opacity duration-300">
<Link href="/" className="flex justify-center mb-8 hover:opacity-80 transition-opacity duration-300">
<Logo />
</Link>
{/* Header */}
<div className="text-center mb-8 sm:mb-10">
<h1 className="font-display text-[2rem] sm:text-[2.5rem] md:text-[3rem] leading-[1.1] tracking-[-0.03em] text-foreground mb-2 sm:mb-3">
Back to the hunt.
<div className="text-center mb-10">
<span className="text-[10px] font-mono text-accent uppercase tracking-[0.2em] mb-2 block flex items-center justify-center gap-2">
<div className="w-1.5 h-1.5 bg-accent animate-pulse" />
Access Granted
</span>
<h1 className="font-display text-3xl text-white mb-2 tracking-tight">
Welcome back.
</h1>
<p className="text-body-sm sm:text-body text-foreground-muted">
Sign in to your account
<p className="text-xs font-mono text-white/40">
Authenticate to access the terminal.
</p>
</div>
{/* Verified Message */}
{verified && (
<div className="mb-6 p-4 bg-accent/10 border border-accent/20 rounded-2xl flex items-center gap-3">
<div className="mb-6 p-4 bg-accent/5 border border-accent/20 flex items-center gap-3">
<CheckCircle className="w-5 h-5 text-accent shrink-0" />
<p className="text-sm text-accent">Email verified successfully! You can now sign in.</p>
<p className="text-xs font-mono text-accent">Email verified. System access ready.</p>
</div>
)}
{/* Form */}
<form onSubmit={handleSubmit} className="space-y-3 sm:space-y-4">
<form onSubmit={handleSubmit} className="space-y-6">
{error && (
<div className="p-3 sm:p-4 bg-danger-muted border border-danger/20 rounded-2xl">
<p className="text-danger text-body-xs sm:text-body-sm text-center">{error}</p>
<div className="p-3 bg-red-500/10 border border-red-500/20">
<p className="text-red-500 text-xs font-mono text-center uppercase tracking-wider">{error}</p>
</div>
)}
<div className="space-y-2.5 sm:space-y-3">
<div className="space-y-4">
<div className="group">
<label className="text-[10px] font-mono text-white/40 uppercase tracking-widest mb-2 block group-focus-within:text-white/70 transition-colors">Email Address</label>
<input
type="email"
value={email}
onChange={(e) => setEmail(e.target.value)}
placeholder="Email address"
placeholder="OPERATOR@POUNCE.IO"
required
autoComplete="email"
className="input-elegant text-body-sm sm:text-body"
className="w-full bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none"
/>
</div>
<div className="group relative">
<label className="text-[10px] font-mono text-white/40 uppercase tracking-widest mb-2 block group-focus-within:text-white/70 transition-colors">Passcode</label>
<div className="relative">
<input
type={showPassword ? 'text' : 'password'}
value={password}
onChange={(e) => setPassword(e.target.value)}
placeholder="Password"
placeholder="••••••••"
required
minLength={8}
autoComplete="current-password"
className="input-elegant text-body-sm sm:text-body pr-12"
className="w-full bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none pr-12"
/>
<button
type="button"
onClick={() => setShowPassword(!showPassword)}
className="absolute right-3 sm:right-4 top-1/2 -translate-y-1/2 text-foreground-muted hover:text-foreground transition-colors duration-200"
className="absolute right-4 top-1/2 -translate-y-1/2 text-white/30 hover:text-white transition-colors"
aria-label={showPassword ? 'Hide password' : 'Show password'}
>
{showPassword ? (
<EyeOff className="w-4 h-4 sm:w-5 sm:h-5" />
<EyeOff className="w-4 h-4" />
) : (
<Eye className="w-4 h-4 sm:w-5 sm:h-5" />
<Eye className="w-4 h-4" />
)}
</button>
</div>
</div>
</div>
<div className="flex justify-end">
<Link
href="/forgot-password"
className="text-body-xs sm:text-body-sm text-foreground-muted hover:text-accent transition-colors duration-300"
className="text-[10px] font-mono text-white/40 hover:text-accent uppercase tracking-wider transition-colors"
>
Forgot password?
Lost Credentials?
</Link>
</div>
<button
type="submit"
disabled={loading}
className="w-full py-3 sm:py-4 bg-foreground text-background text-ui-sm sm:text-ui font-medium rounded-xl
hover:bg-foreground/90 disabled:opacity-50 disabled:cursor-not-allowed
transition-all duration-300 flex items-center justify-center gap-2 sm:gap-2.5"
className="w-full py-4 bg-white text-black text-xs font-bold uppercase tracking-[0.2em] hover:bg-accent transition-all disabled:opacity-50 disabled:cursor-not-allowed flex items-center justify-center gap-3"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
{loading ? (
<Loader2 className="w-4 h-4 animate-spin" />
) : (
<>
Continue
<ArrowRight className="w-3.5 sm:w-4 h-3.5 sm:h-4" />
Initialize Session
<ArrowRight className="w-4 h-4" />
</>
)}
</button>
@ -239,14 +258,13 @@ function LoginForm() {
{/* OAuth Buttons */}
{(oauthProviders.google_enabled || oauthProviders.github_enabled) && (
<div className="mt-6">
{/* Divider */}
<div className="relative mb-6">
<div className="mt-8">
<div className="relative mb-8">
<div className="absolute inset-0 flex items-center">
<div className="w-full border-t border-border" />
<div className="w-full border-t border-white/10" />
</div>
<div className="relative flex justify-center text-xs">
<span className="px-4 bg-background text-foreground-muted">or continue with</span>
<div className="relative flex justify-center">
<span className="px-4 bg-[#050505] text-[10px] font-mono text-white/30 uppercase tracking-widest">Alternative Access</span>
</div>
</div>
@ -254,23 +272,19 @@ function LoginForm() {
{oauthProviders.google_enabled && (
<a
href={api.getGoogleLoginUrl(redirectTo)}
className="w-full py-3 sm:py-3.5 bg-[#24292e] text-white text-sm font-medium rounded-xl
hover:bg-[#2f363d] border border-[#24292e]
transition-all duration-300 flex items-center justify-center gap-3"
className="w-full py-3 bg-[#0A0A0A] border border-white/10 text-white text-xs font-mono uppercase tracking-wide hover:bg-white/5 hover:border-white/30 transition-all flex items-center justify-center gap-3"
>
<GoogleIcon className="w-5 h-5" />
Continue with Google
<GoogleIcon className="w-4 h-4" />
Google
</a>
)}
{oauthProviders.github_enabled && (
<a
href={api.getGitHubLoginUrl(redirectTo)}
className="w-full py-3 sm:py-3.5 bg-[#24292e] text-white text-sm font-medium rounded-xl
hover:bg-[#2f363d] border border-[#24292e]
transition-all duration-300 flex items-center justify-center gap-3"
className="w-full py-3 bg-[#0A0A0A] border border-white/10 text-white text-xs font-mono uppercase tracking-wide hover:bg-white/5 hover:border-white/30 transition-all flex items-center justify-center gap-3"
>
<GitHubIcon className="w-5 h-5" />
Continue with GitHub
<GitHubIcon className="w-4 h-4" />
GitHub
</a>
)}
</div>
@ -278,26 +292,43 @@ function LoginForm() {
)}
{/* Register Link */}
<p className="mt-8 sm:mt-10 text-center text-body-xs sm:text-body-sm text-foreground-muted">
Don&apos;t have an account?{' '}
<Link href={registerLink} className="text-foreground hover:text-accent transition-colors duration-300">
Create one
<div className="mt-8 pt-8 border-t border-white/10 text-center">
<p className="text-xs font-mono text-white/40">
No clearance?{' '}
<Link href={registerLink} className="text-white hover:text-accent border-b border-white/20 hover:border-accent transition-all pb-0.5 ml-1">
Request Access
</Link>
</p>
</div>
</div>
</div>
)
}
export default function LoginPage() {
return (
<div className="min-h-screen flex items-center justify-center px-4 sm:px-6 py-8 sm:py-12 relative">
{/* Ambient glow */}
<div className="fixed inset-0 pointer-events-none">
<div className="absolute top-1/4 left-1/2 -translate-x-1/2 w-[400px] h-[300px] bg-accent/[0.02] rounded-full blur-3xl" />
<div className="min-h-screen flex items-center justify-center px-4 sm:px-6 py-8 sm:py-12 relative bg-[#020202] overflow-hidden">
{/* Living Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none overflow-hidden">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.04] mix-blend-overlay z-10" />
{/* Animated Orbs */}
<div className="absolute top-[-10%] left-[-10%] w-[60vw] h-[60vw] bg-accent/10 rounded-full blur-[120px] animate-pulse-slow mix-blend-screen" />
<div className="absolute bottom-[-10%] right-[-10%] w-[50vw] h-[50vw] bg-purple-500/10 rounded-full blur-[150px] animate-pulse-slower mix-blend-screen" />
<div className="absolute top-[40%] left-[40%] w-[40vw] h-[40vw] bg-blue-500/5 rounded-full blur-[100px] animate-blob mix-blend-screen" />
{/* Grid Overlay */}
<div
className="absolute inset-0 opacity-[0.03] z-0"
style={{
backgroundImage: `linear-gradient(rgba(255,255,255,0.3) 0.5px, transparent 0.5px), linear-gradient(90deg, rgba(255,255,255,0.3) 0.5px, transparent 0.5px)`,
backgroundSize: '40px 40px',
}}
/>
</div>
<Suspense fallback={
<div className="w-5 h-5 border-2 border-accent border-t-transparent rounded-full animate-spin" />
<div className="w-8 h-8 border-2 border-white/10 border-t-accent rounded-full animate-spin" />
}>
<LoginForm />
</Suspense>

View File

@ -1,730 +0,0 @@
'use client'
import { useEffect, useState, useMemo } from 'react'
import { useStore } from '@/lib/store'
import { api } from '@/lib/api'
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { PlatformBadge } from '@/components/PremiumTable'
import {
Clock,
ExternalLink,
Search,
Flame,
Timer,
Gavel,
DollarSign,
X,
Lock,
TrendingUp,
ChevronUp,
ChevronDown,
ChevronsUpDown,
Sparkles,
Diamond,
ShieldCheck,
Zap,
Filter,
} from 'lucide-react'
import Link from 'next/link'
import clsx from 'clsx'
interface MarketItem {
id: string
domain: string
tld: string
price: number
currency: string
price_type: 'bid' | 'fixed' | 'negotiable'
status: 'auction' | 'instant'
source: string
is_pounce: boolean
verified: boolean
time_remaining?: string
end_time?: string
num_bids?: number
slug?: string
seller_verified: boolean
url: string
is_external: boolean
pounce_score: number
}
interface Auction {
domain: string
platform: string
platform_url: string
current_bid: number
currency: string
num_bids: number
end_time: string
time_remaining: string
buy_now_price: number | null
reserve_met: boolean | null
traffic: number | null
age_years: number | null
tld: string
affiliate_url: string
}
type TabType = 'all' | 'ending' | 'hot'
type SortField = 'domain' | 'ending' | 'bid' | 'bids'
type SortDirection = 'asc' | 'desc'
const PLATFORMS = [
{ id: 'All', name: 'All Sources' },
{ id: 'GoDaddy', name: 'GoDaddy' },
{ id: 'Sedo', name: 'Sedo' },
{ id: 'NameJet', name: 'NameJet' },
{ id: 'DropCatch', name: 'DropCatch' },
]
// Premium TLDs that look professional
const PREMIUM_TLDS = ['com', 'io', 'ai', 'co', 'de', 'ch', 'net', 'org', 'app', 'dev', 'xyz']
// Vanity Filter: Only show "beautiful" domains to non-authenticated users
// Rules: No numbers (except short domains), no hyphens, length < 12, only premium TLDs
function isVanityDomain(auction: Auction): boolean {
const domain = auction.domain
const parts = domain.split('.')
if (parts.length < 2) return false
const name = parts[0]
const tld = parts.slice(1).join('.').toLowerCase()
// Check TLD is premium
if (!PREMIUM_TLDS.includes(tld)) return false
// Check length (max 12 characters for the name)
if (name.length > 12) return false
// No hyphens
if (name.includes('-')) return false
// No numbers (unless domain is 4 chars or less - short domains are valuable)
if (name.length > 4 && /\d/.test(name)) return false
return true
}
// Generate a mock "Deal Score" for display purposes
// In production, this would come from a valuation API
function getDealScore(auction: Auction): number | null {
let score = 50
const name = auction.domain.split('.')[0]
if (name.length <= 4) score += 20
else if (name.length <= 6) score += 10
if (['com', 'io', 'ai'].includes(auction.tld)) score += 15
if (auction.age_years && auction.age_years > 5) score += 10
if (auction.num_bids >= 20) score += 15
else if (auction.num_bids >= 10) score += 10
return Math.min(score, 100)
}
function SortIcon({ field, currentField, direction }: { field: SortField, currentField: SortField, direction: SortDirection }) {
if (field !== currentField) {
return <ChevronsUpDown className="w-4 h-4 text-foreground-subtle" />
}
return direction === 'asc'
? <ChevronUp className="w-4 h-4 text-accent" />
: <ChevronDown className="w-4 h-4 text-accent" />
}
export default function MarketPage() {
const { isAuthenticated, checkAuth, isLoading: authLoading } = useStore()
const [allAuctions, setAllAuctions] = useState<Auction[]>([])
const [endingSoon, setEndingSoon] = useState<Auction[]>([])
const [hotAuctions, setHotAuctions] = useState<Auction[]>([])
const [pounceItems, setPounceItems] = useState<MarketItem[]>([])
const [loading, setLoading] = useState(true)
const [activeTab, setActiveTab] = useState<TabType>('all')
const [sortField, setSortField] = useState<SortField>('ending')
const [sortDirection, setSortDirection] = useState<SortDirection>('asc')
const [searchQuery, setSearchQuery] = useState('')
const [selectedPlatform, setSelectedPlatform] = useState('All')
const [maxBid, setMaxBid] = useState('')
useEffect(() => {
checkAuth()
loadAuctions()
}, [checkAuth])
const loadAuctions = async () => {
setLoading(true)
try {
const [allFeed, endingFeed, hotFeed, pounceFeed] = await Promise.all([
api.getMarketFeed({ source: 'all', limit: 100, sortBy: 'time' }),
api.getMarketFeed({ source: 'external', endingWithin: 24, limit: 50, sortBy: 'time' }),
api.getMarketFeed({ source: 'external', limit: 50, sortBy: 'score' }),
api.getMarketFeed({ source: 'pounce', limit: 10 }),
])
const convertToAuction = (item: MarketItem): Auction => ({
domain: item.domain,
platform: item.source,
platform_url: item.url,
current_bid: item.price,
currency: item.currency,
num_bids: item.num_bids || 0,
end_time: item.end_time || '',
time_remaining: item.time_remaining || '',
buy_now_price: item.price_type === 'fixed' ? item.price : null,
reserve_met: null,
traffic: null,
age_years: null,
tld: item.tld,
affiliate_url: item.url,
})
const externalOnly = (items: MarketItem[]) => items.filter(i => !i.is_pounce).map(convertToAuction)
setAllAuctions(externalOnly(allFeed.items || []))
setEndingSoon(externalOnly(endingFeed.items || []))
setHotAuctions(externalOnly(hotFeed.items || []))
setPounceItems(pounceFeed.items || [])
} catch (error) {
console.error('Failed to load auctions:', error)
} finally {
setLoading(false)
}
}
const getCurrentAuctions = (): Auction[] => {
switch (activeTab) {
case 'ending': return endingSoon
case 'hot': return hotAuctions
default: return allAuctions
}
}
// Apply Vanity Filter for non-authenticated users
const displayAuctions = useMemo(() => {
const current = getCurrentAuctions()
if (isAuthenticated) {
return current
}
return current.filter(isVanityDomain)
}, [activeTab, allAuctions, endingSoon, hotAuctions, isAuthenticated])
const filteredAuctions = displayAuctions.filter(auction => {
if (searchQuery && !auction.domain.toLowerCase().includes(searchQuery.toLowerCase())) {
return false
}
if (selectedPlatform !== 'All' && auction.platform !== selectedPlatform) {
return false
}
if (maxBid && auction.current_bid > parseFloat(maxBid)) {
return false
}
return true
})
const handleSort = (field: SortField) => {
if (sortField === field) {
setSortDirection(sortDirection === 'asc' ? 'desc' : 'asc')
} else {
setSortField(field)
setSortDirection('asc')
}
}
const sortedAuctions = [...filteredAuctions].sort((a, b) => {
const modifier = sortDirection === 'asc' ? 1 : -1
switch (sortField) {
case 'domain':
return a.domain.localeCompare(b.domain) * modifier
case 'bid':
return (a.current_bid - b.current_bid) * modifier
case 'bids':
return (a.num_bids - b.num_bids) * modifier
default:
return 0
}
})
const formatCurrency = (amount: number, currency = 'USD') => {
return new Intl.NumberFormat('en-US', { style: 'currency', currency }).format(amount)
}
const getTimeColor = (timeRemaining: string) => {
if (timeRemaining.includes('m') && !timeRemaining.includes('h')) return 'text-red-400'
if (timeRemaining.includes('h') && parseInt(timeRemaining) < 12) return 'text-amber-400'
return 'text-foreground-muted'
}
const hotPreview = hotAuctions.slice(0, 4)
if (authLoading) {
return (
<div className="min-h-screen flex items-center justify-center">
<div className="w-5 h-5 border-2 border-accent border-t-transparent rounded-full animate-spin" />
</div>
)
}
return (
<div className="min-h-screen bg-background relative overflow-hidden">
{/* Background Effects */}
<div className="fixed inset-0 pointer-events-none">
<div className="absolute top-[-20%] left-1/2 -translate-x-1/2 w-[1200px] h-[800px] bg-accent/[0.03] rounded-full blur-[120px]" />
<div className="absolute bottom-[-10%] right-[-10%] w-[600px] h-[600px] bg-accent/[0.02] rounded-full blur-[100px]" />
<div
className="absolute inset-0 opacity-[0.015]"
style={{
backgroundImage: `linear-gradient(rgba(255,255,255,.1) 1px, transparent 1px), linear-gradient(90deg, rgba(255,255,255,.1) 1px, transparent 1px)`,
backgroundSize: '64px 64px',
}}
/>
</div>
<Header />
<main className="relative pt-32 sm:pt-40 pb-20 sm:pb-28 px-4 sm:px-6 flex-1">
<div className="max-w-7xl mx-auto">
{/* Hero Header - gemäß pounce_public.md */}
<div className="text-center mb-16 sm:mb-20 animate-fade-in">
<span className="text-sm font-semibold text-accent uppercase tracking-wider">Live Market</span>
<h1 className="mt-4 font-display text-[2.5rem] sm:text-[3.5rem] md:text-[4.5rem] lg:text-[5rem] leading-[0.95] tracking-[-0.03em] text-foreground">
Live Domain Market
</h1>
<p className="mt-5 text-lg sm:text-xl text-foreground-muted max-w-2xl mx-auto">
Aggregated from GoDaddy, Sedo, and Pounce Direct.
</p>
{!isAuthenticated && displayAuctions.length < allAuctions.length && (
<p className="mt-2 text-sm text-accent flex items-center justify-center gap-1">
<Sparkles className="w-4 h-4" />
Showing {displayAuctions.length} premium domains Sign in to see all {allAuctions.length}
</p>
)}
</div>
{/* Login Banner for non-authenticated users */}
{!isAuthenticated && (
<div className="mb-8 p-5 bg-accent-muted border border-accent/20 rounded-xl flex flex-col sm:flex-row items-center justify-between gap-4 animate-fade-in">
<div className="flex items-center gap-3">
<div className="w-10 h-10 bg-accent/20 rounded-xl flex items-center justify-center">
<Lock className="w-5 h-5 text-accent" />
</div>
<div>
<p className="text-body-sm font-medium text-foreground">Unlock Smart Opportunities</p>
<p className="text-ui-sm text-foreground-muted">
Sign in for valuations, deal scores, and personalized recommendations.
</p>
</div>
</div>
<Link
href="/register"
className="shrink-0 px-5 py-2.5 bg-accent text-background text-ui font-medium rounded-lg
hover:bg-accent-hover transition-all duration-300"
>
Start Hunting
</Link>
</div>
)}
{/* Pounce Direct Section - Featured */}
{pounceItems.length > 0 && (
<div className="mb-12 sm:mb-16 animate-slide-up">
<div className="flex items-center gap-3 mb-4 sm:mb-6">
<div className="flex items-center gap-2">
<Diamond className="w-5 h-5 text-accent fill-accent/20" />
<h2 className="text-body-lg sm:text-heading-sm font-medium text-foreground">
Pounce Direct
</h2>
</div>
<span className="text-ui-sm text-foreground-subtle">Verified Instant Buy 0% Commission</span>
</div>
<div className="border border-accent/20 rounded-xl overflow-hidden bg-gradient-to-br from-accent/5 to-transparent">
{pounceItems.map((item) => (
<Link
key={item.id}
href={item.url}
className="flex items-center justify-between px-5 py-4 border-b border-accent/10 last:border-b-0 hover:bg-accent/5 transition-all group"
>
<div className="flex items-center gap-4">
<Diamond className="w-5 h-5 text-accent fill-accent/20 flex-shrink-0" />
<div>
<div className="font-mono text-body font-medium text-foreground group-hover:text-accent transition-colors">
{item.domain}
</div>
<div className="flex items-center gap-2 mt-1">
{item.verified && (
<span className="inline-flex items-center gap-1 text-[10px] font-bold uppercase tracking-wide text-accent bg-accent/10 px-2 py-0.5 rounded-full">
<ShieldCheck className="w-3 h-3" />
Verified
</span>
)}
{isAuthenticated ? (
<span className="text-ui-sm text-foreground-subtle">
Score: {item.pounce_score}
</span>
) : (
<span className="text-ui-sm text-foreground-subtle blur-[4px]">
Score: XX
</span>
)}
</div>
</div>
</div>
<div className="flex items-center gap-4">
<div className="text-right">
<div className="font-mono text-body-lg font-medium text-foreground">
{formatCurrency(item.price, item.currency)}
</div>
<div className="text-ui-sm text-accent">Instant Buy</div>
</div>
<div className="flex items-center gap-2 px-4 py-2 bg-accent text-background rounded-lg text-ui-sm font-bold opacity-0 group-hover:opacity-100 transition-opacity">
Buy Now
<Zap className="w-3 h-3" />
</div>
</div>
</Link>
))}
</div>
<div className="mt-3 text-center">
<Link
href="/buy"
className="text-ui-sm text-accent hover:underline"
>
Browse all Pounce listings
</Link>
</div>
</div>
)}
{/* Hot Auctions Preview */}
{hotPreview.length > 0 && (
<div className="mb-12 sm:mb-16 animate-slide-up">
<h2 className="text-body-lg sm:text-heading-sm font-medium text-foreground mb-4 sm:mb-6 flex items-center gap-2">
<Flame className="w-5 h-5 text-accent" />
Hot Right Now
</h2>
<div className="grid sm:grid-cols-2 lg:grid-cols-4 gap-3 sm:gap-4">
{hotPreview.map((auction) => (
<a
key={`${auction.domain}-${auction.platform}`}
href={auction.affiliate_url}
target="_blank"
rel="noopener noreferrer"
className="p-4 sm:p-5 bg-background-secondary/50 border border-border rounded-xl hover:border-border-hover hover:bg-background-secondary transition-all duration-300 text-left group"
>
<div className="flex items-center justify-between mb-3">
<span className="font-mono text-body-lg sm:text-heading-sm text-foreground group-hover:text-accent transition-colors">
{auction.domain}
</span>
<span className="text-ui-sm font-medium px-2 py-0.5 rounded-full text-accent bg-accent-muted flex items-center gap-1">
<Flame className="w-3 h-3" />
{auction.num_bids}
</span>
</div>
<div className="flex items-center justify-between">
<span className="text-body-sm text-foreground-muted">
{formatCurrency(auction.current_bid)}
</span>
<span className={clsx("text-body-sm", getTimeColor(auction.time_remaining))}>
{auction.time_remaining}
</span>
</div>
<div className="mt-2">
<PlatformBadge platform={auction.platform} />
</div>
</a>
))}
</div>
</div>
)}
{/* Search & Filters */}
<div className="mb-6 animate-slide-up">
<div className="flex flex-wrap gap-3">
<div className="relative flex-1 min-w-[200px] max-w-md">
<Search className="absolute left-4 top-1/2 -translate-y-1/2 w-5 h-5 text-foreground-subtle" />
<input
type="text"
placeholder="Search domains..."
value={searchQuery}
onChange={(e) => setSearchQuery(e.target.value)}
className="w-full pl-12 pr-10 py-3 bg-background-secondary/50 border border-border rounded-xl
text-body text-foreground placeholder:text-foreground-subtle
focus:outline-none focus:ring-2 focus:ring-accent/30 focus:border-accent
transition-all duration-300"
/>
{searchQuery && (
<button
onClick={() => setSearchQuery('')}
className="absolute right-4 top-1/2 -translate-y-1/2 p-1 text-foreground-subtle hover:text-foreground transition-colors"
>
<X className="w-4 h-4" />
</button>
)}
</div>
<select
value={selectedPlatform}
onChange={(e) => setSelectedPlatform(e.target.value)}
className="px-4 py-3 bg-background-secondary/50 border border-border rounded-xl
text-body text-foreground cursor-pointer focus:outline-none focus:ring-2 focus:ring-accent/30 focus:border-accent"
>
{PLATFORMS.map(p => <option key={p.id} value={p.id}>{p.name}</option>)}
</select>
<div className="relative">
<DollarSign className="absolute left-4 top-1/2 -translate-y-1/2 w-4 h-4 text-foreground-subtle" />
<input
type="number"
placeholder="Max bid"
value={maxBid}
onChange={(e) => setMaxBid(e.target.value)}
className="w-32 pl-10 pr-4 py-3 bg-background-secondary/50 border border-border rounded-xl
text-body text-foreground placeholder:text-foreground-subtle
focus:outline-none focus:ring-2 focus:ring-accent/30 focus:border-accent"
/>
</div>
</div>
</div>
{/* Tabs */}
<div className="flex flex-wrap gap-2 mb-6 animate-slide-up">
{[
{ id: 'all' as const, label: 'All Auctions', icon: Gavel, count: allAuctions.length },
{ id: 'ending' as const, label: 'Ending Soon', icon: Timer, count: endingSoon.length },
{ id: 'hot' as const, label: 'Hot', icon: Flame, count: hotAuctions.length },
].map((tab) => (
<button
key={tab.id}
onClick={() => setActiveTab(tab.id)}
className={clsx(
"flex items-center gap-2 px-4 py-2.5 text-ui-sm font-medium rounded-xl transition-all",
activeTab === tab.id
? "bg-accent text-background"
: "bg-background-secondary/50 text-foreground-muted hover:text-foreground hover:bg-background-secondary border border-border"
)}
>
<tab.icon className="w-4 h-4" />
{tab.label}
<span className={clsx(
"text-xs px-1.5 py-0.5 rounded",
activeTab === tab.id ? "bg-background/20" : "bg-foreground/10"
)}>{tab.count}</span>
</button>
))}
</div>
{/* Auctions Table */}
<div className="bg-background-secondary/30 border border-border rounded-xl overflow-hidden animate-slide-up">
<div className="overflow-x-auto">
<table className="w-full">
<thead>
<tr className="bg-background-secondary border-b border-border">
<th className="text-left px-4 sm:px-6 py-4">
<button
onClick={() => handleSort('domain')}
className="flex items-center gap-2 text-ui-sm text-foreground-subtle font-medium hover:text-foreground transition-colors"
>
Domain
<SortIcon field="domain" currentField={sortField} direction={sortDirection} />
</button>
</th>
<th className="text-left px-4 sm:px-6 py-4 hidden lg:table-cell">
<span className="text-ui-sm text-foreground-subtle font-medium">Source</span>
</th>
<th className="text-right px-4 sm:px-6 py-4">
<button
onClick={() => handleSort('bid')}
className="flex items-center gap-2 ml-auto text-ui-sm text-foreground-subtle font-medium hover:text-foreground transition-colors"
>
Price
<SortIcon field="bid" currentField={sortField} direction={sortDirection} />
</button>
</th>
{/* Pounce Score Column - visible but blurred for non-auth (gemäß pounce_public.md) */}
<th className="text-center px-4 sm:px-6 py-4 hidden md:table-cell">
<span className="text-ui-sm text-foreground-subtle font-medium flex items-center justify-center gap-1">
Pounce Score
{!isAuthenticated && <Lock className="w-3 h-3" />}
</span>
</th>
{/* Valuation Column - visible but blurred for non-auth */}
<th className="text-center px-4 sm:px-6 py-4 hidden lg:table-cell">
<span className="text-ui-sm text-foreground-subtle font-medium flex items-center justify-center gap-1">
Valuation
{!isAuthenticated && <Lock className="w-3 h-3" />}
</span>
</th>
<th className="text-right px-4 sm:px-6 py-4 hidden md:table-cell">
<button
onClick={() => handleSort('ending')}
className="flex items-center gap-2 ml-auto text-ui-sm text-foreground-subtle font-medium hover:text-foreground transition-colors"
>
Time Left
<SortIcon field="ending" currentField={sortField} direction={sortDirection} />
</button>
</th>
<th className="px-4 sm:px-6 py-4"></th>
</tr>
</thead>
<tbody className="divide-y divide-border">
{loading ? (
Array.from({ length: 10 }).map((_, idx) => (
<tr key={idx} className="animate-pulse">
<td className="px-4 sm:px-6 py-4"><div className="h-4 w-32 bg-background-tertiary rounded" /></td>
<td className="px-4 sm:px-6 py-4 hidden lg:table-cell"><div className="h-4 w-20 bg-background-tertiary rounded" /></td>
<td className="px-4 sm:px-6 py-4"><div className="h-4 w-16 bg-background-tertiary rounded ml-auto" /></td>
<td className="px-4 sm:px-6 py-4 hidden md:table-cell"><div className="h-8 w-8 bg-background-tertiary rounded mx-auto" /></td>
<td className="px-4 sm:px-6 py-4 hidden lg:table-cell"><div className="h-4 w-16 bg-background-tertiary rounded mx-auto" /></td>
<td className="px-4 sm:px-6 py-4 hidden md:table-cell"><div className="h-4 w-16 bg-background-tertiary rounded ml-auto" /></td>
<td className="px-4 sm:px-6 py-4"><div className="h-8 w-16 bg-background-tertiary rounded ml-auto" /></td>
</tr>
))
) : sortedAuctions.length === 0 ? (
<tr>
<td colSpan={7} className="px-6 py-12 text-center text-foreground-muted">
{searchQuery ? `No domains found matching "${searchQuery}"` : 'No domains found'}
</td>
</tr>
) : (
sortedAuctions.map((auction) => (
<tr
key={`${auction.domain}-${auction.platform}`}
className="hover:bg-background-secondary/50 transition-colors group"
>
<td className="px-4 sm:px-6 py-4">
<div>
<a
href={auction.affiliate_url}
target="_blank"
rel="noopener noreferrer"
className="font-mono text-body-sm sm:text-body font-medium text-foreground hover:text-accent transition-colors"
>
{auction.domain}
</a>
<div className="flex items-center gap-2 mt-1 lg:hidden">
<PlatformBadge platform={auction.platform} />
</div>
</div>
</td>
<td className="px-4 sm:px-6 py-4 hidden lg:table-cell">
<div className="space-y-1">
<PlatformBadge platform={auction.platform} />
{auction.age_years && (
<span className="text-ui-sm text-foreground-subtle flex items-center gap-1">
<Clock className="w-3 h-3" /> {auction.age_years}y
</span>
)}
</div>
</td>
<td className="px-4 sm:px-6 py-4 text-right">
<div>
<span className="text-body-sm font-medium text-foreground">
{formatCurrency(auction.current_bid)}
</span>
{auction.buy_now_price && (
<p className="text-ui-sm text-accent">Buy: {formatCurrency(auction.buy_now_price)}</p>
)}
</div>
</td>
{/* Pounce Score - blurred for non-authenticated (gemäß pounce_public.md) */}
<td className="px-4 sm:px-6 py-4 text-center hidden md:table-cell">
{isAuthenticated ? (
<div className="inline-flex flex-col items-center">
<span className={clsx(
"inline-flex items-center justify-center w-9 h-9 rounded-lg font-bold text-sm",
(getDealScore(auction) ?? 0) >= 75 ? "bg-accent/20 text-accent" :
(getDealScore(auction) ?? 0) >= 50 ? "bg-amber-500/20 text-amber-400" :
"bg-foreground/10 text-foreground-muted"
)}>
{getDealScore(auction)}
</span>
{(getDealScore(auction) ?? 0) >= 75 && (
<span className="text-[10px] text-accent mt-0.5 font-medium">Good Deal</span>
)}
</div>
) : (
<div
className="inline-flex items-center justify-center w-9 h-9 rounded-lg bg-foreground/5 text-foreground-muted blur-[3px] cursor-pointer"
title="Sign in to unlock valuations"
>
<span className="font-bold text-sm">XX</span>
</div>
)}
</td>
{/* Valuation - blurred for non-authenticated */}
<td className="px-4 sm:px-6 py-4 text-center hidden lg:table-cell">
{isAuthenticated ? (
<span className="text-body-sm font-medium text-foreground">
${(auction.current_bid * 1.5).toFixed(0)}
</span>
) : (
<span className="text-body-sm font-medium text-foreground-muted blur-[3px]">
$X,XXX
</span>
)}
</td>
<td className="px-4 sm:px-6 py-4 text-right hidden md:table-cell">
<span className={clsx("font-medium", getTimeColor(auction.time_remaining))}>
{auction.time_remaining}
</span>
</td>
<td className="px-4 sm:px-6 py-4">
<a
href={auction.affiliate_url}
target="_blank"
rel="noopener noreferrer"
className="inline-flex items-center gap-1 text-ui-sm text-accent hover:text-accent-hover transition-colors opacity-0 group-hover:opacity-100"
>
Bid
<ExternalLink className="w-3 h-3" />
</a>
</td>
</tr>
))
)}
</tbody>
</table>
</div>
</div>
{/* Stats */}
{!loading && (
<div className="mt-6 flex justify-center">
<p className="text-ui-sm text-foreground-subtle">
{searchQuery
? `Found ${sortedAuctions.length} domains matching "${searchQuery}"`
: `${allAuctions.length} domains available across ${PLATFORMS.length - 1} platforms`
}
</p>
</div>
)}
{/* Bottom CTA for upgrade (gemäß pounce_public.md) */}
{!isAuthenticated && (
<div className="mt-12 p-6 sm:p-8 bg-gradient-to-r from-accent/10 to-accent/5 border border-accent/20 rounded-2xl text-center animate-slide-up">
<div className="flex items-center justify-center gap-2 mb-3">
<Filter className="w-5 h-5 text-accent" />
<h3 className="text-lg font-medium text-foreground">Tired of digging through spam?</h3>
</div>
<p className="text-foreground-muted mb-5 max-w-lg mx-auto">
Our &apos;Trader&apos; plan filters 99% of junk domains automatically. See only premium opportunities.
</p>
<Link
href="/pricing"
className="inline-flex items-center gap-2 px-6 py-3 bg-accent text-background rounded-xl font-medium
hover:bg-accent-hover transition-all shadow-[0_0_20px_rgba(16,185,129,0.2)]"
>
Upgrade Filter
<TrendingUp className="w-4 h-4" />
</Link>
</div>
)}
</div>
</main>
<Footer />
</div>
)
}

View File

@ -8,43 +8,29 @@ import { DomainChecker } from '@/components/DomainChecker'
import { useStore } from '@/lib/store'
import { api } from '@/lib/api'
import {
Eye,
Bell,
Clock,
Shield,
ArrowRight,
TrendingUp,
TrendingDown,
Minus,
ChevronRight,
Zap,
BarChart3,
Globe,
Check,
Search,
Target,
Gavel,
Sparkles,
Activity,
LineChart,
Lock,
Filter,
Crosshair,
Tag,
AlertTriangle,
Briefcase,
Coins,
Layers,
ArrowUpRight,
ShieldCheck,
Smartphone,
Globe2,
Server,
Database,
Cpu,
Network,
Share2,
Key
Key,
Shield,
Radar,
Scan,
Radio,
Cpu
} from 'lucide-react'
import Link from 'next/link'
import clsx from 'clsx'
@ -56,36 +42,6 @@ interface HotAuction {
platform: string
}
// Animated counter with easing
function AnimatedNumber({ value, suffix = '' }: { value: number, suffix?: string }) {
const [count, setCount] = useState(0)
useEffect(() => {
const duration = 2500
const steps = 60
const increment = value / steps
let startTime = Date.now()
const timer = setInterval(() => {
const now = Date.now()
const progress = Math.min((now - startTime) / duration, 1)
const easeOutQuart = 1 - Math.pow(1 - progress, 4)
if (progress < 1) {
setCount(Math.floor(value * easeOutQuart))
} else {
setCount(value)
clearInterval(timer)
}
}, 1000 / 60)
return () => clearInterval(timer)
}, [value])
return <>{count.toLocaleString()}{suffix}</>
}
// High-end Live Market Ticker - Monochrome & Technical
function MarketTicker({ auctions }: { auctions: HotAuction[] }) {
const tickerRef = useRef<HTMLDivElement>(null)
@ -112,7 +68,7 @@ function MarketTicker({ auctions }: { auctions: HotAuction[] }) {
className="flex items-center gap-6 px-8 border-r border-white/[0.08] group cursor-default transition-colors hover:bg-white/[0.02]"
>
<div className="flex items-center gap-3">
<div className="w-1.5 h-1.5 rounded-full bg-accent opacity-50 group-hover:opacity-100 transition-opacity" />
<div className="w-1.5 h-1.5 rounded-none bg-accent opacity-50 group-hover:opacity-100 transition-opacity" />
<span className="font-mono text-xs text-white/70 font-medium group-hover:text-white transition-colors tracking-wide">
{auction.domain}
</span>
@ -144,7 +100,7 @@ export default function HomePage() {
const auctions = await api.getHotAuctions(8).catch(() => [])
setHotAuctions(auctions.slice(0, 8))
} catch (error) {
console.error('Failed to fetch data:', error)
console.error('Mission failed:', error)
} finally {
setLoadingAuctions(false)
}
@ -154,7 +110,7 @@ export default function HomePage() {
return (
<div className="min-h-screen flex items-center justify-center bg-[#020202]">
<div className="relative">
<div className="w-12 h-12 rounded-full border-[0.5px] border-white/10 border-t-accent animate-spin" />
<div className="w-12 h-12 border-[0.5px] border-white/10 border-t-accent animate-spin rounded-full" />
</div>
</div>
)
@ -164,10 +120,7 @@ export default function HomePage() {
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Cinematic Background - Architectural & Fine */}
<div className="fixed inset-0 pointer-events-none z-0">
{/* Fine Noise */}
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.04] mix-blend-overlay" />
{/* Architectural Grid - Ultra fine */}
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div
className="absolute inset-0 opacity-[0.03]"
style={{
@ -175,97 +128,93 @@ export default function HomePage() {
backgroundSize: '160px 160px',
}}
/>
{/* Ambient Light - Very Subtle & Localized */}
<div className="absolute top-[-30%] left-1/2 -translate-x-1/2 w-[1200px] h-[800px] bg-accent/[0.03] rounded-full blur-[180px]" />
<div className="absolute top-[-30%] left-1/2 -translate-x-1/2 w-[1200px] h-[800px] bg-accent/[0.02] rounded-full blur-[200px]" />
</div>
<Header />
{/* HERO SECTION: Brutally Catchy & Noble */}
<section className="relative min-h-[90vh] flex flex-col justify-center pt-32 pb-24 px-4 sm:px-6 z-10">
<div className="max-w-[1600px] mx-auto w-full">
<div className="grid lg:grid-cols-12 gap-12 lg:gap-20 items-center">
<div className="max-w-[1400px] mx-auto w-full">
<div className="grid lg:grid-cols-12 gap-16 lg:gap-24 items-center">
{/* Left: Typography & Brand */}
<div className="lg:col-span-7 relative z-20 text-center lg:text-left">
{/* Brand Seal - COLORFUL AGAIN */}
<div className="inline-flex items-center gap-3 mb-12 animate-fade-in opacity-0" style={{ animationDelay: '0.1s', animationFillMode: 'forwards' }}>
<div className="relative w-20 h-20 lg:w-24 lg:h-24">
<div className="absolute inset-0 bg-accent/20 blur-2xl rounded-full animate-pulse" />
{/* Brand Seal */}
<div className="inline-flex items-center gap-4 mb-10 animate-fade-in opacity-0" style={{ animationDelay: '0.1s', animationFillMode: 'forwards' }}>
<div className="relative w-16 h-16">
<div className="absolute inset-0 bg-accent/20 blur-xl rounded-full animate-pulse" />
<Image
src="/pounce-puma.png"
alt="Pounce Seal"
fill
className="object-contain drop-shadow-[0_0_25px_rgba(16,185,129,0.3)]"
className="object-contain drop-shadow-[0_0_20px_rgba(16,185,129,0.2)]"
priority
/>
</div>
<div className="h-px w-12 lg:w-20 bg-gradient-to-r from-accent/40 to-transparent" />
<span className="text-[10px] lg:text-xs font-mono uppercase tracking-[0.3em] text-accent/80">Est. 2025</span>
<div className="h-px w-12 bg-white/10" />
<span className="text-[10px] font-mono uppercase tracking-[0.3em] text-accent">Est. 2025 // Global Operations</span>
</div>
{/* Headline - Improved Spacing & Color */}
<h1 className="font-display text-[3.5rem] sm:text-[5rem] md:text-[6rem] lg:text-[7.5rem] leading-[0.9] tracking-[-0.04em] text-white mb-8 lg:mb-10">
{/* Headline */}
<h1 className="font-display text-[3.5rem] sm:text-[5rem] md:text-[6rem] lg:text-[7rem] leading-[0.9] tracking-[-0.04em] text-white mb-8">
<span className="block animate-slide-up opacity-0" style={{ animationDelay: '0.2s', animationFillMode: 'forwards' }}>
The market
</span>
<span className="block text-white animate-slide-up opacity-0" style={{ animationDelay: '0.4s', animationFillMode: 'forwards' }}>
never sleeps.
</span>
<span className="block mt-4 lg:mt-6 text-white/40 animate-slide-up opacity-0 pb-4" style={{ animationDelay: '0.6s', animationFillMode: 'forwards' }}>
<span className="block mt-4 lg:mt-6 text-white/40 animate-slide-up opacity-0" style={{ animationDelay: '0.6s', animationFillMode: 'forwards' }}>
You should.
</span>
</h1>
{/* Subline & Stats */}
<div className="animate-slide-up opacity-0" style={{ animationDelay: '0.8s', animationFillMode: 'forwards' }}>
<p className="text-lg lg:text-2xl text-white/60 max-w-xl font-light leading-relaxed mb-12">
Institutional-grade intelligence for the digital asset economy.
<span className="text-white block mt-2 font-medium">Scan. Track. Trade. Yield.</span>
<p className="text-lg lg:text-xl text-white/60 max-w-xl font-light leading-relaxed mb-12 lg:mx-0 mx-auto">
Transforming domains from static addresses into yield-bearing financial assets.
<span className="text-white block mt-1 font-medium">Scan. Acquire. Route. Profit.</span>
</p>
{/* Stats Grid - Moved here */}
<div className="grid grid-cols-2 sm:grid-cols-4 gap-8 pt-8 border-t border-white/[0.08]">
{/* Stats Grid */}
<div className="grid grid-cols-2 sm:grid-cols-4 gap-x-8 gap-y-4 pt-8 border-t border-white/[0.08]">
<div>
<div className="text-2xl lg:text-3xl font-display text-white mb-1">886+</div>
<div className="text-[10px] uppercase tracking-widest text-accent/60">TLDs Tracked</div>
<div className="text-2xl font-display text-white mb-1">886+</div>
<div className="text-[10px] uppercase tracking-widest text-white/40 font-mono">TLDs Scanned</div>
</div>
<div>
<div className="text-2xl lg:text-3xl font-display text-white mb-1">24/7</div>
<div className="text-[10px] uppercase tracking-widest text-accent/60">Live Monitoring</div>
<div className="text-2xl font-display text-white mb-1">24/7</div>
<div className="text-[10px] uppercase tracking-widest text-white/40 font-mono">Live Recon</div>
</div>
<div>
<div className="text-2xl lg:text-3xl font-display text-white mb-1">10s</div>
<div className="text-[10px] uppercase tracking-widest text-accent/60">Latency</div>
<div className="text-2xl font-display text-white mb-1">10s</div>
<div className="text-[10px] uppercase tracking-widest text-white/40 font-mono">Latency</div>
</div>
<div>
<div className="text-2xl lg:text-3xl font-display text-white mb-1">$1B+</div>
<div className="text-[10px] uppercase tracking-widest text-accent/60">Volume</div>
<div className="text-2xl font-display text-white mb-1">$1B+</div>
<div className="text-[10px] uppercase tracking-widest text-white/40 font-mono">Assets Tracked</div>
</div>
</div>
</div>
</div>
{/* Right: The Artifact (Domain Checker) - HIGHER VISIBILITY */}
<div className="lg:col-span-5 relative animate-scale-in opacity-0 mt-12 lg:mt-0" style={{ animationDelay: '1s', animationFillMode: 'forwards' }}>
{/* Stronger Glow for Visibility */}
<div className="absolute -inset-1 bg-gradient-to-tr from-accent/20 via-white/20 to-accent/20 blur-xl opacity-50" />
{/* Right: The Artifact (Domain Checker) */}
<div className="lg:col-span-5 relative animate-scale-in opacity-0 mt-8 lg:mt-0" style={{ animationDelay: '1s', animationFillMode: 'forwards' }}>
<div className="absolute -inset-1 bg-gradient-to-tr from-accent/20 via-white/10 to-accent/20 blur-2xl opacity-40" />
<div className="relative z-10 bg-[#0F0F0F] border border-white/30 p-2 shadow-[0_0_60px_-15px_rgba(0,0,0,1)]">
<div className="absolute -top-px -left-px w-4 h-4 border-t border-l border-white/50" />
<div className="absolute -top-px -right-px w-4 h-4 border-t border-r border-white/50" />
<div className="absolute -bottom-px -left-px w-4 h-4 border-b border-l border-white/50" />
<div className="absolute -bottom-px -right-px w-4 h-4 border-b border-r border-white/50" />
<div className="relative z-10 bg-[#0A0A0A] border border-white/20 p-2 shadow-2xl">
{/* Tech Corners */}
<div className="absolute -top-px -left-px w-4 h-4 border-t border-l border-white/40" />
<div className="absolute -top-px -right-px w-4 h-4 border-t border-r border-white/40" />
<div className="absolute -bottom-px -left-px w-4 h-4 border-b border-l border-white/40" />
<div className="absolute -bottom-px -right-px w-4 h-4 border-b border-r border-white/40" />
<div className="bg-[#080808] p-8 lg:p-10 border border-white/10 relative overflow-hidden">
{/* Subtle Background within card */}
<div className="bg-[#050505] p-8 lg:p-10 border border-white/5 relative overflow-hidden">
<div className="absolute inset-0 bg-white/[0.02]" />
<div className="relative z-10">
<div className="flex items-center justify-between mb-8">
<span className="text-[10px] font-mono uppercase tracking-[0.2em] text-accent/80 flex items-center gap-2">
<span className="text-[10px] font-mono uppercase tracking-[0.2em] text-accent flex items-center gap-2">
<span className="w-1.5 h-1.5 bg-accent animate-pulse" />
Terminal Access
</span>
@ -276,8 +225,7 @@ export default function HomePage() {
</div>
</div>
{/* The Checker Component */}
<div className="bg-[#0A0A0A] border-[0.5px] border-white/10 p-1.5 shadow-inner">
<div className="bg-[#0A0A0A] border-[0.5px] border-white/10 p-2 shadow-inner">
<DomainChecker />
</div>
@ -299,40 +247,49 @@ export default function HomePage() {
)}
{/* THE PARADIGM SHIFT - Problem / Solution */}
<section className="relative py-32 px-4 sm:px-6 border-b border-white/[0.08]">
<section className="relative py-32 px-4 sm:px-6 border-b border-white/[0.05]">
<div className="max-w-[1200px] mx-auto">
<div className="grid lg:grid-cols-2 gap-16 lg:gap-24 items-center">
<div>
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">The Problem</span>
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">The Broken Model</span>
<h2 className="font-display text-4xl sm:text-5xl text-white leading-tight mb-8">
99% of domains are <br/><span className="text-white/30">dead capital.</span>
99% of portfolios are <br/><span className="text-white/30">bleeding cash.</span>
</h2>
<div className="space-y-6 text-white/50 leading-relaxed text-lg font-light">
<div className="space-y-6 text-white/60 leading-relaxed text-lg font-light">
<p>
Most investors guess. They buy domains based on "sound" and pay renewal fees for years, hoping for a random buyer.
Investors pay renewal fees for years, hoping for a "Unicorn" sale that never happens. It's gambling, not investing.
</p>
<p>
Traditional marketplaces are flooded with spam, parking pages generate pennies, and valuable assets gather dust.
Traditional parking pays pennies. Marketplaces charge 20% fees. The system is designed to drain your capital.
</p>
</div>
</div>
<div className="relative">
<div className="absolute -inset-4 bg-accent/5 blur-3xl rounded-full" />
<div className="absolute -inset-4 bg-accent/5 blur-3xl" />
<div className="relative bg-[#050505] border border-white/10 p-8 lg:p-12">
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">The Pounce Standard</span>
<h3 className="font-display text-3xl text-white mb-6">Asset Class V2.0</h3>
<ul className="space-y-4 font-mono text-sm text-white/80">
<li className="flex items-start gap-3">
<Check className="w-5 h-5 text-accent mt-px" />
<span><span className="text-white font-bold">Data-Driven:</span> Don't guess price. Know the valuation.</span>
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">The Pounce Protocol</span>
<h3 className="font-display text-3xl text-white mb-8">Asset Class V2.0</h3>
<ul className="space-y-6 font-mono text-sm text-white/80">
<li className="flex items-start gap-4">
<Radar className="w-5 h-5 text-accent mt-px shrink-0" />
<div>
<span className="text-white font-bold block mb-1">Deep Recon</span>
<span className="text-white/50">Zone file analysis reveals what's truly valuable. Don't guess. Know.</span>
</div>
</li>
<li className="flex items-start gap-3">
<Check className="w-5 h-5 text-accent mt-px" />
<span><span className="text-white font-bold">Liquid:</span> Instant settlement. No middlemen.</span>
<li className="flex items-start gap-4">
<Zap className="w-5 h-5 text-accent mt-px shrink-0" />
<div>
<span className="text-white font-bold block mb-1">Frictionless Liquidity</span>
<span className="text-white/50">Instant settlement. Verified owners. 0% Commission.</span>
</div>
</li>
<li className="flex items-start gap-3">
<Check className="w-5 h-5 text-accent mt-px" />
<span><span className="text-white font-bold">Yield-Bearing:</span> Intent Routing turns traffic into revenue.</span>
<li className="flex items-start gap-4">
<Coins className="w-5 h-5 text-accent mt-px shrink-0" />
<div>
<span className="text-white font-bold block mb-1">Automated Yield</span>
<span className="text-white/50">Domains pay for their own renewals via Intent Routing™.</span>
</div>
</li>
</ul>
</div>
@ -341,15 +298,15 @@ export default function HomePage() {
</div>
</section>
{/* THE THREE PILLARS + YIELD - Architectural Layout */}
{/* CORE ARCHITECTURE - 3 Pillars */}
<section className="relative py-40 px-4 sm:px-6 bg-[#020202]">
<div className="max-w-[1600px] mx-auto">
<div className="max-w-[1400px] mx-auto">
{/* Section Header */}
<div className="flex flex-col lg:flex-row justify-between items-end mb-24 border-b border-white/[0.08] pb-12">
<div>
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">Core Architecture</span>
<h2 className="font-display text-4xl sm:text-5xl lg:text-6xl text-white leading-none">
The Domain Lifecycle <br />
The Lifecycle <br />
<span className="text-white/30">Engine.</span>
</h2>
</div>
@ -362,8 +319,8 @@ export default function HomePage() {
<div className="grid grid-cols-1 lg:grid-cols-3 gap-px bg-white/[0.08] border border-white/[0.08]">
{/* 1. INTELLIGENCE (Discover) */}
<div className="group relative bg-[#030303] p-12 lg:p-16 hover:bg-[#050505] transition-colors duration-500">
{/* 1. INTELLIGENCE */}
<div className="group relative bg-[#030303] p-10 lg:p-14 hover:bg-[#050505] transition-colors duration-500">
<div className="absolute top-0 right-0 p-6 opacity-0 group-hover:opacity-100 transition-opacity duration-500">
<ArrowUpRight className="w-6 h-6 text-white/20" />
</div>
@ -375,13 +332,13 @@ export default function HomePage() {
</div>
<h3 className="text-3xl text-white font-display mb-6">Intelligence</h3>
<p className="text-white/50 leading-relaxed text-lg font-light mb-12">
"Find the Asset." We scan 886+ TLDs in real-time to uncover hidden opportunities before the market reacts.
"Identify Targets." We scan 886+ TLDs in real-time to uncover hidden opportunities before the market reacts.
</p>
</div>
<div className="space-y-6 pt-12 border-t border-white/[0.05]">
<div className="flex items-start gap-4">
<Search className="w-5 h-5 text-accent mt-1" />
<Scan className="w-5 h-5 text-accent mt-1" />
<div>
<div className="text-white font-medium mb-1">Global Scan</div>
<div className="text-white/30 text-sm">Zone file analysis & expiration monitoring.</div>
@ -398,8 +355,8 @@ export default function HomePage() {
</div>
</div>
{/* 2. MARKET (Acquire) */}
<div className="group relative bg-[#030303] p-12 lg:p-16 hover:bg-[#050505] transition-colors duration-500">
{/* 2. MARKET */}
<div className="group relative bg-[#030303] p-10 lg:p-14 hover:bg-[#050505] transition-colors duration-500">
<div className="absolute top-0 right-0 p-6 opacity-0 group-hover:opacity-100 transition-opacity duration-500">
<ArrowUpRight className="w-6 h-6 text-white/20" />
</div>
@ -411,7 +368,7 @@ export default function HomePage() {
</div>
<h3 className="text-3xl text-white font-display mb-6">Market</h3>
<p className="text-white/50 leading-relaxed text-lg font-light mb-12">
"Secure the Asset." Direct access to liquidity. A verified marketplace where assets move instantly, securely, and with 0% commission fees.
"Secure the Asset." Direct access to liquidity. A verified exchange where assets move instantly, securely, and with 0% commission fees.
</p>
</div>
@ -434,8 +391,8 @@ export default function HomePage() {
</div>
</div>
{/* 3. YIELD (Monetize) */}
<div className="group relative bg-[#030303] p-12 lg:p-16 hover:bg-[#050505] transition-colors duration-500">
{/* 3. YIELD */}
<div className="group relative bg-[#030303] p-10 lg:p-14 hover:bg-[#050505] transition-colors duration-500">
<div className="absolute top-0 right-0 p-6 opacity-0 group-hover:opacity-100 transition-opacity duration-500">
<ArrowUpRight className="w-6 h-6 text-white/20" />
</div>
@ -447,7 +404,7 @@ export default function HomePage() {
</div>
<h3 className="text-3xl text-white font-display mb-6">Yield</h3>
<p className="text-white/50 leading-relaxed text-lg font-light mb-12">
"Let the Asset Work." Our "Intent Routing" engine transforms idle domains into active revenue generators via automated traffic monetization.
"Deploy the Asset." Our "Intent Routing" engine transforms idle domains into active revenue generators via automated traffic monetization.
</p>
</div>
@ -474,72 +431,77 @@ export default function HomePage() {
</div>
</section>
{/* DEEP DIVE: YIELD - The "Unicorn" Feature */}
{/* DEEP DIVE: YIELD */}
<section className="relative py-32 px-4 sm:px-6 border-b border-white/[0.05] bg-[#050505] overflow-hidden">
<div className="absolute inset-0 bg-accent/[0.02]" />
<div className="max-w-[1200px] mx-auto relative z-10">
<div className="mb-16 text-center">
<div className="mb-20 text-center">
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">The Endgame</span>
<h2 className="font-display text-4xl sm:text-5xl text-white mb-6">Intent Routing™</h2>
<p className="text-white/50 max-w-2xl mx-auto text-lg font-light">
Domains usually park for pennies. We route them for dollars. <br/>
We analyze the intent behind a domain (e.g. "kredit.ch") and route traffic directly to high-paying affiliates.
<p className="text-white/50 max-w-2xl mx-auto text-lg font-light leading-relaxed">
We don't build websites. We build signposts. <br/>
Our engine detects user intent (e.g. "kredit.ch" = Loan Search) and routes traffic directly to high-paying partners.
</p>
</div>
<div className="grid md:grid-cols-3 gap-8">
<div className="bg-[#020202] border border-white/10 p-8 relative group hover:border-accent/30 transition-colors">
<div className="w-12 h-12 bg-white/5 flex items-center justify-center mb-6 text-white group-hover:text-accent group-hover:bg-accent/10 transition-all">
<Network className="w-6 h-6" />
{/* Step 1 */}
<div className="bg-[#020202] border border-white/10 p-10 relative group hover:border-accent/30 transition-colors">
<div className="w-14 h-14 bg-white/5 flex items-center justify-center mb-8 text-white group-hover:text-accent group-hover:bg-accent/10 transition-all">
<Network className="w-7 h-7" />
</div>
<h3 className="text-white font-bold text-xl mb-2">1. Connect</h3>
<p className="text-white/40 text-sm font-mono">User points NS records to Pounce. No coding required.</p>
<h3 className="text-white font-bold text-xl mb-3">1. Connect</h3>
<p className="text-white/40 text-sm font-mono leading-relaxed">Point your nameservers to `ns.pounce.io`. The system takes over instantly.</p>
</div>
<div className="bg-[#020202] border border-white/10 p-8 relative group hover:border-accent/30 transition-colors">
<div className="w-12 h-12 bg-white/5 flex items-center justify-center mb-6 text-white group-hover:text-accent group-hover:bg-accent/10 transition-all">
<Cpu className="w-6 h-6" />
{/* Step 2 */}
<div className="bg-[#020202] border border-white/10 p-10 relative group hover:border-accent/30 transition-colors">
<div className="w-14 h-14 bg-white/5 flex items-center justify-center mb-8 text-white group-hover:text-accent group-hover:bg-accent/10 transition-all">
<Cpu className="w-7 h-7" />
</div>
<h3 className="text-white font-bold text-xl mb-2">2. Analyze</h3>
<p className="text-white/40 text-sm font-mono">AI detects intent. "zahnarzt-zh" -> Intent: "Dentist Booking".</p>
<h3 className="text-white font-bold text-xl mb-3">2. Analyze</h3>
<p className="text-white/40 text-sm font-mono leading-relaxed">We scan the semantic intent. `zahnarzt-zh.ch` is identified as "Medical Booking Lead".</p>
</div>
<div className="bg-[#020202] border border-white/10 p-8 relative group hover:border-accent/30 transition-colors">
<div className="w-12 h-12 bg-white/5 flex items-center justify-center mb-6 text-white group-hover:text-accent group-hover:bg-accent/10 transition-all">
<Share2 className="w-6 h-6" />
{/* Step 3 */}
<div className="bg-[#020202] border border-white/10 p-10 relative group hover:border-accent/30 transition-colors">
<div className="w-14 h-14 bg-white/5 flex items-center justify-center mb-8 text-white group-hover:text-accent group-hover:bg-accent/10 transition-all">
<Share2 className="w-7 h-7" />
</div>
<h3 className="text-white font-bold text-xl mb-2">3. Route</h3>
<p className="text-white/40 text-sm font-mono">Traffic is sent to partners (e.g. Doctolib). You get paid per lead.</p>
<h3 className="text-white font-bold text-xl mb-3">3. Route</h3>
<p className="text-white/40 text-sm font-mono leading-relaxed">Traffic is routed to vertical partners (e.g. Doctolib, Comparis). You earn per qualified lead.</p>
</div>
</div>
</div>
</section>
{/* DEEP DIVE: MARKET - The "Velvet Rope" */}
{/* DEEP DIVE: MARKET */}
<section className="relative py-32 px-4 sm:px-6 bg-[#020202]">
<div className="max-w-[1200px] mx-auto grid lg:grid-cols-2 gap-20 items-center">
<div className="order-2 lg:order-1 relative">
<div className="border border-white/10 bg-[#050505] p-2 shadow-2xl rotate-1 hover:rotate-0 transition-transform duration-500">
<div className="bg-[#020202] p-6">
<div className="flex items-center gap-4 border-b border-white/10 pb-4 mb-4">
<div className="w-2 h-2 rounded-full bg-accent" />
<span className="font-mono text-sm text-white">zurich-immo.ch</span>
<span className="ml-auto text-accent font-bold">$950</span>
<div className="bg-[#020202] p-8">
<div className="flex items-center gap-4 border-b border-white/10 pb-6 mb-6">
<div className="w-2 h-2 rounded-full bg-accent animate-pulse" />
<span className="font-mono text-base text-white">zurich-immo.ch</span>
<span className="ml-auto text-accent font-bold text-lg">$950</span>
</div>
<div className="space-y-3 font-mono text-xs text-white/50">
<div className="flex justify-between">
<div className="space-y-4 font-mono text-xs text-white/50">
<div className="flex justify-between items-center">
<span>Source</span>
<span className="text-white flex items-center gap-2"><div className="w-1.5 h-1.5 bg-accent rounded-full"/> Pounce Direct</span>
</div>
<div className="flex justify-between">
<div className="flex justify-between items-center">
<span>Seller Verified</span>
<span className="text-accent">Yes (DNS Check)</span>
<span className="text-accent flex items-center gap-2"><Check className="w-3 h-3" /> DNS Check Passed</span>
</div>
<div className="flex justify-between">
<div className="flex justify-between items-center">
<span>Commission</span>
<span className="text-white">0%</span>
<span className="text-white bg-white/10 px-2 py-0.5 rounded-none">0%</span>
</div>
</div>
<div className="mt-6 pt-4 border-t border-white/10">
<button className="w-full py-3 bg-white/5 text-white uppercase font-bold text-xs tracking-widest hover:bg-white hover:text-black transition-colors">
<div className="mt-8 pt-6 border-t border-white/10">
<button className="w-full py-4 bg-white/5 text-white uppercase font-bold text-xs tracking-[0.2em] hover:bg-white hover:text-black transition-colors flex items-center justify-center gap-2">
Contact Seller
</button>
</div>
@ -549,30 +511,30 @@ export default function HomePage() {
<div className="order-1 lg:order-2">
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">Exclusive Exchange</span>
<h2 className="font-display text-4xl text-white mb-6">The Velvet Rope Strategy.</h2>
<p className="text-white/50 text-lg leading-relaxed mb-8">
<p className="text-white/50 text-lg leading-relaxed mb-10">
We don't run an open flea market. We run an exclusive club.
Buying is open to everyone, but selling is reserved for members.
Buying is open to everyone, but selling is reserved for verified members.
</p>
<ul className="space-y-4">
<li className="flex gap-4">
<ul className="space-y-6">
<li className="flex gap-5">
<Shield className="w-6 h-6 text-accent shrink-0" />
<div>
<h4 className="text-white font-bold mb-1">Zero Spam</h4>
<p className="text-white/40 text-sm">Gatekeeper technology filters 99% of junk domains automatically.</p>
<h4 className="text-white font-bold mb-1">Zero Noise</h4>
<p className="text-white/40 text-sm leading-relaxed">Gatekeeper technology filters 99% of junk domains automatically.</p>
</div>
</li>
<li className="flex gap-4">
<li className="flex gap-5">
<Key className="w-6 h-6 text-accent shrink-0" />
<div>
<h4 className="text-white font-bold mb-1">Verified Owners</h4>
<p className="text-white/40 text-sm">Sellers must verify ownership via DNS before listing.</p>
<p className="text-white/40 text-sm leading-relaxed">Sellers must verify ownership via DNS before listing. No fakes.</p>
</div>
</li>
<li className="flex gap-4">
<li className="flex gap-5">
<Zap className="w-6 h-6 text-accent shrink-0" />
<div>
<h4 className="text-white font-bold mb-1">0% Commission</h4>
<p className="text-white/40 text-sm">Members keep 100% of the sale price. Direct settlement.</p>
<p className="text-white/40 text-sm leading-relaxed">Members keep 100% of the sale price. Direct settlement.</p>
</div>
</li>
</ul>
@ -587,46 +549,46 @@ export default function HomePage() {
<div className="grid md:grid-cols-3 gap-8 text-left">
{/* Scout */}
<div className="p-8 border border-white/10 bg-[#020202] opacity-60 hover:opacity-100 transition-opacity">
<div className="p-10 border border-white/10 bg-[#020202] opacity-60 hover:opacity-100 transition-opacity flex flex-col">
<h3 className="text-xl font-display text-white mb-2">Scout</h3>
<div className="text-3xl font-mono text-white mb-6">$0<span className="text-sm text-white/30">/mo</span></div>
<ul className="space-y-3 text-sm text-white/50 font-mono mb-8">
<li className="flex gap-2"><span></span> Market Overview</li>
<li className="flex gap-2"><span></span> Basic Search</li>
<li className="flex gap-2"><span></span> 5 Watchlist Items</li>
<div className="text-4xl font-mono text-white mb-8">$0<span className="text-sm text-white/30">/mo</span></div>
<ul className="space-y-4 text-sm text-white/50 font-mono mb-10 flex-1">
<li className="flex gap-3"><span>•</span> Recon Overview</li>
<li className="flex gap-3"><span>•</span> Basic Scan</li>
<li className="flex gap-3"><span>•</span> 5 Targets</li>
</ul>
<Link href="/register" className="block w-full py-3 text-center border border-white/20 text-white uppercase text-xs font-bold tracking-widest hover:bg-white hover:text-black transition-colors">
Start Free
<Link href="/register" className="block w-full py-4 text-center border border-white/20 text-white uppercase text-xs font-bold tracking-widest hover:bg-white hover:text-black transition-colors">
Join the Hunt
</Link>
</div>
{/* Trader - Highlight */}
<div className="p-8 border border-accent bg-[#050505] relative transform md:-translate-y-4">
<div className="absolute top-0 left-1/2 -translate-x-1/2 -translate-y-1/2 bg-accent text-black px-3 py-1 text-[10px] font-bold uppercase tracking-widest">Recommended</div>
<div className="p-10 border border-accent bg-[#050505] relative transform md:-translate-y-4 flex flex-col shadow-[0_0_50px_-20px_rgba(16,185,129,0.2)]">
<div className="absolute top-0 left-1/2 -translate-x-1/2 -translate-y-1/2 bg-accent text-black px-4 py-1.5 text-[10px] font-bold uppercase tracking-widest">Recommended</div>
<h3 className="text-xl font-display text-white mb-2">Trader</h3>
<div className="text-3xl font-mono text-accent mb-6">$9<span className="text-sm text-white/30">/mo</span></div>
<ul className="space-y-3 text-sm text-white/80 font-mono mb-8">
<li className="flex gap-2"><Check className="w-4 h-4 text-accent"/> Clean Feed (No Spam)</li>
<li className="flex gap-2"><Check className="w-4 h-4 text-accent"/> Renewal Price Intel</li>
<li className="flex gap-2"><Check className="w-4 h-4 text-accent"/> Sell Domains (0% Fee)</li>
<li className="flex gap-2"><Check className="w-4 h-4 text-accent"/> 50 Watchlist Items</li>
<div className="text-4xl font-mono text-accent mb-8">$9<span className="text-sm text-white/30">/mo</span></div>
<ul className="space-y-4 text-sm text-white/80 font-mono mb-10 flex-1">
<li className="flex gap-3"><Check className="w-4 h-4 text-accent"/> Clean Feed (No Noise)</li>
<li className="flex gap-3"><Check className="w-4 h-4 text-accent"/> Renewal Intel</li>
<li className="flex gap-3"><Check className="w-4 h-4 text-accent"/> Liquidate (0% Fee)</li>
<li className="flex gap-3"><Check className="w-4 h-4 text-accent"/> 50 Targets</li>
</ul>
<Link href="/pricing" className="block w-full py-3 text-center bg-accent text-black uppercase text-xs font-bold tracking-widest hover:bg-white transition-colors">
Upgrade
<Link href="/pricing" className="block w-full py-4 text-center bg-accent text-black uppercase text-xs font-bold tracking-widest hover:bg-white transition-colors">
Gear Up
</Link>
</div>
{/* Tycoon */}
<div className="p-8 border border-white/10 bg-[#020202] hover:border-white/30 transition-colors">
<div className="p-10 border border-white/10 bg-[#020202] hover:border-white/30 transition-colors flex flex-col">
<h3 className="text-xl font-display text-white mb-2">Tycoon</h3>
<div className="text-3xl font-mono text-white mb-6">$29<span className="text-sm text-white/30">/mo</span></div>
<ul className="space-y-3 text-sm text-white/50 font-mono mb-8">
<li className="flex gap-2"><Check className="w-4 h-4 text-white"/> Full Portfolio Monitor</li>
<li className="flex gap-2"><Check className="w-4 h-4 text-white"/> Priority Alerts (10m)</li>
<li className="flex gap-2"><Check className="w-4 h-4 text-white"/> 500 Watchlist Items</li>
<li className="flex gap-2"><Check className="w-4 h-4 text-white"/> Featured Listings</li>
<div className="text-4xl font-mono text-white mb-8">$29<span className="text-sm text-white/30">/mo</span></div>
<ul className="space-y-4 text-sm text-white/50 font-mono mb-10 flex-1">
<li className="flex gap-3"><Check className="w-4 h-4 text-white"/> Full Portfolio Monitor</li>
<li className="flex gap-3"><Check className="w-4 h-4 text-white"/> First Strike Alerts (10m)</li>
<li className="flex gap-3"><Check className="w-4 h-4 text-white"/> 500 Targets</li>
<li className="flex gap-3"><Check className="w-4 h-4 text-white"/> Featured Listings</li>
</ul>
<Link href="/pricing" className="block w-full py-3 text-center border border-white/20 text-white uppercase text-xs font-bold tracking-widest hover:bg-white hover:text-black transition-colors">
<Link href="/pricing" className="block w-full py-4 text-center border border-white/20 text-white uppercase text-xs font-bold tracking-widest hover:bg-white hover:text-black transition-colors">
Go Professional
</Link>
</div>
@ -641,11 +603,11 @@ export default function HomePage() {
<div className="flex justify-between items-end mb-12">
<div>
<h2 className="font-display text-3xl text-white mb-2">Market Activity</h2>
<p className="text-accent/60 font-mono text-sm">LIVE_FEED_V2.0 // ENCRYPTED</p>
<h2 className="font-display text-3xl text-white mb-2">Live Ops</h2>
<p className="text-accent/60 font-mono text-sm">FEED_V2.0 // ENCRYPTED</p>
</div>
<Link href="/market" className="text-xs font-mono uppercase tracking-widest text-white/40 hover:text-white transition-colors flex items-center gap-2">
View All Markets <ArrowRight className="w-3 h-3" />
<Link href="/acquire" className="text-xs font-mono uppercase tracking-widest text-white/40 hover:text-white transition-colors flex items-center gap-2">
Recon All Markets <ArrowRight className="w-3 h-3" />
</Link>
</div>
@ -656,8 +618,8 @@ export default function HomePage() {
<div className="grid grid-cols-12 gap-4 px-6 py-4 border-b border-white/[0.05] bg-white/[0.01] text-[10px] font-mono text-white/30 uppercase tracking-widest">
<div className="col-span-5">Asset Identifier</div>
<div className="col-span-2 text-right">Valuation</div>
<div className="col-span-2 text-right">Current Bid</div>
<div className="col-span-3 text-right">Time to Expiry</div>
<div className="col-span-2 text-right">Strike Price</div>
<div className="col-span-3 text-right">Window Closes</div>
</div>
{/* Table Rows */}
@ -680,9 +642,10 @@ export default function HomePage() {
<Link
href="/register"
className="group flex items-center gap-4 px-8 py-4 border border-accent/20 bg-accent/10 hover:bg-accent hover:border-accent hover:text-black text-white transition-all duration-500 backdrop-blur-md"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
<Lock className="w-3 h-3" />
<span className="text-xs font-bold uppercase tracking-[0.2em]">Access Full Terminal</span>
<span className="text-xs font-bold uppercase tracking-[0.2em]">Enter HQ</span>
<ArrowRight className="w-3 h-3 group-hover:translate-x-1 transition-transform" />
</Link>
</div>

View File

@ -6,7 +6,7 @@ import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { useStore } from '@/lib/store'
import { api } from '@/lib/api'
import { Check, ArrowRight, Zap, TrendingUp, Crown, Loader2, Clock, X, AlertCircle } from 'lucide-react'
import { Check, ArrowRight, Zap, TrendingUp, Crown, Loader2, Clock, X, AlertCircle, Shield } from 'lucide-react'
import Link from 'next/link'
import clsx from 'clsx'
@ -79,12 +79,12 @@ const tiers = [
]
const comparisonFeatures = [
{ name: 'Market Feed', scout: '🌪️ Raw', trader: 'Curated', tycoon: 'Priority' },
{ name: 'Alert Speed', scout: '🐢 Daily', trader: '🐇 Hourly', tycoon: '10 min' },
{ name: 'Market Feed', scout: 'Raw', trader: 'Curated', tycoon: 'Priority' },
{ name: 'Alert Speed', scout: 'Daily', trader: 'Hourly', tycoon: '10 min' },
{ name: 'Watchlist', scout: '5 Domains', trader: '50 Domains', tycoon: '500 Domains' },
{ name: 'Marketplace', scout: 'Buy Only', trader: 'Sell (0% Fee)', tycoon: 'Sell + Featured' },
{ name: 'TLD Intel', scout: 'Public Trends', trader: 'Renewal Prices', tycoon: 'Full History' },
{ name: 'Valuation', scout: 'Locked', trader: 'Pounce Score', tycoon: 'Score + SEO' },
{ name: 'Valuation', scout: 'Locked', trader: 'Pounce Score', tycoon: 'Score + SEO' },
{ name: 'Sniper Alerts', scout: '—', trader: '5', tycoon: 'Unlimited' },
{ name: 'Portfolio', scout: '—', trader: '25 Domains', tycoon: 'Unlimited' },
]
@ -159,18 +159,18 @@ export default function PricingPage() {
}
return (
<div className="min-h-screen bg-background relative overflow-hidden">
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Background Effects - matching landing page */}
<div className="fixed inset-0 pointer-events-none">
<div className="absolute top-[-20%] left-1/2 -translate-x-1/2 w-[1200px] h-[800px] bg-accent/[0.03] rounded-full blur-[120px]" />
<div className="absolute bottom-[-10%] right-[-10%] w-[600px] h-[600px] bg-accent/[0.02] rounded-full blur-[100px]" />
<div className="fixed inset-0 pointer-events-none z-0">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div
className="absolute inset-0 opacity-[0.015]"
className="absolute inset-0 opacity-[0.03]"
style={{
backgroundImage: `linear-gradient(rgba(255,255,255,.1) 1px, transparent 1px), linear-gradient(90deg, rgba(255,255,255,.1) 1px, transparent 1px)`,
backgroundSize: '64px 64px',
backgroundImage: `linear-gradient(rgba(255,255,255,0.3) 0.5px, transparent 0.5px), linear-gradient(90deg, rgba(255,255,255,0.3) 0.5px, transparent 0.5px)`,
backgroundSize: '160px 160px',
}}
/>
<div className="absolute top-[-20%] left-1/2 -translate-x-1/2 w-[1200px] h-[800px] bg-accent/[0.02] rounded-full blur-[150px]" />
</div>
<Header />
@ -179,18 +179,18 @@ export default function PricingPage() {
<div className="max-w-6xl mx-auto">
{/* Cancelled Banner */}
{showCancelledBanner && (
<div className="mb-8 p-4 bg-amber-500/10 border border-amber-500/20 rounded-xl flex items-start gap-3 animate-fade-in">
<AlertCircle className="w-5 h-5 text-amber-400 shrink-0 mt-0.5" />
<div className="flex-1">
<p className="font-medium text-amber-400">Checkout cancelled</p>
<p className="text-sm text-foreground-muted mt-1">
No worries! Your card was not charged. You can try again whenever you&apos;re ready,
or continue with the free Scout plan.
<div className="mb-8 p-4 bg-amber-500/10 border border-amber-500/20 flex items-start gap-3 animate-fade-in relative overflow-hidden">
<div className="absolute inset-0 bg-amber-500/5 animate-pulse" />
<AlertCircle className="w-5 h-5 text-amber-400 shrink-0 mt-0.5 relative z-10" />
<div className="flex-1 relative z-10">
<p className="font-medium text-amber-400 font-mono text-sm uppercase tracking-wider">Transaction Cancelled</p>
<p className="text-sm text-white/60 mt-1">
Operation aborted. No charges applied. Resume when ready.
</p>
</div>
<button
onClick={() => setShowCancelledBanner(false)}
className="p-1 text-foreground-muted hover:text-foreground transition-colors"
className="p-1 text-white/40 hover:text-white transition-colors relative z-10"
>
<X className="w-4 h-4" />
</button>
@ -199,36 +199,44 @@ export default function PricingPage() {
{/* Hero */}
<div className="text-center mb-16 sm:mb-20 animate-fade-in">
<span className="text-sm font-semibold text-accent uppercase tracking-wider">Pricing</span>
<h1 className="mt-4 font-display text-[2.5rem] sm:text-[3.5rem] md:text-[4.5rem] lg:text-[5rem] leading-[0.95] tracking-[-0.03em] text-foreground">
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block flex items-center justify-center gap-2">
<div className="w-1.5 h-1.5 bg-accent animate-pulse" />
Clearance Levels
</span>
<h1 className="font-display text-[3.5rem] sm:text-[5rem] md:text-[6rem] lg:text-[7rem] leading-[0.9] tracking-[-0.04em] text-white">
Pick your weapon.
</h1>
<p className="mt-5 text-lg sm:text-xl text-foreground-muted max-w-xl mx-auto">
<p className="mt-8 text-lg sm:text-xl text-white/50 max-w-xl mx-auto font-light leading-relaxed">
Start free. Scale when you&apos;re ready. All plans include core features.
</p>
</div>
{/* Pricing Cards */}
<div className="grid md:grid-cols-3 gap-6 mb-20 animate-slide-up items-stretch">
{/* Pricing Cards - AWARD WINNING STYLE */}
<div className="grid md:grid-cols-3 gap-8 mb-24 animate-slide-up items-stretch">
{tiers.map((tier, index) => (
<div
key={tier.id}
className={clsx(
"group relative p-6 sm:p-8 rounded-2xl border transition-all duration-500 flex flex-col",
"group relative p-8 flex flex-col transition-all duration-500",
tier.highlighted
? "bg-background-secondary border-accent/30 shadow-lg shadow-accent/5"
: "bg-background-secondary/50 border-border hover:border-accent/20 hover:bg-background-secondary"
? "bg-[#050505] border border-accent/50 shadow-[0_0_50px_-20px_rgba(16,185,129,0.2)] z-10 transform md:-translate-y-4"
: "bg-[#030303] border border-white/10 hover:border-white/20 hover:bg-[#050505]"
)}
style={{ animationDelay: `${index * 100}ms` }}
>
{/* Hover glow for non-highlighted */}
{!tier.highlighted && (
<div className="absolute inset-0 rounded-2xl bg-accent/5 opacity-0 group-hover:opacity-100 transition-opacity" />
{/* Tech Corners for Highlighted */}
{tier.highlighted && (
<>
<div className="absolute -top-px -left-px w-4 h-4 border-t border-l border-accent" />
<div className="absolute -top-px -right-px w-4 h-4 border-t border-r border-accent" />
<div className="absolute -bottom-px -left-px w-4 h-4 border-b border-l border-accent" />
<div className="absolute -bottom-px -right-px w-4 h-4 border-b border-r border-accent" />
</>
)}
{tier.badge && (
<div className="absolute -top-3 left-1/2 -translate-x-1/2 z-10">
<span className="px-3 py-1 bg-accent text-background text-ui-xs font-medium rounded-full whitespace-nowrap">
<div className="absolute top-0 left-1/2 -translate-x-1/2 -translate-y-1/2 z-20">
<span className="px-4 py-1.5 bg-accent text-black text-[10px] font-bold uppercase tracking-widest whitespace-nowrap shadow-lg shadow-accent/20">
{tier.badge}
</span>
</div>
@ -236,53 +244,47 @@ export default function PricingPage() {
<div className="relative flex-1 flex flex-col">
{/* Header */}
<div className="mb-6">
<div className="flex items-center gap-3 mb-3">
<div className={clsx(
"w-12 h-12 rounded-2xl flex items-center justify-center border transition-all duration-500",
tier.highlighted
? "bg-accent/10 border-accent/30"
: "bg-foreground/5 border-border group-hover:border-accent/30 group-hover:bg-accent/5"
)}>
<tier.icon className={clsx(
"w-5 h-5 transition-colors duration-500",
tier.highlighted ? "text-accent" : "text-foreground-muted group-hover:text-accent"
)} />
</div>
<h3 className="text-xl font-semibold text-foreground">{tier.name}</h3>
</div>
<p className="text-body-sm text-foreground-muted mb-4">{tier.description}</p>
<div className="flex items-baseline gap-1">
<div className="mb-8 text-center pb-8 border-b border-white/10">
<h3 className="text-2xl font-display text-white mb-4">{tier.name}</h3>
<div className="flex items-baseline justify-center gap-1 mb-4">
{tier.price === '0' ? (
<span className="text-5xl font-display text-foreground">Free</span>
<span className="text-5xl font-mono text-white tracking-tight">Free</span>
) : (
<>
<span className="text-5xl font-display text-foreground">${tier.price}</span>
<span className="text-body text-foreground-muted">{tier.period}</span>
<span className="text-5xl font-mono text-white tracking-tight">${tier.price}</span>
<span className="text-sm font-mono text-white/40">{tier.period}</span>
</>
)}
</div>
<p className="text-sm text-white/50 font-mono">{tier.description}</p>
</div>
{/* Features - flex-1 to push button to bottom */}
<ul className="space-y-3 mb-8 flex-1">
{/* Features */}
<ul className="space-y-4 mb-10 flex-1">
{tier.features.map((feature) => (
<li key={feature.text} className="flex items-start gap-3">
{feature.available ? (
<Check className={clsx(
"w-4 h-4 mt-0.5 shrink-0",
feature.highlight ? "text-accent" : "text-foreground-muted"
)} strokeWidth={2.5} />
<div className={clsx(
"w-5 h-5 flex items-center justify-center shrink-0 border",
feature.highlight ? "border-accent bg-accent/10 text-accent" : "border-white/20 bg-white/5 text-white/60"
)}>
<Check className="w-3 h-3" strokeWidth={3} />
</div>
) : (
<X className="w-4 h-4 mt-0.5 shrink-0 text-foreground-subtle" strokeWidth={2} />
<div className="w-5 h-5 flex items-center justify-center shrink-0 border border-white/5 bg-transparent text-white/10">
<X className="w-3 h-3" strokeWidth={3} />
</div>
)}
<span className={clsx(
"text-body-sm",
feature.available ? "text-foreground" : "text-foreground-subtle line-through"
"text-sm font-mono leading-tight pt-0.5",
feature.available ? "text-white/80" : "text-white/20 line-through decoration-white/10"
)}>
{feature.text}
{feature.sublabel && (
<span className="ml-1.5 text-xs text-accent font-medium">
<span className={clsx(
"ml-2 text-[10px] uppercase tracking-wider px-1.5 py-0.5 border",
tier.highlighted ? "text-accent border-accent/30 bg-accent/5" : "text-white/40 border-white/10 bg-white/5"
)}>
{feature.sublabel}
</span>
)}
@ -291,16 +293,17 @@ export default function PricingPage() {
))}
</ul>
{/* CTA - always at bottom */}
{/* CTA */}
<button
onClick={() => handleSelectPlan(tier.id, tier.isPaid)}
disabled={loadingPlan === tier.id}
className={clsx(
"w-full flex items-center justify-center gap-2 py-4 rounded-xl text-ui font-medium transition-all duration-300 mt-auto",
"w-full flex items-center justify-center gap-3 py-4 text-xs font-bold uppercase tracking-[0.2em] transition-all duration-300 mt-auto",
tier.highlighted
? "bg-accent text-background hover:bg-accent-hover shadow-[0_0_20px_rgba(16,185,129,0.15)]"
: "bg-foreground text-background hover:bg-foreground/90"
? "bg-accent text-black hover:bg-white hover:text-black shadow-[0_0_20px_rgba(16,185,129,0.2)]"
: "border border-white/20 text-white hover:bg-white hover:text-black"
)}
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
{loadingPlan === tier.id ? (
<Loader2 className="w-4 h-4 animate-spin" />
@ -316,37 +319,33 @@ export default function PricingPage() {
))}
</div>
{/* Comparison Table */}
<div className="mb-20">
<h2 className="text-heading-md text-foreground text-center mb-8">Compare Plans</h2>
{/* Comparison Table - TECH STYLE */}
<div className="mb-24 border border-white/10 bg-[#050505]">
<div className="px-8 py-6 border-b border-white/10 bg-white/[0.02]">
<h2 className="text-xl font-display text-white">Spec Sheet</h2>
</div>
<div className="overflow-x-auto">
<table className="w-full">
<thead>
<tr className="border-b border-border">
<th className="text-left py-4 px-4 text-body-sm font-medium text-foreground-muted">Feature</th>
<th className="text-center py-4 px-4 text-body-sm font-medium text-foreground-muted">Scout</th>
<th className="text-center py-4 px-4 text-body-sm font-medium text-accent">Trader</th>
<th className="text-center py-4 px-4 text-body-sm font-medium text-foreground-muted">Tycoon</th>
<tr className="border-b border-white/10 bg-[#0A0A0A]">
<th className="text-left py-5 px-8 text-xs font-bold uppercase tracking-widest text-white/40 font-mono">Feature Module</th>
<th className="text-center py-5 px-8 text-xs font-bold uppercase tracking-widest text-white/40 font-mono">Scout</th>
<th className="text-center py-5 px-8 text-xs font-bold uppercase tracking-widest text-accent font-mono">Trader</th>
<th className="text-center py-5 px-8 text-xs font-bold uppercase tracking-widest text-white/40 font-mono">Tycoon</th>
</tr>
</thead>
<tbody>
<tbody className="divide-y divide-white/5">
{comparisonFeatures.map((feature) => (
<tr key={feature.name} className="border-b border-border/50">
<td className="py-4 px-4 text-body-sm text-foreground">{feature.name}</td>
<td className="py-4 px-4 text-center text-body-sm text-foreground-muted">
{feature.scout === 'check' ? (
<Check className="w-5 h-5 text-accent mx-auto" strokeWidth={2.5} />
) : feature.scout}
<tr key={feature.name} className="hover:bg-white/[0.02] transition-colors">
<td className="py-5 px-8 text-sm text-white font-mono">{feature.name}</td>
<td className="py-5 px-8 text-center text-sm text-white/40 font-mono">
{feature.scout}
</td>
<td className="py-4 px-4 text-center text-body-sm text-foreground">
{feature.trader === 'check' ? (
<Check className="w-5 h-5 text-accent mx-auto" strokeWidth={2.5} />
) : feature.trader}
<td className="py-5 px-8 text-center text-sm text-white font-mono bg-accent/[0.02]">
{feature.trader}
</td>
<td className="py-4 px-4 text-center text-body-sm text-foreground">
{feature.tycoon === 'check' ? (
<Check className="w-5 h-5 text-accent mx-auto" strokeWidth={2.5} />
) : feature.tycoon}
<td className="py-5 px-8 text-center text-sm text-white/40 font-mono">
{feature.tycoon}
</td>
</tr>
))}
@ -355,52 +354,62 @@ export default function PricingPage() {
</div>
</div>
{/* FAQ */}
{/* FAQ - TERMINAL STYLE */}
<div className="max-w-3xl mx-auto">
<h2 className="text-heading-md text-foreground text-center mb-8">Frequently Asked</h2>
<div className="space-y-3">
<h2 className="text-3xl font-display text-white text-center mb-12">Mission Support</h2>
<div className="space-y-4">
{faqs.map((faq, i) => (
<div
key={i}
className="border border-border rounded-xl overflow-hidden"
className="border border-white/10 bg-[#050505] transition-all hover:border-white/20"
>
<button
onClick={() => setExpandedFaq(expandedFaq === i ? null : i)}
className="w-full flex items-center justify-between p-5 text-left hover:bg-foreground/5 transition-colors"
className="w-full flex items-center justify-between p-6 text-left"
>
<span className="text-body font-medium text-foreground pr-4">{faq.q}</span>
<span className="text-base font-mono text-white pr-8">{faq.q}</span>
<span className={clsx(
"shrink-0 w-6 h-6 flex items-center justify-center rounded-lg transition-all",
expandedFaq === i ? "bg-accent/10 text-accent rotate-45" : "bg-foreground/5 text-foreground-muted"
"shrink-0 w-6 h-6 flex items-center justify-center border border-white/10 transition-all",
expandedFaq === i ? "bg-accent text-black border-accent" : "text-white/40"
)}>
<span className="text-lg leading-none">+</span>
<span className={clsx("text-lg leading-none transition-transform duration-300", expandedFaq === i ? "rotate-45" : "")}>+</span>
</span>
</button>
{expandedFaq === i && (
<div className="px-5 pb-5">
<p className="text-body-sm text-foreground-muted">{faq.a}</p>
<div className={clsx(
"overflow-hidden transition-all duration-300 ease-in-out",
expandedFaq === i ? "max-h-40 opacity-100" : "max-h-0 opacity-0"
)}>
<div className="px-6 pb-6 pt-0">
<div className="h-px w-full bg-white/5 mb-4" />
<p className="text-sm text-white/50 font-mono leading-relaxed pl-4 border-l border-accent/20">
{faq.a}
</p>
</div>
</div>
)}
</div>
))}
</div>
</div>
{/* Bottom CTA */}
<div className="text-center mt-20 py-12 px-6 bg-background-secondary/50 border border-border rounded-2xl">
<h2 className="text-heading-md text-foreground mb-3">Not sure yet?</h2>
<p className="text-body text-foreground-muted mb-6">
Start with Scout. It&apos;s free forever. Upgrade when you need more.
<div className="text-center mt-24 py-16 px-6 bg-[#050505] border border-white/10 relative overflow-hidden">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.05]" />
<div className="relative z-10">
<Shield className="w-12 h-12 text-white/20 mx-auto mb-6" />
<h2 className="text-3xl font-display text-white mb-4">Not ready to commit?</h2>
<p className="text-white/50 mb-10 font-mono text-sm">
Start with Scout. It&apos;s free forever. Upgrade when you need more firepower.
</p>
<Link
href={isAuthenticated ? "/terminal/radar" : "/register"}
className="btn-primary inline-flex items-center gap-2 px-6 py-3"
className="inline-flex items-center gap-3 px-8 py-4 border border-white/20 text-white text-xs font-bold uppercase tracking-[0.2em] hover:bg-white hover:text-black transition-all"
>
{isAuthenticated ? "Command Center" : "Join the Hunt"}
<ArrowRight className="w-4 h-4" />
</Link>
</div>
</div>
</div>
</main>
<Footer />

View File

@ -6,17 +6,18 @@ import Link from 'next/link'
import Image from 'next/image'
import { useStore } from '@/lib/store'
import { api } from '@/lib/api'
import { Loader2, ArrowRight, Check, Eye, EyeOff, Mail } from 'lucide-react'
import { Loader2, ArrowRight, Check, Eye, EyeOff, Mail, Shield, Zap, TrendingUp } from 'lucide-react'
import clsx from 'clsx'
// Logo Component
function Logo() {
return (
<Image
src="/pounce-logo.png"
src="/pounce-puma.png"
alt="pounce"
width={120}
height={60}
className="w-28 h-auto"
height={120}
className="w-20 h-20 object-contain drop-shadow-[0_0_15px_rgba(16,185,129,0.3)]"
/>
)
}
@ -42,10 +43,9 @@ function GitHubIcon({ className }: { className?: string }) {
}
const benefits = [
'Track up to 5 domains. Free.',
'Daily status scans. Never miss a drop.',
'Market overview. See what\'s moving.',
'Expiry intel. Plan your move.',
{ text: 'Real-time Market Feed', icon: Zap },
{ text: 'Daily Scan Reports', icon: Shield },
{ text: 'Yield Intel Access', icon: TrendingUp },
]
function RegisterForm() {
@ -77,13 +77,10 @@ function RegisterForm() {
try {
await register(email, password)
// Store redirect URL for after email verification
// This will be picked up by the login page after verification
if (redirectTo !== '/terminal/radar') {
localStorage.setItem('pounce_redirect_after_login', redirectTo)
}
// Show verification message
setRegistered(true)
} catch (err) {
setError(err instanceof Error ? err.message : 'Registration failed')
@ -100,125 +97,166 @@ function RegisterForm() {
// Show verification message after registration
if (registered) {
return (
<div className="min-h-screen flex items-center justify-center px-4 sm:px-6 py-8 sm:py-12 relative">
<div className="min-h-screen flex items-center justify-center px-4 sm:px-6 py-8 sm:py-12 relative bg-[#020202] overflow-hidden">
{/* Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none">
<div className="absolute top-1/4 left-1/3 w-[400px] h-[300px] bg-accent/[0.02] rounded-full blur-3xl" />
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div className="absolute top-1/2 left-1/2 -translate-x-1/2 -translate-y-1/2 w-[800px] h-[800px] bg-accent/[0.02] rounded-full blur-[120px]" />
</div>
<div className="relative w-full max-w-md text-center animate-fade-in">
<div className="w-20 h-20 bg-accent/10 rounded-full flex items-center justify-center mx-auto mb-6">
<Mail className="w-10 h-10 text-accent" />
<div className="relative w-full max-w-[450px] animate-fade-in z-10">
<div className="bg-[#050505] border border-white/10 p-10 text-center relative shadow-2xl">
{/* Tech Corners */}
<div className="absolute -top-px -left-px w-4 h-4 border-t border-l border-white/40" />
<div className="absolute -top-px -right-px w-4 h-4 border-t border-r border-white/40" />
<div className="absolute -bottom-px -left-px w-4 h-4 border-b border-l border-white/40" />
<div className="absolute -bottom-px -right-px w-4 h-4 border-b border-r border-white/40" />
<div className="w-16 h-16 bg-accent/10 border border-accent/20 flex items-center justify-center mx-auto mb-8 rounded-none">
<Mail className="w-8 h-8 text-accent" />
</div>
<h2 className="font-display text-3xl sm:text-4xl text-foreground mb-4">
Check your inbox
<h2 className="font-display text-3xl text-white mb-4">
Verify Credentials
</h2>
<p className="text-lg text-foreground-muted mb-6">
We&apos;ve sent a verification link to <strong className="text-foreground">{email}</strong>
<p className="text-sm font-mono text-white/50 mb-8 leading-relaxed">
Security protocol initiated. Verification link sent to <br/><strong className="text-white">{email}</strong>
</p>
<p className="text-sm text-foreground-subtle mb-8">
Click the link in the email to verify your account and start hunting domains.
</p>
<div className="space-y-3">
<div className="space-y-4">
<Link
href={loginLink}
className="block w-full py-3 bg-foreground text-background text-sm font-medium rounded-xl hover:bg-foreground/90 transition-all"
className="block w-full py-4 bg-white text-black text-xs font-bold uppercase tracking-[0.2em] hover:bg-accent transition-all"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
Go to Login
Proceed to Login
</Link>
<Link
href="/verify-email"
className="block w-full py-3 border border-border text-foreground-muted text-sm font-medium rounded-xl hover:border-foreground/20 transition-all"
className="block w-full py-4 border border-white/10 text-white/40 text-xs font-bold uppercase tracking-[0.2em] hover:text-white hover:border-white/30 transition-all"
>
Resend Verification Email
Resend Link
</Link>
</div>
</div>
</div>
</div>
)
}
return (
<div className="min-h-screen flex relative">
{/* Ambient glow */}
<div className="fixed inset-0 pointer-events-none">
<div className="absolute top-1/4 left-1/3 w-[400px] h-[300px] bg-accent/[0.02] rounded-full blur-3xl" />
<div className="min-h-screen flex relative bg-[#020202] overflow-hidden">
{/* Living Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none overflow-hidden">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.04] mix-blend-overlay z-10" />
{/* Animated Orbs */}
<div className="absolute top-[-20%] left-[-10%] w-[70vw] h-[70vw] bg-accent/5 rounded-full blur-[150px] animate-pulse-slow mix-blend-screen" />
<div className="absolute bottom-[-20%] right-[-10%] w-[60vw] h-[60vw] bg-purple-500/5 rounded-full blur-[180px] animate-pulse-slower mix-blend-screen" />
{/* Grid Overlay */}
<div
className="absolute inset-0 opacity-[0.02] z-0"
style={{
backgroundImage: `linear-gradient(rgba(255,255,255,0.3) 0.5px, transparent 0.5px), linear-gradient(90deg, rgba(255,255,255,0.3) 0.5px, transparent 0.5px)`,
backgroundSize: '60px 60px',
}}
/>
</div>
{/* Left Panel - Form */}
<div className="flex-1 flex items-center justify-center px-4 sm:px-6 py-8 sm:py-12">
<div className="relative w-full max-w-sm animate-fade-in">
<div className="flex-1 flex items-center justify-center px-4 sm:px-6 py-8 sm:py-12 relative z-10">
<div className="relative w-full max-w-[450px] animate-fade-in">
{/* Card Container */}
<div className="bg-[#050505] border border-white/10 relative p-8 sm:p-10 shadow-2xl">
{/* Tech Corners */}
<div className="absolute -top-px -left-px w-4 h-4 border-t border-l border-white/40" />
<div className="absolute -top-px -right-px w-4 h-4 border-t border-r border-white/40" />
<div className="absolute -bottom-px -left-px w-4 h-4 border-b border-l border-white/40" />
<div className="absolute -bottom-px -right-px w-4 h-4 border-b border-r border-white/40" />
{/* Logo */}
<Link href="/" className="block mb-12 sm:mb-16 hover:opacity-80 transition-opacity duration-300">
<Link href="/" className="flex justify-center mb-10 hover:opacity-80 transition-opacity duration-300">
<Logo />
</Link>
{/* Header */}
<div className="mb-8 sm:mb-10">
<h1 className="font-display text-[2rem] sm:text-[2.5rem] md:text-[3rem] leading-[1.1] tracking-[-0.03em] text-foreground mb-2 sm:mb-3">
Join the hunt.
<div className="text-center mb-10">
<span className="text-[10px] font-mono text-accent uppercase tracking-[0.2em] mb-2 block flex items-center justify-center gap-2">
<div className="w-1.5 h-1.5 bg-accent animate-pulse" />
New Operator
</span>
<h1 className="font-display text-3xl text-white mb-2 tracking-tight">
Initialize Access.
</h1>
<p className="text-body-sm sm:text-body text-foreground-muted">
Start tracking domains in under a minute
<p className="text-xs font-mono text-white/40">
Create your secure terminal account.
</p>
</div>
{/* Form */}
<form onSubmit={handleSubmit} className="space-y-3 sm:space-y-4">
<form onSubmit={handleSubmit} className="space-y-6">
{error && (
<div className="p-3 sm:p-4 bg-danger-muted border border-danger/20 rounded-2xl">
<p className="text-danger text-body-xs sm:text-body-sm">{error}</p>
<div className="p-3 bg-red-500/10 border border-red-500/20">
<p className="text-red-500 text-xs font-mono text-center uppercase tracking-wider">{error}</p>
</div>
)}
<div className="space-y-2.5 sm:space-y-3">
<div className="space-y-4">
<div className="group">
<label className="text-[10px] font-mono text-white/40 uppercase tracking-widest mb-2 block group-focus-within:text-white/70 transition-colors">Email Address</label>
<input
type="email"
value={email}
onChange={(e) => setEmail(e.target.value)}
placeholder="Email address"
placeholder="OPERATOR@POUNCE.IO"
required
autoComplete="email"
className="input-elegant text-body-sm sm:text-body"
className="w-full bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none"
/>
</div>
<div className="group relative">
<label className="text-[10px] font-mono text-white/40 uppercase tracking-widest mb-2 block group-focus-within:text-white/70 transition-colors">Create Passcode</label>
<div className="relative">
<input
type={showPassword ? 'text' : 'password'}
value={password}
onChange={(e) => setPassword(e.target.value)}
placeholder="Create password (min. 8 characters)"
placeholder="MIN 8 CHARS"
required
minLength={8}
autoComplete="new-password"
className="input-elegant text-body-sm sm:text-body pr-12"
className="w-full bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none pr-12"
/>
<button
type="button"
onClick={() => setShowPassword(!showPassword)}
className="absolute right-3 sm:right-4 top-1/2 -translate-y-1/2 text-foreground-muted hover:text-foreground transition-colors duration-200"
className="absolute right-4 top-1/2 -translate-y-1/2 text-white/30 hover:text-white transition-colors"
aria-label={showPassword ? 'Hide password' : 'Show password'}
>
{showPassword ? (
<EyeOff className="w-4 h-4 sm:w-5 sm:h-5" />
<EyeOff className="w-4 h-4" />
) : (
<Eye className="w-4 h-4 sm:w-5 sm:h-5" />
<Eye className="w-4 h-4" />
)}
</button>
</div>
</div>
</div>
<button
type="submit"
disabled={loading}
className="w-full py-3 sm:py-4 bg-foreground text-background text-ui-sm sm:text-ui font-medium rounded-xl
hover:bg-foreground/90 disabled:opacity-50 disabled:cursor-not-allowed
transition-all duration-300 flex items-center justify-center gap-2 sm:gap-2.5"
className="w-full py-4 bg-white text-black text-xs font-bold uppercase tracking-[0.2em] hover:bg-accent transition-all disabled:opacity-50 disabled:cursor-not-allowed flex items-center justify-center gap-3"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
{loading ? (
<Loader2 className="w-4 h-4 animate-spin" />
) : (
<>
Start Hunting
<ArrowRight className="w-3.5 sm:w-4 h-3.5 sm:h-4" />
<ArrowRight className="w-4 h-4" />
</>
)}
</button>
@ -226,14 +264,13 @@ function RegisterForm() {
{/* OAuth Buttons */}
{(oauthProviders.google_enabled || oauthProviders.github_enabled) && (
<div className="mt-6">
{/* Divider */}
<div className="relative mb-6">
<div className="mt-8">
<div className="relative mb-8">
<div className="absolute inset-0 flex items-center">
<div className="w-full border-t border-border" />
<div className="w-full border-t border-white/10" />
</div>
<div className="relative flex justify-center text-xs">
<span className="px-4 bg-background text-foreground-muted">or continue with</span>
<div className="relative flex justify-center">
<span className="px-4 bg-[#050505] text-[10px] font-mono text-white/30 uppercase tracking-widest">Alternative Access</span>
</div>
</div>
@ -241,23 +278,19 @@ function RegisterForm() {
{oauthProviders.google_enabled && (
<a
href={api.getGoogleLoginUrl(redirectTo)}
className="w-full py-3 sm:py-3.5 bg-[#24292e] text-white text-sm font-medium rounded-xl
hover:bg-[#2f363d] border border-[#24292e]
transition-all duration-300 flex items-center justify-center gap-3"
className="w-full py-3 bg-[#0A0A0A] border border-white/10 text-white text-xs font-mono uppercase tracking-wide hover:bg-white/5 hover:border-white/30 transition-all flex items-center justify-center gap-3"
>
<GoogleIcon className="w-5 h-5" />
Sign up with Google
<GoogleIcon className="w-4 h-4" />
Google
</a>
)}
{oauthProviders.github_enabled && (
<a
href={api.getGitHubLoginUrl(redirectTo)}
className="w-full py-3 sm:py-3.5 bg-[#24292e] text-white text-sm font-medium rounded-xl
hover:bg-[#2f363d] border border-[#24292e]
transition-all duration-300 flex items-center justify-center gap-3"
className="w-full py-3 bg-[#0A0A0A] border border-white/10 text-white text-xs font-mono uppercase tracking-wide hover:bg-white/5 hover:border-white/30 transition-all flex items-center justify-center gap-3"
>
<GitHubIcon className="w-5 h-5" />
Sign up with GitHub
<GitHubIcon className="w-4 h-4" />
GitHub
</a>
)}
</div>
@ -265,42 +298,47 @@ function RegisterForm() {
)}
{/* Login Link */}
<p className="mt-8 sm:mt-10 text-body-xs sm:text-body-sm text-foreground-muted">
Already have an account?{' '}
<Link href={loginLink} className="text-foreground hover:text-accent transition-colors duration-300">
Sign in
<div className="mt-8 pt-8 border-t border-white/10 text-center">
<p className="text-xs font-mono text-white/40">
Already authorized?{' '}
<Link href={loginLink} className="text-white hover:text-accent border-b border-white/20 hover:border-accent transition-all pb-0.5 ml-1">
Sign In
</Link>
</p>
</div>
</div>
</div>
</div>
{/* Right Panel - Benefits */}
<div className="hidden lg:flex flex-1 bg-background-secondary/50 items-center justify-center p-8 xl:p-12 border-l border-border-subtle">
<div className="max-w-sm animate-slide-up delay-200">
<div className="inline-flex items-center gap-2 sm:gap-2.5 px-3 sm:px-4 py-1.5 sm:py-2 bg-background-tertiary border border-border rounded-full mb-8 sm:mb-10">
<div className="w-1.5 h-1.5 rounded-full bg-accent" />
<span className="text-ui-sm sm:text-ui text-foreground-muted">Free Forever</span>
<div className="hidden lg:flex flex-1 bg-[#030303] items-center justify-center p-8 xl:p-12 border-l border-white/10 relative overflow-hidden">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.05]" />
<div className="max-w-md animate-slide-up delay-200 relative z-10">
<div className="inline-flex items-center gap-2 px-3 py-1.5 bg-accent/5 border border-accent/20 mb-8 rounded-none">
<div className="w-1.5 h-1.5 bg-accent animate-pulse" />
<span className="text-[10px] uppercase tracking-widest text-accent font-bold">Scout Access: Granted</span>
</div>
<h2 className="font-display text-[1.75rem] sm:text-[2.25rem] md:text-[2.75rem] leading-[1.15] tracking-[-0.025em] text-foreground mb-8 sm:mb-10">
Your hunting gear. Ready to go.
<h2 className="font-display text-4xl leading-tight text-white mb-10">
Your command center is waiting.
</h2>
<ul className="space-y-4 sm:space-y-5">
<ul className="space-y-6">
{benefits.map((item) => (
<li key={item} className="flex items-center gap-3 sm:gap-4">
<div className="w-8 sm:w-9 h-8 sm:h-9 rounded-lg bg-accent/10 flex items-center justify-center shrink-0">
<Check className="w-3.5 sm:w-4 h-3.5 sm:h-4 text-accent" strokeWidth={2.5} />
<li key={item.text} className="flex items-center gap-4 group">
<div className="w-10 h-10 border border-white/10 bg-white/5 flex items-center justify-center shrink-0 group-hover:border-accent/50 group-hover:text-accent transition-all">
<item.icon className="w-5 h-5 text-white/60 group-hover:text-accent transition-colors" strokeWidth={1.5} />
</div>
<span className="text-body-sm sm:text-body text-foreground-muted">{item}</span>
<span className="font-mono text-sm text-white/60 group-hover:text-white transition-colors">{item.text}</span>
</li>
))}
</ul>
<div className="divider my-8 sm:my-10" />
<div className="h-px w-full bg-white/10 my-10" />
<p className="text-body-xs sm:text-body-sm text-foreground-subtle">
No credit card required. Upgrade anytime.
<p className="font-mono text-xs text-white/30">
// ENCRYPTED CONNECTION<br/>
// NO CREDIT CARD REQUIRED
</p>
</div>
</div>
@ -311,8 +349,8 @@ function RegisterForm() {
export default function RegisterPage() {
return (
<Suspense fallback={
<div className="min-h-screen flex items-center justify-center">
<div className="w-5 h-5 border-2 border-accent border-t-transparent rounded-full animate-spin" />
<div className="min-h-screen flex items-center justify-center bg-[#020202]">
<div className="w-8 h-8 border-2 border-white/10 border-t-accent rounded-full animate-spin" />
</div>
}>
<RegisterForm />

View File

@ -61,86 +61,93 @@ function VerifyEmailContent() {
}
return (
<div className="min-h-screen bg-background relative overflow-hidden">
{/* Background Effects */}
<div className="fixed inset-0 pointer-events-none">
<div className="absolute top-[-20%] left-1/2 -translate-x-1/2 w-[1200px] h-[800px] bg-accent/[0.03] rounded-full blur-[120px]" />
<div className="absolute bottom-[-10%] right-[-10%] w-[600px] h-[600px] bg-accent/[0.02] rounded-full blur-[100px]" />
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Living Background Atmosphere */}
<div className="fixed inset-0 pointer-events-none overflow-hidden">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.04] mix-blend-overlay z-10" />
{/* Animated Orbs */}
<div className="absolute top-[20%] left-[50%] -translate-x-1/2 w-[60vw] h-[60vw] bg-accent/5 rounded-full blur-[150px] animate-pulse-slow mix-blend-screen" />
<div className="absolute bottom-[-20%] right-[-10%] w-[50vw] h-[50vw] bg-purple-500/5 rounded-full blur-[120px] animate-blob mix-blend-screen" />
{/* Grid Overlay */}
<div
className="absolute inset-0 opacity-[0.015]"
className="absolute inset-0 opacity-[0.03] z-0"
style={{
backgroundImage: `linear-gradient(rgba(255,255,255,.1) 1px, transparent 1px), linear-gradient(90deg, rgba(255,255,255,.1) 1px, transparent 1px)`,
backgroundSize: '64px 64px',
backgroundImage: `linear-gradient(rgba(255,255,255,0.3) 0.5px, transparent 0.5px), linear-gradient(90deg, rgba(255,255,255,0.3) 0.5px, transparent 0.5px)`,
backgroundSize: '40px 40px',
}}
/>
</div>
<Header />
<main className="relative flex-1 pt-32 sm:pt-40 pb-20 sm:pb-28 px-4 sm:px-6">
<div className="max-w-md mx-auto">
<div className="text-center mb-8">
<div className="inline-flex items-center gap-2 px-4 py-2 bg-accent/10 border border-accent/20 rounded-full mb-6">
<Mail className="w-4 h-4 text-accent" />
<span className="text-sm font-medium text-accent">Email Verification</span>
</div>
</div>
<main className="min-h-screen flex items-center justify-center px-4 sm:px-6 py-20 relative z-10">
<div className="w-full max-w-[450px] animate-fade-in">
<div className="bg-[#050505] border border-white/10 relative p-8 sm:p-10 shadow-2xl">
{/* Tech Corners */}
<div className="absolute -top-px -left-px w-4 h-4 border-t border-l border-white/40" />
<div className="absolute -top-px -right-px w-4 h-4 border-t border-r border-white/40" />
<div className="absolute -bottom-px -left-px w-4 h-4 border-b border-l border-white/40" />
<div className="absolute -bottom-px -right-px w-4 h-4 border-b border-r border-white/40" />
<div className="bg-background-secondary/50 border border-border rounded-2xl p-8 backdrop-blur-sm">
{status === 'loading' && (
<div className="text-center py-8">
<Loader2 className="w-12 h-12 text-accent animate-spin mx-auto mb-4" />
<p className="text-lg text-foreground">Verifying your email...</p>
<p className="text-sm text-foreground-muted mt-2">This will only take a moment</p>
<Loader2 className="w-12 h-12 text-accent animate-spin mx-auto mb-6" />
<h2 className="font-display text-2xl text-white mb-2">Verifying Credentials</h2>
<p className="text-xs font-mono text-white/40">Secure handshake in progress...</p>
</div>
)}
{status === 'success' && (
<div className="text-center py-8">
<div className="w-16 h-16 bg-accent/10 rounded-full flex items-center justify-center mx-auto mb-4">
<div className="w-16 h-16 bg-accent/10 border border-accent/20 flex items-center justify-center mx-auto mb-6 rounded-none">
<CheckCircle className="w-8 h-8 text-accent" />
</div>
<h2 className="text-2xl font-display text-foreground mb-2">Email Verified!</h2>
<p className="text-foreground-muted mb-6">{message}</p>
<p className="text-sm text-foreground-subtle">Redirecting to login...</p>
<h2 className="font-display text-2xl text-white mb-2">Access Granted</h2>
<p className="text-sm font-mono text-white/50 mb-6">{message}</p>
<div className="inline-flex items-center gap-2 px-4 py-2 bg-white/5 border border-white/10 text-xs font-mono text-white/60">
<Loader2 className="w-3 h-3 animate-spin" /> Redirecting to Terminal...
</div>
</div>
)}
{status === 'error' && (
<div className="text-center py-8">
<div className="w-16 h-16 bg-red-500/10 rounded-full flex items-center justify-center mx-auto mb-4">
<div className="w-16 h-16 bg-red-500/10 border border-red-500/20 flex items-center justify-center mx-auto mb-6 rounded-none">
<XCircle className="w-8 h-8 text-red-500" />
</div>
<h2 className="text-2xl font-display text-foreground mb-2">Verification Failed</h2>
<p className="text-foreground-muted mb-6">{message}</p>
<h2 className="font-display text-2xl text-white mb-2">Verification Failed</h2>
<p className="text-sm font-mono text-white/50 mb-8">{message}</p>
{!resendSuccess ? (
<form onSubmit={handleResend} className="mt-6">
<p className="text-sm text-foreground-muted mb-4">
Need a new verification link?
<p className="text-[10px] font-mono text-white/40 uppercase tracking-widest mb-4">
Request New Link
</p>
<div className="flex gap-2">
<input
type="email"
value={email}
onChange={(e) => setEmail(e.target.value)}
placeholder="Enter your email"
className="flex-1 px-4 py-3 bg-background border border-border rounded-xl text-foreground placeholder:text-foreground-subtle focus:outline-none focus:border-accent/50"
placeholder="EMAIL ADDRESS"
className="flex-1 bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none"
required
/>
<button
type="submit"
disabled={resending}
className="px-4 py-3 bg-accent text-background rounded-xl font-medium hover:bg-accent-hover transition-all disabled:opacity-50"
className="px-4 py-3 bg-white text-black text-xs font-bold uppercase tracking-wider hover:bg-accent transition-all disabled:opacity-50"
>
{resending ? <Loader2 className="w-5 h-5 animate-spin" /> : 'Resend'}
{resending ? <Loader2 className="w-4 h-4 animate-spin" /> : 'Send'}
</button>
</div>
</form>
) : (
<div className="mt-6 p-4 bg-accent/10 border border-accent/20 rounded-xl">
<p className="text-sm text-accent">
If an unverified account exists, a new verification link has been sent.
<div className="mt-6 p-4 bg-accent/5 border border-accent/20">
<p className="text-xs font-mono text-accent">
New verification link dispatched.
</p>
</div>
)}
@ -149,12 +156,12 @@ function VerifyEmailContent() {
{status === 'no-token' && (
<div className="text-center py-8">
<div className="w-16 h-16 bg-foreground/5 rounded-full flex items-center justify-center mx-auto mb-4">
<Mail className="w-8 h-8 text-foreground-muted" />
<div className="w-16 h-16 bg-white/5 border border-white/10 flex items-center justify-center mx-auto mb-6 rounded-none">
<Mail className="w-8 h-8 text-white/40" />
</div>
<h2 className="text-2xl font-display text-foreground mb-2">Verify Your Email</h2>
<p className="text-foreground-muted mb-6">
Check your inbox for a verification link, or request a new one below.
<h2 className="font-display text-2xl text-white mb-2">Verify Identity</h2>
<p className="text-sm font-mono text-white/50 mb-8">
Check your inbox for the verification link.
</p>
{!resendSuccess ? (
@ -164,36 +171,36 @@ function VerifyEmailContent() {
type="email"
value={email}
onChange={(e) => setEmail(e.target.value)}
placeholder="Enter your email"
className="flex-1 px-4 py-3 bg-background border border-border rounded-xl text-foreground placeholder:text-foreground-subtle focus:outline-none focus:border-accent/50"
placeholder="EMAIL ADDRESS"
className="flex-1 bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-sm placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none"
required
/>
<button
type="submit"
disabled={resending}
className="px-4 py-3 bg-accent text-background rounded-xl font-medium hover:bg-accent-hover transition-all disabled:opacity-50"
className="px-4 py-3 bg-white text-black text-xs font-bold uppercase tracking-wider hover:bg-accent transition-all disabled:opacity-50"
>
{resending ? <Loader2 className="w-5 h-5 animate-spin" /> : 'Send'}
{resending ? <Loader2 className="w-4 h-4 animate-spin" /> : 'Send'}
</button>
</div>
</form>
) : (
<div className="mt-6 p-4 bg-accent/10 border border-accent/20 rounded-xl">
<p className="text-sm text-accent">
If an unverified account exists, a verification link has been sent.
<div className="mt-6 p-4 bg-accent/5 border border-accent/20">
<p className="text-xs font-mono text-accent">
Link dispatched. Check inbox.
</p>
</div>
)}
</div>
)}
<div className="mt-8 pt-6 border-t border-border text-center">
<div className="mt-8 pt-8 border-t border-white/10 text-center">
<Link
href="/login"
className="inline-flex items-center gap-2 text-sm text-foreground-muted hover:text-accent transition-colors"
className="inline-flex items-center gap-2 text-xs font-mono text-white/40 hover:text-white transition-colors uppercase tracking-wider"
>
Back to Login
<ArrowRight className="w-4 h-4" />
<ArrowRight className="w-3 h-3 rotate-180" />
Return to Login
</Link>
</div>
</div>
@ -208,8 +215,8 @@ function VerifyEmailContent() {
export default function VerifyEmailPage() {
return (
<Suspense fallback={
<div className="min-h-screen flex items-center justify-center bg-background">
<Loader2 className="w-6 h-6 animate-spin text-accent" />
<div className="min-h-screen flex items-center justify-center bg-[#020202]">
<div className="w-8 h-8 border-2 border-white/10 border-t-accent rounded-full animate-spin" />
</div>
}>
<VerifyEmailContent />

View File

@ -1,11 +1,11 @@
'use client'
import { useState, useEffect } from 'react'
import Image from 'next/image'
import Link from 'next/link'
import { Header } from '@/components/Header'
import { Footer } from '@/components/Footer'
import { useStore } from '@/lib/store'
import { api } from '@/lib/api'
import {
Coins,
TrendingUp,
@ -13,432 +13,432 @@ import {
Target,
ArrowRight,
Check,
Sparkles,
DollarSign,
Globe,
Zap,
BarChart3,
ChevronRight,
Play,
Server,
Network,
Globe,
Lock,
ArrowUpRight,
Cpu,
Share2,
Wallet,
PieChart,
RefreshCw,
Play,
Calculator,
Info
} from 'lucide-react'
import clsx from 'clsx'
// Intent categories for the demo
const INTENT_EXAMPLES = [
{ domain: 'zahnarzt-zuerich.ch', intent: 'Medical / Dental', potential: 'High', revenue: '120-350' },
{ domain: 'hypothek-vergleich.ch', intent: 'Finance / Mortgage', potential: 'High', revenue: '200-500' },
{ domain: 'rechtsanwalt-bern.ch', intent: 'Legal', potential: 'High', revenue: '150-400' },
{ domain: 'wohnung-mieten.ch', intent: 'Real Estate', potential: 'Medium', revenue: '50-150' },
{ domain: 'flug-buchen.ch', intent: 'Travel', potential: 'Medium', revenue: '30-100' },
]
// Yield Simulator Component - SIMPLIFIED & COMPACT
function YieldSimulator() {
const [traffic, setTraffic] = useState(2500)
const [vertical, setVertical] = useState('finance')
export default function YieldPublicPage() {
const { isAuthenticated, checkAuth, isLoading } = useStore()
const [analyzeDomain, setAnalyzeDomain] = useState('')
const [analyzing, setAnalyzing] = useState(false)
const [analysis, setAnalysis] = useState<any>(null)
const [selectedExample, setSelectedExample] = useState(0)
// Vertical data (average CPA and Conversion)
const verticals: Record<string, { cpa: number, conv: number, label: string }> = {
finance: { cpa: 120, conv: 3.5, label: 'Finance & Loans' },
insurance: { cpa: 80, conv: 2.8, label: 'Insurance' },
legal: { cpa: 150, conv: 1.5, label: 'Legal Services' },
medical: { cpa: 60, conv: 4.0, label: 'Medical / Health' },
tech: { cpa: 45, conv: 2.2, label: 'Software / B2B' }
}
const currentVertical = verticals[vertical]
const monthlyRevenue = Math.floor(traffic * (currentVertical.conv / 100) * currentVertical.cpa)
const annualYield = monthlyRevenue * 12
return (
<div className="relative group max-w-md mx-auto lg:ml-auto lg:mr-0">
{/* Ambient Glow - White/Green instead of Amber */}
<div className="absolute -inset-0.5 bg-gradient-to-br from-accent/20 via-white/5 to-accent/20 blur-2xl opacity-30 group-hover:opacity-50 transition-opacity duration-1000" />
{/* Main Container - Compact Tech Card */}
<div className="relative bg-[#050505]/90 backdrop-blur-xl border border-white/10 shadow-2xl overflow-hidden">
{/* Decorative Tech Elements */}
<div className="absolute top-0 right-0 p-3">
<div className="flex gap-1.5">
<div className="w-1 h-1 bg-white/20 rounded-full" />
<div className="w-1 h-1 bg-accent animate-pulse rounded-full" />
</div>
</div>
<div className="p-6 sm:p-8">
<div className="mb-6">
<h3 className="font-display text-2xl text-white mb-1">Yield Projection</h3>
<p className="font-mono text-[10px] text-white/40 uppercase tracking-widest">Est. Passive Income</p>
</div>
{/* Input 1: Traffic Slider */}
<div className="mb-6">
<div className="flex justify-between text-xs font-mono mb-3">
<span className="text-white/60">Monthly Traffic</span>
<span className="text-white">{traffic.toLocaleString()} Visits</span>
</div>
<div className="relative h-4 flex items-center">
<input
type="range"
min="100"
max="10000"
step="100"
value={traffic}
onChange={(e) => setTraffic(parseInt(e.target.value))}
className="absolute w-full h-1 bg-white/10 rounded-full appearance-none cursor-pointer z-20
[&::-webkit-slider-thumb]:appearance-none [&::-webkit-slider-thumb]:w-3 [&::-webkit-slider-thumb]:h-3
[&::-webkit-slider-thumb]:bg-white [&::-webkit-slider-thumb]:rounded-full
[&::-webkit-slider-thumb]:shadow-[0_0_10px_rgba(255,255,255,0.8)]"
/>
<div className="absolute top-1/2 left-0 right-0 h-px bg-white/10 z-10" />
<div
className="absolute top-1/2 left-0 h-px bg-white/50 z-10"
style={{ width: `${((traffic - 100) / (10000 - 100)) * 100}%` }}
/>
</div>
</div>
{/* Input 2: Vertical Selector (Grid) */}
<div className="mb-8">
<label className="block text-xs font-mono text-white/60 mb-3">Domain Vertical</label>
<div className="grid grid-cols-2 gap-2">
{Object.entries(verticals).map(([key, data]) => (
<button
key={key}
onClick={() => setVertical(key)}
className={clsx(
"px-3 py-2 text-[10px] font-bold uppercase tracking-wide text-left transition-all border",
vertical === key
? "bg-white text-black border-white"
: "bg-white/5 text-white/40 border-transparent hover:text-white hover:bg-white/10"
)}
>
{data.label}
</button>
))}
</div>
</div>
{/* Result Area */}
<div className="bg-white/[0.03] border border-white/5 p-5 relative overflow-hidden">
<div className="relative z-10">
<div className="flex justify-between items-end mb-2">
<span className="text-[10px] font-mono uppercase tracking-widest text-white/40">Annual Revenue</span>
<div className="text-right">
<span className="block font-display text-3xl text-white tracking-tight leading-none">${annualYield.toLocaleString('en-US')}</span>
</div>
</div>
<div className="flex justify-between items-center pt-3 border-t border-white/5 text-[10px] font-mono text-white/30">
<span>${monthlyRevenue.toLocaleString('en-US')} / mo</span>
<span>CPA: ${currentVertical.cpa}</span>
</div>
</div>
</div>
</div>
{/* Footer Bar */}
<div className="bg-[#080808] px-6 py-3 border-t border-white/5 flex justify-between items-center text-[9px] font-mono text-white/20 uppercase tracking-wider">
<span>Live Calculation</span>
<span>Fee: 0%</span>
</div>
</div>
</div>
)
}
export default function YieldPage() {
const { isAuthenticated, checkAuth } = useStore()
useEffect(() => {
checkAuth()
}, [checkAuth])
// Rotate through examples
useEffect(() => {
const interval = setInterval(() => {
setSelectedExample(prev => (prev + 1) % INTENT_EXAMPLES.length)
}, 4000)
return () => clearInterval(interval)
}, [])
const handleAnalyze = async () => {
if (!analyzeDomain.trim()) return
setAnalyzing(true)
try {
const result = await api.analyzeYieldDomain(analyzeDomain.trim())
setAnalysis(result)
} catch (err) {
console.error('Analysis failed:', err)
} finally {
setAnalyzing(false)
}
}
const currentExample = INTENT_EXAMPLES[selectedExample]
return (
<div className="min-h-screen bg-background flex flex-col">
<div className="min-h-screen bg-[#020202] text-white relative overflow-x-hidden selection:bg-accent/30 selection:text-white">
{/* Cinematic Background */}
<div className="fixed inset-0 pointer-events-none z-0">
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay" />
<div
className="absolute inset-0 opacity-[0.03]"
style={{
backgroundImage: `linear-gradient(rgba(255,255,255,0.3) 0.5px, transparent 0.5px), linear-gradient(90deg, rgba(255,255,255,0.3) 0.5px, transparent 0.5px)`,
backgroundSize: '160px 160px',
}}
/>
{/* Gold/Amber Glow for Yield context instead of Green */}
<div className="absolute top-[20%] right-[-10%] w-[800px] h-[800px] bg-amber-500/[0.02] rounded-full blur-[150px]" />
</div>
<Header />
{/* Hero Section */}
<section className="relative pt-32 sm:pt-40 pb-20 sm:pb-28 px-4 sm:px-6 overflow-hidden">
{/* Background Effects */}
<div className="absolute inset-0 pointer-events-none overflow-hidden">
<div className="absolute top-20 left-1/4 w-[600px] h-[600px] bg-purple-500/10 rounded-full blur-[120px]" />
<div className="absolute bottom-20 right-1/4 w-[500px] h-[500px] bg-emerald-500/10 rounded-full blur-[100px]" />
{/* HERO SECTION */}
<section className="relative min-h-[90vh] flex flex-col justify-center pt-32 pb-24 px-4 sm:px-6 z-10">
<div className="max-w-[1400px] mx-auto w-full">
<div className="grid lg:grid-cols-12 gap-16 lg:gap-24 items-center">
{/* Left: Typography */}
<div className="lg:col-span-6 relative z-20 text-center lg:text-left">
<div className="inline-flex items-center gap-4 mb-10 animate-fade-in opacity-0" style={{ animationDelay: '0.1s', animationFillMode: 'forwards' }}>
<div className="h-px w-12 bg-white/10" />
<span className="text-[10px] font-mono uppercase tracking-[0.3em] text-accent">Pounce Protocol // Yield</span>
</div>
<div className="relative max-w-7xl mx-auto">
<div className="text-center max-w-3xl mx-auto">
{/* Badge */}
<div className="inline-flex items-center gap-2 px-4 py-2 rounded-full bg-purple-500/10 border border-purple-500/20 text-purple-400 text-sm mb-8">
<Sparkles className="w-4 h-4" />
<span>New Feature</span>
</div>
<h1 className="font-display text-[2.5rem] sm:text-[3.5rem] md:text-[4.5rem] lg:text-[5rem] leading-[0.95] tracking-[-0.03em] text-foreground">
Turn Parked Domains Into
<span className="block text-transparent bg-clip-text bg-gradient-to-r from-emerald-400 via-purple-400 to-emerald-400">
Passive Income
<h1 className="font-display text-[3.5rem] sm:text-[5rem] md:text-[6rem] lg:text-[7rem] leading-[0.9] tracking-[-0.04em] text-white mb-8">
<span className="block animate-slide-up opacity-0" style={{ animationDelay: '0.2s', animationFillMode: 'forwards' }}>
Assets that
</span>
<span className="block text-white animate-slide-up opacity-0" style={{ animationDelay: '0.4s', animationFillMode: 'forwards' }}>
work for you.
</span>
</h1>
<p className="mt-6 text-lg sm:text-xl text-foreground-muted max-w-2xl mx-auto">
Pounce Yield detects the intent behind your domain and routes visitors
to relevant affiliate partners. <span className="text-foreground">You earn 70% of every lead.</span>
<div className="animate-slide-up opacity-0" style={{ animationDelay: '0.8s', animationFillMode: 'forwards' }}>
<p className="text-lg lg:text-xl text-white/60 max-w-xl font-light leading-relaxed mb-12 lg:mx-0 mx-auto">
Turn dormant domains into active cashflow. Our Intent Routing engine directs traffic to high-paying partners automatically.
</p>
{/* CTA Buttons */}
<div className="mt-10 flex flex-col sm:flex-row items-center justify-center gap-4">
<div className="flex flex-col sm:flex-row items-center gap-6 lg:justify-start justify-center">
<Link
href={isAuthenticated ? '/terminal/yield' : '/register?redirect=/terminal/yield'}
className="w-full sm:w-auto inline-flex items-center justify-center gap-2 px-8 py-4
bg-gradient-to-r from-purple-500 to-emerald-500
text-white text-lg font-semibold rounded-xl
hover:from-purple-400 hover:to-emerald-400 transition-all
shadow-lg shadow-purple-500/25"
href={isAuthenticated ? '/terminal/yield' : '/register'}
className="px-8 py-4 bg-accent text-black text-xs font-bold uppercase tracking-[0.2em] hover:bg-white transition-all shadow-[0_0_20px_rgba(16,185,129,0.2)]"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
<Coins className="w-5 h-5" />
Start Earning
<ArrowRight className="w-5 h-5" />
Activate Protocol
</Link>
<button
onClick={() => document.getElementById('demo')?.scrollIntoView({ behavior: 'smooth' })}
className="w-full sm:w-auto inline-flex items-center justify-center gap-2 px-8 py-4
bg-background-secondary border border-border text-foreground
text-lg font-semibold rounded-xl hover:border-accent transition-all"
onClick={() => document.getElementById('how-it-works')?.scrollIntoView({ behavior: 'smooth' })}
className="text-xs font-bold uppercase tracking-[0.2em] text-white/40 hover:text-white flex items-center gap-2"
>
<Play className="w-5 h-5" />
See Demo
<Play className="w-3 h-3" /> How It Works
</button>
</div>
</div>
</div>
{/* Trust Indicators */}
<div className="mt-12 flex flex-wrap items-center justify-center gap-6 text-sm text-foreground-muted">
<div className="flex items-center gap-2">
<Shield className="w-4 h-4 text-emerald-500" />
<span>DNS Verified</span>
</div>
<div className="flex items-center gap-2">
<DollarSign className="w-4 h-4 text-emerald-500" />
<span>70% Revenue Share</span>
</div>
<div className="flex items-center gap-2">
<Globe className="w-4 h-4 text-emerald-500" />
<span>Swiss Partners</span>
</div>
{/* Right: Simulator */}
<div className="lg:col-span-6 relative animate-scale-in opacity-0 mt-8 lg:mt-0" style={{ animationDelay: '1s', animationFillMode: 'forwards' }}>
<YieldSimulator />
</div>
</div>
</div>
</section>
{/* Live Demo Section */}
<section id="demo" className="relative py-20 sm:py-28 px-4 sm:px-6 bg-background-secondary/50">
<div className="max-w-7xl mx-auto">
<div className="text-center mb-12">
<span className="text-sm font-semibold text-purple-400 uppercase tracking-wider">Live Demo</span>
<h2 className="mt-4 font-display text-3xl sm:text-4xl md:text-5xl tracking-[-0.03em] text-foreground">
Analyze Your Domain's Yield Potential
</h2>
</div>
{/* Domain Analyzer */}
<div className="max-w-2xl mx-auto">
<div className="bg-background border border-border rounded-2xl p-6 sm:p-8 shadow-xl">
<div className="flex flex-col sm:flex-row gap-4">
<input
type="text"
value={analyzeDomain}
onChange={(e) => setAnalyzeDomain(e.target.value)}
placeholder="Enter your domain (e.g. zahnarzt-zuerich.ch)"
className="flex-1 px-4 py-3 bg-background-secondary border border-border rounded-xl
text-foreground placeholder:text-foreground-subtle focus:outline-none
focus:border-accent transition-colors"
onKeyDown={(e) => e.key === 'Enter' && handleAnalyze()}
/>
<button
onClick={handleAnalyze}
disabled={analyzing || !analyzeDomain.trim()}
className="px-6 py-3 bg-gradient-to-r from-purple-500 to-emerald-500
text-white font-semibold rounded-xl
hover:from-purple-400 hover:to-emerald-400 transition-all
disabled:opacity-50 disabled:cursor-not-allowed
flex items-center justify-center gap-2"
>
{analyzing ? (
<>
<div className="w-4 h-4 border-2 border-white border-t-transparent rounded-full animate-spin" />
Analyzing...
</>
) : (
<>
<Zap className="w-4 h-4" />
Analyze
</>
)}
</button>
</div>
{/* Analysis Result */}
{analysis && (
<div className="mt-8 p-6 bg-background-secondary rounded-xl border border-border">
<div className="flex items-start justify-between mb-4">
{/* CORE LOGIC */}
<section id="how-it-works" className="relative py-40 px-4 sm:px-6 bg-[#020202]">
<div className="max-w-[1400px] mx-auto">
{/* Section Header - Tech Style */}
<div className="flex flex-col lg:flex-row justify-between items-end mb-24 border-b border-white/[0.08] pb-12">
<div>
<h3 className="text-lg font-semibold text-foreground">{analysis.domain}</h3>
<p className="text-sm text-foreground-muted capitalize">
{analysis.intent.category.replace('_', ' ')}
{analysis.intent.subcategory && ` / ${analysis.intent.subcategory.replace('_', ' ')}`}
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">The Mechanism</span>
<h2 className="font-display text-4xl sm:text-5xl lg:text-6xl text-white leading-none">
Intent Routing
</h2>
</div>
<p className="text-white/50 max-w-md text-sm font-mono mt-8 lg:mt-0 leading-relaxed text-right">
// REPLACING_PARKING_PAGES<br />
// ELIMINATING_MIDDLEMEN<br />
// MAXIMIZING_YIELD
</p>
</div>
<span className={`px-3 py-1 rounded-full text-sm font-medium ${
analysis.monetization_potential === 'high'
? 'bg-emerald-500/20 text-emerald-400 border border-emerald-500/30'
: analysis.monetization_potential === 'medium'
? 'bg-amber-500/20 text-amber-400 border border-amber-500/30'
: 'bg-zinc-500/20 text-zinc-400 border border-zinc-500/30'
}`}>
{analysis.monetization_potential.toUpperCase()} Potential
</span>
<div className="grid grid-cols-1 lg:grid-cols-3 gap-px bg-white/[0.08] border border-white/[0.08]">
{/* Phase 1 */}
<div className="group relative bg-[#030303] p-10 lg:p-14 hover:bg-[#050505] transition-colors duration-500">
<div className="absolute top-0 right-0 p-6 opacity-0 group-hover:opacity-100 transition-opacity duration-500">
<div className="text-[10px] font-mono text-accent">PHASE_01</div>
</div>
<div className="grid sm:grid-cols-2 gap-4">
<div className="p-4 bg-gradient-to-br from-emerald-500/10 to-transparent rounded-xl border border-emerald-500/20">
<p className="text-sm text-foreground-muted mb-1">Estimated Monthly Revenue</p>
<p className="text-2xl font-bold text-emerald-400">
{analysis.value.currency} {analysis.value.estimated_monthly_min} - {analysis.value.estimated_monthly_max}
</p>
</div>
<div className="p-4 bg-background rounded-xl border border-border">
<p className="text-sm text-foreground-muted mb-1">Intent Confidence</p>
<div className="flex items-center gap-2">
<div className="flex-1 h-2 bg-background-secondary rounded-full overflow-hidden">
<div
className="h-full bg-gradient-to-r from-purple-500 to-emerald-500 rounded-full"
style={{ width: `${analysis.intent.confidence * 100}%` }}
/>
</div>
<span className="text-sm font-medium text-foreground">
{Math.round(analysis.intent.confidence * 100)}%
</span>
</div>
</div>
</div>
{/* Keywords */}
{analysis.intent.keywords_matched.length > 0 && (
<div className="mt-4">
<p className="text-sm text-foreground-muted mb-2">Detected Keywords</p>
<div className="flex flex-wrap gap-2">
{analysis.intent.keywords_matched.slice(0, 5).map((kw: string, i: number) => (
<span key={i} className="px-2 py-1 bg-background rounded text-xs text-foreground-subtle">
{kw.split('~')[0]}
</span>
))}
</div>
</div>
)}
<Link
href={isAuthenticated ? '/terminal/yield' : `/register?redirect=/terminal/yield&domain=${analysis.domain}`}
className="mt-6 w-full inline-flex items-center justify-center gap-2 px-6 py-3
bg-gradient-to-r from-purple-500 to-emerald-500
text-white font-semibold rounded-xl
hover:from-purple-400 hover:to-emerald-400 transition-all"
>
Activate This Domain
<ArrowRight className="w-4 h-4" />
</Link>
</div>
)}
{/* Example Carousel */}
{!analysis && (
<div className="mt-8">
<p className="text-sm text-foreground-muted mb-4">Examples:</p>
<div className="space-y-2">
{INTENT_EXAMPLES.map((ex, i) => (
<button
key={ex.domain}
onClick={() => {
setAnalyzeDomain(ex.domain)
setSelectedExample(i)
}}
className={`w-full p-4 rounded-xl border text-left transition-all ${
i === selectedExample
? 'bg-purple-500/10 border-purple-500/30'
: 'bg-background-secondary border-border hover:border-accent/30'
}`}
>
<div className="flex items-center justify-between">
<div className="h-full flex flex-col justify-between">
<div>
<p className="font-medium text-foreground">{ex.domain}</p>
<p className="text-sm text-foreground-muted">{ex.intent}</p>
<div className="w-16 h-16 border border-white/10 bg-white/5 flex items-center justify-center mb-10 text-white group-hover:text-accent group-hover:border-accent/50 transition-all">
<Globe className="w-8 h-8" />
</div>
<div className="text-right">
<p className={`text-sm font-medium ${
ex.potential === 'High' ? 'text-emerald-400' : 'text-amber-400'
}`}>
{ex.potential}
<h3 className="text-3xl text-white font-display mb-6">Capture</h3>
<p className="text-white/50 leading-relaxed text-lg font-light mb-12">
User types a generic domain (e.g. `kredit.ch`). Our DNS intercepts the request instantly. No slow redirects. No parking page ads.
</p>
<p className="text-xs text-foreground-muted">CHF {ex.revenue}/mo</p>
</div>
<div className="pt-8 border-t border-white/[0.05]">
<div className="font-mono text-xs text-white/30 uppercase tracking-widest mb-2">Technical Execution</div>
<div className="text-white font-mono text-sm">DNS A-Record -&gt; Pounce Edge Node</div>
</div>
</div>
</button>
))}
</div>
{/* Phase 2 */}
<div className="group relative bg-[#030303] p-10 lg:p-14 hover:bg-[#050505] transition-colors duration-500">
<div className="absolute top-0 right-0 p-6 opacity-0 group-hover:opacity-100 transition-opacity duration-500">
<div className="text-[10px] font-mono text-accent">PHASE_02</div>
</div>
<div className="h-full flex flex-col justify-between">
<div>
<div className="w-16 h-16 border border-white/10 bg-white/5 flex items-center justify-center mb-10 text-white group-hover:text-accent group-hover:border-accent/50 transition-all">
<Cpu className="w-8 h-8" />
</div>
<h3 className="text-3xl text-white font-display mb-6">Analyze</h3>
<p className="text-white/50 leading-relaxed text-lg font-light mb-12">
Our semantic engine analyzes the SLD (`kredit`) and TLD (`.ch`) to determine user intent: "Financial Service / Loan / Switzerland".
</p>
</div>
<div className="pt-8 border-t border-white/[0.05]">
<div className="font-mono text-xs text-white/30 uppercase tracking-widest mb-2">Processing Time</div>
<div className="text-white font-mono text-sm">&lt; 10ms Latency</div>
</div>
</div>
)}
</div>
{/* Phase 3 */}
<div className="group relative bg-[#030303] p-10 lg:p-14 hover:bg-[#050505] transition-colors duration-500">
<div className="absolute top-0 right-0 p-6 opacity-0 group-hover:opacity-100 transition-opacity duration-500">
<div className="text-[10px] font-mono text-accent">PHASE_03</div>
</div>
<div className="h-full flex flex-col justify-between">
<div>
<div className="w-16 h-16 border border-white/10 bg-white/5 flex items-center justify-center mb-10 text-white group-hover:text-accent group-hover:border-accent/50 transition-all">
<Wallet className="w-8 h-8" />
</div>
<h3 className="text-3xl text-white font-display mb-6">Monetize</h3>
<p className="text-white/50 leading-relaxed text-lg font-light mb-12">
Traffic is routed to the highest-bidding partner for that vertical (e.g. Comparis). You earn a commission (CPA) on conversion.
</p>
</div>
<div className="pt-8 border-t border-white/[0.05]">
<div className="font-mono text-xs text-white/30 uppercase tracking-widest mb-2">Outcome</div>
<div className="text-white font-mono text-sm">70% Revenue Share Payout</div>
</div>
</div>
</div>
</div>
</div>
</section>
{/* How It Works */}
<section className="relative py-20 sm:py-28 px-4 sm:px-6">
<div className="max-w-7xl mx-auto">
<div className="text-center mb-16">
<span className="text-sm font-semibold text-accent uppercase tracking-wider">How It Works</span>
<h2 className="mt-4 font-display text-3xl sm:text-4xl md:text-5xl tracking-[-0.03em] text-foreground">
Three Steps to Passive Income
</h2>
</div>
<div className="grid md:grid-cols-3 gap-8">
{/* Step 1 */}
<div className="relative p-8 bg-background-secondary border border-border rounded-2xl">
<div className="absolute -top-4 left-8 w-8 h-8 bg-purple-500 rounded-full flex items-center justify-center text-white font-bold">
1
</div>
<div className="w-14 h-14 bg-purple-500/10 rounded-xl flex items-center justify-center mb-6">
<Globe className="w-7 h-7 text-purple-400" />
</div>
<h3 className="text-xl font-semibold text-foreground mb-3">Add Your Domain</h3>
<p className="text-foreground-muted">
Enter any domain you own. Our AI analyzes the name and detects the
user intent (dental, finance, travel, etc.)
{/* ECOSYSTEM - Vertical & Partners */}
<section className="relative py-32 px-4 sm:px-6 bg-[#050505] border-y border-white/[0.05]">
<div className="max-w-[1400px] mx-auto grid lg:grid-cols-2 gap-20 items-center">
<div>
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">The Ecosystem</span>
<h2 className="font-display text-4xl sm:text-5xl text-white mb-8">Premium Verticals.</h2>
<p className="text-white/50 text-lg leading-relaxed mb-10">
We focus on high-ticket verticals where a single lead can be worth $50-$200. No penny-clicks. No spam.
</p>
</div>
{/* Step 2 */}
<div className="relative p-8 bg-background-secondary border border-border rounded-2xl md:-translate-y-4">
<div className="absolute -top-4 left-8 w-8 h-8 bg-emerald-500 rounded-full flex items-center justify-center text-white font-bold">
2
</div>
<div className="w-14 h-14 bg-emerald-500/10 rounded-xl flex items-center justify-center mb-6">
<Server className="w-7 h-7 text-emerald-400" />
</div>
<h3 className="text-xl font-semibold text-foreground mb-3">Point Your DNS</h3>
<p className="text-foreground-muted">
Update your nameservers or add a CNAME record. We verify ownership
and activate the domain for yield.
</p>
</div>
{/* Step 3 */}
<div className="relative p-8 bg-background-secondary border border-border rounded-2xl">
<div className="absolute -top-4 left-8 w-8 h-8 bg-purple-500 rounded-full flex items-center justify-center text-white font-bold">
3
</div>
<div className="w-14 h-14 bg-purple-500/10 rounded-xl flex items-center justify-center mb-6">
<DollarSign className="w-7 h-7 text-purple-400" />
</div>
<h3 className="text-xl font-semibold text-foreground mb-3">Earn Automatically</h3>
<p className="text-foreground-muted">
Visitors are routed to relevant partners. You earn 70% of every click,
lead, or sale. Paid out monthly.
</p>
</div>
</div>
</div>
</section>
{/* Features Grid */}
<section className="relative py-20 sm:py-28 px-4 sm:px-6 bg-background-secondary/50">
<div className="max-w-7xl mx-auto">
<div className="text-center mb-16">
<span className="text-sm font-semibold text-accent uppercase tracking-wider">Features</span>
<h2 className="mt-4 font-display text-3xl sm:text-4xl md:text-5xl tracking-[-0.03em] text-foreground">
Why Pounce Yield?
</h2>
</div>
<div className="grid sm:grid-cols-2 lg:grid-cols-3 gap-6">
<div className="space-y-6">
{[
{
icon: Target,
title: 'AI Intent Detection',
desc: 'Our engine analyzes domain names to detect user intent across 20+ categories.',
},
{
icon: Shield,
title: 'Swiss Partners',
desc: 'Comparis, Homegate, Jobs.ch and more. Premium partners, premium payouts.',
},
{
icon: BarChart3,
title: 'Real-Time Analytics',
desc: 'Track clicks, conversions, and revenue in your dashboard. Full transparency.',
},
{
icon: DollarSign,
title: '70% Revenue Share',
desc: 'The highest revenue share in the industry. You keep the lion\'s share.',
},
{
icon: Zap,
title: 'Instant Activation',
desc: 'DNS verified in minutes. Start earning the same day.',
},
{
icon: TrendingUp,
title: 'Monthly Payouts',
desc: 'Reliable monthly payments via Stripe or bank transfer.',
},
].map((feature, i) => (
<div key={i} className="p-6 bg-background border border-border rounded-xl hover:border-accent/30 transition-all">
<feature.icon className="w-8 h-8 text-accent mb-4" />
<h3 className="text-lg font-semibold text-foreground mb-2">{feature.title}</h3>
<p className="text-foreground-muted text-sm">{feature.desc}</p>
{ name: 'Finance & Insurance', cpa: '$80 - $250', examples: 'Loans, Mortgages, Health Insurance' },
{ name: 'Legal Services', cpa: '$100 - $400', examples: 'Lawyers, Divorce, notary' },
{ name: 'Medical & Health', cpa: '$50 - $150', examples: 'Dentists, Cosmetic Surgery, Clinics' },
{ name: 'B2B Services', cpa: '$40 - $120', examples: 'Marketing, SaaS, Hosting' }
].map((vertical, i) => (
<div key={i} className="flex items-start gap-6 p-4 border border-white/5 hover:border-white/10 hover:bg-white/[0.02] transition-colors">
<div className="w-1.5 h-1.5 bg-accent mt-2.5 shrink-0" />
<div className="flex-1">
<div className="flex justify-between items-center mb-1">
<h4 className="text-white font-bold">{vertical.name}</h4>
<span className="text-accent font-mono text-sm">{vertical.cpa} CPA</span>
</div>
<p className="text-white/40 text-sm">{vertical.examples}</p>
</div>
</div>
))}
</div>
</div>
<div className="relative">
<div className="absolute inset-0 bg-gradient-to-tr from-accent/10 to-transparent blur-3xl opacity-20" />
<div className="bg-[#020202] border border-white/10 p-10 relative">
<div className="absolute top-0 left-0 p-4 border-r border-b border-white/10 bg-[#050505]">
<span className="text-[10px] font-mono text-white/30 uppercase tracking-widest">Partner Network</span>
</div>
<div className="mt-8 grid grid-cols-2 gap-4">
{[
{ name: 'COMPARIS', initial: 'C' },
{ name: 'AXA', initial: 'A' },
{ name: 'HOMEGATE', initial: 'H' },
{ name: 'SWISS LIFE', initial: 'S' },
{ name: 'JOBS.CH', initial: 'J' },
{ name: 'SANOTAS', initial: 'S' }
].map((partner, i) => (
<div key={i} className="h-24 bg-white/[0.02] border border-white/5 flex flex-col items-center justify-center hover:bg-white/[0.05] transition-all group cursor-default">
<span className="font-display text-2xl text-white/20 group-hover:text-white transition-colors">{partner.name}</span>
</div>
))}
</div>
<div className="mt-8 pt-8 border-t border-white/10 text-center">
<p className="text-white/40 text-sm font-mono mb-4">
Direct integrations with top-tier Swiss & EU brands.
</p>
<Link
href="/contact"
className="inline-flex items-center gap-2 text-xs font-bold uppercase tracking-widest text-white hover:text-accent transition-colors"
>
Become a Partner <ArrowRight className="w-3 h-3" />
</Link>
</div>
</div>
</div>
</div>
</section>
{/* FEATURES GRID (BENTO STYLE) */}
<section className="relative py-40 px-4 sm:px-6 bg-[#020202]">
<div className="max-w-[1400px] mx-auto">
<div className="mb-20">
<span className="text-accent font-mono text-xs uppercase tracking-[0.2em] mb-4 block">System Capabilities</span>
<h2 className="font-display text-4xl sm:text-5xl text-white">Passive by Design.</h2>
</div>
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-px bg-white/[0.1] border border-white/[0.1]">
{[
{ icon: PieChart, title: 'Revenue Share', desc: 'Industry-leading 70/30 split. We only make money when you do.' },
{ icon: Target, title: '20+ Verticals', desc: 'Finance, Insurance, Travel, Health, B2B Services, and more.' },
{ icon: Shield, title: 'Swiss Partners', desc: 'Direct API integrations with premium Swiss & EU brands.' },
{ icon: BarChart3, title: 'Live Analytics', desc: 'Real-time dashboard showing every click, lead, and conversion.' },
{ icon: RefreshCw, title: 'Auto-Optimization', desc: 'AI automatically routes to the highest-paying partner for each visitor.' },
{ icon: Zap, title: 'Instant DNS', desc: 'Zero downtime. Verify ownership and start earning in < 5 minutes.' }
].map((feat, i) => (
<div key={i} className="bg-[#030303] p-10 hover:bg-[#080808] transition-colors group">
<feat.icon className="w-8 h-8 text-white/20 group-hover:text-accent transition-colors mb-6" />
<h3 className="text-xl font-display text-white mb-3">{feat.title}</h3>
<p className="text-white/40 font-mono text-sm leading-relaxed">{feat.desc}</p>
</div>
))}
</div>
</div>
</section>
{/* CTA Section */}
<section className="relative py-20 sm:py-28 px-4 sm:px-6">
<div className="max-w-4xl mx-auto text-center">
<h2 className="font-display text-3xl sm:text-4xl md:text-5xl tracking-[-0.03em] text-foreground">
Ready to Monetize Your Domains?
{/* CTA */}
<section className="relative py-32 px-4 sm:px-6 border-t border-white/[0.05]">
<div className="max-w-4xl mx-auto text-center relative z-10">
<h2 className="font-display text-5xl sm:text-6xl text-white mb-10">
Your portfolio is <br />
<span className="text-white/30">sleeping on gold.</span>
</h2>
<p className="mt-6 text-lg text-foreground-muted max-w-2xl mx-auto">
Join domain investors who are turning their parked domains into passive income streams.
</p>
<div className="mt-10">
{!isAuthenticated ? (
<div className="flex flex-col items-center gap-6">
<Link
href={isAuthenticated ? '/terminal/yield' : '/register?redirect=/terminal/yield'}
className="inline-flex items-center justify-center gap-2 px-10 py-5
bg-gradient-to-r from-purple-500 to-emerald-500
text-white text-xl font-semibold rounded-xl
hover:from-purple-400 hover:to-emerald-400 transition-all
shadow-xl shadow-purple-500/25"
href="/register"
className="px-10 py-5 bg-accent text-black text-sm font-bold uppercase tracking-[0.2em] hover:bg-white transition-all shadow-[0_0_30px_rgba(16,185,129,0.3)]"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
<Coins className="w-6 h-6" />
Get Started Free
<ArrowRight className="w-6 h-6" />
Start Yield Farming
</Link>
<p className="text-white/30 font-mono text-xs uppercase tracking-widest">Free for the first 30 days</p>
</div>
) : (
<Link
href="/terminal/yield"
className="px-10 py-5 bg-white text-black text-sm font-bold uppercase tracking-[0.2em] hover:bg-accent transition-all"
style={{ clipPath: 'polygon(10px 0, 100% 0, 100% 100%, 0 100%, 0 10px)' }}
>
Go to Dashboard
</Link>
)}
</div>
</section>
@ -446,4 +446,3 @@ export default function YieldPublicPage() {
</div>
)
}

View File

@ -1,158 +1,164 @@
'use client'
import Link from 'next/link'
import { Twitter, Mail, Linkedin } from 'lucide-react'
import Image from 'next/image'
import { Twitter, Mail, Linkedin, ArrowRight } from 'lucide-react'
import { useStore } from '@/lib/store'
export function Footer() {
const { isAuthenticated } = useStore()
return (
<footer className="relative border-t border-border bg-background-secondary/30 backdrop-blur-sm mt-auto">
<div className="max-w-7xl mx-auto px-4 sm:px-6 py-12 sm:py-16">
<div className="grid grid-cols-2 md:grid-cols-4 gap-8 mb-12">
{/* Brand */}
<div className="col-span-2 md:col-span-1">
<div className="mb-4">
<Link href="/" className="inline-block">
<footer className="relative border-t border-white/10 bg-[#020202] mt-auto overflow-hidden">
{/* Background Noise */}
<div className="absolute inset-0 bg-[url('/noise.png')] opacity-[0.03] mix-blend-overlay pointer-events-none" />
<div className="max-w-[1400px] mx-auto px-4 sm:px-6 py-16 sm:py-20 relative z-10">
<div className="grid grid-cols-1 md:grid-cols-4 lg:grid-cols-5 gap-12 lg:gap-8 mb-16">
{/* Brand Column */}
<div className="md:col-span-2 lg:col-span-2">
<div className="mb-6">
<Link href="/" className="inline-block group">
<div className="flex items-center gap-3">
<Image
src="/pounce-puma.png"
alt="POUNCE"
width={40}
height={40}
className="object-contain opacity-80 group-hover:opacity-100 transition-opacity"
/>
<span
className="text-xl font-bold tracking-[0.1em] text-foreground"
style={{ fontFamily: 'var(--font-display), Playfair Display, Georgia, serif' }}
className="text-xl font-black tracking-[0.1em] text-white group-hover:text-accent transition-colors"
style={{ fontFamily: 'var(--font-display), sans-serif' }}
>
POUNCE
</span>
</div>
</Link>
</div>
<p className="text-body-sm text-foreground-muted mb-2">
Don&apos;t guess. Know.
<p className="text-sm font-mono text-white/50 mb-8 max-w-sm leading-relaxed">
Global domain intelligence for serious investors. <br/>
Scan. Acquire. Route. Yield.
</p>
<p className="text-body-xs text-foreground-subtle mb-4">
Domain intelligence for serious investors and founders.
</p>
<div className="flex items-center gap-3">
{/* Newsletter Input - Tech Style */}
<div className="mb-8 max-w-sm">
<label className="text-[10px] font-mono uppercase tracking-widest text-white/30 mb-2 block">Mission Briefings</label>
<div className="flex">
<input
type="email"
placeholder="ENTER_EMAIL"
className="w-full bg-[#0A0A0A] border border-white/10 px-4 py-3 text-white font-mono text-xs placeholder:text-white/20 focus:outline-none focus:border-accent transition-all rounded-none"
/>
<button className="px-4 bg-white text-black hover:bg-accent transition-colors border-l border-white/10">
<ArrowRight className="w-4 h-4" />
</button>
</div>
</div>
<div className="flex items-center gap-4">
<a
href="https://twitter.com/pounce_domains"
target="_blank"
rel="noopener noreferrer"
className="w-9 h-9 flex items-center justify-center rounded-lg bg-foreground/5 hover:bg-foreground/10 transition-colors"
className="w-10 h-10 flex items-center justify-center border border-white/5 hover:border-white/20 hover:bg-white/5 transition-all group"
aria-label="Twitter"
>
<Twitter className="w-4 h-4 text-foreground-muted" />
<Twitter className="w-4 h-4 text-white/40 group-hover:text-white transition-colors" />
</a>
<a
href="https://linkedin.com"
target="_blank"
rel="noopener noreferrer"
className="w-9 h-9 flex items-center justify-center rounded-lg bg-foreground/5 hover:bg-foreground/10 transition-colors"
className="w-10 h-10 flex items-center justify-center border border-white/5 hover:border-white/20 hover:bg-white/5 transition-all group"
aria-label="LinkedIn"
>
<Linkedin className="w-4 h-4 text-foreground-muted" />
<Linkedin className="w-4 h-4 text-white/40 group-hover:text-white transition-colors" />
</a>
<a
href="mailto:hello@pounce.ch"
className="w-9 h-9 flex items-center justify-center rounded-lg bg-foreground/5 hover:bg-foreground/10 transition-colors"
className="w-10 h-10 flex items-center justify-center border border-white/5 hover:border-white/20 hover:bg-white/5 transition-all group"
aria-label="Email"
>
<Mail className="w-4 h-4 text-foreground-muted" />
<Mail className="w-4 h-4 text-white/40 group-hover:text-white transition-colors" />
</a>
</div>
</div>
{/* Product - Matches new navigation (gemäß pounce_public.md) */}
<div>
<h3 className="text-ui font-semibold text-foreground mb-4">Product</h3>
<ul className="space-y-3">
{/* Links Columns */}
<div className="lg:col-span-1">
<h3 className="text-xs font-bold uppercase tracking-[0.2em] text-white mb-6">Protocol</h3>
<ul className="space-y-4">
<li>
<Link href="/market" className="text-body-sm text-foreground-muted hover:text-foreground transition-colors">
Market
<Link href="/acquire" className="text-sm font-mono text-white/40 hover:text-accent transition-colors flex items-center gap-2 group">
<span className="w-1 h-1 bg-white/20 group-hover:bg-accent rounded-full transition-colors" /> Acquire
</Link>
</li>
<li>
<Link href="/discover" className="text-body-sm text-foreground-muted hover:text-foreground transition-colors">
Discover
<Link href="/discover" className="text-sm font-mono text-white/40 hover:text-accent transition-colors flex items-center gap-2 group">
<span className="w-1 h-1 bg-white/20 group-hover:bg-accent rounded-full transition-colors" /> Discover
</Link>
</li>
<li>
<Link href="/pricing" className="text-body-sm text-foreground-muted hover:text-foreground transition-colors">
Pricing
<Link href="/yield" className="text-sm font-mono text-white/40 hover:text-accent transition-colors flex items-center gap-2 group">
<span className="w-1 h-1 bg-white/20 group-hover:bg-accent rounded-full transition-colors" /> Yield
</Link>
</li>
{isAuthenticated ? (
<li>
<Link href="/terminal/radar" className="text-body-sm text-accent hover:text-accent-hover transition-colors">
Command Center
<Link href="/pricing" className="text-sm font-mono text-white/40 hover:text-accent transition-colors flex items-center gap-2 group">
<span className="w-1 h-1 bg-white/20 group-hover:bg-accent rounded-full transition-colors" /> Pricing
</Link>
</li>
) : (
</ul>
</div>
<div className="lg:col-span-1">
<h3 className="text-xs font-bold uppercase tracking-[0.2em] text-white mb-6">Intel</h3>
<ul className="space-y-4">
<li>
<Link href="/register" className="text-body-sm text-accent hover:text-accent-hover transition-colors">
Get Started Free
</Link>
<Link href="/briefings" className="text-sm font-mono text-white/40 hover:text-white transition-colors">Briefings</Link>
</li>
<li>
<Link href="/about" className="text-sm font-mono text-white/40 hover:text-white transition-colors">About Us</Link>
</li>
<li>
<Link href="/contact" className="text-sm font-mono text-white/40 hover:text-white transition-colors">Contact HQ</Link>
</li>
{!isAuthenticated && (
<li>
<Link href="/login" className="text-sm font-mono text-white/40 hover:text-white transition-colors">Login</Link>
</li>
)}
</ul>
</div>
{/* Resources */}
<div>
<h3 className="text-ui font-semibold text-foreground mb-4">Resources</h3>
<ul className="space-y-3">
<div className="lg:col-span-1">
<h3 className="text-xs font-bold uppercase tracking-[0.2em] text-white mb-6">Legal</h3>
<ul className="space-y-4">
<li>
<Link href="/blog" className="text-body-sm text-foreground-muted hover:text-foreground transition-colors">
Briefings
</Link>
<Link href="/legal/privacy" className="text-sm font-mono text-white/40 hover:text-white transition-colors">Privacy Policy</Link>
</li>
<li>
<Link href="/about" className="text-body-sm text-foreground-muted hover:text-foreground transition-colors">
About Us
</Link>
<Link href="/legal/terms" className="text-sm font-mono text-white/40 hover:text-white transition-colors">Terms of Service</Link>
</li>
<li>
<Link href="/contact" className="text-body-sm text-foreground-muted hover:text-foreground transition-colors">
Contact
</Link>
</li>
</ul>
</div>
{/* Legal */}
<div>
<h3 className="text-ui font-semibold text-foreground mb-4">Legal</h3>
<ul className="space-y-3">
<li>
<Link href="/privacy" className="text-body-sm text-foreground-muted hover:text-foreground transition-colors">
Privacy Policy
</Link>
</li>
<li>
<Link href="/terms" className="text-body-sm text-foreground-muted hover:text-foreground transition-colors">
Terms of Service
</Link>
</li>
<li>
<Link href="/imprint" className="text-body-sm text-foreground-muted hover:text-foreground transition-colors">
Imprint
</Link>
<Link href="/legal/imprint" className="text-sm font-mono text-white/40 hover:text-white transition-colors">Imprint</Link>
</li>
</ul>
</div>
</div>
{/* Bottom */}
<div className="pt-8 border-t border-border flex flex-col sm:flex-row justify-between items-center gap-4">
<p className="text-ui-sm text-foreground-subtle">
© {new Date().getFullYear()} pounce.ch All rights reserved.
</p>
{/* Bottom Bar */}
<div className="pt-8 border-t border-white/10 flex flex-col sm:flex-row justify-between items-center gap-4 text-[10px] font-mono text-white/20 uppercase tracking-widest">
<p>© {new Date().getFullYear()} POUNCE AG ZURICH</p>
<div className="flex items-center gap-6">
<Link href="/privacy" className="text-ui-sm text-foreground-subtle hover:text-foreground transition-colors">
Privacy
</Link>
<Link href="/terms" className="text-ui-sm text-foreground-subtle hover:text-foreground transition-colors">
Terms
</Link>
<span>System Status: Online</span>
<span>v2.0.4 [Stable]</span>
</div>
</div>
</div>
</footer>
)
}

View File

@ -40,7 +40,7 @@ export function Header() {
// Navigation: Discover | Acquire | Yield | Pricing
const publicNavItems = [
{ href: '/discover', label: 'Discover', icon: TrendingUp },
{ href: '/market', label: 'Acquire', icon: Gavel },
{ href: '/acquire', label: 'Acquire', icon: Gavel },
{ href: '/yield', label: 'Yield', icon: Coins },
{ href: '/pricing', label: 'Pricing', icon: CreditCard },
]