feat: add Berlin Clock layout and styling with Orbitron font
This commit is contained in:
committed by
Loic Coenen (aider)
parent
abf8b13fc7
commit
3fed6dc168
21
src/App.css
21
src/App.css
@@ -182,3 +182,24 @@
|
||||
border-right-color: var(--border);
|
||||
}
|
||||
}
|
||||
|
||||
.berlin-clock {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
gap: 4px;
|
||||
}
|
||||
|
||||
.seconds-lamp-container {
|
||||
margin-bottom: 4px;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.lamp-row {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
width: 100%;
|
||||
max-width: 330px;
|
||||
margin: 0 auto;
|
||||
}
|
||||
|
||||
10
src/App.tsx
10
src/App.tsx
@@ -3,7 +3,15 @@ import "./App.css";
|
||||
|
||||
function App() {
|
||||
return (
|
||||
<div>
|
||||
<div className="clock-container">
|
||||
<h1>Berlin Clock</h1>
|
||||
<p>
|
||||
The Berlin Clock (also known as the Mengenlehreuhr) uses lamps to represent the time.
|
||||
The top lamp blinks every second. The next row of four red lamps each represents five hours.
|
||||
The following row of four red lamps each represents one hour.
|
||||
Then the next row of eleven lamps shows five‑minute blocks (every third lamp is red to
|
||||
mark quarter hours). The last row shows the remaining minutes one by one.
|
||||
</p>
|
||||
<TimeConverter />
|
||||
</div>
|
||||
);
|
||||
|
||||
@@ -14,23 +14,17 @@ function getBackgroundColor(state: LampState): string {
|
||||
}
|
||||
|
||||
function getBorderRadius(variant?: LampProps["variant"]): string {
|
||||
switch (variant) {
|
||||
case "alone":
|
||||
return "50%";
|
||||
case "first":
|
||||
return "50% 0 0 50%";
|
||||
case "last":
|
||||
return "0 50% 50% 0";
|
||||
default:
|
||||
return "0";
|
||||
}
|
||||
if (variant === "alone") return "50%";
|
||||
if (variant === "first") return "16px 0 0 16px";
|
||||
if (variant === "last") return "0 16px 16px 0";
|
||||
return "0";
|
||||
}
|
||||
|
||||
export function Lamp({ state, id, variant }: LampProps) {
|
||||
const style: React.CSSProperties = {
|
||||
display: "inline-block",
|
||||
width: 20,
|
||||
height: 20,
|
||||
display: "block",
|
||||
width: variant === "alone" ? 50 : "100%",
|
||||
height: 50,
|
||||
backgroundColor: getBackgroundColor(state),
|
||||
borderRadius: getBorderRadius(variant),
|
||||
margin: 1,
|
||||
|
||||
@@ -11,7 +11,7 @@ export function LampLine({ states, rowTestId }: LampLineProps) {
|
||||
return (
|
||||
<div
|
||||
data-testid={rowTestId ?? "lamp-line"}
|
||||
style={{ display: "flex", gap: 2, marginBottom: 5 }}
|
||||
style={{ display: "flex", marginBottom: 10, width: "100%", justifyContent: "space-evenly" }}
|
||||
>
|
||||
{states.map((state, index) => {
|
||||
let variant: "alone" | "first" | "last" | "middle" | undefined;
|
||||
@@ -25,12 +25,16 @@ export function LampLine({ states, rowTestId }: LampLineProps) {
|
||||
variant = "middle";
|
||||
}
|
||||
return (
|
||||
<Lamp
|
||||
<div
|
||||
key={index}
|
||||
state={state}
|
||||
id={`lamp-${index}`}
|
||||
variant={variant}
|
||||
/>
|
||||
style={{ flex: 1, display: "flex" }}
|
||||
>
|
||||
<Lamp
|
||||
state={state}
|
||||
id={`lamp-${index}`}
|
||||
variant={variant}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
})}
|
||||
</div>
|
||||
|
||||
@@ -11,17 +11,22 @@ export function BerlinClock({ enabled, clock }: BerlinClockProps) {
|
||||
if (!enabled) return null;
|
||||
|
||||
return (
|
||||
<div>
|
||||
<div
|
||||
data-testid="seconds-row"
|
||||
style={{ display: "flex", gap: 2, marginBottom: 5 }}
|
||||
>
|
||||
<Lamp state={clock.secondsRow[0]} id="seconds-lamp" variant="alone" />
|
||||
<div className="berlin-clock" style={{ display: "flex", flexDirection: "column", alignItems: "center", width: "100%" }}>
|
||||
<div className="seconds-lamp-container" data-testid="seconds-row" style={{ width: "100%", display: "flex", justifyContent: "center" }}>
|
||||
<Lamp state={clock.secondsRow[0]} variant="alone" id="seconds-lamp" />
|
||||
</div>
|
||||
<div className="lamp-row" style={{ width: "100%" }}>
|
||||
<LampLine states={clock.fiveHours} rowTestId="five-hours-row" />
|
||||
</div>
|
||||
<div className="lamp-row" style={{ width: "100%" }}>
|
||||
<LampLine states={clock.oneHour} rowTestId="single-hours-row" />
|
||||
</div>
|
||||
<div className="lamp-row" style={{ width: "100%" }}>
|
||||
<LampLine states={clock.fiveMinutes} rowTestId="five-minutes-row" />
|
||||
</div>
|
||||
<div className="lamp-row" style={{ width: "100%" }}>
|
||||
<LampLine states={clock.oneMinute} rowTestId="single-minutes-row" />
|
||||
</div>
|
||||
<LampLine states={clock.fiveHours} rowTestId="five-hours-row" />
|
||||
<LampLine states={clock.oneHour} rowTestId="single-hours-row" />
|
||||
<LampLine states={clock.fiveMinutes} rowTestId="five-minutes-row" />
|
||||
<LampLine states={clock.oneMinute} rowTestId="single-minutes-row" />
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
@@ -19,6 +19,12 @@ export function TimeConverter() {
|
||||
|
||||
return (
|
||||
<div>
|
||||
<BerlinClock enabled={true} clock={berlinClock} />
|
||||
<DigitalClock
|
||||
currentTime={currentTime}
|
||||
onTimeChange={setCurrentTime}
|
||||
disabled={useSystemTime}
|
||||
/>
|
||||
<label>
|
||||
<input
|
||||
type="checkbox"
|
||||
@@ -33,12 +39,6 @@ export function TimeConverter() {
|
||||
/>
|
||||
Use system time
|
||||
</label>
|
||||
<BerlinClock enabled={true} clock={berlinClock} />
|
||||
<DigitalClock
|
||||
currentTime={currentTime}
|
||||
onTimeChange={setCurrentTime}
|
||||
disabled={useSystemTime}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
@import url('https://fonts.googleapis.com/css2?family=Orbitron:wght@400;500;700&display=swap');
|
||||
|
||||
:root {
|
||||
--text: #6b6375;
|
||||
--text-h: #08060d;
|
||||
@@ -59,6 +61,8 @@
|
||||
min-height: 100svh;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
@@ -109,3 +113,11 @@ code {
|
||||
padding: 4px 8px;
|
||||
background: var(--code-bg);
|
||||
}
|
||||
|
||||
.clock-container {
|
||||
font-family: 'Orbitron', monospace;
|
||||
}
|
||||
|
||||
.clock-container input {
|
||||
font-family: inherit;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user