Fix project comparison consistency and labor input handling
This commit is contained in:
+67
-1
@@ -390,6 +390,72 @@
|
|||||||
stroke: #a93a3a;
|
stroke: #a93a3a;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.modal-backdrop {
|
||||||
|
position: fixed;
|
||||||
|
inset: 0;
|
||||||
|
display: none;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
padding: 20px;
|
||||||
|
background: rgba(20, 33, 47, 0.5);
|
||||||
|
z-index: 10000;
|
||||||
|
isolation: isolate;
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-backdrop.open,
|
||||||
|
.modal-backdrop.is-open {
|
||||||
|
display: flex;
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-card,
|
||||||
|
.related-modal-card {
|
||||||
|
position: relative;
|
||||||
|
z-index: 1;
|
||||||
|
background: #ffffff;
|
||||||
|
border: 1px solid var(--line);
|
||||||
|
box-shadow: 0 24px 64px rgba(21, 24, 29, 0.18);
|
||||||
|
}
|
||||||
|
|
||||||
|
.related-modal-card {
|
||||||
|
width: min(680px, 100%);
|
||||||
|
max-height: min(70vh, 760px);
|
||||||
|
overflow: hidden;
|
||||||
|
border-radius: 16px;
|
||||||
|
padding: 14px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.related-modal-head {
|
||||||
|
display: flex;
|
||||||
|
justify-content: space-between;
|
||||||
|
align-items: center;
|
||||||
|
gap: 12px;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
}
|
||||||
|
|
||||||
|
.related-modal-head--singleline {
|
||||||
|
flex-wrap: nowrap;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
}
|
||||||
|
|
||||||
|
.related-modal-title {
|
||||||
|
margin: 0;
|
||||||
|
font-size: 16px;
|
||||||
|
font-weight: 800;
|
||||||
|
line-height: 1.2;
|
||||||
|
}
|
||||||
|
|
||||||
|
.related-modal-body {
|
||||||
|
display: grid;
|
||||||
|
gap: 10px;
|
||||||
|
overflow: auto;
|
||||||
|
min-height: 0;
|
||||||
|
overscroll-behavior: contain;
|
||||||
|
}
|
||||||
|
|
||||||
.sr-only {
|
.sr-only {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
width: 1px;
|
width: 1px;
|
||||||
@@ -799,7 +865,7 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
function hasOpenModal() {
|
function hasOpenModal() {
|
||||||
return Boolean(document.querySelector(".modal-backdrop.open"));
|
return Boolean(document.querySelector(".modal-backdrop.open, .modal-backdrop.is-open"));
|
||||||
}
|
}
|
||||||
|
|
||||||
function shouldDelayRefresh() {
|
function shouldDelayRefresh() {
|
||||||
|
|||||||
+120
-16
@@ -333,6 +333,10 @@
|
|||||||
min-width: 0;
|
min-width: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.pc-selected-card[hidden] {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
.pc-selected-head {
|
.pc-selected-head {
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
@@ -452,6 +456,16 @@
|
|||||||
min-height: 32px;
|
min-height: 32px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.pc-chip-link {
|
||||||
|
color: inherit;
|
||||||
|
text-decoration: none;
|
||||||
|
font-weight: 700;
|
||||||
|
}
|
||||||
|
|
||||||
|
.pc-chip-link:hover {
|
||||||
|
text-decoration: underline;
|
||||||
|
}
|
||||||
|
|
||||||
.pc-chip button {
|
.pc-chip button {
|
||||||
border: none;
|
border: none;
|
||||||
background: transparent;
|
background: transparent;
|
||||||
@@ -463,6 +477,33 @@
|
|||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.pc-related-include {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
width: 18px;
|
||||||
|
min-width: 18px;
|
||||||
|
height: 18px;
|
||||||
|
border-radius: 999px;
|
||||||
|
border: 1px solid rgba(217, 221, 227, 0.9);
|
||||||
|
background: #fff;
|
||||||
|
color: var(--muted);
|
||||||
|
font-size: 12px;
|
||||||
|
font-weight: 800;
|
||||||
|
padding: 0;
|
||||||
|
line-height: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
.pc-related-include.is-active {
|
||||||
|
color: #1f6f3d;
|
||||||
|
background: #eefbf3;
|
||||||
|
}
|
||||||
|
|
||||||
|
.pc-related-include:disabled {
|
||||||
|
opacity: 0.42;
|
||||||
|
cursor: default;
|
||||||
|
}
|
||||||
|
|
||||||
.pc-related-form {
|
.pc-related-form {
|
||||||
display: grid;
|
display: grid;
|
||||||
grid-template-columns: minmax(0, 1fr) auto auto;
|
grid-template-columns: minmax(0, 1fr) auto auto;
|
||||||
@@ -686,12 +727,12 @@
|
|||||||
<div class="pc-toolbar">
|
<div class="pc-toolbar">
|
||||||
<div class="pc-tab-row">
|
<div class="pc-tab-row">
|
||||||
<div class="pc-source-tabs">
|
<div class="pc-source-tabs">
|
||||||
<a href="/process-cost?source=hanmac{% if process_cost_selected_start_year %}&start_year={{ process_cost_selected_start_year }}{% endif %}{% if process_cost_selected_end_year %}&end_year={{ process_cost_selected_end_year }}{% endif %}{% if process_cost_selected_code %}&code={{ process_cost_selected_code }}{% endif %}{% if process_cost_include_related %}&include_related=1{% endif %}" class="{% if process_cost_source == 'hanmac' %}active{% endif %}">Hanmac ERP</a>
|
<a href="/process-cost?source=hanmac{% if process_cost_selected_start_year %}&start_year={{ process_cost_selected_start_year }}{% endif %}{% if process_cost_selected_end_year %}&end_year={{ process_cost_selected_end_year }}{% endif %}{% if process_cost_selected_code %}&code={{ process_cost_selected_code }}{% endif %}{% if process_cost_include_related %}&include_related=1&active_related={% if process_cost_active_related_codes %}{{ process_cost_active_related_codes|join(',') }}{% elif process_cost_related_codes %}{{ process_cost_related_codes|join(',') }}{% else %}-{% endif %}{% endif %}" class="{% if process_cost_source == 'hanmac' %}active{% endif %}">Hanmac ERP</a>
|
||||||
<a href="/process-cost?source=wehago{% if process_cost_selected_start_year %}&start_year={{ process_cost_selected_start_year }}{% endif %}{% if process_cost_selected_end_year %}&end_year={{ process_cost_selected_end_year }}{% endif %}{% if process_cost_selected_code %}&code={{ process_cost_selected_code }}{% endif %}{% if process_cost_include_related %}&include_related=1{% endif %}" class="{% if process_cost_source == 'wehago' %}active{% endif %}">WEHAGO</a>
|
<a href="/process-cost?source=wehago{% if process_cost_selected_start_year %}&start_year={{ process_cost_selected_start_year }}{% endif %}{% if process_cost_selected_end_year %}&end_year={{ process_cost_selected_end_year }}{% endif %}{% if process_cost_selected_code %}&code={{ process_cost_selected_code }}{% endif %}{% if process_cost_include_related %}&include_related=1&active_related={% if process_cost_active_related_codes %}{{ process_cost_active_related_codes|join(',') }}{% elif process_cost_related_codes %}{{ process_cost_related_codes|join(',') }}{% else %}-{% endif %}{% endif %}" class="{% if process_cost_source == 'wehago' %}active{% endif %}">WEHAGO</a>
|
||||||
</div>
|
</div>
|
||||||
<div class="pc-source-tabs">
|
<div class="pc-source-tabs">
|
||||||
<a href="/process-cost?source={{ process_cost_source }}{% if process_cost_selected_start_year %}&start_year={{ process_cost_selected_start_year }}{% endif %}{% if process_cost_selected_end_year %}&end_year={{ process_cost_selected_end_year }}{% endif %}{% if process_cost_selected_code %}&code={{ process_cost_selected_code }}{% endif %}" class="{% if not process_cost_include_related %}active{% endif %}">연계 미반영</a>
|
<a href="/process-cost?source={{ process_cost_source }}{% if process_cost_selected_start_year %}&start_year={{ process_cost_selected_start_year }}{% endif %}{% if process_cost_selected_end_year %}&end_year={{ process_cost_selected_end_year }}{% endif %}{% if process_cost_selected_code %}&code={{ process_cost_selected_code }}{% endif %}" class="{% if not process_cost_include_related %}active{% endif %}">연계 미반영</a>
|
||||||
<a href="/process-cost?source={{ process_cost_source }}{% if process_cost_selected_start_year %}&start_year={{ process_cost_selected_start_year }}{% endif %}{% if process_cost_selected_end_year %}&end_year={{ process_cost_selected_end_year }}{% endif %}{% if process_cost_selected_code %}&code={{ process_cost_selected_code }}{% endif %}&include_related=1" class="{% if process_cost_include_related %}active{% endif %}">연계 반영</a>
|
<a href="/process-cost?source={{ process_cost_source }}{% if process_cost_selected_start_year %}&start_year={{ process_cost_selected_start_year }}{% endif %}{% if process_cost_selected_end_year %}&end_year={{ process_cost_selected_end_year }}{% endif %}{% if process_cost_selected_code %}&code={{ process_cost_selected_code }}{% endif %}&include_related=1&active_related={% if process_cost_active_related_codes %}{{ process_cost_active_related_codes|join(',') }}{% elif process_cost_related_codes %}{{ process_cost_related_codes|join(',') }}{% else %}-{% endif %}" class="{% if process_cost_include_related %}active{% endif %}">연계 반영</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<form method="get" action="/process-cost" class="pc-filter">
|
<form method="get" action="/process-cost" class="pc-filter">
|
||||||
@@ -699,6 +740,7 @@
|
|||||||
<input type="hidden" name="code" value="{{ process_cost_selected_code }}">
|
<input type="hidden" name="code" value="{{ process_cost_selected_code }}">
|
||||||
{% if process_cost_include_related %}
|
{% if process_cost_include_related %}
|
||||||
<input type="hidden" name="include_related" value="1">
|
<input type="hidden" name="include_related" value="1">
|
||||||
|
<input type="hidden" name="active_related" value="{% if process_cost_active_related_codes %}{{ process_cost_active_related_codes|join(',') }}{% else %}-{% endif %}">
|
||||||
{% endif %}
|
{% endif %}
|
||||||
<select name="start_year" aria-label="시작 연도 선택" id="processCostStartYear">
|
<select name="start_year" aria-label="시작 연도 선택" id="processCostStartYear">
|
||||||
{% if not process_cost_years %}
|
{% if not process_cost_years %}
|
||||||
@@ -758,7 +800,7 @@
|
|||||||
<div class="pc-project-dropdown" id="projectList" hidden>
|
<div class="pc-project-dropdown" id="projectList" hidden>
|
||||||
{% for item in process_cost_projects %}
|
{% for item in process_cost_projects %}
|
||||||
<a
|
<a
|
||||||
href="/process-cost?source={{ process_cost_source }}{% if process_cost_selected_start_year %}&start_year={{ process_cost_selected_start_year }}{% endif %}{% if process_cost_selected_end_year %}&end_year={{ process_cost_selected_end_year }}{% endif %}&code={{ item.support_dept_code }}{% if process_cost_include_related %}&include_related=1{% endif %}"
|
href="/process-cost?source={{ process_cost_source }}{% if process_cost_selected_start_year %}&start_year={{ process_cost_selected_start_year }}{% endif %}{% if process_cost_selected_end_year %}&end_year={{ process_cost_selected_end_year }}{% endif %}&code={{ item.support_dept_code }}{% if process_cost_include_related %}&include_related=1&active_related={% if process_cost_active_related_codes %}{{ process_cost_active_related_codes|join(',') }}{% else %}-{% endif %}{% endif %}"
|
||||||
class="pc-project-item {% if process_cost_selected_code == item.support_dept_code %}active{% endif %}"
|
class="pc-project-item {% if process_cost_selected_code == item.support_dept_code %}active{% endif %}"
|
||||||
data-project-search="{{ (item.support_dept_code ~ ' ' ~ item.support_dept_name ~ ' ' ~ (item.client_name or ''))|lower }}"
|
data-project-search="{{ (item.support_dept_code ~ ' ' ~ item.support_dept_name ~ ' ' ~ (item.client_name or ''))|lower }}"
|
||||||
data-project-kind="{{ item.project_kind_code|lower }}"
|
data-project-kind="{{ item.project_kind_code|lower }}"
|
||||||
@@ -777,8 +819,8 @@
|
|||||||
<div class="pc-note" id="projectListEmpty" hidden style="padding: 12px;">검색 결과가 없습니다.</div>
|
<div class="pc-note" id="projectListEmpty" hidden style="padding: 12px;">검색 결과가 없습니다.</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{% if selected_project %}
|
{% if selected_project and (selected_project.support_dept_code not in (process_cost_quick_link_codes or [])) %}
|
||||||
<div class="pc-selected-card">
|
<div class="pc-selected-card" id="selectedProjectCard">
|
||||||
<div class="pc-selected-head">
|
<div class="pc-selected-head">
|
||||||
<div class="pc-selected-title">{{ selected_project.support_dept_code }}</div>
|
<div class="pc-selected-title">{{ selected_project.support_dept_code }}</div>
|
||||||
<button
|
<button
|
||||||
@@ -835,7 +877,7 @@
|
|||||||
<span class="meta">목표원가 {{ "{:,.0f}".format(overview.target_cost_amount|default(0)) }}원</span>
|
<span class="meta">목표원가 {{ "{:,.0f}".format(overview.target_cost_amount|default(0)) }}원</span>
|
||||||
</article>
|
</article>
|
||||||
<article class="pc-card">
|
<article class="pc-card">
|
||||||
<span class="label">예상 영업수지</span>
|
<span class="label">영업수지</span>
|
||||||
<strong class="value">{{ "{:,.0f}".format(overview.profit_amount|default(0)) }}원</strong>
|
<strong class="value">{{ "{:,.0f}".format(overview.profit_amount|default(0)) }}원</strong>
|
||||||
<span class="meta">마진율 {{ "{:.1f}".format(overview.profit_rate|default(0)) }}%</span>
|
<span class="meta">마진율 {{ "{:.1f}".format(overview.profit_rate|default(0)) }}%</span>
|
||||||
</article>
|
</article>
|
||||||
@@ -872,14 +914,14 @@
|
|||||||
</section>
|
</section>
|
||||||
|
|
||||||
<section class="pc-block">
|
<section class="pc-block">
|
||||||
<h3>설계 프로세스별 원가 현황</h3>
|
<h3>지출 내역</h3>
|
||||||
<div class="pc-table-wrap">
|
<div class="pc-table-wrap">
|
||||||
<table class="pc-table">
|
<table class="pc-table">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>구분</th>
|
<th>구분</th>
|
||||||
<th>목표 원가</th>
|
<th>목표 원가</th>
|
||||||
<th>실제 집행</th>
|
<th>실지출</th>
|
||||||
<th>차이(목표-실제)</th>
|
<th>차이(목표-실제)</th>
|
||||||
<th>집행률</th>
|
<th>집행률</th>
|
||||||
</tr>
|
</tr>
|
||||||
@@ -905,13 +947,13 @@
|
|||||||
</section>
|
</section>
|
||||||
|
|
||||||
<section class="pc-block">
|
<section class="pc-block">
|
||||||
<h3>계정별 집행 상위 항목</h3>
|
<h3>지출 상위 항목</h3>
|
||||||
<div class="pc-table-wrap">
|
<div class="pc-table-wrap">
|
||||||
<table class="pc-table">
|
<table class="pc-table">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>계정</th>
|
<th>계정</th>
|
||||||
<th>집행금액</th>
|
<th>실지출</th>
|
||||||
<th>비중</th>
|
<th>비중</th>
|
||||||
<th>전표건수</th>
|
<th>전표건수</th>
|
||||||
<th>최근 증빙일</th>
|
<th>최근 증빙일</th>
|
||||||
@@ -1007,6 +1049,7 @@
|
|||||||
const selectedCode = {{ process_cost_selected_code | tojson }};
|
const selectedCode = {{ process_cost_selected_code | tojson }};
|
||||||
const selectedProject = {{ (process_cost_selected_project or {}) | tojson }};
|
const selectedProject = {{ (process_cost_selected_project or {}) | tojson }};
|
||||||
const initialRelatedCodes = {{ (process_cost_related_codes or []) | tojson }};
|
const initialRelatedCodes = {{ (process_cost_related_codes or []) | tojson }};
|
||||||
|
const initialActiveRelatedCodes = {{ (process_cost_active_related_codes or []) | tojson }};
|
||||||
const initialQuickLinkCodes = {{ (process_cost_quick_link_codes or []) | tojson }};
|
const initialQuickLinkCodes = {{ (process_cost_quick_link_codes or []) | tojson }};
|
||||||
const searchInput = document.getElementById("projectSearchInput");
|
const searchInput = document.getElementById("projectSearchInput");
|
||||||
const list = document.getElementById("projectList");
|
const list = document.getElementById("projectList");
|
||||||
@@ -1020,9 +1063,11 @@
|
|||||||
const processModalNote = document.getElementById("processFlowModalNote");
|
const processModalNote = document.getElementById("processFlowModalNote");
|
||||||
const processModalClose = document.getElementById("processFlowModalClose");
|
const processModalClose = document.getElementById("processFlowModalClose");
|
||||||
const processButtons = document.querySelectorAll("[data-process-modal]");
|
const processButtons = document.querySelectorAll("[data-process-modal]");
|
||||||
|
const includeRelatedEnabled = {{ 1 if process_cost_include_related else 0 }};
|
||||||
let bookmarkedCodes = Array.isArray(initialQuickLinkCodes) ? [...initialQuickLinkCodes] : [];
|
let bookmarkedCodes = Array.isArray(initialQuickLinkCodes) ? [...initialQuickLinkCodes] : [];
|
||||||
|
let activeRelatedCodes = Array.isArray(initialActiveRelatedCodes) ? [...initialActiveRelatedCodes] : [];
|
||||||
|
|
||||||
function buildProcessCostUrl(code) {
|
function buildProcessCostUrl(code, options = {}) {
|
||||||
const params = new URLSearchParams();
|
const params = new URLSearchParams();
|
||||||
params.set("source", {{ process_cost_source | tojson }});
|
params.set("source", {{ process_cost_source | tojson }});
|
||||||
if ({{ process_cost_selected_start_year | tojson }}) {
|
if ({{ process_cost_selected_start_year | tojson }}) {
|
||||||
@@ -1034,8 +1079,15 @@
|
|||||||
if (code) {
|
if (code) {
|
||||||
params.set("code", code);
|
params.set("code", code);
|
||||||
}
|
}
|
||||||
if ({{ 1 if process_cost_include_related else 0 }}) {
|
const includeRelated = Object.prototype.hasOwnProperty.call(options, "includeRelated")
|
||||||
|
? Boolean(options.includeRelated)
|
||||||
|
: Boolean(includeRelatedEnabled);
|
||||||
|
const relatedCodes = Array.isArray(options.activeRelatedCodes)
|
||||||
|
? options.activeRelatedCodes
|
||||||
|
: activeRelatedCodes;
|
||||||
|
if (includeRelated) {
|
||||||
params.set("include_related", "1");
|
params.set("include_related", "1");
|
||||||
|
params.set("active_related", relatedCodes.length ? relatedCodes.join(",") : "-");
|
||||||
}
|
}
|
||||||
return `/process-cost?${params.toString()}`;
|
return `/process-cost?${params.toString()}`;
|
||||||
}
|
}
|
||||||
@@ -1072,11 +1124,20 @@
|
|||||||
selectedProjectBookmark.setAttribute("title", active ? "바로가기 해제" : "바로가기 저장");
|
selectedProjectBookmark.setAttribute("title", active ? "바로가기 해제" : "바로가기 저장");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function syncSelectedProjectCard() {
|
||||||
|
const selectedProjectCard = document.getElementById("selectedProjectCard");
|
||||||
|
if (!selectedProjectCard || !selectedProject || !selectedProject.support_dept_code) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
selectedProjectCard.hidden = isBookmarked(selectedProject.support_dept_code);
|
||||||
|
}
|
||||||
|
|
||||||
function renderQuickLinks() {
|
function renderQuickLinks() {
|
||||||
if (!quickLinksContainer) return;
|
if (!quickLinksContainer) return;
|
||||||
const items = getBookmarkedProjects();
|
const items = getBookmarkedProjects();
|
||||||
if (!items.length) {
|
if (!items.length) {
|
||||||
quickLinksContainer.innerHTML = "";
|
quickLinksContainer.innerHTML = "";
|
||||||
|
syncSelectedProjectCard();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
quickLinksContainer.innerHTML = items.map((item) => `
|
quickLinksContainer.innerHTML = items.map((item) => `
|
||||||
@@ -1102,6 +1163,7 @@
|
|||||||
.then(() => {
|
.then(() => {
|
||||||
renderQuickLinks();
|
renderQuickLinks();
|
||||||
syncBookmarkButton();
|
syncBookmarkButton();
|
||||||
|
syncSelectedProjectCard();
|
||||||
closeProjectList();
|
closeProjectList();
|
||||||
filterProjectList();
|
filterProjectList();
|
||||||
})
|
})
|
||||||
@@ -1110,6 +1172,7 @@
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
syncSelectedProjectCard();
|
||||||
}
|
}
|
||||||
|
|
||||||
function getVisibleProjectItems() {
|
function getVisibleProjectItems() {
|
||||||
@@ -1228,6 +1291,7 @@
|
|||||||
|
|
||||||
renderQuickLinks();
|
renderQuickLinks();
|
||||||
syncBookmarkButton();
|
syncBookmarkButton();
|
||||||
|
syncSelectedProjectCard();
|
||||||
filterProjectList();
|
filterProjectList();
|
||||||
|
|
||||||
if (selectedProjectBookmark) {
|
if (selectedProjectBookmark) {
|
||||||
@@ -1242,6 +1306,7 @@
|
|||||||
await persistBookmarkedCodes(nextCodes);
|
await persistBookmarkedCodes(nextCodes);
|
||||||
renderQuickLinks();
|
renderQuickLinks();
|
||||||
syncBookmarkButton();
|
syncBookmarkButton();
|
||||||
|
syncSelectedProjectCard();
|
||||||
closeProjectList();
|
closeProjectList();
|
||||||
filterProjectList();
|
filterProjectList();
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
@@ -1266,19 +1331,57 @@
|
|||||||
function renderRelatedChips() {
|
function renderRelatedChips() {
|
||||||
if (!relatedChipRow) return;
|
if (!relatedChipRow) return;
|
||||||
const fixedHead = selectedCode ? `<span class="pc-chip">${selectedCode} 기준</span>` : "";
|
const fixedHead = selectedCode ? `<span class="pc-chip">${selectedCode} 기준</span>` : "";
|
||||||
const chips = [...relatedSet].sort().map((code) => `
|
const chips = [...relatedSet].sort().map((code) => {
|
||||||
|
const isActive = activeRelatedCodes.includes(code);
|
||||||
|
const nextActiveCodes = isActive
|
||||||
|
? activeRelatedCodes.filter((item) => item !== code)
|
||||||
|
: [...activeRelatedCodes, code];
|
||||||
|
const openActiveCodes = [...new Set(
|
||||||
|
[selectedCode, ...activeRelatedCodes]
|
||||||
|
.filter((item) => item && item !== code)
|
||||||
|
)];
|
||||||
|
return `
|
||||||
<span class="pc-chip" data-related-code="${code}">
|
<span class="pc-chip" data-related-code="${code}">
|
||||||
<span>${code}</span>
|
<a
|
||||||
|
href="${buildProcessCostUrl(code, { activeRelatedCodes: openActiveCodes, includeRelated: includeRelatedEnabled })}"
|
||||||
|
class="pc-chip-link"
|
||||||
|
>${code}</a>
|
||||||
|
<button
|
||||||
|
type="button"
|
||||||
|
class="pc-related-include ${isActive ? "is-active" : ""}"
|
||||||
|
data-related-toggle="${code}"
|
||||||
|
data-related-active="${isActive ? "1" : "0"}"
|
||||||
|
aria-label="${isActive ? "합산 제외" : "합산 포함"}"
|
||||||
|
title="${isActive ? "합산 제외" : "합산 포함"}"
|
||||||
|
${includeRelatedEnabled ? "" : "disabled"}
|
||||||
|
>${isActive ? "−" : "+"}</button>
|
||||||
<button type="button" class="pc-related-remove" data-related-remove="${code}">x</button>
|
<button type="button" class="pc-related-remove" data-related-remove="${code}">x</button>
|
||||||
</span>
|
</span>
|
||||||
`).join("");
|
`;
|
||||||
|
}).join("");
|
||||||
const empty = "";
|
const empty = "";
|
||||||
relatedChipRow.innerHTML = fixedHead + chips + empty;
|
relatedChipRow.innerHTML = fixedHead + chips + empty;
|
||||||
|
relatedChipRow.querySelectorAll("[data-related-toggle]").forEach((button) => {
|
||||||
|
button.addEventListener("click", () => {
|
||||||
|
if (!includeRelatedEnabled) return;
|
||||||
|
const code = button.getAttribute("data-related-toggle") || "";
|
||||||
|
if (!code) return;
|
||||||
|
const currentlyActive = button.getAttribute("data-related-active") === "1";
|
||||||
|
const nextActiveCodes = currentlyActive
|
||||||
|
? activeRelatedCodes.filter((item) => item !== code)
|
||||||
|
: [...activeRelatedCodes, code];
|
||||||
|
window.location.href = buildProcessCostUrl(selectedCode, {
|
||||||
|
includeRelated: true,
|
||||||
|
activeRelatedCodes: [...new Set(nextActiveCodes)],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
relatedChipRow.querySelectorAll("[data-related-remove]").forEach((button) => {
|
relatedChipRow.querySelectorAll("[data-related-remove]").forEach((button) => {
|
||||||
button.addEventListener("click", () => {
|
button.addEventListener("click", () => {
|
||||||
const code = button.dataset.relatedRemove || "";
|
const code = button.dataset.relatedRemove || "";
|
||||||
if (code) {
|
if (code) {
|
||||||
relatedSet.delete(code);
|
relatedSet.delete(code);
|
||||||
|
activeRelatedCodes = activeRelatedCodes.filter((item) => item !== code);
|
||||||
renderRelatedChips();
|
renderRelatedChips();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -1338,6 +1441,7 @@
|
|||||||
for (const code of initialRelatedCodes || []) {
|
for (const code of initialRelatedCodes || []) {
|
||||||
relatedSet.add(code);
|
relatedSet.add(code);
|
||||||
}
|
}
|
||||||
|
activeRelatedCodes = Array.isArray(initialActiveRelatedCodes) ? [...initialActiveRelatedCodes] : [];
|
||||||
if (relatedSearchInput) relatedSearchInput.value = "";
|
if (relatedSearchInput) relatedSearchInput.value = "";
|
||||||
if (relatedSuggestList) {
|
if (relatedSuggestList) {
|
||||||
relatedSuggestList.classList.remove("active");
|
relatedSuggestList.classList.remove("active");
|
||||||
|
|||||||
+904
-115
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user