260717_0
This commit is contained in:
@@ -1,4 +1,5 @@
|
||||
import "./ui_template_workflow_layout.css";
|
||||
import { t } from "./ui_template_locale";
|
||||
|
||||
export interface WorkflowStage {
|
||||
stage_no: number;
|
||||
@@ -13,7 +14,8 @@ export interface WorkflowLayoutOptions {
|
||||
leftPanel: HTMLElement;
|
||||
mainContent: HTMLElement;
|
||||
stages?: WorkflowStage[];
|
||||
routes?: string[];
|
||||
currentStage?: number;
|
||||
routes?: readonly string[];
|
||||
onStepClick?: (stepIndex: number, route: string) => void;
|
||||
onMenuToggle?: (isOpen: boolean) => void;
|
||||
onHeaderToggle?: (isVisible: boolean) => void;
|
||||
@@ -25,17 +27,22 @@ export interface WorkflowLayoutHandle {
|
||||
setHeaderVisible: (isVisible: boolean) => void;
|
||||
}
|
||||
|
||||
function createStepBar(
|
||||
export interface StepBarOptions {
|
||||
stages?: WorkflowStage[];
|
||||
currentStage?: number;
|
||||
routes?: readonly string[];
|
||||
compact?: boolean;
|
||||
onStepClick?: (stepIndex: number, route: string) => void;
|
||||
}
|
||||
|
||||
export function createStepBar(
|
||||
steps: readonly string[],
|
||||
activeStep: number,
|
||||
options?: {
|
||||
stages?: WorkflowStage[];
|
||||
routes?: string[];
|
||||
onStepClick?: (stepIndex: number, route: string) => void;
|
||||
},
|
||||
options?: StepBarOptions,
|
||||
): HTMLElement {
|
||||
const bar = document.createElement("div");
|
||||
bar.className = "ui-workflow-layout__steps";
|
||||
if (options?.compact) bar.classList.add("is-compact");
|
||||
steps.forEach((step, index) => {
|
||||
const button = document.createElement("button");
|
||||
button.type = "button";
|
||||
@@ -43,30 +50,32 @@ function createStepBar(
|
||||
if (index === activeStep) button.classList.add("is-active");
|
||||
button.textContent = step;
|
||||
|
||||
// 스텝바는 항상 자유롭게 이동 가능(게이팅하지 않음).
|
||||
// 단계 완료/무효화 판정은 사용자가 각 페이지의 액션 버튼(업로드·분석 실행 등)을
|
||||
// 눌렀을 때 백엔드가 계산·DB 갱신하며, 여기서는 그 결과를 색상/툴팁으로 표시만 한다.
|
||||
button.classList.add("is-enabled");
|
||||
const stage =
|
||||
options?.stages?.find((item) => item.stage_no === index) ?? options?.stages?.[index];
|
||||
const hasStages = Boolean(options?.stages?.length);
|
||||
const isEnabled =
|
||||
!hasStages || stage?.state !== "NOT_STARTED" || stage?.stage_no === options?.currentStage;
|
||||
button.classList.toggle("is-enabled", isEnabled);
|
||||
button.disabled = !isEnabled;
|
||||
|
||||
// state 기반 스타일링 (표시 전용)
|
||||
if (options?.stages && options.stages[index]) {
|
||||
const state = options.stages[index].state;
|
||||
if (stage) {
|
||||
const state = stage.state;
|
||||
button.classList.add(`state-${state.toLowerCase()}`);
|
||||
if (state === "STALE") {
|
||||
button.title = "Stale (하위 단계 변경으로 무효화됨)";
|
||||
button.title = t("WF_State_Stale");
|
||||
} else if (state === "FAILED") {
|
||||
button.title = "Failed (실패)";
|
||||
button.title = t("WF_State_Failed");
|
||||
} else if (state === "COMPLETE") {
|
||||
button.title = "Complete (완료)";
|
||||
button.title = t("WF_State_Complete");
|
||||
} else if (state === "IN_PROGRESS") {
|
||||
button.title = "In Progress (진행 중)";
|
||||
button.title = t("WF_State_InProgress");
|
||||
} else {
|
||||
button.title = "Not Started (미실행)";
|
||||
button.title = t("WF_State_NotStarted");
|
||||
}
|
||||
}
|
||||
|
||||
// 클릭 이벤트 — 모든 스텝에서 이동 허용
|
||||
if (options?.routes && options?.routes[index]) {
|
||||
if (isEnabled && options?.routes?.[index]) {
|
||||
button.addEventListener("click", () => {
|
||||
options.onStepClick?.(index, options.routes![index]);
|
||||
});
|
||||
@@ -99,6 +108,7 @@ export function createWorkflowLayout(options: WorkflowLayoutOptions): WorkflowLa
|
||||
title,
|
||||
createStepBar(options.steps, options.activeStep, {
|
||||
stages: options.stages,
|
||||
currentStage: options.currentStage,
|
||||
routes: options.routes,
|
||||
onStepClick: options.onStepClick,
|
||||
}),
|
||||
|
||||
Reference in New Issue
Block a user