- Boden-Grid-Fläche auf y = baseElevation des aktiven Geschosses,
ein-/ausschaltbar (Overlay-Button im Viewport, State in viewSlice
grid3dVisible). Eigene LineList-Pipeline in der Engine (grid.rs,
GRID_WGSL, geteilte View-Projection/Depth mit der Mesh-Pipeline),
neue set_ground_grid(visible, elevation, extent, spacing)-Methode.
Minor-Linien dezent, jede 5. als Major betont.
- Kamera-Steuerung überarbeitet (vorher nur Mitte=Orbit, Pan auf
Shift+Mitte versteckt): Links=Orbit, Mitte/Rechts=Pan (bewegen),
Rad=Zoom zum Cursor. Laptop-freundlich, konsistent mit der
2D-Plan-Navigation (dort Mitte=Pan).
- "+ Text"-Knopf entfernt (war ohnehin immer deaktiviert, kein Werkzeug
dahinter — Text wird ein eigenständiges Zeichenwerkzeug, AUDIT B1).
An seiner Stelle ein Zeilenhöhe-Regler (Stepper, Vielfaches der
Schriftgrösse) — neues Paragraph.lineHeight, durchgereicht bis in
HTML-Vorschau (line-height) und SVG-Render (kumulierte Zeilen-
Vorschübe statt festem lineGap).
- Linienstil im Attribute-Panel war rein informativ (kein Setter im
Host-Kontrakt). onSetSelectionLineStyle ergänzt (nur Drawing2D),
jetzt echtes Dropdown statt "—"-Anzeige.
- docs/design/dossier-feature-audit.md: der ausführliche A1-A6/B1-B4/
C1-C3/D1-D3/E-Auditbericht aus einer alten Session gesichert (lag
bisher nur im Transkript, nicht im Repo) — Quelle der HANDOVER.md-
AUDIT-Kürzel.
Text-Werkzeug nutzte bisher OS-abhängige Systemfonts (Helvetica/Arial/
Times/Georgia/Courier) — Darstellung und PDF-Export waren damit nicht
plattformunabhängig deterministisch. Jetzt 15 kuratierte SIL-OFL-
Schriften lokal als WOFF2 gebündelt (je mit OFL.txt-Lizenz):
Inter, Work Sans, IBM Plex Sans/Mono, Source Sans 3, Space Grotesk,
Manrope, Outfit, DM Sans, Public Sans, Karla, Rubik, Jost, Archivo,
Source Serif 4. Ein späterer Einstellungen-Dialog kann weitere
Schriften nachladen.
ColorHexField (neu, geteilt) trennt die zwei Klickziele: Swatch/
natives Farb-Input öffnet weiter den Picker, der Hex-Text daneben ist
jetzt ein eigenes Eingabefeld (Enter übernimmt, Esc verwirft, ungültige
Eingabe fällt auf den letzten gültigen Wert zurück). Ersetzt die
bisherige reine Text-Anzeige in SettingsDialog + AttributesPanel.
- Marke (DOSSIER-Wortmarke) + Ressourcen-Icon ganz links, wie im
Rhino-Plugin; Settings-Icon folgt über den neuen Einstellungs-Dialog.
- Massstab/Zoom-Cluster bereinigt: doppelte Massstab-Dropdown entfernt,
Zoom-Aktionen unter dem Massstab-Dropdown gestapelt (gleiche Breite),
Ring bei "am Massstab" statt Flächen-Aufhellung.
- PDF/DXF-Export aus der Leiste raus, zusammen mit Speichern/Öffnen/
Import in einem neuen Datei-Burger-Menü ganz rechts. Speichern/Öffnen
sind echte JSON-Download/-Upload-Handler fürs ganze Projekt.
- Einstellungs-Fenster (neu): Accent-Palette, Auswahlrahmen-/Snap-Farbe
editierbar (freier Picker + Presets), Projekt-Referenzhöhe (m ü. M.)
als Feld.
- LayoutMenu auf die eigene Dropdown-Komponente umgestellt (war noch
natives <select>).
- Custom Fenstersteuerung (_/□/X) für die randlose Electron-Shell via
Preload+IPC, eigener Look statt OS-Chrome; Oberleiste als Drag-Region.
- Dark-Theme ist jetzt fester Standard (vorher an OS-Präferenz
gekoppelt, zeigte je nach Umgebung fälschlich Light) — Light bleibt
als Opt-in (`[data-theme="light"]`) für einen künftigen Umschalter.
Alle Oberleisten-Pillen (Dropdown-Trigger, Segmente, Icon-Knöpfe,
Ansichts-Icons) auf dieselbe dunkle Fläche wie das Kontextmenü
vereinheitlicht. Panel-Köpfe nicht mehr separat aufgehellt, feste
Höhe (40px) unabhängig von optionalem Darstellungsmodus-Dropdown.
- 2D-Zoom-Grenzen deutlich erweitert (20000x/0.005x statt 50x/0.2x).
setProject wird jetzt von einer History gewrappt (undoStack/redoStack,
Limit 100). Echte Aenderungen (Referenzvergleich) landen auf dem
Undo-Stack, eine neue Aktion leert den Redo-Stack. Hochfrequente
Drag-Mutatoren (Griffe/Body-Move) bekommen einen coalesceKey, damit
ein Drag nicht hunderte Einzelschritte erzeugt. Tastatur-Bindung
(Ctrl+Z/Ctrl+Shift+Z/Ctrl+Y) folgt im TopBar-Commit (App.tsx).
Mehrere Stellen (ResourceManager SelectField + Material-Browser,
ImportDialog, AttributesPanel, SitePanel, ToolsPanel,
DisplayModeSelect, RichTextEditor) nutzten noch native <select>, deren
Optionsliste vom Betriebssystem gerendert wird und optisch nicht zur
eigenen Dropdown-Komponente (dunkles Kontextmenü-Popover) passt. Jetzt
durchgaengig dieselbe Optik.
Bisher zeigte nur three.js importierte Gebaeude/DXF-Meshes und das
Terrain-TIN (Project.context). Neuer MeshInput-Typ + Kontext-Mesh-Pfad
in render3d (Flat-Normalen, doppelseitig gegen unbekanntes Winding),
projectToModel3d speist project.context jetzt in beide Renderer
(nativ + WASM) ein. Nebenbei: fehlendes layers-Feld in demo_walls()
behoben, das den native3d-Feature-Build zuvor schon brach.
Wie bei Schraffuren/Linien/Wandstile: Liste links, Detail-Panel rechts.
Vorarbeit vor der eigentlichen Bauteil-Logik. Alte Tabellen-Bausteine
(ResTable/ResRow/ResCell/AddButton) entfernt, da nicht mehr genutzt.
Nach-Ebene-Schraffur war in der Resolve-Logik bereits fertig, aber
LayerCategory.hatch liess sich im Kategorie-Editor nicht setzen.
Dropdown mit Vorschau ergaenzt, patcht ueber patchCategory.
Die Grenzlinien zwischen den Wandschichten (achsparallel, aus der addWallPoche-
Offset-Logik gespiegelt: refOff-total/2, je Schicht +thickness, n+1 Linien inkl.
Aussenflaechen) werden als Snap-Segmente in collectSegments eingereiht. Damit
fangen die bestehenden Snap-Arten (Endpunkt/Mittelpunkt/Schnittpunkt/Lot)
automatisch daran — Decken/Elemente koennen an einzelnen Wandschichten fangen.
Kein neuer SnapKind/Toggle noetig (Default-aktiv). 4 neue Tests, 156 gruen.
Vordergrund, Hintergrund, Strichstaerke und Schraffur je Element (Wand/Decke/
Drawing2D) haben jetzt einen 3-Wege-Quellen-Dropdown: Nach Ebene / Nach
Bauteil / eigener Wert. Aufloesungsreihenfolge: expliziter Wert > (Quelle
'layer' => LayerCategory-Wert color/lw/hatch) > Bauteil/LineStyle-Default.
Neue *Source-Felder + strokeWeight/hatchId-Overrides am Modell (additiv,
optional), getLayerCategory-Accessor, resolveHatchId/resolveStrokeWeight;
resolveForeground/Background um category+source erweitert. Sample rendert
identisch (kein Override/Source gesetzt => Default 'object' = altes Verhalten).
Offen: LayerCategory-Schraffur noch nicht im Kategorie-Dialog editierbar.
Wand- und Deckenstile bekommen dasselbe Master-Detail wie Schraffuren/Linien:
Liste links mit Querschnitt-Thumbnail + Name, Detail rechts mit grossem
Querschnitt und Aufbau-Editor (Schichten: Bauteil/Dicke/Fugenlinie,
hinzufuegen/entfernen/umordnen), Inline-Rename, Trash-Delete, Neu anlegen.
Neuer WallTypeSwatch (hatchPreview) zeichnet die geschichtete Wand/Decke als
proportionale Baender mit den Bauteil-Schnittschraffuren. Add/Delete-Handler
(addWallType/deleteWallType/addCeilingType/deleteCeilingType, In-Use-Schutz)
in App.tsx + host ergaenzt.
Wo sich Schicht-Baender verschiedener Elemente im Schnitt ueberlappen, gewinnt
die staerkere Schicht (hoehere joinPriority) und schneidet die schwaechere per
Rechteck-Subtraktion weg (elementuebergreifend: die Betondecke schneidet den
Wand-Putz). Gleiche Prioritaet koexistiert (durchgehende Betonflaeche Wand+
Decke). attachCutStyles sammelt jetzt alle Baender mit joinPriority und laesst
subtractDominantBands global gegen alle staerkeren Cutter subtrahieren; die
ueberlappungsfreie Zerlegung liefert exakt die Material-/Fugenlinien zwischen
den Schichten. Neuer subtractRect-Helfer, 11 neue Tests, 152 gruen.
splitWallLayers legte die Schichtbaender bisher fix layers[0]->uMin, ohne die
tatsaechliche Wandorientierung — gegenueberliegende Waende sahen identisch aus
statt gespiegelt. Jetzt wird die Aufbaurichtung aus der Grundriss-Konvention
gespiegelt (Schichten stapeln entlang leftNormal der Wandachse), gegen die
Schnitt-u-Weltachse (aus der SectionPlane) projiziert; ist das Skalarprodukt
negativ, wird die Bandreihenfolge umgekehrt (layers[0]->uMax). Damit liegt die
Daemmung aussen, der Backstein innen, und gegenueberliegende Waende sind
spiegelbildlich. Neue Helfer sectionUAxisModel/wallLayersReversedInU, additiv
durch attachCutStyles durchgereicht. 6 neue Tests, 141 gruen.
Gebaeude-Footprints (swisstopo vec25) werden jetzt zu Volumen extrudiert
(z=0 bis Hoehe; Hoehe aus OSM height/building:levels, sonst 9 m; Deckel/
Boden via Delaunay, konkave Grundrisse) und als importedMesh gerendert — der
flache Footprint-contourSet bleibt fuer den 2D-Plan erhalten. Neuer
Terrain-Abruf (swissALTI3D ueber den CORS-faehigen profile.json-Dienst,
zeilenweise parallel) liefert ein N-Raster, das terrainMeshFromGrid
trianguliert; Hoehen aufs Zentrum bezogen, lagerichtig zu den Gebaeuden.
Neue Quelle 'Swisstopo-Gelaende' im Import-Dialog. Viewport3D unveraendert
(bestehender importedMesh/terrainMesh-Pfad). 8 neue Tests.
Der Ressourcen-Editor ist von einem blockierenden Modal (dunkler Backdrop,
Canvas gesperrt) zu einem frei schwebenden Fenster geworden: verschiebbar
ueber die Kopfzeile (Pointer-Capture-Drag), unten rechts resizable, KEIN
Backdrop — der Plan bleibt bedienbar, sodass Schraffur-/Linien-Aenderungen
live am Modell sichtbar sind. Der Ressourcen-Button bleibt Toggle, Esc
schliesst weiter. FloatingPanel-Bausteine wiederverwendet; die interne
Tab-/Master-Detail-Struktur unveraendert.
Der Linien-Editor ist modular: eine Linie ist eine geordnete, loopende Folge
aus Segmenten Strich (Laenge), Punkt (Dot) und Luecke (Laenge) — beliebige
Sequenzen (Volllinie/Strichlinie/Punktlinie/Strich-Punkt als Presets, plus
frei), die Schluss-Luecke ist die letzte Luecke. Datenbasis bleibt
LineStyle.dash (mm, alternierend); ein Punkt ist ein 0-Laengen-AN-Segment.
Enthaelt dash eine 0, wird die Linie mit runder Kappe gezeichnet, damit
Punkte als Dots erscheinen (Live + Print; GL/DXF Folgearbeit). Neue reine
Segment-Logik in ui/lineSegments.ts. LineSwatch zeigt den ersten Loop dunkel
und 2 weitere grau (Loop-Kontext). 14 neue Tests, 127 gruen.
Random-Verankerung (Bugfix): die Streu-Striche haengen nicht mehr an der
Polygon-Bounding-Box, sondern an einem absoluten Modellraum-Gitter
(hashCell aus absoluten Zell-Indizes + hatch.seed). Beim Vergroessern der
Flaeche bleiben bestehende Striche stehen, am Rand kommen neue dazu, die
Dichte bleibt konstant, Verschieben wandert nicht; 'Neu wuerfeln' (neuer
Seed) verschiebt das ganze Feld. Alle Renderpfade ziehen aus derselben
Funktion. Verankerungs- und Verschiebe-Dichte-Test ergaenzt.
Motiv-Editor: neuer wiederverwendbarer MotifEditor (Punkte setzen/ziehen in
einer Einheitszelle, Live-Loop-Vorschau). LineStyle.kind 'custom' + motif
(points/length), additiv durchgereicht (analog zigzag) und in allen
Renderpfaden gekachelt (motifPoints, Verallgemeinerung von zigzagPoints).
ResourceManager-Umschalter Vollinie/Strich/Zickzack/Motiv, LineSwatch-
Vorschau. Insgesamt 5 neue Tests, 113 gruen.
Linien-Editor: Umschalter Vollinie (dash null) / Strich mit editierbarer
Segment-Liste (mm, alternierend Strich/Luecke, hinzufuegen/entfernen), Live-
Vorschau. Das Strichstaerken-Feld ist aus dem Linien-Editor entfernt —
LineStyle.weight ist @deprecated (bleibt Render-Fallback), die echte
per-Element-Aufloesung (Attribut->Ebene->Default) folgt separat.
Random-Schraffur: additive HatchStyle-Parameter seed/density/lengthMin/Max +
Neu-wuerfeln-Button (neuer Seed nur zur Editzeit). buildRandomHatchRuns mischt
den expliziten Seed in den Hash und nutzt Dichte/Laenge — Determinismus
gewahrt (gleicher Seed+Flaeche => gleiche Streuung), ueber alle Renderpfade
konsistent, da alle aus derselben Funktion ziehen. resolveHatch/HatchRender
reichen die Parameter rein additiv durch. 2 neue Tests.
Schraffuren- und Linien-Tab im Master-Detail-Layout (DOSSIER-Vorbild): Liste
links mit Live-SVG-Thumbnail + Name, Detail rechts mit grosser Live-Vorschau,
Inline-Rename, Trash-Delete, Typ-Umschalter. Schraffur: Vektor (parallel/
zufaellig) oder Bild (Upload -> Data-URL, scaleX/scaleY/rotation); kein
Farbfeld mehr (Farbe kommt von Bauteil/Attribut). Linie: Strich oder Zickzack
(Amplitude/Wellenlaenge). Bauteil-Tabelle: Vordergrund + Hintergrund statt
einer Farbe. Neuer eigenstaendiger Vorschau-Helfer ui/hatchPreview.tsx (kein
Renderer-Import).
Bild-Schraffur als getiltes <pattern>/<image> (scaleX/scaleY/rotation) im
Live-SVG- und Print-Pfad; GL/WASM/DXF vorerst neutraler Fallback (Folgearbeit,
im Code vermerkt). Random-Vektor-Schraffur als deterministische Streu-Striche
(mulberry32-Seed aus Flaechen-Bounding-Box, kein Math.random) in allen Pfaden.
Zickzack-Linie als getilteter Pfad; LineStyle.kind/zigzag additiv durch die
Linien-Emission (generatePlan) bis zu den Renderern durchgereicht. Geteilte
Geometrie in glPlanHatch (scatterStrokes/buildRandomHatchRuns/zigzagPoints) —
eine Wahrheit fuer Live/Print/GL/DXF. 8 neue Tests.
Die Attribut-Sektion 'Fuellung' zeigt statt der einen Fuellfarbe jetzt zwei
Felder: Vordergrund (Muster-/Schraffurfarbe) und Hintergrund (Fuellung),
jeweils per Element ueberschreibbar. Leerer Override = 'Nach System' (erbt);
Farbe waehlen setzt den Override, x loescht ihn wieder. Schreibt
Wall/Ceiling/Drawing2D.foreground/background ueber neue Store-Mutationen
(setElementForeground/Background), gespiegelt zum bestehenden Fuellfarbe-Pfad.
Die Resolve-Schicht (generatePlan) liest diese Overrides bereits, wirkt also
sofort im Plan.
Beim Verschieben einer Kante ueber den Dreiecks-Griff wird der Cursor jetzt
durch die Snap-Engine (snapFor) gefuehrt: bei einem Geometrie-Snap
(Endpunkt/Mittelpunkt/Schnittpunkt) wird der gefangene Punkt statt des rohen
Cursors auf die Kanten-Normale projiziert — die Kante rastet an reale
Geometrie statt nur ans Raster. Ohne Geometrie-Snap bleibt die bisherige
Raster-Rundung. Der freie Delta-Fall bleibt unveraendert.
Nummerntasten waehlen Zeichenwerkzeuge: 2 Linie, 4 Rechteck, 5 Polylinie,
6 Wand, 7 Decke, 8 Fenster, 9 Tuere, 0 Raum. Nur auf Geschoss-Tabs, nicht
beim Tippen in Feldern und nicht mit Ctrl/Cmd/Alt. 1 (Text) und 3 (Kreis)
bleiben vorerst frei — dafuer fehlt noch ein Werkzeug.
Die Zoom-Anzeige band 100% bisher an die eingepasste Default-Ansicht, nicht
an den angewandten Papier-Massstab — der Wert driftete willkürlich. Er wird
jetzt in App.tsx aus angewandtem Nenner und Live-Nenner abgeleitet
(scaleDenominator / liveScale * 100): im angewandten Massstab exakt 100%,
hineinzoomen >100%, herauszoomen <100%. Die fit-basierte onZoom-Meldekette
aus PlanView entfällt (Single Source).
An spitzen Wandecken wählte die Distanz-Heuristik in miterLine die falsche
B-Fläche und lieferte eine um 90° verdrehte Gehrungslinie — die Poché-Bänder
überlappten kreuzweise. Die Paarung erfolgt jetzt orientierungsbasiert: über
die Auslaufrichtungen der Achsen (dot(n, d)) wird Aussenfläche mit Aussen-,
Innen mit Innenfläche verschnitten, nie über Kreuz — für jeden Winkel. Rechte
und stumpfe Ecken bleiben bit-identisch (Rust-Parität gewahrt). Kein
Miter-Limit; die Gehrungslinie ist geometrisch exakt. Neuer Test joins.test.ts
mit rechtwinkligem und spitzwinkligem Fall (fängt den alten Bug).
Der Referenzlinien-Schalter wandert aus der TopBar in die Statusleiste
(neben Fang) — dort passt er besser zu den übrigen Anzeige-/Fang-Kontrollen.
Die doppelt gezeigten Werte Massstab und Zoom fallen aus der Statusleiste
weg; sie stehen weiterhin im TopBar-Cluster. Die Ansichts-Icons blenden sich
auf Nicht-Geschoss-Ebenen (Schnitt/Ansicht/2D) nicht mehr komplett aus,
sondern bleiben sichtbar und werden nur deaktiviert.
Die Tab-Leiste zeigt je Panel nur noch ein Inline-SVG-Icon; der Titel
wandert in Tooltip (title) und aria-label. PanelDef bekommt ein optionales
icon-Feld, die sieben eingebauten Panels je ein schlichtes stroke-Icon
(currentColor, erbt die Tab-Farbe). Fehlt ein Icon (Plugin), fällt der Tab
auf den Titeltext zurück. Tabs sind jetzt kompakt und quadratisch; Klick-,
Drag- und Dock-Logik unverändert.
Analog zur Decke (splitSlabLayers) wird ein mehrschichtiger Wandtyp im
Schnitt nicht mehr mit einer repräsentativen Schraffur über die ganze
Dicke gefüllt, sondern in Schicht-Bänder zerlegt — quer zur Dicke entlang
u (volle Höhe je Band), jedes Band mit der Schnittschraffur seines
Bauteils. Einschicht-Wände laufen unverändert über resolveWallSectionStyle.
Seitenorientierung (aussen/innen) vorerst deterministisch layers[0]→uMin;
korrekte Orientierung via Wandnormale bleibt Folge-Iteration.
Die flache Ebenenliste ist in vier einklappbare Kategorien gegliedert —
Geschosse/Schnitte/Ansichten/2D-Zeichnungen nach drawingLevel.kind. Jeder
Kopf trägt ein Chevron und rechtsbündig ein blankes +-Glyph (kein
Button-Chrome), das je Kategorie eine neue Ebene der passenden Art anlegt;
leere Kategorien bleiben mit Kopf und + sichtbar. Für Schnitt und Ansicht
sind dafür neue Platzhalter-Aktionen addSection/addElevation ergänzt
(analog addFloor/addDrawing, noch ohne Schnittlinie).
Bauteil trägt jetzt zwei Schraffuren: die bestehende hatchId als
Schnittschraffur (nur wo tatsächlich aufgeschnitten) und ein neues
optionales Feld viewHatchId als Ansichtsschraffur für die frontale,
ungeschnittene Sicht. Die Deckenpoché im Grundriss — die Decke liegt
über der horizontalen Schnittebene, wird also frontal gesehen — nutzt
nun die Ansichtsschraffur (Default weiss/leer) statt pauschal keiner.
Schnitt-Pfade und die echt geschnittene Wand-Grundriss-Poché bleiben
auf der Schnittschraffur. Editierbar im Ressourcen-Manager.
Die Decke wird in der Aufsicht frontal gesehen, nicht aufgeschnitten
— Bauteil-Schraffuren gehoeren nur auf Schnittflaechen. Die neue
3-schichtige Betondecke zeigte sonst ihre dichte Schraffur ueber dem
ganzen Raum im Grundriss.
Analog zu den Wandstilen erhalten Decken jetzt einen eigenen
Deckentyp mit Schichtaufbau (CeilingType, ceilingTypeId). Der
Schichtaufbau erscheint nur im Schnitt als gestapelte Bänder von OK
bis UK; der Grundriss bleibt eine flächige Poché wie bisher, da die
Schichtung von oben ohnehin nicht sichtbar ist. Auswahl solide/
mehrschichtig im Objektinfo-Panel wie bei Wänden, neuer
"Deckenstile"-Tab im Ressourcen-Manager mit Fugenlinien je Schicht.
Bisher war viewType (Grundriss/Perspektive) ein einziger globaler
Wert. Beim Tab-Wechsel blieb er unverändert stehen, was wirkte, als
würde die Ansicht "durchsickern". Jede Ebene merkt sich jetzt ihren
zuletzt gewählten Ansichtstyp und stellt ihn beim Zurückwechseln
wieder her.
mesh.rs berechnet die Ecken-Verschneidung jetzt selbst (portiert aus dem
Web-Kern computeJoins/clippedBand): Wandenden werden per Rundungs-Key
gruppiert, ueber Hoehen-Ueberlappung geclustert (gestapelte Geschosse mit
gleichem Grundriss verschneiden sich NICHT), und Zweier-Cluster ueber die
gemeinsame Gehrungslinie geschnitten. T-/X-Stoesse und freie Enden bleiben
stumpf, wie im Web-Kern. Endkappen-Normalen geometrisch aus dem Kreuzprodukt.
WallInput bekommt optional layers (WallLayer{thickness,color}, serde-default,
rueckwaertskompatibel): jede Schicht wird als eigenes Band ueber dieselbe
gehrte Grundflaeche extrudiert und materialgefaerbt. toWalls3d.ts loest die
WallType-Schichten je Wand auf (hexToRgb) und reicht sie durch.
39/39 Rust-Tests (7 neue: Gehrung, T-Stoss, freies Ende, Schichten, Kombi).
Die alte Eigenschaften-Leiste (Geschosshoehe/Schnitthoehe/OKFF) weicht einer
Tab-Leiste 'Zeichnungen': ein Tab je Geschoss-Grundriss, Klick wechselt die
aktive Zeichnungsebene. Bindet an activeLevelId/setActiveLevelId — dieselbe
Store-Quelle wie das Panel 'Zeichnungsebenen', beide bleiben synchron.
Geschosshoehe/Schnitthoehe werden in den Geschoss-Einstellungen gepflegt.
Der Drawing-Typ (kind: 'plan') und der switch beim Aktivieren lassen spaeter
Schnitt-/Layout-Tabs zu, ohne die Leiste umzubauen.
Jede Stempelzeile (Name, Name-2, Bodenflaeche, Nutzung) hat jetzt eine
eigene Ausrichtung links/mitte/rechts, im Stempel-Editor pro Zeile
waehlbar und in SVG- wie nativer Darstellung honoriert (text-anchor bzw.
align). Bodenflaeche/Nutzung fallen auf mitte zurueck (bisheriges Bild).
Der Stempel-Anker (stampAnchor bzw. Schwerpunkt) meldet sich zusaetzlich
als Endpunkt-Snapkandidat an — gefiltert nach Geschoss und sichtbarer
Kategorie; der ziehbare Griff war bereits verdrahtet.
Die Kamera-Presets liefen zuvor als Viewport-Overlay mit eigenen JS-yaw/pitch-
Winkeln, rein perspektivisch (Iso falsch, keine Parallelprojektion). Jetzt
haengt der Engine-Viewport am app-weiten view3d-State (TopBar-CameraMenu, wie
three.js) und nutzt die vorhandene Rust-preset_camera:
- web.rs: set_view_preset(preset) + model_bounds/fit; Front/Top/Side echt
orthografisch, Iso/Perspektive perspektivisch - wie das native Fenster.
default_fov() pub(crate), damit Fit denselben FOV nutzt.
- useWasm3dRenderer: applyViewPreset; render(null) ueberschreibt die
Preset-Kamera nicht.
- Wasm3DViewport: konsumiert view3d/renderMode als Props (Overlay + lokaler
Umschalter entfernt, wasm3dOverlay.css geloescht); Orbit bleibt frei
(Preset = Sprung, kein Lock), three.js-Verhalten gespiegelt.
- Viewport3D-Switcher reicht view3d/renderMode an den Engine-Viewport durch
(kein three.js-Szenencode angefasst).
- Sample-Raum R1: boundary auf die echte Innenkante der Aussenwaende
(Achse +/- halbe Wanddicke 0.1725 bei Wandtyp aw 0.345 m) statt 0.1-Inset -
der Umriss lag bisher ~7 cm im Wandkoerper.
- Raumfarbe #5a7a9a -> neutrales Grau #6b7280 (Umriss + Stempel).
- ROOM_FILL_ALPHA 33 -> 00: keine transluzente Farbfuellung mehr
(Plandarstellung schwarz/grau); das Polygon bleibt fuer die Auswahl
erhalten (Hit-Test laeuft ueber pointInPolygon, nicht ueber die Fuellung).
Offen: automatische Ableitung der Raum-Boundary aus den Wand-Innenflaechen
fuer spaeter gezeichnete Raeume.
Der Engine-3D-Viewport (render3d/wgpu) war reines Ansehen (Orbit/Zoom). Jetzt:
- Kamera-Presets als Overlay: Top/Unten/Vorne/Hinten/Links/Rechts/Iso.
Richtungen exakt wie der three.js-Pfad (applyView3d); framen die aktuelle
Modell-Bounding-Box (fitTargetDist) und springen auf den Preset-Winkel,
danach Orbit/Pan/Zoom weiter frei. Rein JS.
- Render-Modus Schattiert/Weiss: mode-Uniform in Globals (WGSL/Rust),
Weiss = beleuchtetes Clay-Grau; wasm-Binding set_render_mode_white,
durchgereicht via useWasm3dRenderer.
- Overlay-CSS self-contained (wasm3dOverlay.css), Theme-aware.
three.js unangetastet. Auswahl/Grips/Zeichnen + Wireframe/HLR bewusst noch
offen (naechste Scheibe).
Mehrschichtige Waende zeichnen die Trennlinie an jeder Materialfuge jetzt mit
einem pro Fuge waehlbaren LineStyle statt einer festen Haarlinie.
- Layer.jointLineStyleId (optional): LineStyle der Fuge an der Innenkante
dieser Schicht; fehlt er, gilt die Default-Haarlinie (0.02) in Wandfarbe.
- generatePlan: Schicht-Baender tragen nur noch Fuellung + Schraffur (kein
Band-Umriss); jede innere Fuge wird als eigene Linie mit ihrem LineStyle
(Gewicht/Farbe/Dash, x Detailfaktor) gezeichnet. Wand-Umriss (0.35) und
grob-Pfad unveraendert.
- ResourceManager: neue Abteilung "Wandstile" - je Wandtyp die Schichten
mit Fugen-LineStyle-Dropdown.
- Sample: LineStyle "Schichtfuge 0.13"; der Daemmung-Backstein-Fuge (massiv/
massiv) zugewiesen, Putzfugen bleiben Haarlinie.
- 2 Joint-Tests ergaenzt.
Boegen (Tuer-Schwenkbogen) wurden mit fester Segmentzahl (16/90 Grad) beim
Kompilieren tesselliert und beim Zoom nur per Matrix neu gezeichnet - beim
Reinzoomen daher sichtbare Facetten. Jetzt skaliert die Segmentzahl mit der
Bildschirmgroesse des Bogens: Sagitta < 0.5 px (segs = clamp(ceil(|dPhi|/theta),
8, 2048)), theta = 2*acos(1 - 0.5/rPx). Weit weg wenige Segmente (Perf),
nah rund.
Anti-Thrash per LOD-Bucket round(log2(pxPerMeter)): Neu-Tessellierung nur
bei Bucket-Wechsel, sonst bleibt Zoom/Pan reiner Matrix-Update. Bogen laeuft
weiter durch strokePolyline - runde Caps/Joins bleiben erhalten.
Plandarstellung ist schwarz/grau; Farbe bleibt spaeteren Schemaelementen
vorbehalten.
- Tuerblatt, Schwenkbogen, Fensterscheibe und Anschlagstriche: einheitlich
#1a1a1a statt blau (#2b3039/#4a86c7/#6b7280), im render2d/PDF-Pfad
(CLS_STROKE) und im SVG-CSS.
- Schwenkbogen als Volllinie (Strichelung entfernt).
- Tuer-/Fenstersymbol-Linien auf Haarlinie 0.02 mm (SYMBOL_HAIRLINE_MM).
- Decken-Poche: Schraffur auf weissem Grund wie mehrschichtige Waende
(pocheFill), solid schwarz - nicht mehr die Bauteil-Fuellfarbe.
quantizePen hob bisher jede Breite <= 0.13 mm auf die unterste Stift-Stufe
(0.13 mm) an. Dadurch druckte die 0.02-mm-Schraffur/Schichtfuge im PDF und
im SVG-Print-Modus als 0.13 mm - im Viewport duenn, im Export dick.
Breiten unter MIN_PEN_MM gelten jetzt als bewusste Haarlinien und werden
exakt (unquantelt) durchgereicht; ab 0.13 mm rundet die Leiter wie gehabt.