diff --git a/frontend/src/components/network/ContextMenu.tsx b/frontend/src/components/network/ContextMenu.tsx index ca4e4151..2b76a681 100644 --- a/frontend/src/components/network/ContextMenu.tsx +++ b/frontend/src/components/network/ContextMenu.tsx @@ -1,6 +1,6 @@ import { useEffect, useRef } from 'react' import { - Copy, CopyPlus, Trash2, ClipboardPaste, BoxSelect, Maximize2, BringToFront, SendToBack, + Copy, CopyPlus, Trash2, ClipboardPaste, BoxSelect, Ungroup, Maximize2, BringToFront, SendToBack, AlignStartVertical, AlignCenterHorizontal, AlignEndVertical, AlignStartHorizontal, AlignCenterVertical, AlignEndHorizontal, AlignHorizontalSpaceAround, AlignVerticalSpaceAround, @@ -168,7 +168,7 @@ export function ContextMenu({ )} {canUngroup && ( )} diff --git a/frontend/src/components/network/edges/ConnectionEdge.tsx b/frontend/src/components/network/edges/ConnectionEdge.tsx index 5b769eec..bc87b1be 100644 --- a/frontend/src/components/network/edges/ConnectionEdge.tsx +++ b/frontend/src/components/network/edges/ConnectionEdge.tsx @@ -54,7 +54,7 @@ function ConnectionEdgeComponent(props: EdgeProps) { {props.label && (
- +
-
+
@@ -135,7 +135,7 @@ function DeviceNodeComponent({ id, data, selected, width, height }: NodeProps) { )} {CATEGORY_LABELS[category] ?? nodeData.deviceType.replace(/-/g, ' ')} diff --git a/frontend/src/components/network/nodes/GroupNode.tsx b/frontend/src/components/network/nodes/GroupNode.tsx index c65feac7..55156a4c 100644 --- a/frontend/src/components/network/nodes/GroupNode.tsx +++ b/frontend/src/components/network/nodes/GroupNode.tsx @@ -51,7 +51,7 @@ const GroupNodeComponent = ({ data, selected, id }: NodeProps) => { boxSizing: 'border-box', }} > -
+
{editing ? ( { if (e.key === 'Enter' || e.key === 'Escape') handleLabelCommit() e.stopPropagation() }} - className="text-[11px] font-medium bg-transparent border-none outline-none text-primary min-w-[40px] max-w-[200px]" + className="rounded-sm px-1.5 py-0.5 text-[11px] font-semibold bg-card/90 border-none outline-none min-w-[40px] max-w-[200px]" style={{ color }} /> ) : ( setEditing(true)} > diff --git a/frontend/src/components/network/panels/DeviceToolbar.tsx b/frontend/src/components/network/panels/DeviceToolbar.tsx index 22f59669..7ee2e0c7 100644 --- a/frontend/src/components/network/panels/DeviceToolbar.tsx +++ b/frontend/src/components/network/panels/DeviceToolbar.tsx @@ -151,22 +151,22 @@ export function DeviceToolbar({ deviceTypes, onDeviceTypesChange }: DeviceToolba
{[ - { slug: 'subnet', label: 'Subnet' }, - { slug: 'vlan', label: 'VLAN' }, - { slug: 'site', label: 'Site' }, - { slug: 'dmz', label: 'DMZ' }, + { slug: 'subnet', label: 'Subnet', color: '#60a5fa' }, + { slug: 'vlan', label: 'VLAN', color: '#a78bfa' }, + { slug: 'site', label: 'Site', color: '#34d399' }, + { slug: 'dmz', label: 'DMZ', color: '#f87171' }, ].map(item => (
{ - e.dataTransfer.setData('application/reactflow-group', JSON.stringify(item)) + e.dataTransfer.setData('application/reactflow-group', JSON.stringify({ slug: item.slug, label: item.label })) e.dataTransfer.effectAllowed = 'move' }} className="flex cursor-grab items-center gap-2 rounded px-2 py-1.5 text-xs text-primary hover:bg-elevated active:cursor-grabbing active:scale-[0.98] transition-transform" > - + {item.label}
))} diff --git a/frontend/src/components/network/panels/PropertiesPanel.tsx b/frontend/src/components/network/panels/PropertiesPanel.tsx index 0f870091..26c760eb 100644 --- a/frontend/src/components/network/panels/PropertiesPanel.tsx +++ b/frontend/src/components/network/panels/PropertiesPanel.tsx @@ -4,7 +4,7 @@ import { AlignStartVertical, AlignCenterHorizontal, AlignEndVertical, AlignStartHorizontal, AlignCenterVertical, AlignEndHorizontal, AlignHorizontalSpaceAround, AlignVerticalSpaceAround, - BoxSelect, Ungroup, + BoxSelect, Ungroup, MousePointer, } from 'lucide-react' import { cn } from '@/lib/utils' import type { DeviceProperties, DiagramEdge } from '@/types' @@ -235,12 +235,15 @@ export function PropertiesPanel({ if (!selectedNode && !selectedEdge) { return ( -
-

- Select a device or connection to edit its properties +

+
+ +
+

+ Select a device or connection

-

- Hover a device to preview its info +

+ Properties appear here. Hover a device to see a quick summary.

) diff --git a/frontend/src/components/network/ui/base-handle.tsx b/frontend/src/components/network/ui/base-handle.tsx index 4f57ca45..42cbb062 100644 --- a/frontend/src/components/network/ui/base-handle.tsx +++ b/frontend/src/components/network/ui/base-handle.tsx @@ -9,7 +9,7 @@ export function BaseHandle({ className, children, ...props }: ComponentProps = { } const STATUS_GLOW: Record = { - online: 'shadow-[0_0_8px_rgba(52,211,153,0.3)]', - offline: 'shadow-[0_0_8px_rgba(248,113,113,0.3)]', - degraded: 'shadow-[0_0_8px_rgba(250,204,21,0.3)]', + online: 'shadow-[0_0_6px_rgba(52,211,153,0.15)]', + offline: 'shadow-[0_0_6px_rgba(248,113,113,0.15)]', + degraded: 'shadow-[0_0_6px_rgba(250,204,21,0.15)]', unknown: '', } diff --git a/frontend/src/pages/NetworkDiagrams/DiagramEditor.tsx b/frontend/src/pages/NetworkDiagrams/DiagramEditor.tsx index ed3e1661..9b86d82a 100644 --- a/frontend/src/pages/NetworkDiagrams/DiagramEditor.tsx +++ b/frontend/src/pages/NetworkDiagrams/DiagramEditor.tsx @@ -853,11 +853,11 @@ function DiagramEditorInner() { {nodes.length === 0 && !loading && ( )} - {/* Keyboard shortcut hint button — bottom-right corner */} + {/* Keyboard shortcut hint button — above the MiniMap */} diff --git a/frontend/src/pages/NetworkDiagrams/index.tsx b/frontend/src/pages/NetworkDiagrams/index.tsx index 643a492d..e4771800 100644 --- a/frontend/src/pages/NetworkDiagrams/index.tsx +++ b/frontend/src/pages/NetworkDiagrams/index.tsx @@ -1,6 +1,6 @@ import { useState, useEffect, useCallback, useMemo, useRef } from 'react' import { useNavigate } from 'react-router-dom' -import { Plus, Search, Network, MoreHorizontal, Upload, ChevronDown, FileJson, FileOutput } from 'lucide-react' +import { Plus, Search, Network, MoreHorizontal, Upload, ChevronDown, FileJson, FileOutput, ExternalLink, Copy, Archive } from 'lucide-react' import { cn } from '@/lib/utils' import { networkDiagramsApi } from '@/api' import { toast } from '@/lib/toast' @@ -444,8 +444,16 @@ export default function NetworkDiagramsPage() { />
) : ( -
- +
+ + + + + + + + +
)} {d.node_count > 0 && ( @@ -482,20 +490,24 @@ export default function NetworkDiagramsPage() { <> +