webgl-max-headroom
Version:
WebGL-powered Max Headroom style background and video overlay web components with AI-driven person segmentation, retro cyberpunk effects, and real-time shader animations
164 lines (144 loc) • 4.26 kB
HTML
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Max Headroom Video Overlay Demo</title>
<style>
body {
margin: 0;
overflow: hidden;
font-family: Arial, sans-serif;
}
#container {
position: relative;
width: 100vw;
height: 100vh;
}
max-headroom-bg {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
z-index: 1;
}
max-headroom-video-overlay {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
z-index: 2;
}
#status-container {
position: absolute;
display: flex;
justify-content: center;
top: 10px;
left: 10px;
min-width: 20em;
background:
repeating-linear-gradient(
45deg,
#ffbf00 0px,
#ffbf00 35px,
#000000 0px,
#000000 70px
);
color: #000000;
padding: 15px;
border-radius: 8px;
z-index: 100;
font-family: 'Courier New', monospace;
border: 2px solid #ffbf00;
font-weight: bold;
}
#status {
background: #FFF;
padding: 0.2em 0.4em;
font-family: Arial, Helvetica, sans-serif;
text-transform: uppercase;
text-align: center;
}
#controls {
position: absolute;
top: 10px;
right: 10px;
background: rgba(0,0,0,0.8);
color: #00ffff;
padding: 15px;
border-radius: 8px;
z-index: 100;
font-family: 'Courier New', monospace;
border: 1px solid #00ffff;
}
#controls label {
display: block;
margin-bottom: 8px;
color: #00ffff;
text-shadow: 0 0 5px #00ffff;
}
#controls input[type="range"] {
width: 150px;
margin-left: 10px;
}
</style>
</head>
<body>
<div id="container">
<!-- Max Headroom background -->
<max-headroom-bg
id="background"
speed="0.5"
fisheye-strength="0.15"
camera-distance="0.8"
line-width="0.3"
line-spacing="60.0">
</max-headroom-bg>
<!-- Video overlay component -->
<max-headroom-video-overlay
id="videoOverlay"
glitch-frequency="3">
</max-headroom-video-overlay>
<div id="status-container">
<div id="status">Loading...</div>
</div>
<div id="controls">
<label>Background Speed: <input type="range" id="speedSlider" min="0.1" max="2.0" step="0.1" value="0.5"></label>
<label>Fisheye Effect: <input type="range" id="fisheyeSlider" min="0.0" max="0.5" step="0.05" value="0.15"></label>
<label>Glitch Frequency: <input type="range" id="glitchSlider" min="0" max="10" step="1" value="3"></label>
</div>
</div>
<!-- Load components -->
<script type="module" src="src/webcomponent.js"></script>
<script type="module" src="src/video-overlay-webcomponent.js"></script>
<script>
const status = document.getElementById('status');
const background = document.getElementById('background');
const videoOverlay = document.getElementById('videoOverlay');
// Control elements
const speedSlider = document.getElementById('speedSlider');
const fisheyeSlider = document.getElementById('fisheyeSlider');
const glitchSlider = document.getElementById('glitchSlider');
// Set up control event listeners
speedSlider.addEventListener('input', (e) => {
background.setAttribute('speed', e.target.value);
});
fisheyeSlider.addEventListener('input', (e) => {
background.setAttribute('fisheye-strength', e.target.value);
});
glitchSlider.addEventListener('input', (e) => {
videoOverlay.setAttribute('glitch-frequency', e.target.value);
});
// Listen for status updates from the video overlay component
videoOverlay.addEventListener('status-change', (e) => {
status.innerText = e.detail.status === 'Ready' ? 'MAX HEADROOM' : e.detail.status;
});
// Start when page loads
window.addEventListener('load', () => {
status.innerText = 'Initializing...';
});
</script>
</body>
</html>