From 275e51c93bfcba936789bb679b6294fb9f313903 Mon Sep 17 00:00:00 2001 From: king Date: Tue, 1 Sep 2026 14:08:13 +0900 Subject: [PATCH] =?UTF-8?q?feat(cupang):=20=EB=B0=9C=EC=A3=BC=20=EC=97=85?= =?UTF-8?q?=EB=A1=9C=EB=93=9C=20UX=20=EA=B0=9C=EC=84=A0=20+=203=EC=97=B4?= =?UTF-8?q?=20=ED=94=84=EB=A0=88=EC=9E=84=20=EA=B0=81=EA=B0=81=20=EC=8A=A4?= =?UTF-8?q?=ED=81=AC=EB=A1=A4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - [쿠팡 발주파일 업로드] 라벨 버튼, 파일 선택 즉시 자동 분석(분석 버튼 제거) - 안내 문구와 분석 결과 상세 표시 제거 — 경고만 남김 - ①②③ 카드가 각자 스크롤: 문서 전체는 스크롤되지 않음 · ① 표 머리글 sticky, 행 높이 축소로 품목 더 많이 표시 · ② KPI 요약까지 고정, 아래 목록만 스크롤 · ③ 헤더/센터 선택 고정, 센터 목록만 스크롤 Co-Authored-By: Claude Opus 5 --- .../cupang/templates/cupang/box_calc.html | 62 +++++++------------ .../cupang/templates/cupang/box_rules.html | 2 +- .../cupang/templates/cupang/centers.html | 2 +- .../cupang/templates/cupang/detail.html | 2 +- app/modules/cupang/templates/cupang/form.html | 2 +- .../cupang/templates/cupang/index.html | 2 +- .../cupang/templates/cupang/products.html | 2 +- app/static/cupang.css | 50 ++++++++++++++- 8 files changed, 76 insertions(+), 48 deletions(-) diff --git a/app/modules/cupang/templates/cupang/box_calc.html b/app/modules/cupang/templates/cupang/box_calc.html index c577fee..9cc9784 100644 --- a/app/modules/cupang/templates/cupang/box_calc.html +++ b/app/modules/cupang/templates/cupang/box_calc.html @@ -1,6 +1,6 @@ {% extends "erp_base.html" %} -{% block head_extra %}{% endblock %} +{% block head_extra %}{% endblock %} {% block content %}
@@ -34,19 +34,16 @@

① 쿠팡 발주 업로드

- 엑셀 여러 개 선택 가능 · F13 입고예정일의 하루 전 = 출고일
+ - +
-

- B열 쿠팡상품코드 · F열 센터 · G열 수량을 22행부터 읽습니다. -

@@ -90,11 +87,13 @@
@@ -372,7 +371,6 @@ // 업로드 → 센터별 수량 합산(서버) → 센터마다 박스 계산 → ②③ 자동 채움. // 박스는 센터별로 포장하므로 계산도 센터 단위로 한다(자투리 혼합 박스 포함). var poFile = document.getElementById("cpg-po-file"); - var poRun = document.getElementById("cpg-po-run"); var poMsg = document.getElementById("cpg-po-msg"); var poResult = document.getElementById("cpg-po-result"); var uploadShipDate = ""; // F13 − 1일 (확정 대화상자 기본값) @@ -560,36 +558,17 @@ return st; } + // 분석 결과 상세는 화면에 두지 않는다. 놓치면 안 되는 경고만 남긴다. function renderPoResult(data, skipped) { if (!poResult) return; - var html = '
' + - '출고일 ' + esc(data.ship_date || "미확인") + "" + - '파일 ' + ((data.files || []).length) + "개" + - '센터 ' + ((data.centers || []).length) + "곳" + - "
"; - if ((data.groups || []).length > 1) { - html += '
    ' + data.groups.map(function (g) { - return "
  • " + esc(g.ship_date || "날짜 미확인") + "" + - "센터 " + ((g.centers || []).length) + "곳 · " + (g.quantity || 0) + "개
  • "; - }).join("") + "
"; - } - html += '
    '; - (data.files || []).forEach(function (f) { - html += "
  • " + esc(f.filename) + "" + - "입고 " + esc(f.arrival_date || "?") + " → 출고 " + esc(f.ship_date || "?") + "" + - "" + f.quantity + "개
  • "; - }); - html += "
"; var warns = (data.warnings || []).slice(); if (skipped && skipped.length) { warns.push("등록되지 않은 센터라 자동 배분에서 제외: " + skipped.join(", ")); } - if (warns.length) { - html += '
    ' + warns.map(function (w) { - return "
  • " + esc(w) + "
  • "; - }).join("") + "
"; - } - poResult.innerHTML = html; + if (!warns.length) { poResult.hidden = true; poResult.innerHTML = ""; return; } + poResult.innerHTML = '
    ' + warns.map(function (w) { + return "
  • " + esc(w) + "
  • "; + }).join("") + "
"; poResult.hidden = false; } @@ -599,8 +578,7 @@ } var fd = new FormData(); Array.prototype.forEach.call(poFile.files, function (f) { fd.append("files", f); }); - poRun.disabled = true; - poMsg.textContent = "분석 중…"; + poMsg.textContent = "분석 중… (" + poFile.files.length + "개)"; fetch("/cupang/api/box-calc/upload", { method: "POST", body: fd }) .then(function (r) { return r.json().catch(function () { return {}; }).then(function (d) { @@ -668,11 +646,15 @@ : "업로드 결과로 계산했습니다. 센터마다 출고방식을 고르면 확정할 수 있습니다."; }); }) - .catch(function (err) { poMsg.textContent = (err && err.message) || "업로드 실패"; }) - .then(function () { poRun.disabled = false; }); + .catch(function (err) { poMsg.textContent = (err && err.message) || "업로드 실패"; }); } - if (poRun) poRun.addEventListener("click", runUpload); + // 파일을 고르고 [열기] 를 누르면 곧바로 분석한다(별도 버튼 없음). + if (poFile) { + poFile.addEventListener("change", function () { + if (poFile.files && poFile.files.length) runUpload(); + }); + } // ── 배분 집계 ───────────────────────────────────── function allocatedFor(key) { diff --git a/app/modules/cupang/templates/cupang/box_rules.html b/app/modules/cupang/templates/cupang/box_rules.html index 43ce413..0c8a48b 100644 --- a/app/modules/cupang/templates/cupang/box_rules.html +++ b/app/modules/cupang/templates/cupang/box_rules.html @@ -1,6 +1,6 @@ {% extends "erp_base.html" %} -{% block head_extra %}{% endblock %} +{% block head_extra %}{% endblock %} {% block content %}
diff --git a/app/modules/cupang/templates/cupang/centers.html b/app/modules/cupang/templates/cupang/centers.html index 8bdd4dc..0c652b4 100644 --- a/app/modules/cupang/templates/cupang/centers.html +++ b/app/modules/cupang/templates/cupang/centers.html @@ -1,6 +1,6 @@ {% extends "erp_base.html" %} -{% block head_extra %}{% endblock %} +{% block head_extra %}{% endblock %} {% block content %}
diff --git a/app/modules/cupang/templates/cupang/detail.html b/app/modules/cupang/templates/cupang/detail.html index 37b0d56..bff93c2 100644 --- a/app/modules/cupang/templates/cupang/detail.html +++ b/app/modules/cupang/templates/cupang/detail.html @@ -1,6 +1,6 @@ {% extends "erp_base.html" %} -{% block head_extra %}{% endblock %} +{% block head_extra %}{% endblock %} {% block content %}
diff --git a/app/modules/cupang/templates/cupang/form.html b/app/modules/cupang/templates/cupang/form.html index 227dc06..626a7ed 100644 --- a/app/modules/cupang/templates/cupang/form.html +++ b/app/modules/cupang/templates/cupang/form.html @@ -1,6 +1,6 @@ {% extends "erp_base.html" %} -{% block head_extra %}{% endblock %} +{% block head_extra %}{% endblock %} {% block content %}
diff --git a/app/modules/cupang/templates/cupang/index.html b/app/modules/cupang/templates/cupang/index.html index 31c5c39..77711a3 100644 --- a/app/modules/cupang/templates/cupang/index.html +++ b/app/modules/cupang/templates/cupang/index.html @@ -1,6 +1,6 @@ {% extends "erp_base.html" %} -{% block head_extra %}{% endblock %} +{% block head_extra %}{% endblock %} {% block content %}
diff --git a/app/modules/cupang/templates/cupang/products.html b/app/modules/cupang/templates/cupang/products.html index 8607ded..3240c1e 100644 --- a/app/modules/cupang/templates/cupang/products.html +++ b/app/modules/cupang/templates/cupang/products.html @@ -1,6 +1,6 @@ {% extends "erp_base.html" %} -{% block head_extra %}{% endblock %} +{% block head_extra %}{% endblock %} {% block content %}
diff --git a/app/static/cupang.css b/app/static/cupang.css index 5b42ca0..9127072 100644 --- a/app/static/cupang.css +++ b/app/static/cupang.css @@ -601,7 +601,6 @@ .cpg-calc-card .erp-table-wrap { overflow-x: hidden; overflow-y: auto; - max-height: min(58vh, 560px); } .cpg-calc-card .cpg-calc-table thead th { position: sticky; @@ -615,7 +614,7 @@ .cpg-calc-layout { align-items: stretch; } .cpg-calc-layout > .erp-card { display: flex; flex-direction: column; } .cpg-calc-card .erp-table-wrap { flex: 1 1 auto; } -.cpg-calc-sum { overflow: auto; max-height: min(78vh, 900px); } +.cpg-calc-sum { overflow: hidden; } /* 제품명 설정 — 수기 추가 폼 */ .cpg-prod-manual { @@ -1343,3 +1342,50 @@ body.cpg-dragging { cursor: grabbing; user-select: none; } padding: 2px 8px; font-size: 12px; line-height: 1.6; cursor: pointer; } + +/* ══════════════════════════════════════════════════════════════ + 박스 계산 3열 — 카드마다 자체 스크롤(문서 전체는 스크롤 안 함) + 각 카드: 헤더/요약은 고정, 목록만 스크롤 + ══════════════════════════════════════════════════════════════ */ +.cpg-calc3 { flex: 1 1 auto; min-height: 0; } +.cpg-calc3 > .erp-card { min-height: 0; overflow: hidden; } +.cpg-calc3 .cpg-card-head, +.cpg-calc3 .cpg-po-box, +.cpg-calc3 .cpg-sum-kpis, +.cpg-calc3 .cpg-center-pick, +.cpg-calc3 .cpg-calc-actions, +.cpg-calc3 > .erp-card > .cpg-sum-h3 { flex-shrink: 0; } + +/* ① 입력 표 — 표 머리글 고정 + 표만 스크롤 */ +.cpg-calc-card .erp-table-wrap { flex: 1 1 auto; min-height: 0; } +.cpg-calc-card .cpg-calc-table thead th { + position: sticky; top: 0; z-index: 2; background: var(--color-canvas-white); +} +/* 행 높이 축소 — 한 화면에 더 많은 품목 */ +.cpg-calc-card .cpg-calc-table th, +.cpg-calc-card .cpg-calc-table td { padding: 2px 6px; } +.cpg-calc-card .cpg-calc-table .erp-select, +.cpg-calc-card .cpg-calc-table .erp-input { + padding: 2px 6px; font-size: 12px; line-height: 1.5; height: auto; +} +.cpg-calc-card .cpg-calc-table .cpg-calc-del { padding: 0 6px; font-size: 11px; line-height: 1.6; } + +/* ② 요약 — KPI 까지 고정, 아래 목록만 스크롤 */ +.cpg-calc-sum #cpg-sum-body { display: flex; flex-direction: column; flex: 1 1 auto; min-height: 0; } +.cpg-sum-scroll { flex: 1 1 auto; min-height: 0; overflow-y: auto; padding-right: 2px; } +.cpg-sum-scroll > .cpg-sum-h3:first-child { margin-top: 0; } + +/* ③ 센터 분배 — 센터 목록만 스크롤 */ +.cpg-dist-card .cpg-dist-list { flex: 1 1 auto; min-height: 0; overflow-y: auto; padding-right: 2px; } + +/* 업로드 버튼 — 네이티브 file input 은 숨기고 라벨을 버튼처럼 */ +.cpg-po-pick { cursor: pointer; } +.cpg-po-box .cpg-po-file { + position: absolute; width: 1px; height: 1px; + padding: 0; margin: -1px; border: 0; overflow: hidden; clip: rect(0 0 0 0); +} +.cpg-po-row { align-items: center; } +.cpg-po-msg { margin: 0; font-size: 12px; } +/* 상단 액션/출고일 탭은 줄어들지 않게 (3열 프레임만 남은 높이를 차지) */ +.cpg > .erp-page-actions, +.cpg > .cpg-date-tabs { flex-shrink: 0; }