/* 沼の環境スタイル。§2 パレット／§4.1 待機アニメーション／§4.2 まばたき。 */

.swamp {
  --sky:#171B16;
  --sky2:#171B16;
  --w1:#414A38; --w2:#39412F; --w3:#333B2A;
  --wline:#6B7860;
  --rim:#7A8A6C;
  --rip1:#5A6650; --rip2:#525E49; --rip3:#4A5343;
  --grass:#22281F;
  --weed:#4A5343;
  --fore:#293026;
  --fogc:#2E362B;
  --moonop:1;
  display: block;
  width: 100%;
}

.swamp .sky      { fill: var(--sky); }
.swamp .horizon  { fill: var(--sky2); opacity: var(--horizonop, .08); }
.swamp .w1       { fill: var(--w1); }
.swamp .w2       { fill: var(--w2); }
.swamp .w3       { fill: var(--w3); }
.swamp .wline    { stroke: var(--wline); }
.swamp .rim path { stroke: var(--rim); }

.swamp .moon { opacity: var(--moonop); animation: moonFade 8s ease-in-out infinite; }
.swamp .moon-shade { fill: var(--sky); opacity: var(--moonop); }

/* 空の薄雲。月より手前に置き、重なった領域だけ同じ形を月色で弱く重ねる。 */
.swamp .cloud-field path { fill: var(--cloud); opacity: .19; }
.swamp .cloud-light path { fill: #E2DCC8; opacity: var(--cloudlight, .16); }
.swamp .cloud-lane {
  animation: cloudDrift var(--cloud-duration) linear infinite;
  animation-delay: var(--cloud-delay);
  transform-box: view-box;
  transform-origin: 0 0;
  will-change: transform;
}

@keyframes cloudDrift {
  0%,100% { transform: translateX(-3.8px); }
  50%     { transform: translateX(3.8px); }
}

.swamp .fog ellipse { fill: var(--fogc); opacity: var(--fogop, .18); }
.swamp .shore-scenery .reed {
  stroke: var(--grass);
  fill: none;
  stroke-linecap: round;
  transform-box: fill-box;
  transform-origin: center bottom;
}
.swamp .shore-scenery .reed { stroke-width: 1.15; opacity: .42; }

.swamp .foreground-rocks ellipse { fill: var(--fore); }
.swamp .foreground-branches path {
  fill: none;
  stroke: var(--fore);
  stroke-width: 2.1;
  stroke-linecap: round;
}

/* ---- §4.1 待機（B-1）：すべて非同期・3秒未満のループを作らない ---- */

.swamp .breathe  {
  animation: breathe 9.7s cubic-bezier(.45,.03,.38,.98) infinite;
  transform-box: fill-box;
  transform-origin: center bottom;
  will-change: transform;
}
.swamp .reflx    { animation: reflH 7s   ease-in-out infinite; }
.swamp .reflwrap {
  animation: reflV 9.7s cubic-bezier(.45,.03,.38,.98) infinite;
  transform-box: fill-box;
  transform-origin: center top;
  will-change: transform;
}
.swamp .rim      { animation: rimSlide 5.5s ease-in-out infinite; }
.swamp .slit     { animation: slitA 4.6s ease-in-out infinite; }
.swamp .slit.sl2 { animation: slitB 5.8s ease-in-out infinite; }
.swamp .moonref  { animation: moonRef 12.8s ease-in-out infinite; opacity: var(--moonref-min, .12); }

/* 月光の道。帯ごとに独立して横へ揺れる。
 * 周期はすべて3秒以上・素数的にずらす。振幅は4px以内（R19）。 */
.swamp .mg  { stroke: #C8C2A8; stroke-linecap: round; }
.swamp .mg0 { animation: mgA 7.1s ease-in-out infinite; }
.swamp .mg1 { animation: mgB 8.3s ease-in-out infinite; }
.swamp .mg2 { animation: mgA 9.7s ease-in-out infinite; }
.swamp .mg3 { animation: mgB 11.3s ease-in-out infinite; }
.swamp .mg4 { animation: mgA 13.1s ease-in-out infinite; }

@keyframes mgA { 0%,100% { transform: translateX(-3.5px); }
                 50%     { transform: translateX(3.5px); } }
@keyframes mgB { 0%,100% { transform: translateX(3px); }
                 50%     { transform: translateX(-3px); } }
.swamp .fog1     { animation: fogA 11s ease-in-out infinite; }
.swamp .fog2     { animation: fogB 14s ease-in-out infinite; }
.swamp .fog3     { animation: fogA 17s ease-in-out infinite; }
.swamp .shore-scenery .br0 { animation: sway1 9.1s ease-in-out infinite; }
.swamp .shore-scenery .br1 { animation: sway2 11.3s ease-in-out infinite; }
.swamp .shore-scenery .br2 { animation: sway1 13.7s ease-in-out infinite; }

/* 朝も周期は変えず、色と濃度だけを時刻から連続補間する。 */
.swamp.morning .fog1 { animation-duration: 11s; }
.swamp.morning .fog2 { animation-duration: 14s; }
.swamp.morning .fog3 { animation-duration: 17s; }

@keyframes breathe {
  0%,100% { transform: translateY(0) scale(1,1); }
  29%     { transform: translateY(1.2px) scale(1.003,.999); }
  63%     { transform: translateY(3.4px) scale(.997,1.002); }
  82%     { transform: translateY(2px) scale(1.001,1); }
}
@keyframes reflV {
  0%,100% { transform: translateY(0) scale(1,1); }
  29%     { transform: translateY(-1.2px) scale(1.003,.999); }
  63%     { transform: translateY(-3.4px) scale(.997,1.002); }
  82%     { transform: translateY(-2px) scale(1.001,1); }
}
@keyframes reflH   { 0%,100%{transform:translateX(-1.5px)} 50%{transform:translateX(1.5px)} }
@keyframes rimSlide{ 0%,100%{transform:translateX(-2.5px);opacity:.85}
                     50%    {transform:translateX(2.5px); opacity:.55} }
@keyframes slitA   { 0%,100%{transform:translateX(-3px)} 50%{transform:translateX(3px)} }
@keyframes slitB   { 0%,100%{transform:translateX(3px)}  50%{transform:translateX(-3px)} }
@keyframes moonRef { 0%,100%{opacity:var(--moonref-min,.12)} 50%{opacity:var(--moonref-max,.38)} }
@keyframes moonFade{ 0%,100%{opacity:calc(var(--moonop) * .85)} 50%{opacity:var(--moonop)} }
@keyframes fogA    { 0%,100%{transform:translateX(-14px)} 50%{transform:translateX(14px)} }
@keyframes fogB    { 0%,100%{transform:translateX(12px)}  50%{transform:translateX(-12px)} }
@keyframes sway1   { 0%,100%{transform:rotate(-1.2deg)} 50%{transform:rotate(1.2deg)} }
@keyframes sway2   { 0%,100%{transform:rotate(1.2deg)}  50%{transform:rotate(-1.2deg)} }

/* 記録されない水草。視線を奪わず、水面の奥でごくゆっくり流れる。 */
.swamp .water-plants path {
  fill: none;
  stroke: var(--weed);
  stroke-width: .95;
  stroke-linecap: round;
}
.swamp .water-plants ellipse { fill: var(--weed); }
.swamp .water-weed { transform-box: fill-box; transform-origin: center; }
.swamp .water-weed.ww0 { animation: weedA 31s cubic-bezier(.42,0,.58,1) infinite; }
.swamp .water-weed.ww1 { animation: weedB 37s cubic-bezier(.42,0,.58,1) infinite; }
.swamp .water-weed.ww2 { animation: weedA 43s cubic-bezier(.42,0,.58,1) infinite; }

@keyframes weedA {
  0%,100% { transform: translate(-3.5px,.6px); }
  50%     { transform: translate(3.5px,-.6px); }
}
@keyframes weedB {
  0%,100% { transform: translate(3px,-.5px); }
  50%     { transform: translate(-3px,.5px); }
}

/* 環境波紋 ×3。clip: belowR の内側にあるので空へは出ない（R10）。
 * transform-box を省くと SVG 既定の view-box 基準になり、拡大の軸が
 * viewBox 中心（340,150＝空の中）に移って波紋が水面より上へ飛ぶ。
 * これは R10 と同じ破綻なので、拡大する要素には必ず fill-box を書く。 */
.swamp .rp  { fill: none; stroke-width: 1.1; opacity: 0;
              transform-box: fill-box; transform-origin: center;
              animation: ripAmb 5.5s linear infinite; }
.swamp .rp1 { stroke: var(--rip1); animation-delay: 0s; }
.swamp .rp2 { stroke: var(--rip2); animation-delay: 1.8s; }
.swamp .rp3 { stroke: var(--rip3); animation-delay: 3.6s; }

@keyframes ripAmb {
  0%   { transform: scale(0.5); opacity: 0; }
  40%  { opacity: 0.7; }
  100% { transform: scale(1.3); opacity: 0; }
}

/* 利用者が水面へ触れた位置にだけ出る、記録されない単発波紋。 */
.swamp .touch-ripple {
  fill: none;
  stroke: var(--rip1);
  stroke-width: 1;
  opacity: 0;
  pointer-events: none;
  transform-box: fill-box;
  transform-origin: center;
  animation: touchRipple 4s ease-out forwards;
}

@keyframes touchRipple {
  0%   { transform: scale(.25); opacity: 0; }
  20%  { opacity: .42; }
  100% { transform: scale(1.45); opacity: 0; }
}

/* 記録されない遠景現象。波紋は必ず belowR の子孫に置く。 */
.swamp .far-ripple {
  fill: none;
  stroke: var(--rip3);
  stroke-width: 1;
  opacity: 0;
  transform-box: fill-box;
  transform-origin: center;
  animation: farRipple 5.3s ease-out forwards;
}
.swamp.far-fog .fog { animation: farFog 13s ease-in-out both; }

@keyframes farRipple {
  0% { transform: scale(.35); opacity: 0; }
  22% { opacity: .38; }
  100% { transform: scale(1.7); opacity: 0; }
}
@keyframes farFog {
  0%,100% { filter: brightness(1); }
  48%,62% { filter: brightness(1.28); }
}

/* ---- §4.2 まばたき（R12）----
 * 潰す方向は各目自身の傾き軸に垂直。画面垂直方向への単純な scaleY は禁止。
 * #face を <use> で参照しているため、映り込みの目にも同一の潰れが自動で乗る。 */
.eyeL { animation: blinkL 7s ease-in-out infinite;
        transform-box: fill-box; transform-origin: center;
        animation-play-state: var(--eyeplay, running); }
.eyeR { animation: blinkR 7s ease-in-out infinite;
        transform-box: fill-box; transform-origin: center;
        animation-play-state: var(--eyeplay, running); }

@keyframes blinkL {
  0%,91%,100% { transform: rotate(-5deg) scaleY(1) rotate(5deg); }
  94.5%       { transform: rotate(-5deg) scaleY(0.08) rotate(5deg); }
}
@keyframes blinkR {
  0%,91%,100% { transform: rotate(-6.5deg) scaleY(1) rotate(6.5deg); }
  94.5%       { transform: rotate(-6.5deg) scaleY(0.08) rotate(6.5deg); }
}

/* 視線合わせ（§4.4）。まばたきグループの外側に入れ子。既定は無効。 */
.gazeL, .gazeR { transform-box: fill-box; transform-origin: center; }
.swamp.gazing .gazeL { animation: gazeL 20s ease-in-out infinite; }
.swamp.gazing .gazeR { animation: gazeR 20s ease-in-out infinite; }

@keyframes gazeL { 0%,42%,58%,100% { transform: rotate(0deg); }
                   46%,54% { transform: rotate(3deg); } }
@keyframes gazeR { 0%,42%,58%,100% { transform: rotate(0deg); }
                   46%,54% { transform: rotate(-3deg); } }

@media (prefers-reduced-motion: reduce) {
  .swamp .cloud-lane { animation-play-state: paused; }
}
