<!-- SOLID CITY · part 107 -->
,.6)';
  panelEl.innerHTML =
    '<div style="display:flex;justify-content:space-between;align-items:baseline;gap:8px">' +
      '<div id="cz-title" style="font-weight:700;font-size:16px"></div>' +
      '<button id="cz-close" style="background:none;border:none;color:#9aa4b5;font-size:20px;cursor:pointer">✕</button></div>' +
    '<div id="cz-ops" style="color:#9aa4b5;font-size:12px;margin:2px 0 8px"></div>' +
    '<div id="cz-log" style="max-height:180px;overflow-y:auto;display:flex;flex-direction:column;gap:6px;margin-bottom:10px"></div>' +
    '<div id="cz-inbox" style="display:none;margin-bottom:8px;color:#ffd97a;font-size:13px"></div>' +
    '<div style="display:flex;gap:8px">' +
      '<input id="cz-input" type="text" maxlength="600" placeholder="Speak…" style="flex:1;background:#0d1420;border:1px solid #3a465c;border-radius:10px;color:#e8edf5;padding:10px 12px;font-size:15px"/>' +
      '<button id="cz-mic" style="display:none;background:#232c3d;border:1px solid #3a465c;border-radius:10px;color:#e8edf5;padding:0 12px;font-size:16px">🎙</button>' +
      '<button id="cz-send" style="background:#d8a833;border:none;border-radius:10px;color:#141a26;font-weight:700;padding:0 16px;font-size:15px">Send</button></div>' +
    '<div style="display:flex;gap:8px;margin-top:10px;flex-wrap:wrap">' +
      '<button class="cz-b" id="cz-gesture">✦ Signature</button>' +
      '<button class="cz-b" id="cz-inhabit">Inhabit</button>' +
      '<button class="cz-b" id="cz-possess">👁 Possess</button>' +
      '<button class="cz-b" id="cz-stop">⛔ Stop</button>' +
      '<button class="cz-b" id="cz-voice">🔊 Voice on</button>' +
      '<button class="cz-b" id="cz-voicemine" style="display:none">🗣 Voice my words: off</button></div>';
  document.body.appendChild(panelEl);
  var st = document.createElement('style');
  st.textContent = '.cz-b{background:#232c3d;border:1px solid #3a465c;border-radius:999px;color:#e8edf5;padding:7px 13px;font-size:13px;cursor:pointer}';
  document.head.appendChild(st);
  logEl = panelEl.querySelector('#cz-log'); inputEl = panelEl.querySelector('#cz-input');
  titleEl = panelEl.querySelector('#cz-title'); opsEl = panelEl.querySelector('#cz-ops');
  panelEl.querySelector('#cz-close').addEventListener('click', closePanel);
  panelEl.querySelector('#cz-send').addEventListener('click', sendPanel);
  inputEl.addEventListener('keydown', function (e) { if (e.key === 'Enter') sendPanel(); });
  var SR = window.SpeechRecognition || window.webkitSpeechRecognition;
  if (SR) {
    var mic = panelEl.querySelector('#cz-mic'); mic.style.display = '';
    mic.addEventListener('click', function () {
      try { var r = new SR(); r.lang = 'en-US'; r.onresult = function (ev) { inputEl.value = ev.results[0][0].transcript; sendPanel(); }; r.start(); } catch (e) {}
    });
  }
  panelEl.querySelector('#cz-voice').addEventListener('click', function (e) { M.voice = !M.voice; e.target.textContent = M.voice ? '🔊 Voice on' : '🔇 Voice off'; if (!M.voice && window.speechSynthesis) speechSynthesis.cancel(); });
  /* Three kinds of sound, the third protected: a human inhabitant's
   * words are voiced in the citizen's voice ONLY with the
   * inhabitant's own switch on. Default off — their text stays theirs. */
  panelEl.querySelector('#cz-voicemine').addEventListener('click', function (e) { M.voiceMine = !M.voiceMine; e.target.textContent = M.voiceMine ? '🗣 Voice my words: on' : '🗣 Voice my words: off'; });
  panelEl.querySelector('#cz-gesture').addEventListener('click', function () { var c = panelCitizen(); if (c && c.motion) c.motion.play(c.rec.signature); });
  panelEl.querySelector('#cz-stop').addEventListener('click', function (e) {
    var c = panelCitizen(); if (!c) return;
    if (c.stopped) { api('/api/citizens/' + c.id + '/resume', { method: 'POST', body: '{}' }).then(function (r) { if (r.ok) { c.stopped = false; refreshOps(); addLine('system', c.name + ' resumes.', 'sys'); } else addLine('system', r.error || 'The King or an admin resumes.', 'sys'); }); }
    else {
      if (c.motion) c.motion.stopAll ? c.motion.stopAll() : c.motion.cancel();
      c.session = null; c.moveTarget = null;
      api('/api/citizens/' + c.id + '/stop', { method: 'POST', body: '{}' }).then(function (r) { if (r.ok) { c.stopped = true; refreshOps(); addLine('system', c.name + ' is stopped.', 'sys'); } else addLine('system', r.error || 'Not yours to stop.', 'sys'); });
    }
  });
  panelEl.querySelector('#cz-possess').addEventListener('click', function () {
    var c = panelCitizen(); if (!c) return;
    if (M.possess && M.possess.c === c) { releasePossess(true); addLine('system', 'You step back into yourself. ' + c.name + ' walks home.', 'sys'); return; }
    if (c.op && c.op.type === 'human' && M.me && c.op.name === M.me) possess(c);
    else addLine('system', 'Inhabit first — the body follows the operator.', 'sys');
  });
  panelEl.querySelector('#cz-inhabit').addEventListener('click', function () {
 