feat: click-drag drawing, layer tree, settings modal, UI improvements

- interaction: click-drag drawing for 2-point tools (line, rect, circle, dimension, leader)
- interaction: preview rendering during drag with setPreviewElement
- interaction: handleDrawDown only sets phase=drawing on first point
- CanvasArea: sync activeLayerId to LayerManager
- CanvasArea: callback refresh useEffect prevents stale closures
- App.tsx: functional setElements updates for handleElementCreated/Deleted/Modified
- LayerPanel: tree structure with sub-layers (onReorder, onAddSubLayer)
- TreeView: drag-and-drop reordering support
- RightSidebar: onReorder, onAddSubLayer, onUpdateElement props
- PropertiesPanel: onUpdateElement prop
- SettingsModal: personal/password/language/theme/users/plugins/AI tabs
- styles.css: extensive UI styling additions
- types: updated RightSidebarProps, CanvasAreaProps, LayerPanelProps
This commit is contained in:
2026-06-27 14:12:37 +02:00
parent 39422a4348
commit 4303076ce4
17 changed files with 929 additions and 144 deletions
+4 -1
View File
@@ -1,7 +1,7 @@
import React from 'react';
import type { TopbarProps } from '../types/ui.types';
const Topbar: React.FC<TopbarProps> = ({ projectName, savedStatus, onUndo, onRedo, onThemeToggle, theme }) => {
const Topbar: React.FC<TopbarProps> = ({ projectName, savedStatus, onUndo, onRedo, onThemeToggle, theme, onOpenSettings }) => {
return (
<header className="topbar" role="banner">
<div className="topbar-left">
@@ -49,6 +49,9 @@ const Topbar: React.FC<TopbarProps> = ({ projectName, savedStatus, onUndo, onRed
<button className="icon-btn-top" aria-label="Benachrichtigungen" title="Benachrichtigungen">
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M6 8a6 6 0 0 1 12 0c0 7 3 9 3 9H3s3-2 3-9"/><path d="M10.3 21a1.94 1.94 0 0 0 3.4 0"/></svg>
</button>
<button className="icon-btn-top" aria-label="Einstellungen" title="Einstellungen" onClick={onOpenSettings}>
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="3"/><path d="M19.4 15a1.65 1.65 0 0 0 .33 1.82l.06.06a2 2 0 0 1 0 2.83 2 2 0 0 1-2.83 0l-.06-.06a1.65 1.65 0 0 0-1.82-.33 1.65 1.65 0 0 0-1 1.51V21a2 2 0 0 1-2 2 2 2 0 0 1-2-2v-.09A1.65 1.65 0 0 0 9 19.4a1.65 1.65 0 0 0-1.82.33l-.06.06a2 2 0 0 1-2.83 0 2 2 0 0 1 0-2.83l.06-.06a1.65 1.65 0 0 0 .33-1.82 1.65 1.65 0 0 0-1.51-1H3a2 2 0 0 1-2-2 2 2 0 0 1 2-2h.09A1.65 1.65 0 0 0 4.6 9a1.65 1.65 0 0 0-.33-1.82l-.06-.06a2 2 0 0 1 0-2.83 2 2 0 0 1 2.83 0l.06.06a1.65 1.65 0 0 0 1.82.33H9a1.65 1.65 0 0 0 1-1.51V3a2 2 0 0 1 2-2 2 2 0 0 1 2 2v.09a1.65 1.65 0 0 0 1 1.51 1.65 1.65 0 0 0 1.82-.33l.06-.06a2 2 0 0 1 2.83 0 2 2 0 0 1 0 2.83l-.06.06a1.65 1.65 0 0 0-.33 1.82V9a1.65 1.65 0 0 0 1.51 1H21a2 2 0 0 1 2 2 2 2 0 0 1-2 2h-.09a1.65 1.65 0 0 0-1.51 1z"/></svg>
</button>
<div className="avatar" aria-label="Benutzer Leopold M." title="Leopold M.">LM</div>
</div>
</header>