:root { color-scheme: dark light; } /* Overlay opacity is configurable here. Set to 1 to let PNG alpha be authoritative */ :root { --overlay-opacity: 1; /* default overlay alpha applied client-side */ } body { font-family: system-ui, -apple-system, Segoe UI, Roboto, sans-serif; margin: 0; padding: 1rem; background: #0b1020; color: #e7eaf6; } h1, h2 { margin: 0.5rem 0 0.25rem; } .grid { display: grid; gap: 1rem; /* grid-auto-flow: column; grid-auto-columns: 1280px; justify-content: start; */ grid-template-columns: repeat(auto-fit, minmax(1280px, 1fr)); align-items: start; } .panel { background: #141b34; border: 1px solid #242c4f; border-radius: 12px; padding: 1rem; box-shadow: 0 10px 24px rgba(0,0,0,0.25); } .video-wrap { position: relative; background: #000; border-radius: 8px; overflow: hidden; width: 100%; max-width: 1280px; aspect-ratio: 4 / 3; margin: 0 auto; } /* Ensure canvas and overlay are sized identically and keep the same aspect ratio so overlays align correctly when the window is resized. */ .video-wrap canvas, .video-wrap img, #overlayImg { position: absolute; inset: 0; /* top:0; right:0; bottom:0; left:0 */ /*width: 100%;*/ width: 1280px; height: 100%; /* Use `contain` so both layers scale uniformly and show letterboxing instead of stretching or cropping when the container size differs from the image. */ object-fit: contain; background: #000; } .video-wrap canvas { z-index: 1; } .video-wrap img, #overlayImg { z-index: 2; pointer-events: none; /* don't block interactions with the canvas */ opacity: var(--overlay-opacity); } .status { font-size: 0.9rem; opacity: 0.85; margin: 0.5rem 0 0; } .controls { display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: 0.5rem; margin-top: 0.75rem; } .controls label { display: grid; gap: 0.25rem; font-size: 0.9rem; } select, input, button { padding: 0.5rem 0.6rem; border-radius: 8px; border: 1px solid #2d3766; background: #0d1530; color: #e7eaf6; } button.primary { background: #355dff; border-color: #355dff; } a { color: #9eb8ff; } footer { margin-top: 1.25rem; opacity: 0.7; font-size: 0.9rem; } .muted { opacity: 0.8; } /* Ensure overlay uses contain and respects alpha channel from the PNG (the PNG's transparency is the authoritative source of which pixels are transparent; CSS opacity only adjusts global alpha). */ #overlayImg { position: absolute; inset: 0; /* shorthand for top:0; right:0; bottom:0; left:0; */ width: 100%; height: 100%; pointer-events: none; opacity: var(--overlay-opacity); object-fit: contain; /* preserve aspect ratio and don't distort */ background: transparent; } /* CSV table styles */ .csv-table { width: 440px; /* 4 columns * 200px each */ border-collapse: collapse; margin-top: 0.5rem; table-layout: fixed; /* use fixed layout so column widths are respected */ } .csv-table th, .csv-table td { border: 1px solid rgba(255,255,255,0.06); padding: 0.35rem 0.5rem; text-align: center; font-size: 0.9rem; width: 110px; /* fixed column width */ white-space: nowrap; overflow: hidden; text-overflow: ellipsis; } .csv-table th { background: rgba(255,255,255,0.02); font-weight: 600; } .csv-table tr:nth-child(even) td { background: rgba(255,255,255,0.01); } /* Right-align CSV numeric data and use tabular digits for stable column alignment */ .csv-table td { text-align: right; font-variant-numeric: tabular-nums; } #GCodeWindow { width: 100%; height: 200px; } /* Layout: place the buttons and GCode window side-by-side in their panel. - `#divButtons` gets a fixed ~300px width - `#divGCodeWindow` uses the remaining width - On small screens they stack vertically for usability */ /* Use floats for a predictable two-column layout inside the panel. */ #divButtons { float: left; width: 300px; box-sizing: border-box; margin-right: 1rem; } #divGCodeWindow { display: block; margin-left: 320px; /* 300px left column + 1rem gap */ box-sizing: border-box; } /* Clear floats inside panels so subsequent content flows correctly */ .panel::after { content: ""; display: table; clear: both; } @media (max-width: 800px) { #divButtons, #divGCodeWindow { display: block; float: none; width: 100%; margin-left: 0; margin-right: 0; } }