Öffnung: ⚙-Knopf springt in den Tür-/Fenstertyp-Editor
Discoverability für die vertieften Bauteil-Typen: neben dem Typ-Dropdown einer gewählten Öffnung öffnet ein ⚙-Knopf das Ressourcen-Fenster direkt beim passenden Typeditor-Tab (Tür→doorStyles, Fenster→windowStyles). - ResourceManager: initialTab-Prop (springt auch bei bereits offenem Fenster auf den angeforderten Tab). - host.onEditOpeningType(kind) + App-Wiring (resourcesTab-State). tsc + vitest 620 grün.
This commit is contained in:
+9
-1
@@ -93,7 +93,7 @@ import { Viewport3D } from "./viewport/Viewport3D";
|
|||||||
import type { DisplayResolver, ViewportContextInfo } from "./viewport/Viewport3D";
|
import type { DisplayResolver, ViewportContextInfo } from "./viewport/Viewport3D";
|
||||||
import type { Pick3dHit } from "./viewport/Wasm3DViewport";
|
import type { Pick3dHit } from "./viewport/Wasm3DViewport";
|
||||||
import { ResourceManager } from "./ui/ResourceManager";
|
import { ResourceManager } from "./ui/ResourceManager";
|
||||||
import type { ResourceManagerHandlers } from "./ui/ResourceManager";
|
import type { ResourceManagerHandlers, TabId as ResourceTabId } from "./ui/ResourceManager";
|
||||||
import { LayoutSheetView } from "./ui/LayoutSheet";
|
import { LayoutSheetView } from "./ui/LayoutSheet";
|
||||||
import {
|
import {
|
||||||
createLayout,
|
createLayout,
|
||||||
@@ -408,6 +408,9 @@ export default function App() {
|
|||||||
// bleibt lokal. Wird über die Oberleiste geöffnet und über X / Hintergrund-
|
// bleibt lokal. Wird über die Oberleiste geöffnet und über X / Hintergrund-
|
||||||
// Klick / Esc geschlossen.
|
// Klick / Esc geschlossen.
|
||||||
const [resourcesOpen, setResourcesOpen] = useState(false);
|
const [resourcesOpen, setResourcesOpen] = useState(false);
|
||||||
|
// Angeforderter Start-Tab des Ressourcen-Fensters (z. B. „doorStyles", wenn man
|
||||||
|
// von einer gewählten Tür in den Typeditor springt).
|
||||||
|
const [resourcesTab, setResourcesTab] = useState<ResourceTabId>("components");
|
||||||
|
|
||||||
// Aktives Layout-Blatt im HAUPT-Viewport (DOSSIER A3, Phase 2b): Id des offenen
|
// Aktives Layout-Blatt im HAUPT-Viewport (DOSSIER A3, Phase 2b): Id des offenen
|
||||||
// Layouts oder null (= normale Modell-Ansicht). Transienter UI-State; das
|
// Layouts oder null (= normale Modell-Ansicht). Transienter UI-State; das
|
||||||
@@ -3109,6 +3112,10 @@ export default function App() {
|
|||||||
if (selection?.kind === "opening")
|
if (selection?.kind === "opening")
|
||||||
updateOpening(selection.id, { typeId: typeId || undefined });
|
updateOpening(selection.id, { typeId: typeId || undefined });
|
||||||
},
|
},
|
||||||
|
onEditOpeningType: (kind) => {
|
||||||
|
setResourcesTab(kind === "door" ? "doorStyles" : "windowStyles");
|
||||||
|
setResourcesOpen(true);
|
||||||
|
},
|
||||||
// ── Treppen-Attribute (nur bei selektierter Treppe) ────────────────────
|
// ── Treppen-Attribute (nur bei selektierter Treppe) ────────────────────
|
||||||
onSetStairShape: (shape) => {
|
onSetStairShape: (shape) => {
|
||||||
if (selection?.kind === "stair") updateStair(selection.id, { shape });
|
if (selection?.kind === "stair") updateStair(selection.id, { shape });
|
||||||
@@ -4910,6 +4917,7 @@ export default function App() {
|
|||||||
<ResourceManager
|
<ResourceManager
|
||||||
project={project}
|
project={project}
|
||||||
handlers={resourceHandlers}
|
handlers={resourceHandlers}
|
||||||
|
initialTab={resourcesTab}
|
||||||
onClose={() => setResourcesOpen(false)}
|
onClose={() => setResourcesOpen(false)}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
|
|||||||
@@ -340,6 +340,7 @@ export const de = {
|
|||||||
// ── Öffnungs-Attribute (Object-Info-Panel) ──────────────────────────────
|
// ── Öffnungs-Attribute (Object-Info-Panel) ──────────────────────────────
|
||||||
"objinfo.opening.section": "Öffnung",
|
"objinfo.opening.section": "Öffnung",
|
||||||
"objinfo.opening.type": "Typ",
|
"objinfo.opening.type": "Typ",
|
||||||
|
"objinfo.opening.editType": "Typ bearbeiten (Ressourcen)",
|
||||||
"objinfo.stair.type": "Typ",
|
"objinfo.stair.type": "Typ",
|
||||||
"objinfo.type.none": "(kein Typ)",
|
"objinfo.type.none": "(kein Typ)",
|
||||||
"objinfo.opening.kind": "Art",
|
"objinfo.opening.kind": "Art",
|
||||||
|
|||||||
@@ -340,6 +340,7 @@ export const en: Record<TranslationKey, string> = {
|
|||||||
// ── Opening attributes (object info panel) ──────────────────────────────
|
// ── Opening attributes (object info panel) ──────────────────────────────
|
||||||
"objinfo.opening.section": "Opening",
|
"objinfo.opening.section": "Opening",
|
||||||
"objinfo.opening.type": "Type",
|
"objinfo.opening.type": "Type",
|
||||||
|
"objinfo.opening.editType": "Edit type (Resources)",
|
||||||
"objinfo.stair.type": "Type",
|
"objinfo.stair.type": "Type",
|
||||||
"objinfo.type.none": "(no type)",
|
"objinfo.type.none": "(no type)",
|
||||||
"objinfo.opening.kind": "Type",
|
"objinfo.opening.kind": "Type",
|
||||||
|
|||||||
@@ -578,7 +578,8 @@ export function OpeningSection({
|
|||||||
<div className="objinfo-sep" />
|
<div className="objinfo-sep" />
|
||||||
<div className="objinfo-section-label">{t("objinfo.opening.section")}</div>
|
<div className="objinfo-section-label">{t("objinfo.opening.section")}</div>
|
||||||
|
|
||||||
{/* Tür-/Fenstertyp (Bibliothek) — je nach Art aus doorTypes bzw. windowTypes. */}
|
{/* Tür-/Fenstertyp (Bibliothek) — je nach Art aus doorTypes bzw. windowTypes.
|
||||||
|
Der ⚙-Knopf springt direkt in den Typeditor (Ressourcen-Fenster). */}
|
||||||
<div className="objinfo-field">
|
<div className="objinfo-field">
|
||||||
<span className="objinfo-flabel">{t("objinfo.opening.type")}</span>
|
<span className="objinfo-flabel">{t("objinfo.opening.type")}</span>
|
||||||
<Dropdown
|
<Dropdown
|
||||||
@@ -592,8 +593,17 @@ export function OpeningSection({
|
|||||||
).map((ty) => ({ value: ty.id, label: ty.name })),
|
).map((ty) => ({ value: ty.id, label: ty.name })),
|
||||||
]}
|
]}
|
||||||
title={t("objinfo.opening.type")}
|
title={t("objinfo.opening.type")}
|
||||||
width={130}
|
width={106}
|
||||||
/>
|
/>
|
||||||
|
<button
|
||||||
|
type="button"
|
||||||
|
className="objinfo-typebtn"
|
||||||
|
title={t("objinfo.opening.editType")}
|
||||||
|
aria-label={t("objinfo.opening.editType")}
|
||||||
|
onClick={() => host.onEditOpeningType(isDoor ? "door" : "window")}
|
||||||
|
>
|
||||||
|
⚙
|
||||||
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{/* Art-Segment Fenster/Tür. */}
|
{/* Art-Segment Fenster/Tür. */}
|
||||||
|
|||||||
@@ -294,6 +294,11 @@ export interface PanelHostValue {
|
|||||||
onSetOpeningLintelLines: (lintelLines: "keine" | "innen" | "aussen" | "beide") => void;
|
onSetOpeningLintelLines: (lintelLines: "keine" | "innen" | "aussen" | "beide") => void;
|
||||||
/** Weist der Öffnung einen Tür-/Fenstertyp (Bibliothek) zu; "" löst die Zuweisung. */
|
/** Weist der Öffnung einen Tür-/Fenstertyp (Bibliothek) zu; "" löst die Zuweisung. */
|
||||||
onSetOpeningType: (typeId: string) => void;
|
onSetOpeningType: (typeId: string) => void;
|
||||||
|
/**
|
||||||
|
* Öffnet das Ressourcen-Fenster direkt beim Tür- bzw. Fenstertyp-Editor
|
||||||
|
* (Discoverability: von der gewählten Öffnung in den Typeditor springen).
|
||||||
|
*/
|
||||||
|
onEditOpeningType: (kind: "door" | "window") => void;
|
||||||
|
|
||||||
// ── Treppen-Attribute (Object-Info-Panel; nur die selektierte Treppe) ───
|
// ── Treppen-Attribute (Object-Info-Panel; nur die selektierte Treppe) ───
|
||||||
/** Setzt die Grundform (gerade/L/Wendel). */
|
/** Setzt die Grundform (gerade/L/Wendel). */
|
||||||
|
|||||||
@@ -4044,6 +4044,24 @@ body {
|
|||||||
letter-spacing: 0.04em;
|
letter-spacing: 0.04em;
|
||||||
margin: 2px 2px 4px;
|
margin: 2px 2px 4px;
|
||||||
}
|
}
|
||||||
|
/* „Typ bearbeiten"-Knopf (⚙) neben dem Öffnungstyp-Dropdown. */
|
||||||
|
.objinfo-typebtn {
|
||||||
|
margin-left: 4px;
|
||||||
|
width: 22px;
|
||||||
|
height: 22px;
|
||||||
|
padding: 0;
|
||||||
|
border: 1px solid var(--border, #444);
|
||||||
|
border-radius: 4px;
|
||||||
|
background: transparent;
|
||||||
|
color: var(--fg, inherit);
|
||||||
|
cursor: pointer;
|
||||||
|
font-size: 12px;
|
||||||
|
line-height: 1;
|
||||||
|
}
|
||||||
|
.objinfo-typebtn:hover {
|
||||||
|
background: var(--hover, rgba(127, 127, 127, 0.18));
|
||||||
|
}
|
||||||
|
|
||||||
/* Mess-Werkzeug: Live-Messwerte im Objekt-Info-Panel. */
|
/* Mess-Werkzeug: Live-Messwerte im Objekt-Info-Panel. */
|
||||||
.objinfo-measure {
|
.objinfo-measure {
|
||||||
margin: 2px 2px 8px;
|
margin: 2px 2px 8px;
|
||||||
|
|||||||
@@ -2951,7 +2951,7 @@ function EmptyState({ text }: { text: string }) {
|
|||||||
|
|
||||||
// ── Manager-Schublade ──────────────────────────────────────────────────────
|
// ── Manager-Schublade ──────────────────────────────────────────────────────
|
||||||
|
|
||||||
type TabId =
|
export type TabId =
|
||||||
| "components"
|
| "components"
|
||||||
| "hatches"
|
| "hatches"
|
||||||
| "lines"
|
| "lines"
|
||||||
@@ -3064,12 +3064,20 @@ export function ResourceManager({
|
|||||||
project,
|
project,
|
||||||
onClose,
|
onClose,
|
||||||
handlers,
|
handlers,
|
||||||
|
initialTab,
|
||||||
}: {
|
}: {
|
||||||
project: Project;
|
project: Project;
|
||||||
onClose: () => void;
|
onClose: () => void;
|
||||||
handlers: ResourceManagerHandlers;
|
handlers: ResourceManagerHandlers;
|
||||||
|
/** Beim Öffnen (bzw. bei erneutem Sprung) direkt aktiver Tab, z. B. „doorStyles". */
|
||||||
|
initialTab?: TabId;
|
||||||
}) {
|
}) {
|
||||||
const [tab, setTab] = useState<TabId>("components");
|
const [tab, setTab] = useState<TabId>(initialTab ?? "components");
|
||||||
|
// Erneuter Sprung aus einem Element heraus (z. B. „Typ bearbeiten" an einer
|
||||||
|
// Öffnung): auf den angeforderten Tab wechseln, auch wenn das Fenster schon offen ist.
|
||||||
|
useEffect(() => {
|
||||||
|
if (initialTab) setTab(initialTab);
|
||||||
|
}, [initialTab]);
|
||||||
const [rect, setRect] = useState<WindowRect>(initialRect);
|
const [rect, setRect] = useState<WindowRect>(initialRect);
|
||||||
|
|
||||||
// Verschieben über die Kopfzeile: Cursor − linke/obere Kante festhalten und die
|
// Verschieben über die Kopfzeile: Cursor − linke/obere Kante festhalten und die
|
||||||
|
|||||||
Reference in New Issue
Block a user