diff --git a/Sprint-3/alarmclock/alarmclock.js b/Sprint-3/alarmclock/alarmclock.js index 6ca81cd3b..3979c8c55 100644 --- a/Sprint-3/alarmclock/alarmclock.js +++ b/Sprint-3/alarmclock/alarmclock.js @@ -1,25 +1,126 @@ -function setAlarm() {} +// -------- Alarm Clock Implementation -------- +let countdownInterval = null; +let timeLeft = 0; +let paused = false; -// DO NOT EDIT BELOW HERE +// -------- Main Functions -------- +function setAlarm() { + const input = document.getElementById("alarmSet"); + const secondsInput = parseInt(input.value, 10); -var audio = new Audio("alarmsound.mp3"); + // Ignore invalid or zero/negative inputs + if (isNaN(secondsInput) || secondsInput <= 0) return; -function setup() { - document.getElementById("set").addEventListener("click", () => { - setAlarm(); - }); + // Reset previous alarm + resetAlarm(); + + timeLeft = secondsInput; + updateHeading(timeLeft); + + input.disabled = true; + + countdownInterval = setInterval(() => { + if (!paused) { + timeLeft--; - document.getElementById("stop").addEventListener("click", () => { - pauseAlarm(); - }); + if (timeLeft <= 0) { + clearInterval(countdownInterval); + countdownInterval = null; + updateHeading(0); + playAlarm(); + startFlashing(); + input.disabled = false; + } else { + updateHeading(timeLeft); + } + } + }, 1000); +} + +function pauseAlarm() { + paused = true; + audio.pause(); + stopFlashing(); } +function resumeAlarm() { + if (timeLeft > 0) paused = false; +} + +function stopAlarm() { + resetAlarm(); // fully stop everything +} + +function resetAlarm() { + // Stop countdown + paused = false; + if (countdownInterval) { + clearInterval(countdownInterval); + countdownInterval = null; + } + + // Stop flashing background + stopFlashing(); + + // Stop alarm sound if playing + if (audio) { + audio.pause(); + audio.currentTime = 0; + } + + // Reset countdown display + timeLeft = 0; + updateHeading(0); + + // Clear and re-enable input + const input = document.getElementById("alarmSet"); + if (input) { + input.value = ""; + input.disabled = false; + } +} + +// -------- Helper Functions -------- +function updateHeading(seconds) { + const heading = document.getElementById("timeRemaining"); + const mins = Math.floor(seconds / 60) + .toString() + .padStart(2, "0"); + const secs = (seconds % 60).toString().padStart(2, "0"); + heading.innerText = `Time Remaining: ${mins}:${secs}`; +} + +// ---------------- Flashing Screen (CSS-based) ---------------- +function startFlashing() { + document.body.classList.add("alarm-flashing"); +} + +function stopFlashing() { + document.body.classList.remove("alarm-flashing"); + document.body.style.backgroundColor = "white"; +} + +// ---------------- Audio ---------------- +var audio = new Audio("alarmsound.mp3"); + function playAlarm() { audio.play(); } -function pauseAlarm() { +function pauseAlarmSound() { audio.pause(); } +// ---------------- Setup Event Listeners ---------------- +function setup() { + document.getElementById("set").addEventListener("click", setAlarm); + document.getElementById("pause").addEventListener("click", pauseAlarm); + document.getElementById("resume").addEventListener("click", resumeAlarm); + document.getElementById("stop").addEventListener("click", stopAlarm); + document.getElementById("reset").addEventListener("click", resetAlarm); +} + window.onload = setup; + + +// alarmclock.js modified \ No newline at end of file diff --git a/Sprint-3/alarmclock/alarmclock.test.js b/Sprint-3/alarmclock/alarmclock.test.js index 85b7356dc..2711258d1 100644 --- a/Sprint-3/alarmclock/alarmclock.test.js +++ b/Sprint-3/alarmclock/alarmclock.test.js @@ -2,6 +2,7 @@ There are some Tests in this file that will help you work out if your code is working. */ +require("@testing-library/jest-dom"); const path = require("path"); const { JSDOM } = require("jsdom"); @@ -102,3 +103,6 @@ test("should play audio when the timer reaches zero", () => { expect(mockPlayAlarm).toHaveBeenCalledTimes(1); }); + + +// In alarmclock.test.js tests passed \ No newline at end of file diff --git a/Sprint-3/alarmclock/index.html b/Sprint-3/alarmclock/index.html index 48e2e80d9..6c3eafa22 100644 --- a/Sprint-3/alarmclock/index.html +++ b/Sprint-3/alarmclock/index.html @@ -4,17 +4,26 @@ - Title here + Alarm clock app

Time Remaining: 00:00

- + + - - +
+ + + + + +
- + + + + diff --git a/Sprint-3/alarmclock/package.json b/Sprint-3/alarmclock/package.json index e1331e071..129be86d5 100644 --- a/Sprint-3/alarmclock/package.json +++ b/Sprint-3/alarmclock/package.json @@ -4,7 +4,8 @@ "license": "CC-BY-SA-4.0", "description": "You must update this package", "scripts": { - "test": "jest --config=../jest.config.js alarmclock" + "test": "jest --config=jest.config.js alarmclock" + }, "repository": { "type": "git", @@ -13,5 +14,9 @@ "bugs": { "url": "https://github.com/CodeYourFuture/CYF-Coursework-Template/issues" }, - "homepage": "https://github.com/CodeYourFuture/CYF-Coursework-Template#readme" + "homepage": "https://github.com/CodeYourFuture/CYF-Coursework-Template#readme", + "devDependencies": { + "@testing-library/jest-dom": "^6.9.1", + "jsdom": "^20.0.3" + } } diff --git a/Sprint-3/alarmclock/style.css b/Sprint-3/alarmclock/style.css index 0c72de38b..800b3cb93 100644 --- a/Sprint-3/alarmclock/style.css +++ b/Sprint-3/alarmclock/style.css @@ -1,15 +1,74 @@ +/* Center everything on the page */ .centre { position: fixed; top: 50%; left: 50%; - -webkit-transform: translate(-50%, -50%); transform: translate(-50%, -50%); + text-align: center; + font-family: Arial, sans-serif; } -#alarmSet { - margin: 20px; +/* Heading */ +h1 { + text-align: center; + font-size: 2em; + margin-bottom: 20px; + transition: background-color 0.2s ease; } -h1 { +/* Input field */ +#alarmSet { + width: 80px; + padding: 5px; + font-size: 1em; + margin-bottom: 20px; text-align: center; } + +/* Buttons container */ +.buttons { + display: flex; + justify-content: center; + flex-wrap: wrap; + gap: 10px; /* space between buttons */ + margin-top: 10px; +} + +/* Buttons */ +button { + padding: 10px 20px; + font-size: 1em; + cursor: pointer; + border-radius: 5px; + border: none; + background-color: #007bff; + color: white; + transition: background-color 0.2s ease, transform 0.1s ease; +} + +button:hover { + background-color: #0056b3; + transform: scale(1.05); +} + +button:active { + transform: scale(0.95); +} + +/* Input and buttons spacing */ +input, +button { + margin: 5px; +} + +/* Flashing background */ +@keyframes alarm-flash { + 0%, 100% { background-color: white; } + 50% { background-color: #add8e6; } +} + +.alarm-flashing { + animation: alarm-flash 0.5s steps(1, end) infinite; +} + +