Index: src/views/shell.ejs
===================================================================
--- src/views/shell.ejs	(revision a0bff445a23aaf9813e1aadbc4a793496eac0087)
+++ src/views/shell.ejs	(revision 9ef3c567e925f3102a1ed486c62e7456a9cfc239)
@@ -163,5 +163,5 @@
 
 <!-- v9 stylesheet (full palette system) -->
-<link rel="stylesheet" href="/assets/css/style.css?v=11">
+<link rel="stylesheet" href="/assets/css/style.css?v=12">
 
 <!-- Audio player styles: loaded on every page so the mini-player works
@@ -528,4 +528,28 @@
 </script>
 
+<!-- Mobiel toetsenbord vs. site-layout: zet body.kb-open zodra het toetsenbord
+     open is (visual viewport fors korter dan het venster) ÉN er een invoerveld
+     focus heeft. CSS verbergt dan de vaste onderbalken (bottom-tab + mini-speler)
+     zodat ze niet over het invoerveld zweven. -->
+<script>
+(function () {
+  var vv = window.visualViewport;
+  if (!vv) return;
+  function isField(el) {
+    if (!el) return false;
+    var t = el.tagName;
+    return t === 'INPUT' || t === 'TEXTAREA' || el.isContentEditable;
+  }
+  function update() {
+    var open = (window.innerHeight - vv.height) > 150 && isField(document.activeElement);
+    document.body.classList.toggle('kb-open', open);
+  }
+  vv.addEventListener('resize', update);
+  vv.addEventListener('scroll', update);
+  document.addEventListener('focusin', function () { setTimeout(update, 60); });
+  document.addEventListener('focusout', function () { setTimeout(update, 60); });
+})();
+</script>
+
 <!-- PWA install prompt — show button when browser fires beforeinstallprompt -->
 <script>
