ui(cupang): 품목 라인 번호열을 체크박스로 + 선택 라인 삭제 + 전체선택

- # 열 → 체크박스(헤더 전체선택, indeterminate 지원)
- "라인 삭제" → "선택 라인 삭제": 체크된 행 삭제(최소 1줄 유지)
- 캐시 버전 h

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
2026-05-30 06:23:16 +09:00
parent f25948185b
commit fdabeec4e3
9 changed files with 47 additions and 22 deletions
@@ -1,6 +1,6 @@
{% extends "erp_base.html" %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530g" />{% endblock %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530h" />{% endblock %}
{% block content %}
<section class="cpg">
@@ -1,6 +1,6 @@
{% extends "erp_base.html" %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530g" />{% endblock %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530h" />{% endblock %}
{% block content %}
<section class="cpg">
@@ -1,6 +1,6 @@
{% extends "erp_base.html" %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530g" />{% endblock %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530h" />{% endblock %}
{% block content %}
<section class="cpg">
@@ -1,6 +1,6 @@
{% extends "erp_base.html" %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530g" />{% endblock %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530h" />{% endblock %}
{% block content %}
<section class="cpg">
@@ -76,7 +76,7 @@
</span>
<div class="cpg-lines-btns">
<button type="button" class="erp-btn erp-btn-outline" id="cpg-add-line">+ 라인 추가</button>
<button type="button" class="erp-btn erp-btn-danger" id="cpg-del-line">라인 삭제</button>
<button type="button" class="erp-btn erp-btn-danger" id="cpg-del-line">선택 라인 삭제</button>
</div>
</div>
@@ -84,7 +84,8 @@
<table class="erp-table cpg-lines">
<thead>
<tr>
<th>#</th><th>제품명</th><th>제품코드</th><th>수량</th>
<th class="cpg-check-col"><input type="checkbox" id="cpg-check-all" title="전체 선택" /></th>
<th>제품명</th><th>제품코드</th><th>수량</th>
<th>입수량</th><th>박스 계산</th><th>라인메모</th>
</tr>
</thead>
@@ -118,4 +119,4 @@
</script>
{% endblock %}
{% block scripts %}<script src="/static/cupang.js?v=20260530g" defer></script>{% endblock %}
{% block scripts %}<script src="/static/cupang.js?v=20260530h" defer></script>{% endblock %}
@@ -1,6 +1,6 @@
{% extends "erp_base.html" %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530g" />{% endblock %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530h" />{% endblock %}
{% block content %}
<section class="cpg">
@@ -1,6 +1,6 @@
{% extends "erp_base.html" %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530g" />{% endblock %}
{% block head_extra %}<link rel="stylesheet" href="/static/cupang.css?v=20260530h" />{% endblock %}
{% block content %}
<section class="cpg">
+2
View File
@@ -174,6 +174,8 @@
/* ── 라인 테이블 ── */
.cpg-lines td { vertical-align: middle; }
.cpg-check-col { width: 36px; text-align: center; }
.cpg-check-col input { cursor: pointer; }
.cpg-lines .cpg-name-sel { width: 100%; min-width: 160px; }
/* 폭 고정: 제품코드 140px, 수량·입수량 60px */
.cpg-lines .cpg-code { width: 140px; min-width: 140px; box-sizing: border-box; }
+33 -11
View File
@@ -67,9 +67,9 @@
function makeRow(data) {
data = data || {};
var tr = document.createElement("tr");
// 컬럼: # / 제품명(select) / 제품코드 / 수량 / 입수량 / 박스계산 / 라인메모 / 삭제
// 컬럼: 체크 / 제품명(select) / 제품코드 / 수량 / 입수량 / 박스계산 / 라인메모
tr.innerHTML =
'<td class="cpg-line-no"></td>' +
'<td class="cpg-check-col"><input type="checkbox" class="cpg-row-check" /></td>' +
'<td class="cpg-cell-name"></td>' +
'<td><input class="erp-input cpg-code" type="text" placeholder="제품코드" /></td>' +
'<td><input class="erp-input cpg-qty" type="number" min="1" /></td>' +
@@ -108,27 +108,49 @@
body.appendChild(tr);
recalc(tr);
renumber();
syncCheckAll();
return tr;
}
function renumber() {
Array.prototype.forEach.call(body.querySelectorAll("tr"), function (tr, i) {
tr.querySelector(".cpg-line-no").textContent = i + 1;
// 전체 선택 체크박스 상태 동기화
var checkAll = document.getElementById("cpg-check-all");
function syncCheckAll() {
if (!checkAll) return;
var checks = body.querySelectorAll(".cpg-row-check");
var total = checks.length;
var on = 0;
Array.prototype.forEach.call(checks, function (c) { if (c.checked) on++; });
checkAll.checked = total > 0 && on === total;
checkAll.indeterminate = on > 0 && on < total;
}
if (checkAll) {
checkAll.addEventListener("change", function () {
Array.prototype.forEach.call(body.querySelectorAll(".cpg-row-check"), function (c) {
c.checked = checkAll.checked;
});
});
}
body.addEventListener("change", function (e) {
if (e.target && e.target.classList.contains("cpg-row-check")) syncCheckAll();
});
// 초기 라인
if (initLines.length) { initLines.forEach(makeRow); } else { makeRow(); }
document.getElementById("cpg-add-line").addEventListener("click", function () { makeRow(); });
// 마지막 라인 삭제 (최소 1줄 유지)
// 선택 라인 삭제 (체크된 행 삭제, 최소 1줄 유지)
var delBtn = document.getElementById("cpg-del-line");
if (delBtn) {
delBtn.addEventListener("click", function () {
var rows = body.querySelectorAll("tr");
if (rows.length <= 1) { alert("최소 1개 라인은 필요합니다."); return; }
rows[rows.length - 1].remove();
renumber();
var checked = body.querySelectorAll(".cpg-row-check:checked");
if (!checked.length) { alert("삭제할 라인을 선택하세요."); return; }
Array.prototype.forEach.call(checked, function (c) {
var tr = c.closest("tr");
if (tr) tr.remove();
});
if (!body.querySelectorAll("tr").length) makeRow(); // 최소 1줄
if (checkAll) { checkAll.checked = false; checkAll.indeterminate = false; }
syncCheckAll();
});
}
+2 -2
View File
@@ -4,8 +4,8 @@
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<title>{{ page_title or "ERP" }} — DBX Corporation</title>
<link rel="stylesheet" href="/static/erp.css?v=20260530g" />
<link rel="stylesheet" href="/static/erp-shell.css?v=20260530g" />
<link rel="stylesheet" href="/static/erp.css?v=20260530h" />
<link rel="stylesheet" href="/static/erp-shell.css?v=20260530h" />
<link rel="stylesheet" href="/static/erp-attach-viewer.css" />
{% block head_extra %}{% endblock %}
</head>