feat: 어드민 적립내역 클릭 시 품목 상세 모달 + 키오스크 UI 개선

- 어드민 최근 적립 내역에서 행 클릭 시 MSSQL 품목 상세 모달 표시
- transaction_id가 있는 행만 클릭 가능 (돋보기 아이콘 표시)
- 키오스크 품목 목록 표시, 세로 모니터 반응형 레이아웃 추가

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
thug0bin
2026-02-25 16:37:50 +09:00
parent 22cbf3d42e
commit cb927d2207
3 changed files with 137 additions and 11 deletions

View File

@@ -38,8 +38,9 @@
align-items: center;
padding: 24px;
position: relative;
overflow-y: auto;
}
.screen { display: none; width: 100%; height: 100%; }
.screen { display: none; width: 100%; }
.screen.active { display: flex; }
/* ══════════════════════════════════════
@@ -207,6 +208,39 @@
.claim-amount-label { font-size: 15px; color: #6b7280; margin-bottom: 4px; }
.claim-amount { font-size: 36px; font-weight: 900; color: #1e1b4b; letter-spacing: -1px; }
.claim-points { font-size: 20px; color: #6366f1; font-weight: 700; margin-top: 8px; }
/* 품목 카드 */
.items-card {
background: #fff;
border-radius: 16px;
padding: 16px 20px;
box-shadow: 0 4px 20px rgba(0,0,0,0.06);
width: 100%;
max-height: 200px;
overflow-y: auto;
}
.items-title {
font-size: 13px;
font-weight: 700;
color: #6b7280;
margin-bottom: 8px;
text-transform: uppercase;
letter-spacing: 0.5px;
}
.items-list { display: flex; flex-direction: column; gap: 4px; }
.item-row {
display: flex;
align-items: center;
gap: 8px;
font-size: 14px;
color: #374151;
padding: 4px 0;
border-bottom: 1px solid #f3f4f6;
}
.item-row:last-child { border-bottom: none; }
.item-name { flex: 1; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; font-weight: 500; }
.item-qty { color: #9ca3af; font-size: 13px; flex-shrink: 0; }
.item-total { font-weight: 600; color: #6366f1; flex-shrink: 0; min-width: 60px; text-align: right; }
.qr-container {
background: #fff;
border-radius: 20px;
@@ -246,6 +280,7 @@
padding: 14px 20px;
display: flex;
align-items: center;
justify-content: center;
transition: border-color 0.2s;
min-height: 64px;
}
@@ -256,7 +291,6 @@
font-weight: 700;
color: #9ca3af;
letter-spacing: 1px;
margin-right: 4px;
flex-shrink: 0;
}
.phone-number {
@@ -264,8 +298,7 @@
font-weight: 700;
color: #1e1b4b;
letter-spacing: 2px;
flex: 1;
text-align: center;
margin-left: 2px;
}
.phone-number.placeholder { color: #d1d5db; }
@@ -348,9 +381,52 @@
/* ── 적립/성공 화면 배경 밝게 ── */
.claim-screen, .success-screen { background: #f5f7fa; border-radius: 24px; padding: 32px; }
/* ── 반응형 ── */
/* ── 반응형: 세로 모니터 (portrait, 폭 700px 이상) ── */
@media (orientation: portrait) and (min-width: 700px) {
.main { padding: 32px; }
/* 적립 화면: 세로 스택, 공간 활용 */
.claim-screen {
flex-direction: column;
gap: 24px;
padding: 32px 48px;
max-width: 640px;
align-items: center;
justify-content: center;
}
.claim-left {
flex-direction: row;
flex-wrap: wrap;
gap: 16px;
width: 100%;
align-items: flex-start;
}
.claim-info-card { flex: 1; min-width: 200px; }
.qr-container { flex-shrink: 0; }
.items-card { width: 100%; max-height: 160px; }
.qr-container img { width: 140px; height: 140px; }
.divider { flex-direction: row; }
.divider-line { width: 60px; height: 2px; }
.claim-right { width: 100%; align-items: center; }
.phone-display-wrap { max-width: 440px; }
.phone-prefix { font-size: 30px; }
.phone-number { font-size: 30px; white-space: nowrap; }
.numpad { max-width: 440px; }
.submit-btn { max-width: 440px; }
/* 슬라이드 더 크게 */
.slides-wrapper { height: 420px; }
.slide-icon { width: 110px; height: 110px; font-size: 56px; }
.slide-title { font-size: 34px; }
.slide-desc { font-size: 19px; }
.slide-highlight { font-size: 16px; padding: 12px 32px; }
}
/* ── 반응형: 좁은 화면 (모바일) ── */
@media (max-width: 700px) {
.claim-screen { flex-direction: column; gap: 20px; padding: 20px; }
.claim-screen { flex-direction: column; gap: 24px; padding: 20px; }
.divider { flex-direction: row; }
.divider-line { width: 60px; height: 2px; }
.claim-amount { font-size: 28px; }
@@ -438,6 +514,10 @@
<div class="claim-amount" id="claimAmount">0원</div>
<div class="claim-points">적립 <span id="claimPoints">0</span>P</div>
</div>
<div class="items-card" id="itemsCard" style="display:none;">
<div class="items-title">구매 품목</div>
<div class="items-list" id="itemsList"></div>
</div>
<div class="qr-container" id="qrContainer" style="display:none;">
<img id="qrImage" src="" alt="QR Code">
<div class="qr-hint">휴대폰으로 QR을 스캔하여<br>적립할 수도 있습니다</div>
@@ -453,7 +533,7 @@
<div class="claim-right">
<div class="phone-section-title">전화번호로 적립하기</div>
<div class="phone-display-wrap" id="phoneWrap">
<span class="phone-prefix">010 -</span>
<span class="phone-prefix">010-</span>
<span class="phone-number placeholder" id="phoneDisplay">0000-0000</span>
</div>
<div class="error-msg" id="errorMsg"></div>
@@ -677,6 +757,22 @@ async function pollKioskSession() {
document.getElementById('claimAmount').textContent = data.amount.toLocaleString() + '원';
document.getElementById('claimPoints').textContent = data.points.toLocaleString();
// 품목 목록 표시
const itemsCard = document.getElementById('itemsCard');
const itemsList = document.getElementById('itemsList');
if (data.items && data.items.length > 0) {
itemsList.innerHTML = data.items.map(item =>
`<div class="item-row">
<span class="item-name">${item.name}</span>
<span class="item-qty">${item.qty}개</span>
<span class="item-total">${item.total.toLocaleString()}원</span>
</div>`
).join('');
itemsCard.style.display = '';
} else {
itemsCard.style.display = 'none';
}
if (data.qr_url) {
document.getElementById('qrImage').src =
'https://api.qrserver.com/v1/create-qr-code/?size=200x200&data=' +