- AgentOffice renders TopBar + AgentGrid + dynamic right panel - Right panel: SidePanel (active) / EmptyDetailPanel (initial or placeholder) - TopBar simplified to connected status only (theme/zoom dropped) - Wire AgentGrid through useAgentManager state - Remove canvas/ (9 files), useOfficeCanvas, office-map.json - New CSS for grid cards (state dot, notification badge, accent border) - Mobile: 2-column grid + bottom-sheet panel Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
76 lines
2.2 KiB
JavaScript
76 lines
2.2 KiB
JavaScript
// src/pages/agent-office/AgentOffice.jsx
|
|
import { useState, useCallback } from 'react';
|
|
import { useAgentManager } from './hooks/useAgentManager.js';
|
|
import { AGENT_META } from './constants.js';
|
|
import TopBar from './components/TopBar.jsx';
|
|
import AgentGrid from './components/AgentGrid.jsx';
|
|
import SidePanel from './components/SidePanel.jsx';
|
|
import EmptyDetailPanel from './components/EmptyDetailPanel.jsx';
|
|
import './AgentOffice.css';
|
|
|
|
export default function AgentOffice() {
|
|
const {
|
|
agents, pendingTasks, notifications, connected,
|
|
refreshTrigger, clearNotifications
|
|
} = useAgentManager();
|
|
|
|
// selectedAgent: null | active agent id | "placeholder-N"
|
|
const [selectedAgent, setSelectedAgent] = useState(null);
|
|
|
|
const handleSelectAgent = useCallback((agentId) => {
|
|
setSelectedAgent(agentId);
|
|
clearNotifications(agentId);
|
|
}, [clearNotifications]);
|
|
|
|
const handleSelectPlaceholder = useCallback((placeholderKey) => {
|
|
setSelectedAgent(placeholderKey);
|
|
}, []);
|
|
|
|
const handleClose = useCallback(() => {
|
|
setSelectedAgent(null);
|
|
}, []);
|
|
|
|
const pendingTask = selectedAgent && AGENT_META[selectedAgent]
|
|
? pendingTasks.find(t => t.agent_id === selectedAgent)
|
|
: null;
|
|
|
|
let rightPanel;
|
|
if (selectedAgent === null) {
|
|
rightPanel = <EmptyDetailPanel variant="initial" />;
|
|
} else if (selectedAgent.startsWith('placeholder-')) {
|
|
rightPanel = <EmptyDetailPanel variant="placeholder" onClose={handleClose} />;
|
|
} else {
|
|
rightPanel = (
|
|
<SidePanel
|
|
agentId={selectedAgent}
|
|
agentState={agents[selectedAgent]}
|
|
pendingTask={pendingTask}
|
|
onClose={handleClose}
|
|
refreshTrigger={refreshTrigger}
|
|
/>
|
|
);
|
|
}
|
|
|
|
return (
|
|
<div className="ao-root">
|
|
<TopBar connected={connected} />
|
|
<div className="ao-main">
|
|
<div className="ao-grid-wrap">
|
|
<AgentGrid
|
|
agents={agents}
|
|
notifications={notifications}
|
|
selectedAgent={selectedAgent}
|
|
onSelectAgent={handleSelectAgent}
|
|
onSelectPlaceholder={handleSelectPlaceholder}
|
|
/>
|
|
</div>
|
|
{rightPanel}
|
|
</div>
|
|
</div>
|
|
);
|
|
}
|
|
|
|
export function Component() {
|
|
return <AgentOffice />;
|
|
}
|