/* 연구기회 인텔리전스 플랫폼 관리자 UI
   명세 21.11 접근성·사용성 / 27.8 접근성
   - 한국어 UI
   - 색상만으로 상태를 구분하지 않는다 (아이콘·텍스트 병기)
   - 충분한 대비, 키보드 탐색, 명확한 Label */

:root {
  --bg: #f5f6f8;
  --surface: #ffffff;
  --border: #d7dae0;
  --text: #1f2933;
  --text-muted: #52606d;
  --primary: #1a4f8a;
  --primary-hover: #14406f;
  --danger: #a3262b;
  --danger-hover: #851f23;
  --ok-bg: #e3f2e6;
  --ok-fg: #1c5c2b;
  --wait-bg: #fdf3d8;
  --wait-fg: #7a5a05;
  --stop-bg: #fbe4e5;
  --stop-fg: #8c2126;
  --off-bg: #e8eaed;
  --off-fg: #414c56;
  --radius: 8px;
  --focus: #0b63ce;
}

* { box-sizing: border-box; }

/* hidden 속성이 항상 이기게 한다.
   .notice 처럼 display 를 지정한 클래스가 붙어 있으면 UA 기본값이 덮여
   빈 알림 상자가 보이는 문제가 생긴다. */
[hidden] { display: none !important; }

body {
  margin: 0;
  font-family: "Pretendard", "Malgun Gothic", -apple-system, BlinkMacSystemFont,
    "Segoe UI", system-ui, sans-serif;
  background: var(--bg);
  color: var(--text);
  line-height: 1.6;
  font-size: 15px;
  /* 한국어는 단어 중간에서 줄이 끊기면 읽기 어렵다. 어절 단위로 넘긴다. */
  word-break: keep-all;
  overflow-wrap: break-word;
}

/* 키보드 탐색 시 초점이 분명히 보이게 한다 (명세 27.8) */
:focus-visible {
  outline: 3px solid var(--focus);
  outline-offset: 2px;
}

.skip-link {
  position: absolute;
  left: -9999px;
  top: 0;
  background: var(--primary);
  color: #fff;
  padding: .6rem 1rem;
  z-index: 100;
}
.skip-link:focus { left: 0; }

/* ---------- 인증 확인 게이트 ----------
   세션 확인이 끝나기 전에는 화면 내용을 그리지 않는다.
   미로그인 상태에서 대시보드가 잠깐 보였다가 로그인 화면으로 넘어가는
   현상을 막기 위함이다. 스타일시트가 렌더링을 막으므로 깜빡임이 없다. */
/* 숨길 때만 display 를 건드린다.
   `display: revert` 로 되돌리면 .topbar 의 flex 같은 원래 값이 아니라
   브라우저 기본값(block)이 되어 배치가 무너진다. */
html[data-auth="checking"] .app-shell { display: none !important; }

#auth-gate {
  min-height: 100vh;
  display: grid;
  place-items: center;
  padding: 1.5rem;
  text-align: center;
  color: var(--text-muted);
}
html[data-auth="ready"] #auth-gate { display: none; }

#auth-gate .spinner {
  width: 1.75rem;
  height: 1.75rem;
  margin: 0 auto .75rem;
  border: 3px solid var(--border);
  border-top-color: var(--primary);
  border-radius: 50%;
  animation: spin .8s linear infinite;
}
@keyframes spin { to { transform: rotate(360deg); } }

/* 화면 깜빡임을 줄이려는 장치일 뿐이므로, 모션을 줄이는 설정에서는 회전을 멈춘다. */
@media (prefers-reduced-motion: reduce) {
  #auth-gate .spinner { animation: none; }
}

/* ---------- 레이아웃 ---------- */
.topbar {
  background: var(--surface);
  border-bottom: 1px solid var(--border);
  padding: .75rem 1.5rem;
  display: flex;
  align-items: center;
  gap: 1rem;
  flex-wrap: wrap;
}
.topbar h1 { font-size: 1.05rem; margin: 0; font-weight: 700; }
.topbar .spacer { flex: 1; }
.topbar nav { display: flex; gap: .25rem; flex-wrap: wrap; }
.topbar nav a {
  color: var(--text-muted);
  text-decoration: none;
  padding: .4rem .7rem;
  border-radius: var(--radius);
  font-size: .92rem;
}
.topbar nav a:hover { background: var(--bg); color: var(--text); }
.topbar nav a[aria-current="page"] {
  background: var(--primary);
  color: #fff;
  font-weight: 600;
}

main { max-width: 1120px; margin: 0 auto; padding: 1.5rem; }

.card {
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  padding: 1.25rem;
  margin-bottom: 1.25rem;
}
.card > h2 {
  margin: 0 0 .25rem;
  font-size: 1.05rem;
}
.card > .hint { margin: 0 0 1rem; color: var(--text-muted); font-size: .9rem; }

/* ---------- 표 ---------- */
.table-wrap { overflow-x: auto; }  /* 긴 표는 가로 스크롤 (명세 21.11) */
table { width: 100%; border-collapse: collapse; font-size: .92rem; }
/* 표 caption 은 보조기술에만 제공한다.
   화면에는 카드 제목과 설명이 이미 같은 내용을 보여 주므로 시각적으로는 감춘다. */
caption, .sr-only {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  overflow: hidden;
  clip-path: inset(50%);
  white-space: nowrap;
  border: 0;
}
th, td {
  text-align: left;
  padding: .65rem .7rem;
  border-bottom: 1px solid var(--border);
  vertical-align: top;
}
th { background: #eef0f3; font-weight: 600; white-space: nowrap; }
tbody tr:hover { background: #fafbfc; }
td.actions { white-space: nowrap; }

/* ---------- 상태 배지: 색 + 기호 + 글자 ---------- */
.badge {
  display: inline-flex;
  align-items: center;
  gap: .3rem;
  padding: .15rem .5rem;
  border-radius: 999px;
  font-size: .82rem;
  font-weight: 600;
  white-space: nowrap;
}
.badge::before { font-weight: 700; }
.badge-ok   { background: var(--ok-bg);   color: var(--ok-fg); }
.badge-ok::before { content: "●"; }
.badge-wait { background: var(--wait-bg); color: var(--wait-fg); }
.badge-wait::before { content: "◐"; }
.badge-stop { background: var(--stop-bg); color: var(--stop-fg); }
.badge-stop::before { content: "■"; }
.badge-off  { background: var(--off-bg);  color: var(--off-fg); }
.badge-off::before { content: "○"; }

/* ---------- 버튼·폼 ---------- */
button, .btn {
  font: inherit;
  border-radius: var(--radius);
  border: 1px solid var(--border);
  background: var(--surface);
  color: var(--text);
  padding: .45rem .85rem;
  cursor: pointer;
}
button:hover:not(:disabled) { background: var(--bg); }
button:disabled { opacity: .55; cursor: not-allowed; }
.btn-primary {
  background: var(--primary);
  border-color: var(--primary);
  color: #fff;
  font-weight: 600;
}
.btn-primary:hover:not(:disabled) { background: var(--primary-hover); }
.btn-danger { background: var(--surface); border-color: var(--danger); color: var(--danger); }
.btn-danger:hover:not(:disabled) { background: var(--stop-bg); }
.btn-sm { padding: .3rem .6rem; font-size: .87rem; }

label { display: block; font-weight: 600; margin-bottom: .3rem; font-size: .92rem; }
input[type="text"], input[type="password"], input[type="search"], select, textarea {
  font: inherit;
  width: 100%;
  padding: .5rem .6rem;
  border: 1px solid var(--border);
  border-radius: var(--radius);
  background: #fff;
  color: var(--text);
}
fieldset { border: 1px solid var(--border); border-radius: var(--radius); padding: .8rem; }
legend { font-weight: 600; padding: 0 .35rem; font-size: .92rem; }
.field { margin-bottom: .9rem; }
.field-hint { font-size: .85rem; color: var(--text-muted); margin-top: .25rem; }
.checks { display: grid; gap: .4rem; }
.checks label {
  display: flex;
  gap: .5rem;
  align-items: flex-start;
  font-weight: 400;
  margin: 0;
}
.checks input { margin-top: .35rem; }
.checks .role-name { font-weight: 600; }
.checks .role-desc { color: var(--text-muted); font-size: .87rem; }

/* ---------- 알림 ---------- */
.notice {
  border-radius: var(--radius);
  padding: .8rem 1rem;
  margin-bottom: 1rem;
  border: 1px solid;
  display: flex;
  gap: .6rem;
  align-items: flex-start;
}
.notice strong { flex-shrink: 0; }
.notice-info  { background: #e8f1fb; border-color: #9cc3e8; color: #17436f; }
.notice-ok    { background: var(--ok-bg);   border-color: #9ecfa8; color: var(--ok-fg); }
.notice-wait  { background: var(--wait-bg); border-color: #e2c86a; color: var(--wait-fg); }
.notice-error { background: var(--stop-bg); border-color: #dfa2a5; color: var(--stop-fg); }

.muted { color: var(--text-muted); }
.small { font-size: .87rem; }
.mono { font-family: ui-monospace, "SFMono-Regular", Menlo, Consolas, monospace; }
.empty { padding: 2rem; text-align: center; color: var(--text-muted); }
.counts { display: flex; gap: .5rem; flex-wrap: wrap; margin-bottom: 1rem; }

/* ---------- 로그인 ---------- */
.login-page {
  min-height: 100vh;
  display: grid;
  place-items: center;
  padding: 1.5rem;
}
.login-box { width: 100%; max-width: 25rem; }
.login-box h1 { font-size: 1.2rem; margin: 0 0 .25rem; }
.login-box .sub { color: var(--text-muted); margin: 0 0 1.5rem; font-size: .92rem; }
.google-btn {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: .6rem;
  width: 100%;
  padding: .7rem;
  font-weight: 600;
  text-decoration: none;
  color: var(--text);
  background: #fff;
  border: 1px solid var(--border);
  border-radius: var(--radius);
}
.google-btn:hover { background: var(--bg); }
.divider {
  display: flex;
  align-items: center;
  gap: .75rem;
  margin: 1.25rem 0;
  color: var(--text-muted);
  font-size: .87rem;
}
.divider::before, .divider::after {
  content: "";
  flex: 1;
  height: 1px;
  background: var(--border);
}

/* ---------- 모달 ---------- */
dialog {
  border: 1px solid var(--border);
  border-radius: var(--radius);
  padding: 1.25rem;
  max-width: 30rem;
  width: calc(100% - 2rem);
  color: var(--text);
}
dialog::backdrop { background: rgba(31, 41, 51, .5); }
dialog h2 { margin-top: 0; font-size: 1.05rem; }
.dialog-actions {
  display: flex;
  gap: .5rem;
  justify-content: flex-end;
  margin-top: 1.25rem;
}

@media (max-width: 640px) {
  main { padding: 1rem; }
  .topbar { padding: .6rem 1rem; }
}
