To run this project locally:
- Clone the repository
- Run
npm installto install dependencies - Run
node index.js - Open
http://localhost:3000in your browser
- CSS custom properties
- Flexbox
- CSS Grid
- Mobile-first workflow
- JavaScript
- Node.js
- Express.js
- NPM: body-parser, axios
This project was a capstone project for a full-stack web development course, focused on integrating APIs. I used an API that streams soundtracks from various Animal Crossing games. Data handling between the client and the server remains a challenge for me, but this has been one of my favourite projects so far.
The project initially fetched soundtracks based on the current hour. As I added more features - such as automatically updating the soundtrack when the hour changed - conflicts arose. Specifically, when a user selected a specific time (and thus a specific soundtrack), the auto-polling feature would override the selection every 30 seconds. To resolve this, I moved away from tracking input using global booleans and used URL flags instead.
Here is how I handled it on the server:
app.post("/set-soundtrack", async (req, res) => {
// Handle incoming request to change hourly soundtrack based on selected time by client
const selectedTime = req.body.setTime; // Output eg.: 12AM
if (selectedTime) {
try {
... // Fetch soundtrack from API
// Redirect to homepage with manual override flag
res.redirect(`/?manual=true&time=${encodeURIComponent(selectedTime)}`);
...
} catch (error) {
... // Error handling
}
}
});And on the client side, I checked for this flag to disable auto-polling:
const songWasRequested = window.location.search.includes("manual=true"); // Skip polling if the URL includes a manual override flag (?manual=true)
if (!songWasRequested) {
setInterval(async () => {
... // Fetch new soundtrack from server
}, 30000); // To fetch data every 30secs
}This small shift made a big difference in user experience and taught me a lot about clean client-server communication.
Animating elements based on my own drawings made this one of the most enjoyable parts of the project. I have only scratched the surface of CSS animations, and I hope to refine this further in future iterations. I would like to add more subtle animations to create depth, while ensuring they do not distract from the purpose of this app - a calm, focused study space.
I also plan to practice working with more complex API routes. For this project specifically, I would love to add a feature that allows users to choose soundtracks from different Animal Crossing games.
UPDATE: It is now possible for users to choose the Animal Crossing game they would like to listen to.
- Creating a Custom Audio Player I have not implemented this yet, but it offers great tips I hope to follow when replacing the default browser player with a custom one.
- Website - ShannyxMP
-
Huge thanks to Dr Angela Yu for providing such a clear and supportive learning experience in Full-stack Web Development.
-
Thanks to Matt for the Animal Crossing API.
- Customise audio player to match the theme
- Allow users to select which game’s soundtrack to listen to
- Refine layout
- Expand animations
- Post kind reminders
- Add a digital clock with local time
- Add local date
- Store user-specific settings (like game/time) using sessions or query params - so multiple users don’t override each other’s soundtrack settings
