Files
Aislo/M02_MasterTemplete/M02_MasterTemplete_UI_Side_Precombo.ts
T
eomsangdonandClaude Opus 5.5 9d9955631f feat(M02): 일위대가 조합 서고 — 좌측 항목 둘 · 상세 목록표(51-4)
- 좌측 컨테이너 = 층 단추 + 「단가산출 승격」 · 「일위대가 사전조합」 항목만 · 새로 · 본떠 · 지우기 단추 없앰
- 항목 누름 = 상세 칸 목록표(고름 · 키 · 이름 · 단위 · 기준 금액 · 고친 날) · 줄 누름 = 그 문서 상세
- 머리 [생성] · [복사](고른 줄) · [삭제](고른 줄 · 쓰는 곳 있으면 서버 까닭 알림)
- 층 목록 서고 줄에 1 단위 기준 계(`기준금액`) 실음 · 시험 한 개 · 화면 시나리오 51-4

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016PSXsvyDxjNmufteN5bqmt
2026-10-05 19:39:07 +09:00

69 lines
2.5 KiB
TypeScript

/* =============================================================================
* M02_MasterTemplete_UI_Side_Precombo.ts
* 좌측 「일위대가 조합」 컨테이너(50-3 ③ · 51-4) — 구조물 조합 아래 · 층 단추(페이지가 만듦) ·
* 항목 둘 「단가산출 승격」(promote) · 「일위대가 사전조합」(precombo)만.
* 항목 누름 = 상세 칸에 그 종류 목록표(`Library_List` · 생성 · 복사 · 삭제는 거기) ·
* 표 줄 누름 = 편집 칸(UI_Main 종류 promote · precombo = 일위대가 상세 모드).
* ========================================================================== */
import { el } from "@ui/ui_template_elements";
import type { Kind, Layer } from "./M02_MasterTemplete_Api_Fetch";
import { tc } from "./M02_MasterTemplete_Labor_Text";
import type { Selection } from "./M02_MasterTemplete_UI_Main";
export type PrecomboKind = Extract<Kind, "promote" | "precombo">;
const PARTS = [
{ kind: "promote", label: "Lib_Promote" },
{ kind: "precombo", label: "Lib_PrecomboAll" },
] as const;
export const PRECOMBO_TITLE = "일위대가 조합";
export const isPrecombo = (kind: Kind): kind is PrecomboKind =>
kind === "promote" || kind === "precombo";
export interface PrecomboOptions {
layer: Layer;
/** 층 단추 줄(페이지가 만듦 · 누르면 그 층 화면 + 이 컨테이너 펼침) */
bar: HTMLElement[];
confirmLeave: () => Promise<boolean>;
onOpen: (sel: Selection | null) => void;
/** 이 층에서 지금 열린 종류(목록이든 문서든) — 항목 고름 표시 */
openKind: () => Kind | null;
}
export interface PrecomboHandle {
body: HTMLElement;
paint: () => void;
}
export function buildPrecomboSection(opt: PrecomboOptions): PrecomboHandle {
const items = PARTS.map((part) => {
const b = el("button", {
className: "m02-side__item ui-sidebar-row",
text: tc(part.label),
attrs: { type: "button", "data-precombo": part.kind },
});
// 이름 "" = 목록표(UI_Main)
b.addEventListener("click", async () => {
if (!(await opt.confirmLeave())) return;
opt.onOpen({
layer: opt.layer,
projectId: null,
kind: part.kind,
name: "",
label: tc(part.label),
});
});
return b;
});
const body = el("div", {
className: "m02-side__items ui-sidebar-list",
children: [...opt.bar, ...items],
});
const paint = (): void => {
const on = opt.openKind();
items.forEach((b, i) => b.classList.toggle("is-active", PARTS[i].kind === on));
};
return { body, paint };
}