/* =========
Dark TV Dashboard Theme
Drop this into your
========= */
:root{
/* Core palette */
--bg: #0b0f16;
--surface: rgba(255,255,255,0.06);
--surface-2: rgba(255,255,255,0.09);
--border: rgba(255,255,255,0.10);
--text: rgba(255,255,255,0.92);
--muted: rgba(255,255,255,0.68);
--faint: rgba(255,255,255,0.52);
/* Accents */
--accent: #4cc9f0; /* cool cyan */
--accent-2: #a78bfa; /* soft purple */
--good: #34d399;
--warn: #fbbf24;
/* Layout */
--radius: 18px;
--radius-sm: 12px;
--pad: 18px;
--gap: 16px;
/* Type */
--font: system-ui, -apple-system, Segoe UI, Roboto, Ubuntu, Cantarell, "Noto Sans", Arial, sans-serif;
}
*{ box-sizing:border-box; }
html, body{ height:100%; width:100%; }
body{
margin:0;
font-family: var(--font);
color: var(--text);
background:
radial-gradient(1200px 600px at 20% 10%, rgba(76,201,240,0.12), transparent 60%),
radial-gradient(900px 500px at 85% 20%, rgba(167,139,250,0.10), transparent 55%),
radial-gradient(800px 600px at 50% 100%, rgba(255,255,255,0.06), transparent 55%),
var(--bg);
overflow:hidden; /* TV: never scroll */
}
/* Optional: make text crisp on TVs */
body{
-webkit-font-smoothing: antialiased;
text-rendering: geometricPrecision;
}
/* =========
Grid Layout
========= */
.grid{
height:100vh;
width:100vw;
padding: 18px;
display:grid;
grid-template-columns: 1.1fr 1.4fr;
grid-template-rows: 1fr 1fr;
gap: var(--gap);
}
.topLeft, .topRight, .bottomLeft, .bottomRight{
position:relative;
min-height: 0; /* important so children can size/clip inside grid */
border-radius: var(--radius);
background: linear-gradient(180deg, rgba(255,255,255,0.06), rgba(255,255,255,0.03));
border: 1px solid var(--border);
box-shadow:
0 10px 30px rgba(0,0,0,0.35),
inset 0 1px 0 rgba(255,255,255,0.06);
overflow:hidden;
}
/* =========
Top Left: Date/Time + Current Weather
========= */
.topLeft{
display:flex;
flex-direction:column;
padding: var(--pad);
gap: 14px;
}
/* Date/Time card */
.dateTime{
display:flex;
flex-direction:column;
gap: 6px;
padding: 14px 16px;
border-radius: var(--radius-sm);
background: rgba(0,0,0,0.22);
border: 1px solid rgba(255,255,255,0.08);
}
#date{
margin:0;
font-size: 22px;
letter-spacing: 0.4px;
color: var(--muted);
}
#time{
margin:0;
font-size: 56px;
font-weight: 700;
letter-spacing: 1.2px;
line-height: 1.05;
color: var(--text);
}
/* Weather block */
.weather{
flex: 1;
min-height: 0;
display:flex;
}
.weatherBlock{
flex: 1;
min-height: 0;
padding: 16px;
border-radius: var(--radius-sm);
background:
radial-gradient(600px 240px at 20% 10%, rgba(76,201,240,0.10), transparent 60%),
rgba(0,0,0,0.18);
border: 1px solid rgba(255,255,255,0.08);
display:flex;
flex-direction:column;
gap: 12px;
}
.weatherBlock h2{
margin:0;
font-size: 18px;
font-weight: 700;
letter-spacing: 0.5px;
color: var(--text);
display:flex;
align-items:center;
gap: 10px;
}
.weatherBlock h2::before{
content:"";
width: 10px;
height: 10px;
border-radius: 50%;
background: linear-gradient(135deg, var(--accent), var(--accent-2));
box-shadow: 0 0 18px rgba(76,201,240,0.35);
}
/* Condition row: icon + text */
.condition{
display:flex;
align-items:center;
gap: 12px;
padding: 10px 12px;
border-radius: 14px;
background: rgba(255,255,255,0.04);
border: 1px solid rgba(255,255,255,0.06);
}
.condition img{
width: 54px;
height: 54px;
object-fit: contain;
filter: drop-shadow(0 6px 10px rgba(0,0,0,0.45));
}
.conditionText{
margin:0;
font-size: 22px;
font-weight: 650;
letter-spacing: 0.2px;
color: var(--text);
}
/* Weather info list */
.weatherInfo{
display:grid;
grid-template-columns: 1fr 1fr;
gap: 10px 12px;
margin-top: 2px;
}
.weatherInfo p{
margin:0;
padding: 10px 12px;
border-radius: 14px;
background: rgba(255,255,255,0.035);
border: 1px solid rgba(255,255,255,0.06);
font-size: 18px;
color: var(--muted);
display:flex;
align-items:center;
justify-content:space-between;
}
.weatherInfo p strong{
color: var(--text);
}
/* If you don't wrap labels/values in , still make the numbers pop a bit */
#temp, #feels, #wind, #humidity{
color: var(--text);
}
#temp{ font-size: 20px; font-weight: 650; }
#feels, #wind, #humidity{ font-weight: 550; }
/* =========
Top Right: Radar Image
========= */
.topRight{
padding: 12px;
display:flex;
align-items:center;
justify-content:center;
background:
radial-gradient(800px 520px at 70% 10%, rgba(167,139,250,0.09), transparent 55%),
rgba(0,0,0,0.10);
}
#radar{
width:100%;
height:100%;
object-fit: cover;
border-radius: calc(var(--radius) - 6px);
border: 1px solid rgba(255,255,255,0.08);
box-shadow: 0 14px 40px rgba(0,0,0,0.45);
filter: contrast(1.04) saturate(1.05);
}
/* Subtle label overlay (optional, doesn’t require HTML changes) */
.topRight::after{
content:"Radar";
position:absolute;
top: 12px;
left: 14px;
padding: 6px 10px;
font-size: 14px;
letter-spacing: 0.6px;
text-transform: uppercase;
color: rgba(255,255,255,0.72);
background: rgba(0,0,0,0.40);
border: 1px solid rgba(255,255,255,0.08);
border-radius: 999px;
backdrop-filter: blur(8px);
}
/* =========
Bottom Left: Forecast Table
========= */
.bottomLeft{
padding: 12px;
display:flex;
}
table{
width:100%;
height:100%;
border-collapse: separate;
border-spacing: 0;
overflow:hidden;
border-radius: calc(var(--radius) - 6px);
background: rgba(0,0,0,0.18);
border: 1px solid rgba(255,255,255,0.08);
}
/* Head row */
thead th{
padding: 12px 10px;
font-size: 15px;
color: rgba(255,255,255,0.80);
letter-spacing: 0.4px;
text-transform: uppercase;
background:
linear-gradient(90deg, rgba(76,201,240,0.10), rgba(167,139,250,0.08));
border-bottom: 1px solid rgba(255,255,255,0.10);
}
tbody td{
padding: 12px 10px;
font-size: 16px;
color: var(--muted);
border-bottom: 1px solid rgba(255,255,255,0.06);
}
/* Left column labels */
tbody td:first-child{
width: 38%;
color: rgba(255,255,255,0.86);
font-weight: 650;
letter-spacing: 0.2px;
background: rgba(255,255,255,0.03);
border-right: 1px solid rgba(255,255,255,0.06);
}
/* Center the forecast values */
tbody td:not(:first-child),
thead th:not(:first-child){
text-align:center;
}
/* Zebra rows */
tbody tr:nth-child(odd) td{
background: rgba(255,255,255,0.018);
}
tbody tr:nth-child(even) td{
background: rgba(255,255,255,0.028);
}
tbody tr:nth-child(odd) td:first-child{
background: rgba(255,255,255,0.040);
}
tbody tr:nth-child(even) td:first-child{
background: rgba(255,255,255,0.055);
}
/* Remove bottom border on last row */
tbody tr:last-child td{
border-bottom: none;
}
/* =========
Bottom Right: YouTube iframe
========= */
.bottomRight{
padding: 10px;
background:
radial-gradient(900px 600px at 20% 20%, rgba(76,201,240,0.08), transparent 55%),
rgba(0,0,0,0.10);
}
.bottomRight iframe{
width:100%;
height:100%;
border: 1px solid rgba(255,255,255,0.10);
border-radius: calc(var(--radius) - 6px);
box-shadow: 0 18px 50px rgba(0,0,0,0.55);
background: #000;
}
/* =========
TV Safety: prevent accidental focus outlines being huge, but keep accessible
========= */
:focus{
outline: 2px solid rgba(76,201,240,0.55);
outline-offset: 2px;
}
/* =========
Responsive scaling (if you ever use it on smaller screens)
========= */
@media (max-width: 1100px){
.grid{
grid-template-columns: 1fr;
grid-template-rows: auto auto auto auto;
}
#time{ font-size: 48px; }
.weatherInfo{ grid-template-columns: 1fr; }
}
/* =========
Optional: reduce “burn-in”-like static sharp edges by a tiny overall dim
========= */
.grid{
filter: brightness(0.98);
}