- 사용자 매뉴얼: league/commonmark 기반 bag/manual(로그인 전용), ManualRenderer + Config\Manual manifest, 콘텐츠 8종, E2E - 번호알기(봉투번호확인): bag/number-lookup, BagNumberLookup, E2E - gov-portal 대시보드 시안(기본/strip)·기본코드관리 화면 - 메뉴 관리: 등록·수정 후 메뉴 화면 유지, 수정 버튼 클릭 시 상단 스크롤 - 수불/분석 리포트(LOT 수불·반품/파기·수급계획·추이) 표시 보강 - .gitignore: docs/ → /docs/ 앵커링(최상위 개발문서만 제외, app/Docs는 추적) Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
639 lines
20 KiB
PHP
639 lines
20 KiB
PHP
<?php
|
|
declare(strict_types=1);
|
|
/**
|
|
* 공공 포털형 UI — 기본 레이아웃 (좌측 MY MENU)
|
|
*
|
|
* @var string $lgLabel
|
|
* @var string $activeVariant
|
|
*/
|
|
helper('admin');
|
|
$govPortalNavPartial = gov_portal_nav_partial_vars(get_defined_vars());
|
|
?>
|
|
<!DOCTYPE html>
|
|
<html lang="ko">
|
|
<head>
|
|
<?= view('home/_dashboard_gov_portal_head') ?>
|
|
<link href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.0/css/all.min.css" rel="stylesheet"/>
|
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/gh/orioncactus/pretendard@v1.3.9/dist/web/static/pretendard.min.css"/>
|
|
<?= view('home/_dashboard_gov_portal_map_leaflet_assets') ?>
|
|
<style>
|
|
:root {
|
|
--navy: #1a2b4b;
|
|
--navy-deep: #002b4e;
|
|
--blue: #0056b3;
|
|
--blue-ui: #007bff;
|
|
--blue-menu: #4a69bd;
|
|
--blue-light: #eef6ff;
|
|
--teal: #009688;
|
|
--bg: #f0f4f8;
|
|
--card: #fff;
|
|
--text: #444;
|
|
--text-dark: #222;
|
|
--muted: #888;
|
|
--border: #dde4ec;
|
|
--font-scale: 1;
|
|
}
|
|
* { box-sizing: border-box; margin: 0; padding: 0; }
|
|
html {
|
|
font-size: calc(14px * var(--font-scale));
|
|
-webkit-text-size-adjust: 100%;
|
|
}
|
|
body {
|
|
font-family: 'Pretendard', 'Malgun Gothic', 'Apple SD Gothic Neo', 'Noto Sans KR', sans-serif;
|
|
font-size: 0.8125rem; /* ~13px @14px root — 본문 */
|
|
font-weight: 400;
|
|
line-height: 1.45;
|
|
letter-spacing: -0.01em;
|
|
color: var(--text);
|
|
background: var(--bg);
|
|
min-height: 100vh;
|
|
display: flex;
|
|
flex-direction: column;
|
|
-webkit-font-smoothing: antialiased;
|
|
-moz-osx-font-smoothing: grayscale;
|
|
}
|
|
<?php include __DIR__ . '/_dashboard_gov_portal_brand_css.php'; ?>
|
|
<?php include __DIR__ . '/_dashboard_gov_portal_topnav_css.php'; ?>
|
|
.layout {
|
|
display: flex;
|
|
flex: 1;
|
|
min-height: 0;
|
|
}
|
|
/* 좌측 사이드 */
|
|
.sidebar {
|
|
width: 168px;
|
|
flex-shrink: 0;
|
|
background: #fff;
|
|
border-right: 1px solid var(--border);
|
|
display: flex;
|
|
flex-direction: column;
|
|
font-size: 0.8125rem;
|
|
}
|
|
.my-menu-hd {
|
|
background: var(--navy);
|
|
color: #fff;
|
|
padding: 0.5rem 0.625rem;
|
|
font-weight: 700;
|
|
font-size: 0.6875rem; /* 11px — MY MENU 라벨 */
|
|
letter-spacing: 0.04em;
|
|
}
|
|
.my-menu-list { list-style: none; padding: 0.375rem 0.25rem; flex: 1; }
|
|
.my-menu-list li { margin: 0.1875rem 0.375rem; }
|
|
.my-menu-list a,
|
|
.my-menu-list .menu-sub {
|
|
display: flex;
|
|
align-items: center;
|
|
gap: 0.375rem;
|
|
padding: 0.4375rem 0.625rem;
|
|
margin: 0;
|
|
border-radius: 10px;
|
|
border: 1px solid rgba(255, 255, 255, 0.22);
|
|
text-decoration: none;
|
|
font-size: 0.8125rem; /* 13px */
|
|
font-weight: 600;
|
|
line-height: 1.35;
|
|
letter-spacing: -0.02em;
|
|
box-sizing: border-box;
|
|
transition: filter 0.15s ease, border-color 0.15s ease, box-shadow 0.15s ease;
|
|
}
|
|
.my-menu-list a {
|
|
color: #fff;
|
|
background: var(--blue-menu);
|
|
}
|
|
.my-menu-list a .menu-ico,
|
|
.my-menu-list .menu-sub .menu-ico {
|
|
font-size: 0.625rem;
|
|
opacity: .9;
|
|
width: 0.75rem;
|
|
text-align: center;
|
|
flex-shrink: 0;
|
|
}
|
|
.my-menu-list a:hover { filter: brightness(1.06); border-color: rgba(255, 255, 255, 0.35); }
|
|
.my-menu-list a.active {
|
|
background: #3d5a9e;
|
|
font-weight: 700;
|
|
border-color: rgba(255, 255, 255, 0.4);
|
|
box-shadow: 0 1px 3px rgba(26, 43, 75, 0.12);
|
|
}
|
|
.my-menu-list a.menu-sub,
|
|
.my-menu-list .menu-sub {
|
|
background: var(--blue-light);
|
|
color: var(--blue);
|
|
font-size: 0.75rem;
|
|
font-weight: 600;
|
|
border-color: rgba(0, 86, 179, 0.18);
|
|
}
|
|
.sidebar-blocks { margin-top: auto; }
|
|
.sb-teal {
|
|
background: var(--teal);
|
|
color: #fff;
|
|
padding: 0.75rem 0.625rem;
|
|
font-size: 0.6875rem;
|
|
line-height: 1.5;
|
|
letter-spacing: -0.02em;
|
|
}
|
|
.sb-teal i { font-size: 1.125rem; margin-bottom: 0.25rem; display: block; }
|
|
.sb-gray {
|
|
background: #4a5568;
|
|
color: #fff;
|
|
padding: 0.625rem;
|
|
font-size: 0.6875rem;
|
|
line-height: 1.45;
|
|
}
|
|
.sb-links {
|
|
padding: 0.625rem;
|
|
background: #f5f7fa;
|
|
font-size: 0.6875rem;
|
|
}
|
|
.sb-links a {
|
|
display: block;
|
|
color: #555;
|
|
text-decoration: none;
|
|
padding: 0.1875rem 0;
|
|
letter-spacing: -0.02em;
|
|
font-weight: 600;
|
|
}
|
|
.sb-links a:hover { color: var(--blue-ui); }
|
|
|
|
/* 메인 그리드 */
|
|
.main {
|
|
flex: 1;
|
|
padding: 0.875rem 1rem 1rem;
|
|
overflow-y: auto;
|
|
}
|
|
.grid {
|
|
display: grid;
|
|
grid-template-columns: repeat(12, 1fr);
|
|
gap: 0.875rem; /* ~14px */
|
|
align-items: stretch;
|
|
}
|
|
.grid .card-low-stock.stock-tall {
|
|
grid-row: span 2;
|
|
}
|
|
.card {
|
|
background: var(--card);
|
|
border-radius: 12px;
|
|
box-shadow: 0 1px 3px rgba(26,43,75,.06), 0 2px 8px rgba(26,43,75,.04);
|
|
border: 1px solid var(--border);
|
|
overflow: hidden;
|
|
}
|
|
.card-hd {
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: space-between;
|
|
padding: 0.625rem 0.875rem;
|
|
border-bottom: 1px solid var(--border);
|
|
font-weight: 700;
|
|
font-size: 1rem; /* ~16px 카드 제목 */
|
|
color: var(--text-dark);
|
|
letter-spacing: -0.03em;
|
|
line-height: 1.3;
|
|
}
|
|
.card-hd i {
|
|
color: var(--blue-ui);
|
|
margin-right: 0.3rem;
|
|
font-size: 0.875rem;
|
|
}
|
|
.card-bd { padding: 0.875rem 1rem; }
|
|
.span-3 { grid-column: span 3; }
|
|
.span-4 { grid-column: span 4; }
|
|
.span-5 { grid-column: span 5; }
|
|
.span-6 { grid-column: span 6; }
|
|
.span-8 { grid-column: span 8; }
|
|
.span-12 { grid-column: span 12; }
|
|
@media (max-width: 1200px) {
|
|
.span-3, .span-4, .span-5, .span-6, .span-8 { grid-column: span 12; }
|
|
.grid .card-low-stock.stock-tall { grid-row: span 1; }
|
|
.sidebar { width: 100%; border-right: none; border-bottom: 1px solid var(--border); }
|
|
.layout { flex-direction: column; }
|
|
.my-menu-list { display: flex; flex-wrap: wrap; }
|
|
}
|
|
|
|
.card-welcome {
|
|
background: #4a5568;
|
|
color: #fff;
|
|
border: none;
|
|
box-shadow: 0 2px 6px rgba(74,85,104,.25);
|
|
}
|
|
.card-welcome .card-bd { padding: 1rem 0.875rem; }
|
|
.welcome-hi {
|
|
font-size: 0.75rem;
|
|
color: rgba(255,255,255,.75);
|
|
letter-spacing: -0.02em;
|
|
}
|
|
.welcome-name {
|
|
font-size: 1rem;
|
|
font-weight: 700;
|
|
margin: 0.25rem 0 0.375rem;
|
|
letter-spacing: -0.03em;
|
|
}
|
|
.welcome-meta {
|
|
font-size: 0.6875rem;
|
|
color: rgba(255,255,255,.7);
|
|
line-height: 1.5;
|
|
letter-spacing: -0.02em;
|
|
}
|
|
.welcome-btns { display: flex; gap: 0.375rem; margin-top: 0.625rem; }
|
|
.welcome-btns a {
|
|
padding: 0.3125rem 0.625rem;
|
|
border-radius: 4px;
|
|
font-size: 0.75rem;
|
|
font-weight: 500;
|
|
text-decoration: none;
|
|
border: 1px solid rgba(255,255,255,.35);
|
|
background: rgba(255,255,255,.08);
|
|
color: #fff;
|
|
letter-spacing: -0.02em;
|
|
}
|
|
.welcome-btns a:hover { background: rgba(255,255,255,.18); }
|
|
|
|
.notice-item {
|
|
padding: 0.4375rem 0;
|
|
border-bottom: 1px dashed #e8edf2;
|
|
}
|
|
.notice-item:last-child { border-bottom: none; }
|
|
.notice-item .notice-title {
|
|
display: block;
|
|
font-size: 0.8125rem;
|
|
font-weight: 600;
|
|
color: var(--text-dark);
|
|
margin-bottom: 0.25rem;
|
|
line-height: 1.4;
|
|
letter-spacing: -0.02em;
|
|
}
|
|
.notice-item .notice-date {
|
|
display: inline-block;
|
|
font-size: 0.6875rem;
|
|
font-weight: 500;
|
|
color: var(--blue-ui);
|
|
background: var(--blue-light);
|
|
padding: 0.125rem 0.375rem;
|
|
border-radius: 2px;
|
|
letter-spacing: 0;
|
|
}
|
|
|
|
.stat-grid {
|
|
display: grid;
|
|
grid-template-columns: repeat(3, 1fr);
|
|
gap: 0.375rem;
|
|
text-align: center;
|
|
}
|
|
.stat-grid .num {
|
|
font-size: 1.5rem; /* ~22px */
|
|
font-weight: 700;
|
|
color: #2563eb;
|
|
line-height: 1.15;
|
|
letter-spacing: -0.03em;
|
|
}
|
|
.stat-grid .num.num-text { font-size: 1.125rem; color: #10b981; }
|
|
.stat-grid .lbl {
|
|
font-size: 0.6875rem;
|
|
color: var(--muted);
|
|
margin-top: 0.1875rem;
|
|
font-weight: 400;
|
|
letter-spacing: -0.02em;
|
|
}
|
|
.stat-foot {
|
|
margin-top: 0.625rem;
|
|
padding-top: 0.4375rem;
|
|
border-top: 1px solid var(--border);
|
|
font-size: 0.6875rem;
|
|
color: var(--muted);
|
|
letter-spacing: -0.02em;
|
|
}
|
|
|
|
<?php include __DIR__ . '/_dashboard_gov_portal_stock_cards_css.php'; ?>
|
|
|
|
.search-teal {
|
|
background: var(--teal);
|
|
color: #fff;
|
|
padding: 0.875rem;
|
|
border-radius: 12px;
|
|
height: 100%;
|
|
min-height: 5.5rem;
|
|
}
|
|
.search-teal strong {
|
|
font-size: 0.875rem;
|
|
font-weight: 600;
|
|
letter-spacing: -0.02em;
|
|
}
|
|
.search-teal input {
|
|
width: 100%;
|
|
margin-top: 0.4375rem;
|
|
padding: 0.4375rem 1.75rem 0.4375rem 0.625rem;
|
|
border: none;
|
|
border-radius: 4px;
|
|
font-size: 0.8125rem;
|
|
font-family: inherit;
|
|
letter-spacing: -0.02em;
|
|
}
|
|
.search-wrap { position: relative; }
|
|
.search-wrap i {
|
|
position: absolute;
|
|
right: 0.65rem;
|
|
top: 50%;
|
|
transform: translateY(-50%);
|
|
color: var(--muted);
|
|
}
|
|
<?php include __DIR__ . '/_dashboard_gov_portal_menu_search_css.php'; ?>
|
|
|
|
.desk-blue {
|
|
background: linear-gradient(160deg, #1a4a8a 0%, #007bff 100%);
|
|
color: #fff;
|
|
padding: 0.875rem;
|
|
border-radius: 12px;
|
|
font-size: 0.75rem;
|
|
line-height: 1.65;
|
|
letter-spacing: -0.02em;
|
|
height: 100%;
|
|
min-height: 5.5rem;
|
|
}
|
|
.desk-blue strong {
|
|
font-size: 0.875rem;
|
|
font-weight: 700;
|
|
display: block;
|
|
margin-bottom: 0.3rem;
|
|
letter-spacing: -0.03em;
|
|
}
|
|
|
|
<?php include __DIR__ . '/_dashboard_gov_portal_map_css.php'; ?>
|
|
.timeline-side {
|
|
background: var(--navy-deep);
|
|
color: #fff;
|
|
padding: 0.375rem 0.25rem;
|
|
max-height: 200px;
|
|
overflow-y: auto;
|
|
font-size: 0.75rem;
|
|
}
|
|
.timeline-side .item {
|
|
padding: 0.375rem 0.3125rem;
|
|
border-bottom: 1px solid rgba(255,255,255,.12);
|
|
}
|
|
.timeline-side .time {
|
|
display: block;
|
|
font-size: 0.8125rem;
|
|
font-weight: 700;
|
|
color: #fff;
|
|
letter-spacing: -0.02em;
|
|
margin-bottom: 0.125rem;
|
|
}
|
|
.timeline-side .ev-text {
|
|
font-size: 0.75rem;
|
|
font-weight: 600;
|
|
color: #4fc3f7;
|
|
line-height: 1.35;
|
|
letter-spacing: -0.02em;
|
|
}
|
|
|
|
.donut-wrap {
|
|
display: flex;
|
|
align-items: center;
|
|
gap: 1rem;
|
|
}
|
|
.donut {
|
|
width: 82px;
|
|
height: 82px;
|
|
border-radius: 50%;
|
|
background: conic-gradient(#3b82f6 0% 52%, #10b981 52% 80%, #f59e0b 80% 100%);
|
|
position: relative;
|
|
flex-shrink: 0;
|
|
}
|
|
.donut::after {
|
|
content: '52%';
|
|
position: absolute;
|
|
inset: 24%;
|
|
background: #fff;
|
|
border-radius: 50%;
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
font-weight: 700;
|
|
font-size: 1.125rem;
|
|
color: var(--navy);
|
|
letter-spacing: -0.03em;
|
|
}
|
|
.donut-legend { list-style: none; font-size: 0.6875rem; color: var(--muted); line-height: 1.5; }
|
|
.mini-bars {
|
|
display: flex;
|
|
align-items: flex-end;
|
|
gap: 3px;
|
|
height: 64px;
|
|
}
|
|
.mini-bars .col {
|
|
flex: 1;
|
|
display: flex;
|
|
flex-direction: column;
|
|
align-items: center;
|
|
justify-content: flex-end;
|
|
gap: 2px;
|
|
font-size: 0.625rem;
|
|
color: var(--muted);
|
|
font-weight: 500;
|
|
}
|
|
.mini-bars .bar {
|
|
width: 100%;
|
|
background: linear-gradient(180deg, #2563eb, #60a5fa);
|
|
border-radius: 3px 3px 0 0;
|
|
min-height: 4px;
|
|
}
|
|
.gis-btn {
|
|
background: var(--blue-ui);
|
|
color: #fff;
|
|
font-size: 0.6875rem;
|
|
font-weight: 500;
|
|
padding: 0.25rem 0.5rem;
|
|
border-radius: 3px;
|
|
text-decoration: none;
|
|
letter-spacing: -0.02em;
|
|
}
|
|
.flash-ok {
|
|
grid-column: 1 / -1;
|
|
background: #ecfdf5;
|
|
border: 1px solid #a7f3d0;
|
|
color: #065f46;
|
|
padding: 0.65rem 1rem;
|
|
border-radius: 8px;
|
|
font-size: 12px;
|
|
}
|
|
</style>
|
|
</head>
|
|
<body>
|
|
<header class="portal-header">
|
|
<div class="portal-header-inner">
|
|
<?= view('home/_dashboard_gov_portal_brand', ['brandHref' => base_url('dashboard/gov-portal')]) ?>
|
|
<?= view('home/_dashboard_gov_portal_topnav_click', $govPortalNavPartial) ?>
|
|
<?= view('home/_dashboard_gov_portal_header_utils', ['activeVariant' => $activeVariant, 'portalVariants' => $portalVariants, 'mbName' => $mbName, 'levelName' => $levelName, 'lgLabel' => $lgLabel]) ?>
|
|
</div>
|
|
</header>
|
|
|
|
<div class="layout">
|
|
<?= view('home/_dashboard_gov_portal_sidebar', $govPortalNavPartial) ?>
|
|
|
|
<main class="main">
|
|
<div class="grid">
|
|
<?php if (session()->getFlashdata('success')): ?>
|
|
<div class="flash-ok"><?= esc(session()->getFlashdata('success')) ?></div>
|
|
<?php endif; ?>
|
|
|
|
<!-- 사용자 정보 (스크린샷: 다크 그레이 프로필 카드) -->
|
|
<div class="card card-welcome span-3">
|
|
<div class="card-bd">
|
|
<p class="welcome-hi">안녕하세요.</p>
|
|
<p class="welcome-name"><?= esc($mbName) ?>님</p>
|
|
<p class="welcome-meta">아이디 <?= esc($mbId) ?><br/>최근접속 <?= date('Y.m.d H:i') ?></p>
|
|
<div class="welcome-btns">
|
|
<a href="<?= base_url(gov_portal_code_kinds_portal_path('base')) ?>">기본 코드관리</a>
|
|
<a href="<?= base_url('dashboard/simple') ?>">마이페이지</a>
|
|
<a href="<?= base_url('logout') ?>">로그아웃</a>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 메시지 -->
|
|
<div class="card span-4">
|
|
<div class="card-hd"><span><i class="fa-regular fa-envelope"></i> 메시지</span></div>
|
|
<div class="card-bd">
|
|
<?php foreach ($notices as $n): ?>
|
|
<div class="notice-item">
|
|
<span class="notice-title"><?= esc($n['title']) ?></span>
|
|
<span class="notice-date"><?= esc($n['date']) ?></span>
|
|
</div>
|
|
<?php endforeach; ?>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 핵심 지표 (메인 요약과 동일) -->
|
|
<div class="card span-5">
|
|
<div class="card-hd"><span><i class="fa-solid fa-warehouse"></i> 업무 현황 요약</span></div>
|
|
<div class="card-bd">
|
|
<div class="stat-grid">
|
|
<div>
|
|
<div class="num num-text">양호</div>
|
|
<div class="lbl">봉투 재고</div>
|
|
</div>
|
|
<div>
|
|
<div class="num">12</div>
|
|
<div class="lbl">미처리 구매신청</div>
|
|
</div>
|
|
<div>
|
|
<div class="num">4</div>
|
|
<div class="lbl">승인 대기</div>
|
|
</div>
|
|
</div>
|
|
<div class="stat-foot">
|
|
<i class="fa-solid fa-location-dot"></i> <?= esc($lgLabel) ?> · 기준일 <?= date('Y.m.d') ?>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 지도/타임라인 영역 -->
|
|
<div class="card span-8" style="padding:0;">
|
|
<div class="card-hd">
|
|
<span><i class="fa-solid fa-map"></i> 판매·수불 최근 동향</span>
|
|
<a href="<?= base_url('bag/flow') ?>" class="gis-btn">수불 통합 조회 ></a>
|
|
</div>
|
|
<div style="display:grid;grid-template-columns:1fr 140px;">
|
|
<?= view('home/_dashboard_gov_portal_map_panel', [
|
|
'mapId' => 'govPortalMainMap',
|
|
'mapHeight' => '200px',
|
|
'lgLabel' => $lgLabel,
|
|
'govMapPanel' => $govMapPanel,
|
|
]) ?>
|
|
<div class="timeline-side">
|
|
<?php foreach ($timeline as $ev): ?>
|
|
<div class="item">
|
|
<span class="time"><?= esc($ev['time']) ?></span>
|
|
<span class="ev-text"><?= esc($ev['text']) ?></span>
|
|
</div>
|
|
<?php endforeach; ?>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 메뉴 검색 -->
|
|
<div class="span-4">
|
|
<?= view('home/_dashboard_gov_portal_menu_search', [
|
|
'variant' => 'teal',
|
|
'inputId' => 'menuSearch',
|
|
'menuSearchOptions' => $menuSearchOptions,
|
|
]) ?>
|
|
</div>
|
|
|
|
<!-- 서비스 데스크 -->
|
|
<div class="span-4">
|
|
<div class="desk-blue">
|
|
<strong><i class="fa-solid fa-headset"></i> 서비스 데스크</strong>
|
|
담당: 시스템 운영팀<br/>
|
|
문의: help@wxn.local (목업)<br/>
|
|
평일 09:00 ~ 18:00
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 재고 경보 단계 -->
|
|
<div class="card span-4">
|
|
<div class="card-hd"><span><i class="fa-solid fa-triangle-exclamation"></i> 재고 경보</span></div>
|
|
<div class="card-bd">
|
|
<?= view('home/_dashboard_gov_portal_stock_alert_levels', ['stockAlerts' => $stockAlerts]) ?>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 부족 재고 — 2행 span으로 재고 구성 오른쪽 빈칸(4열)까지 세로 채움 -->
|
|
<div class="card card-low-stock stock-tall span-4">
|
|
<div class="card-hd"><span><i class="fa-solid fa-box-open"></i> 부족 재고</span></div>
|
|
<div class="card-bd">
|
|
<div class="low-stock-grid">
|
|
<?php foreach ($lowStock as $item): ?>
|
|
<div class="bar-row">
|
|
<div class="meta"><span><?= esc($item['name']) ?></span><span><?= esc((string) $item['percent']) ?>%</span></div>
|
|
<div class="bar-track"><div class="bar-fill" style="width:<?= (int) $item['percent'] ?>%"></div></div>
|
|
</div>
|
|
<?php endforeach; ?>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 7일 추이 -->
|
|
<div class="card span-4">
|
|
<div class="card-hd"><span><i class="fa-solid fa-chart-column"></i> 최근 7일 신청</span></div>
|
|
<div class="card-bd">
|
|
<?php $maxReq = max($weeklyRequests); ?>
|
|
<div class="mini-bars">
|
|
<?php foreach ($weeklyRequests as $idx => $v): ?>
|
|
<?php $h = (int) round(($v / $maxReq) * 100); ?>
|
|
<div class="col">
|
|
<span><?= esc((string) $v) ?></span>
|
|
<div class="bar" style="height:<?= $h ?>%"></div>
|
|
<span>D<?= 6 - $idx ?></span>
|
|
</div>
|
|
<?php endforeach; ?>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 재고 구성 -->
|
|
<div class="card span-4">
|
|
<div class="card-hd"><span><i class="fa-solid fa-chart-pie"></i> 재고 구성</span></div>
|
|
<div class="card-bd">
|
|
<div class="donut-wrap">
|
|
<div class="donut" aria-hidden="true"></div>
|
|
<ul class="donut-legend">
|
|
<?php foreach ($stockMix as $item): ?>
|
|
<li>
|
|
<span style="display:inline-block;width:7px;height:7px;border-radius:50%;background:<?= esc($item['color'], 'attr') ?>;vertical-align:middle;margin-right:3px;"></span>
|
|
<?= esc($item['name']) ?> <?= esc((string) $item['value']) ?>%
|
|
</li>
|
|
<?php endforeach; ?>
|
|
</ul>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
</div>
|
|
</main>
|
|
</div>
|
|
|
|
<?= view('home/_dashboard_gov_portal_nav_script_base', $govPortalNavPartial) ?>
|
|
<?= view('home/_dashboard_gov_portal_font_zoom_script') ?>
|
|
</body>
|
|
</html>
|