Files
Aislo/B05_wf2_Route/B05_wf2_Route_UI_Profile_Panel.ts
T
2026-07-18 23:59:28 +09:00

66 lines
2.1 KiB
TypeScript

import type {
LongitudinalSection,
SectionDetailResponse,
} from "../B06_wf3_ProfileCross/B06_wf3_ProfileCross_Api_Fetch";
import { createLongitudinalProfile } from "../B06_wf3_ProfileCross/B06_wf3_ProfileCross_UI_Section_View";
import "../B06_wf3_ProfileCross/B06_wf3_ProfileCross_UI_Style.css";
const COLLAPSED_KEY = "b05-route-profile-collapsed";
function normalizedLongitudinal(data: LongitudinalSection): LongitudinalSection {
return {
...data,
samples: data.samples.map((sample) => ({
...sample,
elevation_m: sample.elevation_m ?? sample.z ?? null,
})),
};
}
export function createRouteProfilePanel() {
const root = document.createElement("section");
root.className = "b05-route-profile";
const header = document.createElement("header");
const title = document.createElement("strong");
title.textContent = "종단면도";
const toggle = document.createElement("button");
toggle.type = "button";
toggle.className = "b05-route-profile__toggle";
const body = document.createElement("div");
body.className = "b05-route-profile__body";
const empty = document.createElement("p");
empty.className = "b05-route-profile__empty";
empty.textContent = "최적 경로를 계산하면 종단면도가 표시됩니다.";
body.append(empty);
header.append(title, toggle);
root.append(header, body);
function setCollapsed(collapsed: boolean): void {
root.classList.toggle("is-collapsed", collapsed);
toggle.textContent = collapsed ? "펼치기" : "접기";
toggle.setAttribute("aria-expanded", String(!collapsed));
sessionStorage.setItem(COLLAPSED_KEY, String(collapsed));
}
toggle.addEventListener("click", () => setCollapsed(!root.classList.contains("is-collapsed")));
setCollapsed(sessionStorage.getItem(COLLAPSED_KEY) === "true");
return {
root,
render(detail: SectionDetailResponse) {
body.replaceChildren(
createLongitudinalProfile(
normalizedLongitudinal(detail.longitudinal),
null,
1,
undefined,
() => undefined,
),
);
},
clear() {
body.replaceChildren(empty);
},
};
}