diff --git a/app/api/telegram-members/route.ts b/app/api/telegram-members/route.ts new file mode 100644 index 0000000..a3e9b44 --- /dev/null +++ b/app/api/telegram-members/route.ts @@ -0,0 +1,11 @@ +export async function GET() { + try { + const res = await fetch('https://t.me/gudteksolana', { next: { revalidate: 3600 } }) + const text = await res.text() + const match = text.match(/tgme_page_extra[^>]*>([^<]+) members/) + const count = match ? parseInt(match[1].replace(/[^0-9]/g, '')) : 0 + return Response.json({ count }) + } catch (err) { + return Response.json({ count: 0 }) + } +} diff --git a/app/tokenomics/page.tsx b/app/tokenomics/page.tsx new file mode 100644 index 0000000..88288d8 --- /dev/null +++ b/app/tokenomics/page.tsx @@ -0,0 +1,142 @@ +'use client' + +import { useEffect, useState } from 'react' +import Navbar from '@/components/Navbar' +import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from '@/components/ui/table' +import { Progress } from '@/components/ui/progress' +import { PieChart, Pie, Cell, Tooltip, ResponsiveContainer } from 'recharts' +import { formatTokenBalance } from '@/lib/wallet' +import Link from 'next/link' + +const INITIAL_SUPPLY = 1_000_000_000 // 1B tokens + +const TEAM_WALLETS = [ + { name: 'Treasury', address: '3xmpZy4SFCp6wzqgk4Mh7jg1yF3ggvG5Xqkt3F9CEbLj', balance: 250_000_000 }, + { name: 'Operations', address: 'CXcG8pN7fT9VqgaJcfH8YzjzD4xfH14RJCdxu2YgSUn9', balance: 50_000_000 }, + { name: 'Marketing', address: '4HwME8YgUCnYJdeL9N2qHcNXTc3swaP42gnikLzeGWih', balance: 30_000_000 }, + { name: 'Liquidity', address: 'HkENe7A1Ji4VwWUvDdDhcW7UZ5EKeosFVJeFt3PcTJSd', balance: 120_000_000 } +] + +const GOALS = [ + { name: 'Twitter Followers', target: 10000, value: 4200, burn: 0.5 }, + { name: 'Token Holders', target: 5000, value: 1300 }, + { name: 'Telegram Members', target: 2000, value: 800 } +] + +export default function TokenomicsPage() { + const [now, setNow] = useState(Date.now()) + // pretend the market cap recently crossed $400k + const marketCap = 450_000 + const nextThreshold = 500_000 + const holdStart = Date.now() - 12 * 60 * 60 * 1000 // halfway through 24h hold + + useEffect(() => { + const id = setInterval(() => setNow(Date.now()), 1000) + return () => clearInterval(id) + }, []) + + const countdown = Math.max(0, 24 * 60 * 60 * 1000 - (now - holdStart)) + const countdownPct = ((24 * 60 * 60 * 1000 - countdown) / (24 * 60 * 60 * 1000)) * 100 + + const burnedTokens = 150_000_000 + const burnedPercent = (burnedTokens / INITIAL_SUPPLY) * 100 + const teamTotal = TEAM_WALLETS.reduce((acc, w) => acc + w.balance, 0) + const teamPercent = (teamTotal / INITIAL_SUPPLY) * 100 + + const pieData = [ + { name: 'Burned', value: burnedPercent }, + { name: 'Team', value: teamPercent } + ] + const colors = ['#FF3B3B', '#FFA500'] + + return ( +
+ + ) +} + diff --git a/components/Navbar.tsx b/components/Navbar.tsx index f4b8f8e..a4d5da8 100644 --- a/components/Navbar.tsx +++ b/components/Navbar.tsx @@ -23,7 +23,8 @@ export default function Navbar() { { name: "GudMusic", href: "/music" }, { name: "GUD AI", href: "/pfp" }, { name: "Hackathon", href: "/hackathon" }, - { name: "Utility", href: "/utility" } + { name: "Utility", href: "/utility" }, + { name: "Tokenomics", href: "/tokenomics" }, ] // Close mobile menu when route changes