diff --git a/src/i18n/de.ts b/src/i18n/de.ts index 69d2ed6..8fcfc51 100644 --- a/src/i18n/de.ts +++ b/src/i18n/de.ts @@ -319,8 +319,17 @@ export const de = { "objinfo.room.editStamp": "Stempel bearbeiten …", "objinfo.wall.floorAboveNone": "Kein oberes Geschoss", "levels.addFloor": "+ Geschoss", + "levels.addSection": "+ Schnitt", + "levels.addElevation": "+ Ansicht", "levels.addDrawing": "+ Zeichnung", "layers.addCategory": "+ Ebene", + + // ── Zeichnungsebenen: Kategorie-Titel (einklappbare Gruppen) ───────────── + "levelCat.floor": "Geschosse", + "levelCat.section": "Schnitte", + "levelCat.elevation": "Ansichten", + "levelCat.drawing": "2D-Zeichnungen", + "levelCat.collapse": "Kategorie ein-/ausklappen", "nav.visibility": "Sichtbarkeit", "nav.hide": "Ausblenden", "nav.show": "Einblenden", @@ -417,6 +426,8 @@ export const de = { // ── Default-Namen neuer Elemente ───────────────────────────────────────── "default.floorName": "Geschoss {n}", + "default.sectionName": "Schnitt {n}", + "default.elevationName": "Ansicht {n}", "default.drawingName": "Zeichnung {n}", "default.categoryName": "Neue Ebene", "default.subCategoryName": "Neue Sub-Ebene", @@ -475,7 +486,9 @@ export const de = { "resources.components.placeholder": "Bauteil", "resources.col.name": "Name", "resources.col.color": "Farbe", - "resources.col.hatch": "Schraffur", + "resources.col.hatch": "Schnittschraffur", + "resources.col.viewHatch": "Ansichtsschraffur", + "resources.viewHatch.none": "(keine)", "resources.col.prio": "Prio", "resources.col.prio.hint": "Höhere Priorität läuft am Stoß durch", "resources.col.texture": "Textur", diff --git a/src/i18n/en.ts b/src/i18n/en.ts index 242af7b..fa3f277 100644 --- a/src/i18n/en.ts +++ b/src/i18n/en.ts @@ -317,8 +317,17 @@ export const en: Record = { "objinfo.room.refFloor": "Reference floor", "objinfo.room.editStamp": "Edit stamp …", "levels.addFloor": "+ Floor", + "levels.addSection": "+ Section", + "levels.addElevation": "+ Elevation", "levels.addDrawing": "+ Drawing", "layers.addCategory": "+ Layer", + + // Drawing levels: category titles (collapsible groups). + "levelCat.floor": "Floors", + "levelCat.section": "Sections", + "levelCat.elevation": "Elevations", + "levelCat.drawing": "2D drawings", + "levelCat.collapse": "Collapse/expand category", "nav.visibility": "Visibility", "nav.hide": "Hide", "nav.show": "Show", @@ -414,6 +423,8 @@ export const en: Record = { // Default names. "default.floorName": "Floor {n}", + "default.sectionName": "Section {n}", + "default.elevationName": "Elevation {n}", "default.drawingName": "Drawing {n}", "default.categoryName": "New layer", "default.subCategoryName": "New sub-layer", @@ -471,7 +482,9 @@ export const en: Record = { "resources.components.placeholder": "Component", "resources.col.name": "Name", "resources.col.color": "Color", - "resources.col.hatch": "Hatch", + "resources.col.hatch": "Section hatch", + "resources.col.viewHatch": "View hatch", + "resources.viewHatch.none": "(none)", "resources.col.prio": "Prio", "resources.col.prio.hint": "Higher priority runs through at the join", "resources.col.texture": "Texture", diff --git a/src/model/types.ts b/src/model/types.ts index 5c5753b..2369b90 100644 --- a/src/model/types.ts +++ b/src/model/types.ts @@ -108,8 +108,15 @@ export interface Component { name: string; /** Füllfarbe im Grundriss (Poché) und 3D-Diffusfarbe. */ color: string; - /** Schnitt-Schraffur → Hatch Manager. */ + /** Schnitt-Schraffur → Hatch Manager. Gilt, wo das Bauteil echt geschnitten ist. */ hatchId: string; + /** + * Ansichts-Schraffur → Hatch Manager. Gilt, wo das Bauteil frontal/ungeschnitten + * gesehen wird (z. B. Deckenpoché im Grundriss: die Decke liegt über der + * horizontalen Schnittebene und wird von unten gesehen, nicht aufgeschnitten). + * Leer/`undefined` ⇒ keine Schraffur (weiss). + */ + viewHatchId?: string; /** Optionale 3D-Textur (vorerst ignoriert). */ texture3d?: string; /** diff --git a/src/plan/generatePlan.ts b/src/plan/generatePlan.ts index 79d662e..15b63b0 100644 --- a/src/plan/generatePlan.ts +++ b/src/plan/generatePlan.ts @@ -1200,8 +1200,9 @@ function addReferenceLine(out: Primitive[], wall: Wall, greyed: boolean): void { * Schichtaufbau einer Decke in Z (oben → unten) — von oben unsichtbar. Die * Schichtbänderung erscheint daher NUR im Schnitt (siehe `toSection.ts`), nicht * hier. Im Detailgrad „grob" entfällt die Schraffur (nur Fläche + Umriss); - * „mittel"/„fein" zeigen die Component-Schraffur. `lwMm` ist die Kategorie- - * Strichstärke. + * „mittel"/„fein" zeigen die Ansichts-Schraffur des Bauteils (`viewHatchId`, + * Default weiss) — die frontal gesehene Aufsicht ist kein Schnitt. `lwMm` ist + * die Kategorie-Strichstärke. */ function addCeilingPoche( out: Primitive[], @@ -1219,11 +1220,16 @@ function addCeilingPoche( const outlineMm = lwMm * OUTLINE_DETAIL_FACTOR[detail]; const ceilingId = ceiling.id; - // Gefüllte Fläche, ohne Schraffur: die Decke wird im Grundriss frontal von - // oben gesehen, nicht aufgeschnitten — Bauteil-Schraffuren gehören nur auf - // Schnittflächen (siehe resolveCeilingSectionStyle/splitSlabLayers), nicht - // auf die Aufsicht. - const hatch = NO_HATCH; + // Gefüllte Fläche mit der Ansichts-Schraffur: die Decke wird im Grundriss + // frontal von unten gesehen, nicht aufgeschnitten — daher greift hier + // NICHT die Schnitt-Schraffur (die gehört auf echte Schnittflächen, siehe + // resolveCeilingSectionStyle/splitSlabLayers), sondern `viewHatchId`. Fehlt + // sie (Default), bleibt die Aufsicht weiss. Im Detailgrad „grob" entfällt + // die Schraffur ganz (nur Fläche + Umriss). + const hatch = + detail !== "grob" && comp?.viewHatchId + ? resolveHatch(project, comp.viewHatchId) + : NO_HATCH; const solid = hatch.pattern === "solid"; out.push({ kind: "polygon", diff --git a/src/ui/ResourceManager.tsx b/src/ui/ResourceManager.tsx index ade9e3c..2936ca8 100644 --- a/src/ui/ResourceManager.tsx +++ b/src/ui/ResourceManager.tsx @@ -283,11 +283,12 @@ function ResCell({ // ── Bauteile (Components) ────────────────────────────────────────────────── -// Spalten: Name | Farbe | Schraffur | Prio | Textur | Material | (löschen). +// Spalten: Name | Farbe | Schnittschraffur | Ansichtsschraffur | Prio | Textur | Material | (löschen). const COMPONENT_COLUMNS: ResColumn[] = [ { titleKey: "resources.col.name" }, { titleKey: "resources.col.color" }, { titleKey: "resources.col.hatch" }, + { titleKey: "resources.col.viewHatch" }, { titleKey: "resources.col.prio", align: "right", @@ -298,7 +299,7 @@ const COMPONENT_COLUMNS: ResColumn[] = [ { titleKey: "" }, ]; const COMPONENT_TEMPLATE = - "minmax(120px, 1fr) auto minmax(120px, 0.8fr) 64px minmax(90px, 0.7fr) minmax(130px, 0.9fr) 36px"; + "minmax(120px, 1fr) auto minmax(120px, 0.8fr) minmax(120px, 0.8fr) 64px minmax(90px, 0.7fr) minmax(130px, 0.9fr) 36px"; /** * Material-Zelle der Bauteil-Tabelle: ein Button, der den aktuellen Material- @@ -766,6 +767,11 @@ function ComponentRow({ onDelete: () => void; }) { const hatchOptions = hatches.map((h) => ({ value: h.id, label: h.name })); + // Ansichts-Schraffur ist optional; Leer-Eintrag = keine Schraffur (weiss). + const viewHatchOptions = [ + { value: "", label: t("resources.viewHatch.none") }, + ...hatchOptions, + ]; return ( @@ -788,6 +794,13 @@ function ComponentRow({ options={hatchOptions} /> + + onPatch({ viewHatchId: viewHatchId || undefined })} + options={viewHatchOptions} + /> +