From af676aaa9fa4f68e94742694cf7423d693b9d298 Mon Sep 17 00:00:00 2001 From: cialloo Date: Sat, 4 Oct 2025 13:23:40 +0800 Subject: [PATCH] Refactor App component to integrate mock statistics and recent chat messages; update localization for stats and activity sections --- src/App.tsx | 174 +++++++++++++++++++++++++++++++++++++------- src/locales/en.json | 18 ++--- src/locales/zh.json | 19 +++-- 3 files changed, 165 insertions(+), 46 deletions(-) diff --git a/src/App.tsx b/src/App.tsx index 8006cd7..35ff03f 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -7,21 +7,139 @@ function App() { const { t } = useTranslation() // Mock data - in real app, this would come from API + // API endpoints: /api/server/statistics/* + // To integrate real API, replace mock data with: + // + // const [stats, setStats] = useState({ totalPlayers: 0, totalConnects: 0, totalPlayTime: 0, totalKills: 0 }) + // + // useEffect(() => { + // const timeRangeEnd = Date.now() + // const timeRangeStart = 0 // or specific start time + // const requestBody = { timeRangeStart, timeRangeEnd, playerFilter: [] } + // + // Promise.all([ + // fetch('/api/server/statistics/total-player-count', { method: 'POST', body: JSON.stringify(requestBody) }), + // fetch('/api/server/statistics/total-connect-count', { method: 'POST', body: JSON.stringify(requestBody) }), + // fetch('/api/server/statistics/total-play-time', { method: 'POST', body: JSON.stringify(requestBody) }), + // fetch('/api/server/statistics/total-kill-count', { + // method: 'POST', + // body: JSON.stringify({ ...requestBody, headshotOnly: false, weaponFilter: [] }) + // }) + // ]).then(responses => Promise.all(responses.map(r => r.json()))) + // .then(([players, connects, playTime, kills]) => { + // setStats({ + // totalPlayers: players.count, + // totalConnects: connects.totalConnectCount, + // totalPlayTime: playTime.totalPlayTime, + // totalKills: kills.totalKillCount + // }) + // }) + // }, []) + const stats = { - onlinePlayers: 1247, - totalServers: 89, - totalPlayTime: '2.4M', - activeGames: 23 + totalPlayers: 1247, // from /api/server/statistics/total-player-count + totalConnects: 3456, // from /api/server/statistics/total-connect-count + totalPlayTime: 8640000, // from /api/server/statistics/total-play-time (in seconds) + totalKills: 15420 // from /api/server/statistics/total-kill-count } + // Format playtime from seconds to hours + const formatPlayTime = (seconds: number) => { + const hours = Math.floor(seconds / 3600) + if (hours >= 1000000) { + return `${(hours / 1000000).toFixed(1)}M` + } else if (hours >= 1000) { + return `${(hours / 1000).toFixed(1)}K` + } + return hours.toLocaleString() + } + + // Mock recent chat messages - from /api/server/statistics/recent-chat-message + // Response format: { messages: [{ steamID64, userName, message, timeStamp }] } + // To integrate real API: + // const [recentChats, setRecentChats] = useState([]) + // useEffect(() => { + // fetch('/api/server/statistics/recent-chat-message', { + // method: 'POST', + // headers: { 'Content-Type': 'application/json' }, + // body: JSON.stringify({ + // timeRangeStart: Date.now() - 3600000, // last hour + // timeRangeEnd: Date.now() + // }) + // }).then(r => r.json()) + // .then(data => setRecentChats(data.messages)) + // }, []) const recentChats = [ - { user: 'ProGamer99', message: 'GG everyone! Great match!', time: '2m ago' }, - { user: 'SniperElite', message: 'Anyone up for a quick match?', time: '5m ago' }, - { user: 'HeadshotKing', message: 'New server just went live!', time: '8m ago' }, - { user: 'TacticalNuke', message: 'Looking for team players', time: '12m ago' }, - { user: 'FragMaster', message: 'Server maintenance complete', time: '15m ago' } + { + steamID64: '76561198281616762', + userName: 'ProGamer99', + message: 'GG everyone! Great match!', + timeStamp: Date.now() - 120000 // 2 minutes ago + }, + { + steamID64: '76561198281616763', + userName: 'SniperElite', + message: 'Anyone up for a quick match?', + timeStamp: Date.now() - 300000 // 5 minutes ago + }, + { + steamID64: '76561198281616764', + userName: 'HeadshotKing', + message: 'New server just went live!', + timeStamp: Date.now() - 480000 // 8 minutes ago + }, + { + steamID64: '76561198281616765', + userName: 'TacticalNuke', + message: 'Looking for team players', + timeStamp: Date.now() - 720000 // 12 minutes ago + }, + { + steamID64: '76561198281616766', + userName: 'FragMaster', + message: 'Server maintenance complete', + timeStamp: Date.now() - 900000 // 15 minutes ago + } ] + // Mock top players - from /api/server/statistics/top-play-time + // Response format: { players: [{ steamID64, userName, playTime }] } + // To integrate real API: + // const [topPlayers, setTopPlayers] = useState([]) + // useEffect(() => { + // fetch('/api/server/statistics/top-play-time', { + // method: 'POST', + // headers: { 'Content-Type': 'application/json' }, + // body: JSON.stringify({ + // timeRangeStart: 0, // all time + // timeRangeEnd: Date.now() + // }) + // }).then(r => r.json()) + // .then(data => setTopPlayers(data.players.slice(0, 3))) // top 3 + // }, []) + const topPlayers = [ + { steamID64: '76561198281616762', userName: 'ProGamer99', playTime: 882000 }, // 245 hours + { steamID64: '76561198281616763', userName: 'SniperElite', playTime: 784800 }, // 218 hours + { steamID64: '76561198281616764', userName: 'HeadshotKing', playTime: 702000 } // 195 hours + ] + + // Format time ago from timestamp + const formatTimeAgo = (timestamp: number) => { + const seconds = Math.floor((Date.now() - timestamp) / 1000) + if (seconds < 60) return `${seconds}s ago` + const minutes = Math.floor(seconds / 60) + if (minutes < 60) return `${minutes}m ago` + const hours = Math.floor(minutes / 60) + if (hours < 24) return `${hours}h ago` + const days = Math.floor(hours / 24) + return `${days}d ago` + } + + // Format playtime to hours for leaderboard + const formatPlayTimeHours = (seconds: number) => { + return Math.floor(seconds / 3600) + } + return ( {/* Hero Section */} @@ -57,23 +175,23 @@ function App() {
👥
-
{stats.onlinePlayers.toLocaleString()}
-
{t('stats.onlinePlayers')}
+
{stats.totalPlayers.toLocaleString()}
+
{t('stats.totalPlayers')}
-
🖥️
-
{stats.totalServers}
-
{t('stats.activeServers')}
+
+
{stats.totalConnects.toLocaleString()}
+
{t('stats.totalConnects')}
⏱️
-
{stats.totalPlayTime}
-
{t('stats.hoursPlayed')}
+
{formatPlayTime(stats.totalPlayTime)}
+
{t('stats.totalPlayTime')}
🎯
-
{stats.activeGames}
-
{t('stats.liveMatches')}
+
{stats.totalKills.toLocaleString()}
+
{t('stats.totalKills')}
@@ -125,9 +243,9 @@ function App() {
{recentChats.map((chat, index) => (
-
{chat.user}:
+
{chat.userName}:
{chat.message}
-
{chat.time}
+
{formatTimeAgo(chat.timeStamp)}
))}
@@ -136,17 +254,19 @@ function App() {

{t('activity.topPlayers')}

-
1. ProGamer99 - 2,450 pts
-
2. SniperElite - 2,180 pts
-
3. HeadshotKing - 1,950 pts
+ {topPlayers.map((player, index) => ( +
+ {index + 1}. {player.userName} - {formatPlayTimeHours(player.playTime)}h +
+ ))}
-

{t('activity.quickStats')}

+

{t('activity.serverInfo')}

-
{t('activity.avgMatchTime')}
-
{t('activity.mostPopularMap')}
-
{t('activity.peakHours')}
+
{t('activity.serverStatus')}
+
{t('activity.currentMap')}
+
{t('activity.nextRestart')}
diff --git a/src/locales/en.json b/src/locales/en.json index ea05a9e..dfe4249 100644 --- a/src/locales/en.json +++ b/src/locales/en.json @@ -18,10 +18,10 @@ "viewStats": "📊 View Stats" }, "stats": { - "onlinePlayers": "Online Players", - "activeServers": "Active Servers", - "hoursPlayed": "Hours Played", - "liveMatches": "Live Matches" + "totalPlayers": "Total Players", + "totalConnects": "Total Connections", + "totalPlayTime": "Hours Played", + "totalKills": "Total Kills" }, "features": { "title": "Community Features", @@ -53,11 +53,11 @@ }, "activity": { "title": "Recent Activity", - "topPlayers": "🏆 Top Players", - "quickStats": "🎯 Quick Stats", - "avgMatchTime": "Avg Match Time: 12m 34s", - "mostPopularMap": "Most Popular Map: Dust2", - "peakHours": "Peak Hours: 8-11 PM" + "topPlayers": "Top Players by Playtime", + "serverInfo": "Server Info", + "serverStatus": "Status: Online ✓", + "currentMap": "Map: de_dust2", + "nextRestart": "Restart: 6h 30m" }, "footer": { "community": "🎯 CS Community", diff --git a/src/locales/zh.json b/src/locales/zh.json index 4fce58c..2976190 100644 --- a/src/locales/zh.json +++ b/src/locales/zh.json @@ -1,6 +1,5 @@ { "nav": { - "logo": "CS 社区", "home": "首页", "servers": "服务器", "blog": "博客", @@ -18,10 +17,10 @@ "viewStats": "📊 查看统计" }, "stats": { - "onlinePlayers": "在线玩家", - "activeServers": "活跃服务器", - "hoursPlayed": "游戏时长", - "liveMatches": "实时比赛" + "totalPlayers": "总玩家数", + "totalConnects": "总连接数", + "totalPlayTime": "游戏时长", + "totalKills": "总击杀数" }, "features": { "title": "社区功能", @@ -53,11 +52,11 @@ }, "activity": { "title": "最近活动", - "topPlayers": "🏆 顶级玩家", - "quickStats": "🎯 快速统计", - "avgMatchTime": "平均比赛时长:12分34秒", - "mostPopularMap": "最受欢迎地图:Dust2", - "peakHours": "高峰时段:晚上8-11点" + "topPlayers": "游戏时长排行榜", + "serverInfo": "服务器信息", + "serverStatus": "状态:在线 ✓", + "currentMap": "地图:de_dust2", + "nextRestart": "重启:6小时30分钟" }, "footer": { "community": "🎯 CS 社区",