Skip to content
Open
Show file tree
Hide file tree
Changes from 18 commits
Commits
Show all changes
30 commits
Select commit Hold shift + click to select a range
b24ca73
Created ItchEmbed component for widget
nicostellar Nov 29, 2025
d5c2e34
Added page structure for game pages
nicostellar Nov 29, 2025
93b80d3
Fix file structure in-line with desired URLs
nicostellar Nov 29, 2025
9e3c0a3
Enhance GameLandingPage with detailed game information and art gallery
bilibilistack Nov 29, 2025
ebccffd
rename from header to section for first image
bilibilistack Nov 29, 2025
286b245
rename function to IndividualGamePage to better reflect purpose
nicostellar Nov 29, 2025
ba6ef8d
add itch.io embed with ItchEmbed component
nicostellar Nov 29, 2025
51ecf1e
Created Games model with fields and sample Event fields for foreignkey
RadinMan Nov 29, 2025
bd8811b
Merge branch 'issue-7-Individual_game_pages' of https://github.com/co…
RadinMan Nov 29, 2025
6f225ea
Add Game Cover Image and Style Enhancements to Individual Game Page
bilibilistack Nov 29, 2025
101cb75
Refactor Individual Game Page layout and remove unused CSS styles
bilibilistack Nov 29, 2025
e5c4d1b
Fix issue of ItchEmbed inconsistent between server response and clien…
bilibilistack Nov 29, 2025
437d605
Fixed: Games class completion field to use models.IntegerChoices
RadinMan Nov 29, 2025
c400dc4
Created new migration for the new models in models.py
RadinMan Nov 29, 2025
8e7f777
Merge branch 'issue-7-Individual_game_pages' of https://github.com/co…
RadinMan Nov 29, 2025
af3483b
Added: itchEmbeddedID field to the Game Class for itch.io widget embe…
RadinMan Nov 29, 2025
35c68b4
Merge branch 'main' into issue-7-Individual_game_pages
bilibilistack Dec 3, 2025
4e034e4
Enhance Individual Game Page: Update game cover image, and include ex…
bilibilistack Dec 3, 2025
7f04583
Improved file readability
RadinMan Dec 3, 2025
efba98f
Issue Fixed: itchEmbeddedID gets default to None, for games with itch…
RadinMan Dec 3, 2025
2956ed9
Fix layout of ItchEmbed section on Individual Game Page for better al…
bilibilistack Dec 4, 2025
32a089a
Merge branch 'issue-7-Individual_game_pages' of https://github.com/co…
RadinMan Dec 6, 2025
360990a
Merge pull request #26 from codersforcauses/issue-7-Individual_game_p…
bilibilistack Dec 6, 2025
0dee0b2
Remove unnecessary link from ItchEmbed component for cleaner renderin…
bilibilistack Dec 6, 2025
91de20c
Fixed: pathToThumbnail renamed from pathhToMedia and fixed the models…
RadinMan Dec 6, 2025
aa8791c
Enhance Individual Game Page layout and content; add game description…
bilibilistack Dec 6, 2025
6d60160
Update Individual Game Page layout; enhance game description and adju…
bilibilistack Dec 10, 2025
d542650
Refactor Individual Game Page layout; streamline game description ren…
bilibilistack Dec 10, 2025
acd3dbf
Merge branch 'main' into issue-7-Individual_game_pages
bilibilistack Dec 10, 2025
3a30cff
Remove wiki picture configuration
bilibilistack Dec 15, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions client/next.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,15 @@ const config = {
root: import.meta.dirname,
},
outputFileTracingRoot: import.meta.dirname,
// Include external image domains to display images for example game covers and arts
images: {
remotePatterns: [
{
protocol: 'https',
hostname: 'upload.wikimedia.org',
},
],
},
// Turns on file change polling for the Windows Dev Container
// Doesn't work currently for turbopack, so file changes will not automatically update the client.
// watchOptions: isWindowsDevContainer()
Expand Down
42 changes: 42 additions & 0 deletions client/src/components/ui/ItchEmbed.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
/*
relevant game model values:
name
hostURL
itchEmbedID
*/

type ItchEmbedProps = {
embedID: string;
hostURL: string;
name: string;
width?: number;
height?: number;
};

export function ItchEmbed({
embedID,
hostURL,
name,
width = 552,
height = 167,
}: ItchEmbedProps) {
return (
<div>
<iframe
width={width}
height={height}
className="border-0"
src={`https://itch.io/embed/${embedID}`}
title={name}
/>
<a
href={hostURL}
target="_blank"
rel="noopener noreferrer"
className="mt-2 block text-[#7ecfff] underline"
>
{name}
</a>
</div>
);
}
123 changes: 123 additions & 0 deletions client/src/pages/games/[id].tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,123 @@
import Image from "next/image";
import React from "react";

import { ItchEmbed } from "@/components/ui/ItchEmbed";

export default function IndividualGamePage() {
return (
<div className="min-h-screen bg-[#181a25] font-sans text-[#e3e6f3]">
<section className="flex justify-center bg-[#232345] py-8">
<div className="flex max-w-4xl items-center justify-center rounded-2xl bg-[#232345] shadow-xl">
<Image
src="https://upload.wikimedia.org/wikipedia/en/b/b6/Minecraft_2024_cover_art.png"
alt="Game Cover"
width={832}
height={540}
className="rounded-2xl bg-[#232345] object-cover shadow-lg"
priority
/>
</div>
</section>
<main className="mx-auto max-w-4xl p-8">
<section className="mb-8 flex items-center justify-center rounded-xl bg-[#232345] p-6 shadow-lg">
<div className="w-full">
<h1 className="mb-4 text-center font-jersey10 text-4xl font-bold tracking-wide text-[#7ecfff] drop-shadow-lg">
Game Title
</h1>
<div className="flex flex-col items-start gap-8 md:flex-row">
<div className="flex-[2]">
<p>
Lorem ipsum dolor sit amet. Non numquam dicta nam autem dicta
33 error molestias...
</p>
<ul>
<li>Et laborum vitae est inventore obcaecati...</li>
<li>Qui quisquam nihil non porro velit hic magni...</li>
</ul>
<p>
<strong>Eum veniam quisquam et veniam distinctio.</strong>
</p>
<p>
<em>In laudantium adipisci aut molestiae consequatur.</em>
</p>
<p>
<strong>Eum itaque rerum qui enim aliquam.</strong>
</p>
<p>
<em>Id dolor consequatur ut aperiam omnis.</em>
</p>
<p>
Minecraft is a sandbox game developed and published by Mojang
Studios. Formally released on 18 November 2011 for personal
computers following its initial public alpha release on 17 May
2009, it has been ported to numerous platforms, including
mobile devices and various video game consoles....
</p>
</div>
<div className="min-w-[220px] flex-1">
<table className="w-full border-collapse border-spacing-0">
<tbody>
<tr className="border-b-2 border-gray-300">
<td className="py-2 pr-2">Contributors</td>
<td className="py-2">
Developer 1<br />
Developer 2<br />
Artist 1
</td>
</tr>
<tr className="border-b-2 border-gray-300">
<td className="py-2 pr-2">Development Stage</td>
<td className="py-2">Beta</td>
</tr>
<tr className="border-b-2 border-gray-300">
<td className="py-2 pr-2">Host Site</td>
<td className="py-2">itch.io/xxx</td>
</tr>
<tr>
<td className="py-2 pr-2">Event</td>
<td className="py-2">Game Jam November 2025</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</section>
<section className="mt-8 flex flex-col items-center">
<h2 className="mb-4 font-jersey10 text-3xl tracking-wide text-[#7ecfff]">
GAME ART
</h2>
<div className="mx-auto mb-6 flex h-[240px] w-full max-w-4xl justify-center gap-6 overflow-hidden">
<Image
src="https://upload.wikimedia.org/wikipedia/commons/thumb/a/aa/Minecraft_Zombie.png/120px-Minecraft_Zombie.png"
alt="Minecraft Zombie"
width={240}
height={240}
className="rounded-lg bg-[#232345] object-contain shadow-md"
/>
<Image
src="https://upload.wikimedia.org/wikipedia/commons/thumb/d/d8/Minecraft_Enderman.png/120px-Minecraft_Enderman.png"
alt="Minecraft Enderman"
width={240}
height={240}
className="rounded-lg bg-[#232345] object-contain shadow-md"
/>
<Image
src="https://upload.wikimedia.org/wikipedia/en/thumb/1/17/Minecraft_explore_landscape.png/375px-Minecraft_explore_landscape.png"
alt="Minecraft Landscape"
width={240}
height={240}
className="rounded-lg bg-[#232345] object-contain shadow-md"
/>
</div>
<ItchEmbed
embedID="3"
hostURL="https://leafo.itch.io/x-moon"
name="X-Moon by leafy"
/>
</section>
</main>
{/* <Footer /> */}
</div>
);
}
Empty file.
69 changes: 69 additions & 0 deletions server/game_dev/migrations/0002_events_games.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
# Generated by Django 5.1.14 on 2025-11-29 07:26

import django.db.models.deletion
from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
("game_dev", "0001_initial"),
]

operations = [
migrations.CreateModel(
name="Events",
fields=[
(
"id",
models.BigAutoField(
auto_created=True,
primary_key=True,
serialize=False,
verbose_name="ID",
),
),
("name", models.CharField(max_length=200)),
("description", models.CharField(max_length=4500)),
],
),
migrations.CreateModel(
name="Games",
fields=[
(
"id",
models.BigAutoField(
auto_created=True,
primary_key=True,
serialize=False,
verbose_name="ID",
),
),
("name", models.CharField(max_length=200)),
("description", models.CharField(max_length=4500)),
(
"completion",
models.IntegerField(
choices=[
(1, "Work in Progress (Unplayable)"),
(2, "Playable - In Development"),
(3, "Beta - Stable but not Final"),
(4, "Completed"),
],
default=1,
),
),
("active", models.BooleanField(default=True)),
("hostURL", models.CharField(max_length=2083)),
("isItch", models.BooleanField(default=True)),
("pathToMedia", models.CharField(max_length=2083)),
(
"event",
models.ForeignKey(
on_delete=django.db.models.deletion.CASCADE,
to="game_dev.events",
),
),
],
),
]
36 changes: 36 additions & 0 deletions server/game_dev/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,39 @@ class Member(models.Model):

def __str__(self):
return str(self.name)


# Sample Events Class made
class Events(models.Model):
name = models.CharField(max_length=200, null=False)
description = models.CharField(max_length=4500)

def __str__(self):
return str(self.name)


class Games(models.Model):

# Enum choices
class CompletionStatus(models.IntegerChoices):
WIP = 1, "Work in Progress (Unplayable)"
PLAYABLE_DEV = 2, "Playable - In Development"
BETA = 3, "Beta - Stable but not Final"
COMPLETED = 4, "Completed"

name = models.CharField(max_length=200, null=False)
description = models.CharField(max_length=4500)
completion = models.IntegerField(
choices=CompletionStatus.choices, # ← important
default=CompletionStatus.WIP,
null=False,
)
active = models.BooleanField(default=True, null=False)
hostURL = models.CharField(max_length=2083)
isItch = models.BooleanField(default=True, null=False)
pathToMedia = models.CharField(max_length=2083)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Similarly to the "members" table, we should be storing the images with an Image field.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@SafetyInObscurity Thanks for the feedback. I have fixed the field to be called pathToThumbnail with the correct model datatype and path to "games/" subfolder under the media/ folder. The changes have been pushed to the issue-7-Individual_game_pages branch

event = models.ForeignKey(Events, on_delete=models.CASCADE, null=False)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Event is an optional field. Not all games must have an associated game. When an event is deleted, the field should be set to Null.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Events problem "event = models.ForeignKey(Events, on_delete=models.CASCADE, null=False)" has been fixed event = models.ForeignKey(Events, on_delete=models.SET_NULL, null=True, blank=True), accommodating changing/deleting of events to not effect this field (becomes set to null) and can be null or blank as not all games must have an associated event.

# event reference uuid events.id model

def __str__(self):
return str(self.name)