/* =========================================================================
   components.css —— 互动组件：万用表 / 配电柜 / 端子排 / 提示条 / 挂接区
   【WorkBuddy 独占 · WS-20261029-03A】
   零外部依赖：纯 CSS + 字符图形，无外链字体/图片/动画库，断网可用
   ========================================================================= */

/* ===== 挂载区（三组件共用容器） ===== */
.rig{display:flex;flex-direction:column;gap:12px;margin:10px 0 4px;width:100%}
.rig>*{width:100%}
.stage.operate{overflow:auto;-webkit-overflow-scrolling:touch;padding-bottom:56px}

/* ===== 通用小件 ===== */
.shake{animation:shake .34s}
@keyframes shake{0%,100%{transform:translateX(0)}20%{transform:translateX(-5px)}40%{transform:translateX(5px)}60%{transform:translateX(-3px)}80%{transform:translateX(3px)}}
.ws-cap{display:flex;align-items:baseline;gap:8px;font-size:12px;color:var(--dim);font-family:var(--mono);letter-spacing:1px;margin-bottom:6px}
.ws-cap small{color:#516274;letter-spacing:0;font-family:inherit}

/* =========================================================================
   一、万用表
   ========================================================================= */
.ws-meter{width:100%}
.meter-body{width:320px;max-width:100%;min-height:180px;padding:8px;display:flex;flex-direction:column;gap:6px;
  border-radius:12px;background:linear-gradient(180deg,#3b444f,#22282f);border:1px solid #4d5865;
  box-shadow:inset 0 1px 0 rgba(255,255,255,.12),0 10px 22px rgba(0,0,0,.45)}

.meter-screen{min-height:54px;background:#08130f;border:1px solid #17352a;border-radius:6px;padding:6px 10px;
  display:flex;flex-direction:column;justify-content:center;box-shadow:inset 0 0 20px rgba(70,214,224,.09)}
.meter-val{font-family:var(--mono);font-size:28px;line-height:1.1;letter-spacing:1px;color:var(--cyan);
  text-shadow:0 0 12px rgba(70,214,224,.35)}
.meter-unit{font-family:var(--mono);font-size:11.5px;color:var(--dim);margin-top:1px}
.meter-note{font-size:11.5px;color:var(--amber);margin-top:4px;min-height:15px;line-height:1.3}

.meter-mid{flex:1;display:flex;align-items:center;justify-content:space-between;gap:8px}

.meter-dial{position:relative;width:104px;height:104px;flex:none}
.dial-base{position:absolute;left:50%;top:50%;width:68px;height:68px;margin:-34px 0 0 -34px;border-radius:50%;
  background:radial-gradient(circle at 34% 28%,#5d6874,#232a31 72%);border:1px solid #5b6672;
  box-shadow:inset 0 1px 0 rgba(255,255,255,.14)}
.dial-knob{position:absolute;left:50%;top:50%;width:44px;height:44px;margin:-22px 0 0 -22px;border-radius:50%;
  background:linear-gradient(180deg,#d3dbe3,#8d99a6);border:1px solid #6b7684;transition:transform .2s ease;
  box-shadow:0 3px 8px rgba(0,0,0,.45)}
.dial-knob i{position:absolute;left:50%;top:3px;width:4px;height:16px;margin-left:-2px;border-radius:2px;background:#2b323a}
.dial-labels{position:absolute;inset:0}
.dial-pos{position:absolute;width:30px;height:30px;margin:-15px 0 0 -15px;padding:0;border:0;background:transparent;
  color:var(--dim);font-family:var(--mono);font-size:11px;cursor:pointer;border-radius:6px;line-height:30px;text-align:center}
.dial-pos:hover{color:var(--ink);background:rgba(255,255,255,.06)}
.dial-pos.on{color:var(--amber);font-weight:700;text-shadow:0 0 8px rgba(245,166,35,.5)}

.meter-sockets{display:flex;flex-direction:column;gap:6px}
.probe-handle{width:56px;height:44px;border-radius:8px;border:1px dashed #3a4b5a;background:#0d1720;color:var(--dim);
  font-size:11px;cursor:grab;touch-action:none;display:flex;align-items:center;justify-content:center;gap:5px;padding:0}
.probe-handle:active{cursor:grabbing}
.probe-handle .tip{width:11px;height:11px;border-radius:50%;flex:none;box-shadow:0 0 9px currentColor;background:currentColor}
.probe-handle.red .tip{color:var(--red)}
.probe-handle.black .tip{color:#9aa7b4}
.probe-handle.attached{border-style:solid;border-color:var(--green);color:var(--ink);background:#0e1c17}
.probe-handle .pl{font-family:var(--mono);font-size:10px;max-width:32px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}

.probe-ghost{position:fixed;z-index:9999;pointer-events:none;width:18px;height:18px;margin:-9px 0 0 -9px;border-radius:50%;
  box-shadow:0 0 14px currentColor;background:currentColor}
.probe-ghost.red{color:var(--red)}
.probe-ghost.black{color:#9aa7b4}

/* =========================================================================
   二、配电柜
   ========================================================================= */
.ws-cab{width:100%}
.cab-shell{position:relative;width:100%;max-width:420px;min-height:236px;border-radius:10px;overflow:hidden;
  border:1px solid #2a3a4a;background:linear-gradient(180deg,#141d27,#0b1219);
  box-shadow:inset 0 0 40px rgba(0,0,0,.5)}
.cab-head{display:flex;align-items:center;justify-content:space-between;gap:8px;font-size:12px;color:var(--dim);
  font-family:var(--mono);letter-spacing:1px;margin-bottom:6px}
.door-btn{min-height:44px;padding:0 12px;border-radius:8px;border:1px solid var(--line);background:#101c28;color:var(--ink);
  font:inherit;font-size:13px;cursor:pointer}
.door-btn:hover{border-color:var(--cyan);color:var(--cyan)}

.cab-interior{position:absolute;inset:10px;display:grid;grid-template-columns:1fr 1fr;gap:8px;align-content:start;
  transition:opacity .3s}
.cab-shell.closed .cab-interior{opacity:.2;pointer-events:none}
.cab-mask{position:absolute;inset:0;background:rgba(6,11,16,.55);display:none}
.cab-shell.closed .cab-mask{display:block}

.cab-item{background:#0d1620;border:1px solid var(--line);border-radius:8px;padding:8px;
  display:flex;flex-direction:column;align-items:center;justify-content:center;gap:6px;min-height:96px}
.cab-name{font-size:11px;color:var(--dim);letter-spacing:1px}
.cab-state{font-family:var(--mono);font-size:11px;color:var(--dim)}
.cab-state.on{color:var(--red)}
.cab-state.off{color:var(--green)}

/* QF1 拨杆 */
.qf1{width:46px;height:76px;border-radius:9px;border:1px solid #3a4b5a;background:linear-gradient(180deg,#0f1a24,#0a1219);
  position:relative;cursor:pointer;padding:0;overflow:hidden}
.qf1 .lever{position:absolute;left:50%;width:24px;height:28px;margin-left:-12px;bottom:38px;border-radius:5px;
  background:linear-gradient(180deg,#e6edf4,#9aa6b3);border:1px solid #6b7684;
  transition:bottom .18s cubic-bezier(.3,1.5,.5,1),background .18s}
.qf1.off .lever{bottom:8px;background:linear-gradient(180deg,#9aa6b3,#5d6874)}
.qf1.snap{animation:snap .3s}
@keyframes snap{0%{transform:scale(1)}25%{transform:scale(.92)}45%{transform:scale(1.05) rotate(-1deg)}70%{transform:scale(.98)}100%{transform:scale(1)}}

/* 挂牌锁 */
.lock-slot{width:52px;height:52px;border-radius:8px;border:1px dashed #4a5a6a;background:#0e1620;color:var(--dim);
  font-size:20px;cursor:pointer;padding:0}
.lock-slot:hover{border-color:var(--amber);color:var(--amber)}
.cab-shell.locked .lock-slot{border-style:solid;border-color:var(--red);color:var(--red)}
.lock-tag{position:absolute;right:10px;bottom:10px;transform:rotate(-6deg);background:#7a1418;border:1px solid var(--red);
  color:#ffe0e0;font-size:11px;line-height:1.35;padding:6px 9px;border-radius:4px;text-align:center;
  box-shadow:0 8px 18px rgba(0,0,0,.55);display:none;max-width:120px}
.cab-shell.locked .lock-tag{display:block}

/* KM1 接触器 */
.km1{display:flex;align-items:center;gap:8px}
.km1 .led{width:16px;height:16px;border-radius:50%;background:#22303c;border:1px solid #3a4b5a;transition:.25s}
.km1.on .led{background:var(--green);border-color:var(--green);box-shadow:0 0 12px rgba(93,211,158,.85)}
.km1 .km1-txt{font-family:var(--mono);font-size:11px;color:var(--dim)}
.km1.on .km1-txt{color:var(--green)}

/* SB1 启动按钮 */
.sb1{width:56px;height:56px;border-radius:50%;border:2px solid #2f6b4f;color:#eafff4;font:inherit;font-size:13px;
  background:radial-gradient(circle at 40% 32%,#4fd08a,#1b563a);cursor:pointer;transition:transform .12s,box-shadow .12s;
  box-shadow:0 4px 0 #14402b,0 8px 16px rgba(0,0,0,.4)}
.sb1:active{transform:translateY(3px);box-shadow:0 1px 0 #14402b,0 4px 10px rgba(0,0,0,.4)}

/* 带电指示 */
.cab-live{position:absolute;left:10px;bottom:10px;font-family:var(--mono);font-size:11px;color:var(--dim);
  border:1px solid var(--line);border-radius:20px;padding:4px 10px;background:rgba(8,14,20,.8)}
.cab-live.on{color:var(--red);border-color:var(--red);animation:breathe 1.5s infinite}
@keyframes breathe{0%,100%{opacity:.5}50%{opacity:1;text-shadow:0 0 10px rgba(255,93,93,.85)}}

/* 柜门 */
.cab-door{position:absolute;inset:0;transform-origin:left center;transition:transform .3s ease,opacity .3s ease;
  background:linear-gradient(135deg,#3d4853,#242c35 60%);border:1px solid #4c5865;border-radius:8px;
  display:flex;flex-direction:column;align-items:center;justify-content:center;gap:6px;color:#a9b7c4;cursor:pointer;
  box-shadow:inset 0 1px 0 rgba(255,255,255,.1)}
.cab-door .dk{font-size:26px}
.cab-door small{font-size:11px;color:#7d90a3}
.cab-shell.open .cab-door{transform:perspective(700px) rotateY(-76deg);opacity:.4;pointer-events:none}
/* ↑ 开门后必须让门板"穿透"：rotateY(-76deg)+perspective(700px) 会把 420px 门板投影回 x≈0~243px，
   正好压住左列的 QF1 / KM1（详见 §6.6 相关回归），不穿透的话玩家点不到 QF1，关卡直接卡死。
   关门走顶栏 .door-btn，不依赖点门板，闭环不破。 */

/* =========================================================================
   三、端子排
   ========================================================================= */
.ws-term{width:100%}
.term-row{display:flex;gap:10px;flex-wrap:wrap}
.term{position:relative;width:74px;padding:8px 4px 6px;border:1px solid var(--line);border-radius:8px;
  background:linear-gradient(180deg,#131f2a,#0d1620);display:flex;flex-direction:column;align-items:center;gap:4px;
  transition:box-shadow .2s,border-color .2s}
.term.drop-hover{border-color:var(--cyan);box-shadow:0 0 0 2px rgba(70,214,224,.35)}
.term.p-red{border-color:var(--red)}
.term.p-black{border-color:#9aa7b4}
.term.p-red.p-black{border-color:var(--amber);box-shadow:0 0 12px rgba(245,166,35,.28)}

.screw{position:relative;width:44px;height:44px;border:0;background:transparent;cursor:pointer;padding:0;
  display:flex;align-items:center;justify-content:center;transition:transform .18s}
.screw::before{content:"";position:absolute;width:26px;height:26px;border-radius:50%;
  background:radial-gradient(circle at 34% 28%,#e6b878,#8a5a24);border:1px solid #6b441a;
  box-shadow:0 2px 6px rgba(0,0,0,.5)}
.screw .slot{position:relative;width:18px;height:3px;border-radius:2px;background:#5a3a14;transition:transform .25s ease}
.screw.loose{transform:translateY(-2px) rotate(-8deg)}
.screw.scratched::after{content:"";position:absolute;width:26px;height:2px;left:9px;top:14px;transform:rotate(-30deg);
  background:linear-gradient(90deg,transparent,#fff 45%,rgba(255,255,255,.9) 55%,transparent);
  opacity:.75;animation:scratchFlash 1s ease-out}
@keyframes scratchFlash{0%{opacity:0}18%{opacity:1;box-shadow:0 0 10px rgba(255,255,255,.9)}100%{opacity:.6}}

.term-label{font-family:var(--mono);font-size:11px;color:var(--dim)}
.term-badge{font-family:var(--mono);font-size:10px;color:var(--dim);min-height:14px;text-align:center}
.term-badge .pd{display:inline-block;width:8px;height:8px;border-radius:50%;margin-right:3px;vertical-align:1px}
.term-badge .pd.red{background:var(--red);box-shadow:0 0 6px var(--red)}
.term-badge .pd.black{background:#9aa7b4;box-shadow:0 0 6px #9aa7b4}

/* =========================================================================
   四、提示条（页面底部，替代 alert）
   ========================================================================= */
.hintbar{position:absolute;left:12px;right:12px;bottom:12px;z-index:44;pointer-events:none;
  background:#121d28;border:1px solid var(--amber);border-left-width:4px;border-radius:8px;padding:10px 14px;
  font-size:13.5px;line-height:1.6;color:#ffe7bd;box-shadow:0 10px 26px rgba(0,0,0,.5);
  opacity:0;transform:translateY(10px);transition:opacity .3s,transform .3s}
.hintbar.show{opacity:1;transform:translateY(0)}
.hintbar.bad{border-color:var(--red);color:#ffdede;background:#1d1013}
.hb-who{font-weight:700;color:var(--amber);margin-right:4px}
.hintbar.bad .hb-who{color:var(--red)}

/* =========================================================================
   五、移动端（375px 不横向溢出 + 触控热区 ≥44px）
   ========================================================================= */
@media(max-width:560px){
  .meter-body{width:100%;min-height:0}
  .meter-mid{flex-direction:column;align-items:center;gap:10px}
  .meter-sockets{flex-direction:row;justify-content:center;width:100%}
  .probe-handle{width:96px}
  .dial-labels{position:static;display:flex;flex-wrap:wrap;gap:6px;justify-content:center;width:100%;margin-top:6px}
  .dial-pos{position:static;width:auto;min-width:44px;height:44px;margin:0;padding:0 8px;line-height:44px;
    border:1px solid var(--line);background:#0e1720;border-radius:8px}
  .cab-interior{grid-template-columns:1fr 1fr;gap:6px}
  .term{width:calc(50% - 5px);max-width:96px}
}
