<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <meta name="viewport" content="width=device-width, initial-scale=1"> <script src="https://unpkg.com/jquery@3.7.1/dist/jquery.js"></script> <link rel="stylesheet" type="text/css" href="https://unpkg.com/fomantic-ui@2.9.3/dist/semantic.min.css"> <script src="https://unpkg.com/fomantic-ui@2.9.3/dist/semantic.min.js"></script> <title>Soundboard</title> <script> function setLandscape() { if (screen.orientation && screen.orientation.lock) { screen.orientation.lock('landscape').then(() => { console.log("Landscape mode activated"); }).catch((error) => { console.error("Landscape mode failed:", error); }); } else { console.log("Screen Orientation API not supported"); } } function setPortrait() { if (screen.orientation && screen.orientation.lock) { screen.orientation.lock('portrait').then(() => { console.log("Portrait mode activated"); }).catch((error) => { console.error("Portrait mode failed:", error); }); } else { console.log("Screen Orientation API not supported"); } } function toggleFullScreen() { if (!document.fullscreenElement) { document.documentElement.requestFullscreen().catch((error) => { console.error("Error attempting to enable full-screen mode:", error); }); } else { if (document.exitFullscreen) { document.exitFullscreen(); } } } var disableTimeout; var none = null; function play(hash, timeout) { if (timeout && timeout != "none") { // Add the "disabled" class to all clip buttons $('.clip').addClass('disabled'); // Add "primary" and "loading" classes to the clicked button var clickedButton = $('#clip-' + hash); clickedButton.addClass('double loading positive'); // Clear any existing timeout to avoid conflicts clearTimeout(disableTimeout); // Set a new timeout disableTimeout = setTimeout(function () { $('.clip').removeClass('disabled'); clickedButton.removeClass('double loading positive'); }, timeout); } fetch("/play/" + hash); } function stop() { fetch("/stop"); // Clear the timeout clearTimeout(disableTimeout); // Remove the "disabled" class from all clip buttons // and the "primary" and "loading" classes from any button that might have them $('.clip').removeClass('disabled'); $('.clip').removeClass('double loading positive'); } </script> <style type="text/css"> :root { --left-column-width: 98px; /* Define a CSS variable for the width */ } .ui.ui.ui.ui.ui.ui.loading.button { color: black !important; } .left-column { width: var(--left-column-width) !important; height: 100%; position: fixed; /* Fix the position relative to the viewport */ top: 0; /* Align the top edge with the top of the viewport */ bottom: 0; /* Align the bottom edge with the bottom of the viewport */ overflow-y: auto; /* Add scroll to the left column if content overflows */ background-color: rgb(27, 28, 29); } .right-column { margin-left: var(--left-column-width) !important; } </style> </head> <body> <div class="left-column column fixed"> <div class="ui inverted labeled icon inline vertical compact mini menu" style="min-width: 96.75px;"> <a class="item" onclick="stop()"> <i class="stop icon"></i> Stop </a> <a class="item" onclick="toggleFullScreen()"> <i class="expand layout icon"></i> Fullscreen </a> <a class="item" onclick="setLandscape()"> <i class="tv icon"></i> Landscape </a> <a class="item" onclick="setPortrait()"> <i class="mobile alternate icon"></i> Portrait </a> </div> </div> <div class="right-column column"> <div class="ui basic segment"> <div class="ui wrapped compact wrapping spaced /**buttons"> {% for clip in clips %} <button id="clip-{{clip.hash}}" class="ui {{ loop.cycle('red', 'blue', 'green', 'violet', 'orange') }} basic button clip" onclick="play('{{clip.hash}}', {{clip.length}})">{{clip.title}}</button> {% endfor %} </div> </div> </div> </div> </body> </html>