/* ==========================================================
   マゼモン図鑑 3D回遊バージョン (index-3d.html 専用)
   - body.zukan3d が付いたページでのみ有効
   - 全カードが単一の円周軌道に並び、常に正面を向いたまま
     周回する(配置・回転は zukan-3d.js が毎フレーム駆動)
   ========================================================== */

/* ---- 図鑑セクションをダークなデジタル空間に上書き ---- */

body.zukan3d #zukan {
  background:
    radial-gradient(ellipse 90% 60% at 50% 110%, rgba(2, 161, 243, 0.25), transparent 70%),
    linear-gradient(180deg, #0a1130 0%, #0d1840 45%, #071028 100%);
  background-image:
    radial-gradient(circle, rgba(157, 252, 255, 0.08) 1px, transparent 1.6px),
    radial-gradient(ellipse 90% 60% at 50% 110%, rgba(2, 161, 243, 0.25), transparent 70%),
    linear-gradient(180deg, #0a1130 0%, #0d1840 45%, #071028 100%);
  background-size: 26px 26px, 100% 100%, 100% 100%;
  color: var(--color-text-cyan-pale);
  overflow: hidden;
}

/* 2026-08-26: パーク選択・ステータスは削除したので、
   それらへの上書きも撤去した。

   カードは実測で「ステージ内の 135px〜522px」を占めるので、
   ステージの外側(セクションのpadding + stageのmargin)だけを削り、
   ステージ自体の高さと ring の位置(top:48%)は触っていない
   —— そこは奥のカードが上に浮く立体感の作りなので、
   詰めると遠近の見え方が変わってしまう。

   2026-09-09: 見出しを戻したので、上の padding は
   見出しが入るぶんだけ空けている(8px だと題字がヘッダーの帯に詰まる) */
body.zukan3d #zukan {
  padding-top: 34px;
  padding-bottom: 24px;
}
body.zukan3d #zukan .zukan3d-stage { margin-top: 0; }

/* データソースのグリッドは非表示(.card-grid の display:grid が hidden 属性に勝つため明示) */
body.zukan3d #card-grid[hidden] { display: none; }

/* ==========================================================
   3Dステージ
   ========================================================== */

.zukan3d-stage {
  position: relative;
  z-index: 1;
  /* カードサイズ・軌道は全デバイス固定(zukan-3d.js)のため、
     ステージ高さも固定。狭い画面では環の見える範囲だけが変わる */
  height: 600px;
  margin-top: 28px;
  /* 遠近の投影は zukan-3d.js が2D transformで計算する
     (CSSのperspective+preserve-3dは枚数が多いと描画が破綻するため不使用) */
  overflow: hidden;
}

/* 奥に流れるグリッドの床。
   【性能】以前は background-position をアニメーションさせていたが、
   それだと 200vw × 420px の面(マスク付き)を**毎フレーム塗り直す**ことになり、
   スマホでは重い。グリッドは静止させたまま、中身(::before)を
   transform で 60px ずらす方式に変えてある。
   transform は合成側で処理されるので塗り直しが起きない。見た目は同じ */
.zukan3d-floor {
  position: absolute;
  left: 50%;
  bottom: -12%;
  width: 200vw;
  height: 70%;
  transform: translateX(-50%) rotateX(76deg);
  transform-origin: center bottom;
  overflow: hidden;
  -webkit-mask-image: radial-gradient(ellipse 55% 90% at 50% 100%, #000 30%, transparent 75%);
  mask-image: radial-gradient(ellipse 55% 90% at 50% 100%, #000 30%, transparent 75%);
}

.zukan3d-floor::before {
  content: "";
  position: absolute;
  /* 上へ60px はみ出させておく。1マス(60px)ぶん下へ動いた時点で
     見た目が元と一致するので、継ぎ目なくつながる */
  left: 0;
  right: 0;
  top: -60px;
  bottom: 0;
  background-image:
    repeating-linear-gradient(0deg, rgba(77, 250, 255, 0.35) 0 1px, transparent 1px 60px),
    repeating-linear-gradient(90deg, rgba(77, 250, 255, 0.25) 0 1px, transparent 1px 60px);
  /* 無限の transform アニメーションは Chromium が自動で合成側に載せるので
     will-change の指定は不要 */
  animation: floor-flow 3s linear infinite;
}

@keyframes floor-flow {
  from { transform: translateY(0); }
  to   { transform: translateY(60px); }
}

/* 中央のエネルギーコア(光)。
   【性能】以前は filter: blur(6px) をかけた要素を拡縮・明滅させていて、
   毎フレームぼかし直していた。ぼかしはグラデーションの止め位置に
   織り込んで filter を外してある(見た目はほぼ同じ) */
.zukan3d-core {
  position: absolute;
  left: 50%;
  top: 56%;
  width: 132px;
  height: 132px;
  transform: translate(-50%, -50%);
  border-radius: 50%;
  background: radial-gradient(circle,
    rgba(157, 252, 255, 0.8) 0%,
    rgba(107, 226, 255, 0.5) 28%,
    rgba(0, 169, 255, 0.22) 52%,
    rgba(0, 169, 255, 0.06) 66%,
    transparent 76%);
  animation: core-pulse 2.6s ease-in-out infinite;
  pointer-events: none;
}

@keyframes core-pulse {
  0%, 100% { transform: translate(-50%, -50%) scale(1); opacity: 0.75; }
  50%      { transform: translate(-50%, -50%) scale(1.35); opacity: 1; }
}

/* ---- シーン ---- */

.zukan3d-scene {
  position: absolute;
  inset: 0;
}

/* 楕円軌道の中心アンカー(各カードはここからの translate で配置される) */
.zukan3d-ring {
  position: absolute;
  left: 50%;
  top: 48%;
}

/* ---- カード ----
   transform は JS が毎フレーム設定:
   translate(円周のX, 奥行きに応じたY) scale(奥行きに応じた縮尺)
   + z-index/opacity で前後関係と遠近感を表現 */

.zukan3d-card {
  position: absolute;
  left: 0;
  top: 0;
  width: var(--card-w, 150px);
  aspect-ratio: 222 / 332;
  margin-left: calc(var(--card-w, 150px) / -2);
  margin-top: calc(var(--card-w, 150px) * 332 / 222 / -2);
  padding: 0;
  border: none;
  background: transparent;
  cursor: pointer;
  /* 【性能】カードを合成レイヤーに載せる。
     transform/opacity を毎フレーム書き換えるので、レイヤーに載せないと
     30枚ぶんのカード絵と影(box-shadow 2つ)を毎フレーム塗り直すことになり、
     スマホ実機ではこれが周回のカクつきになっていた。
     載せておけばラスタライズは1枚につき1回で済み、
     以降の移動・明滅は合成側だけで処理される */
  will-change: transform;
}

/* まだ画像を読めていないカードのうら面。
   画像は正面に近づいてから順に読む(zukan-3d.js の LOAD_ANGLE)ので、
   それまでは伏せたカードとして見せる。
   background-size は contain —— カード絵(1276×2008)は枠の比率
   (222/332)よりわずかに縦長で object-fit: contain で少し余白が出るため、
   うら面も同じ収め方にして位置をぴったり合わせている */
.zukan3d-card::before {
  content: "";
  position: absolute;
  inset: 0;
  border-radius: 8px;
  background: url("../assets/zukan/card_back.jpg") center / contain no-repeat;
  box-shadow: 0 0 14px rgba(77, 250, 255, 0.35), 0 14px 26px rgba(0, 0, 0, 0.45);
  transition: transform 0.25s, box-shadow 0.25s, opacity 0.35s;
}

/* 読み終わったらうら面と入れ替える */
.zukan3d-card.is-loaded::before { opacity: 0; }

.zukan3d-card img {
  position: relative;
  width: 100%;
  height: 100%;
  object-fit: contain;
  border-radius: 8px;
  box-shadow: 0 0 14px rgba(77, 250, 255, 0.35), 0 14px 26px rgba(0, 0, 0, 0.45);
  opacity: 0;
  transition: transform 0.25s, box-shadow 0.25s, opacity 0.35s;
}

.zukan3d-card.is-loaded img { opacity: 1; }

.zukan3d-card:hover img,
.zukan3d-card:focus-visible img,
.zukan3d-card:hover::before,
.zukan3d-card:focus-visible::before {
  transform: scale(1.12) translateY(-6px);
  box-shadow: 0 0 30px var(--color-shadow-cyan-glow), 0 18px 30px rgba(0, 0, 0, 0.5);
}

.zukan3d-card:focus-visible { outline: 3px solid var(--color-text-cyan); outline-offset: 3px; }

/* ヒント */
.zukan3d-hint {
  position: absolute;
  left: 0;
  right: 0;
  bottom: 10px;
  text-align: center;
  font-size: 0.75rem;
  font-weight: 600;
  letter-spacing: 0.1em;
  color: rgba(157, 252, 255, 0.65);
  pointer-events: none;
  animation: hint-blink 3s ease-in-out infinite;
  z-index: 2;
}

@keyframes hint-blink {
  0%, 100% { opacity: 0.5; }
  50%      { opacity: 1; }
}

/* ---- レスポンシブ ----
   カードサイズ・軌道半径は全デバイス共通(zukan-3d.js の固定値)。
   メディアクエリでの縮小は行わない。 */
