fixed little controller issue and wired up stats in top bar
This commit is contained in:
16
get_stats_paths.cjs
Normal file
16
get_stats_paths.cjs
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
const fs = require('fs');
|
||||||
|
try {
|
||||||
|
const content = fs.readFileSync('./romm_swagger.json', 'utf16le');
|
||||||
|
let data;
|
||||||
|
try {
|
||||||
|
data = JSON.parse(content);
|
||||||
|
} catch (e) {
|
||||||
|
// maybe it's utf8
|
||||||
|
data = JSON.parse(fs.readFileSync('./romm_swagger.json', 'utf8'));
|
||||||
|
}
|
||||||
|
const paths = Object.keys(data.paths);
|
||||||
|
const targets = paths.filter(p => p.toLowerCase().includes('stat') || p.toLowerCase().includes('count') || p.toLowerCase().includes('size') || p.toLowerCase().includes('system'));
|
||||||
|
console.log("Matching Endpoints:", targets);
|
||||||
|
} catch (e) {
|
||||||
|
console.error("Failed:", e.message);
|
||||||
|
}
|
||||||
1
romm_swagger_utf8.json
Normal file
1
romm_swagger_utf8.json
Normal file
File diff suppressed because one or more lines are too long
@@ -126,6 +126,12 @@ export const rommApiClient = {
|
|||||||
return json.items ? json.items.map(mapRomToGame) : [];
|
return json.items ? json.items.map(mapRomToGame) : [];
|
||||||
},
|
},
|
||||||
|
|
||||||
|
async fetchStats(): Promise<any> {
|
||||||
|
const res = await fetch(`${this.apiBase}/stats`, { headers: this.headers });
|
||||||
|
if (!res.ok) throw new Error('Failed to fetch stats.');
|
||||||
|
return res.json();
|
||||||
|
},
|
||||||
|
|
||||||
async fetchCollections(): Promise<RommCollection[]> {
|
async fetchCollections(): Promise<RommCollection[]> {
|
||||||
const res = await fetch(`${this.apiBase}/collections`, { headers: this.headers });
|
const res = await fetch(`${this.apiBase}/collections`, { headers: this.headers });
|
||||||
if (!res.ok) throw new Error('Failed to fetch collections meta.');
|
if (!res.ok) throw new Error('Failed to fetch collections meta.');
|
||||||
|
|||||||
@@ -1,7 +1,22 @@
|
|||||||
|
import { useQuery } from '@tanstack/react-query';
|
||||||
|
import { rommApiClient } from '../api/client';
|
||||||
import { useInputMode } from '../context/InputModeContext';
|
import { useInputMode } from '../context/InputModeContext';
|
||||||
|
|
||||||
export const TopNav = () => {
|
export const TopNav = () => {
|
||||||
const { mode } = useInputMode();
|
const { mode } = useInputMode();
|
||||||
|
|
||||||
|
const { data: stats } = useQuery({
|
||||||
|
queryKey: ['stats'],
|
||||||
|
queryFn: () => rommApiClient.fetchStats(),
|
||||||
|
staleTime: 60000, // 1 minute caching
|
||||||
|
});
|
||||||
|
|
||||||
|
const formatBytes = (bytes?: number) => {
|
||||||
|
if (!bytes) return '--';
|
||||||
|
const gb = bytes / (1024 * 1024 * 1024);
|
||||||
|
if (gb >= 1024) return `${(gb / 1024).toFixed(1)} TB`;
|
||||||
|
return `${Math.round(gb)} GB`;
|
||||||
|
};
|
||||||
return (
|
return (
|
||||||
<header className="fixed top-0 right-0 left-64 h-16 z-50 bg-[#10131f]/80 backdrop-blur-2xl flex items-center justify-between px-12 border-b border-white/5">
|
<header className="fixed top-0 right-0 left-64 h-16 z-50 bg-[#10131f]/80 backdrop-blur-2xl flex items-center justify-between px-12 border-b border-white/5">
|
||||||
<div className="flex items-center gap-6 w-full">
|
<div className="flex items-center gap-6 w-full">
|
||||||
@@ -13,27 +28,27 @@ export const TopNav = () => {
|
|||||||
<div className="hidden xl:flex items-center gap-6 ml-4 geist-mono justify-end flex-1">
|
<div className="hidden xl:flex items-center gap-6 ml-4 geist-mono justify-end flex-1">
|
||||||
<div className="flex items-center gap-2">
|
<div className="flex items-center gap-2">
|
||||||
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="account_tree">account_tree</span>
|
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="account_tree">account_tree</span>
|
||||||
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">12</span> Platforms</span>
|
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">{stats?.PLATFORMS ?? '--'}</span> Platforms</span>
|
||||||
</div>
|
</div>
|
||||||
<div className="flex items-center gap-2">
|
<div className="flex items-center gap-2">
|
||||||
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="sports_esports">sports_esports</span>
|
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="sports_esports">sports_esports</span>
|
||||||
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">1,402</span> Games</span>
|
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">{stats?.ROMS?.toLocaleString() ?? '--'}</span> Games</span>
|
||||||
</div>
|
</div>
|
||||||
<div className="flex items-center gap-2">
|
<div className="flex items-center gap-2">
|
||||||
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="hard_drive">hard_drive</span>
|
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="hard_drive">hard_drive</span>
|
||||||
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">2.4 TB</span></span>
|
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">{formatBytes(stats?.TOTAL_FILESIZE_BYTES)}</span></span>
|
||||||
</div>
|
</div>
|
||||||
<div className="flex items-center gap-2">
|
<div className="flex items-center gap-2">
|
||||||
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="save">save</span>
|
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="save">save</span>
|
||||||
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">842</span> Saves</span>
|
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">{stats?.SAVES?.toLocaleString() ?? '--'}</span> Saves</span>
|
||||||
</div>
|
</div>
|
||||||
<div className="flex items-center gap-2">
|
<div className="flex items-center gap-2">
|
||||||
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="history">history</span>
|
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="history">history</span>
|
||||||
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">142</span> States</span>
|
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">{stats?.STATES?.toLocaleString() ?? '--'}</span> States</span>
|
||||||
</div>
|
</div>
|
||||||
<div className="flex items-center gap-2">
|
<div className="flex items-center gap-2">
|
||||||
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="photo_library">photo_library</span>
|
<span className="material-symbols-outlined text-[#2563eb] text-sm" data-icon="photo_library">photo_library</span>
|
||||||
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">5,103</span> Screens</span>
|
<span className="text-[11px] uppercase text-[#c3c6d7] font-bold"><span className="text-white">{stats?.SCREENSHOTS?.toLocaleString() ?? '--'}</span> Screens</span>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div className="w-px h-4 bg-white/10 mx-2"></div>
|
<div className="w-px h-4 bg-white/10 mx-2"></div>
|
||||||
|
|||||||
@@ -10,13 +10,7 @@ interface InputModeContextType {
|
|||||||
const InputModeContext = createContext<InputModeContextType | undefined>(undefined);
|
const InputModeContext = createContext<InputModeContextType | undefined>(undefined);
|
||||||
|
|
||||||
export const InputModeProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {
|
export const InputModeProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {
|
||||||
const [mode, setModeState] = useState<InputMode>('mouse');
|
const [mode, setMode] = useState<InputMode>('mouse');
|
||||||
|
|
||||||
const setMode = (newMode: InputMode) => {
|
|
||||||
if (newMode !== mode) {
|
|
||||||
setModeState(newMode);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
// Spatial Engine Override
|
// Spatial Engine Override
|
||||||
|
|||||||
Reference in New Issue
Block a user