5d30d1f4a1
CI / build-and-push (push) Successful in 36s
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
70 lines
2.5 KiB
TypeScript
70 lines
2.5 KiB
TypeScript
import { useState, useEffect } from 'react';
|
|
import { X, Bug } from 'lucide-react';
|
|
import { ResourcesTab } from './ResourcesTab';
|
|
import { TimeCompletionTab } from './TimeCompletionTab';
|
|
import { StateInspectionTab } from './StateInspectionTab';
|
|
import { EventTriggersTab } from './EventTriggersTab';
|
|
|
|
type Tab = 'resources' | 'time' | 'inspect' | 'events';
|
|
|
|
const TABS: { id: Tab; label: string }[] = [
|
|
{ id: 'resources', label: 'Resources' },
|
|
{ id: 'time', label: 'Time' },
|
|
{ id: 'inspect', label: 'Inspect' },
|
|
{ id: 'events', label: 'Events' },
|
|
];
|
|
|
|
export function DevMenu() {
|
|
const [isOpen, setIsOpen] = useState(false);
|
|
const [activeTab, setActiveTab] = useState<Tab>('resources');
|
|
|
|
useEffect(() => {
|
|
const handler = () => setIsOpen((o) => !o);
|
|
window.addEventListener('toggle-dev-menu', handler);
|
|
return () => window.removeEventListener('toggle-dev-menu', handler);
|
|
}, []);
|
|
|
|
if (!isOpen) return null;
|
|
|
|
return (
|
|
<div className="fixed bottom-4 right-4 z-50 w-[440px] max-h-[520px] flex flex-col bg-surface-900 border border-surface-700 rounded-lg shadow-2xl">
|
|
<div className="flex items-center justify-between px-3 py-2 border-b border-surface-700">
|
|
<div className="flex items-center gap-2">
|
|
<Bug className="w-4 h-4 text-amber-400" />
|
|
<span className="text-sm font-semibold text-surface-100">Dev Menu</span>
|
|
<span className="text-[10px] text-surface-500">Ctrl+D</span>
|
|
</div>
|
|
<button
|
|
onClick={() => setIsOpen(false)}
|
|
className="p-0.5 rounded hover:bg-surface-700 text-surface-400 hover:text-surface-200"
|
|
>
|
|
<X className="w-4 h-4" />
|
|
</button>
|
|
</div>
|
|
|
|
<div className="flex border-b border-surface-700">
|
|
{TABS.map(({ id, label }) => (
|
|
<button
|
|
key={id}
|
|
onClick={() => setActiveTab(id)}
|
|
className={`flex-1 px-3 py-1.5 text-xs font-medium transition-colors ${
|
|
activeTab === id
|
|
? 'text-amber-400 border-b-2 border-amber-400 bg-surface-800/50'
|
|
: 'text-surface-400 hover:text-surface-200 hover:bg-surface-800/30'
|
|
}`}
|
|
>
|
|
{label}
|
|
</button>
|
|
))}
|
|
</div>
|
|
|
|
<div className="flex-1 overflow-y-auto p-3">
|
|
{activeTab === 'resources' && <ResourcesTab />}
|
|
{activeTab === 'time' && <TimeCompletionTab />}
|
|
{activeTab === 'inspect' && <StateInspectionTab />}
|
|
{activeTab === 'events' && <EventTriggersTab />}
|
|
</div>
|
|
</div>
|
|
);
|
|
}
|