Skip to content

Feature/event gallery#87

Open
Robin-deng617 wants to merge 8 commits into
mainfrom
feature/event-gallery
Open

Feature/event gallery#87
Robin-deng617 wants to merge 8 commits into
mainfrom
feature/event-gallery

Conversation

@Robin-deng617
Copy link
Copy Markdown
Contributor

@Robin-deng617 Robin-deng617 commented May 21, 2026

Added a event gallery page to view and download event photos.

Type of change

  • Feature
  • Bug fix
  • Chore / config
  • Hotfix

Checklist

  • My branch follows the naming convention (feature/, fix/, chore/, hotfix/)
  • My commit messages follow the conventional commits format
  • CI checks pass

Copy link
Copy Markdown
Collaborator

@joengy joengy left a comment

Choose a reason for hiding this comment

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

Great work initally on the components and gallery pages so far Robin, I've left some comments and suggestions so when you get the chance could you implement those. Otherwise happy with how the code is so far.

Comment on lines +22 to +27
export default async function GalleryPage({
params,
}: {
params: { eventID: string }
}) {
const { eventID } = await params
Copy link
Copy Markdown
Collaborator

@joengy joengy May 23, 2026

Choose a reason for hiding this comment

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

In Next.js 15+/16 (our repo is on next@16.1.6), params is a Promise that resolves to the params object, not the object itself. A Promise<T> is just "a value of type T that isn't ready yet" so you unwrap it with await. Your code already awaits it which is why it works, but the type annotation still claims it's a plain object. Fix the type like this:

export default async function GalleryPage({
  params,
}: {
  params: Promise<{ eventID: string }>
}) {
  const { eventID } = await params
  ...
}

Comment thread web/src/components/PhotoAlbum.tsx Outdated
{/* Close button */}
<button
onClick={onClose}
className="absolute top-4 right-4 w-8 h-8 rounded-full bg-ssa-light-grey/20 flex items-center justify-center text-ssa-white hover:bg-ssa-skin-yellow hover:text-ssa-light-brown transition-colors"
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Modal container is missing dialog semantics. Add role="dialog", aria-modal="true", and aria-labelledby pointing at the <h2>. The close/prev/next buttons also need aria-labels.

key={img.id}
onClick={() => openModal(index)}
className="relative aspect-square rounded-lg md:rounded-xl overflow-hidden group cursor-pointer"
>
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Clickable <div> thumbnail isn't keyboard-accessible (no tabIndex, no Enter/Space handler). Make it a <button type="button"> .

Comment thread web/src/components/GalleryGrid.tsx Outdated
import ZoomInIcon from '@mui/icons-material/ZoomIn'

const INITIAL_COUNT = 12
const LOAD_MORE_COUNT = 30
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Change LOAD_MORE_COUNT = 30 to 12 so each "page" matches the initial render and the layout doesn't jump on the first click.

Comment thread web/src/components/GalleryGrid.tsx Outdated

return (
<>
<div className="flex flex-col items-center gap-10 max-w-8xl mx-auto w-full px-4 md:px-30 py-10 md:py-30">
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

max-w-8xl, md:px-30, md:py-30 aren't default Tailwind tokens (max is max-w-7xl and spacing scale jumps from 28 to 32). Unless they're added to the Tailwind config they shouldn't be properly styling. Use max-w-7xl / md:px-28 / md:px-32 or extend the theme. See if changing those values does anything to the gallery grid.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

it made it a little smaller but i think it should be fine

Comment thread web/src/components/PhotoAlbum.tsx Outdated
Comment on lines +127 to +135
className="absolute left-3 top-1/2 -translate-y-1/2 w-10 h-10 rounded-full flex items-center justify-center text-gray-700 bg-[#FFF7E9]/60 hover:bg-[#FFF7E9]/90 transition-colors duration-200 border border-white"
>
<ArrowBackIcon fontSize="small" />
</button>

{/* Right arrow */}
<button
onClick={handleNext}
className="absolute right-3 top-1/2 -translate-y-1/2 w-10 h-10 rounded-full flex items-center justify-center text-gray-700 bg-[#FFF7E9]/60 hover:bg-ssa-yellow-light/90 transition-colors duration-200 border border-white"
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Another set of hardcoded hex colors (#FFF7E9, #D4CECE, #C9A84C). These exist have very similar colours in the global CSS file. If they are completely new colours you can add an additonal colour in global.css, otherwise change them.

Comment thread web/src/app/globals.css Outdated
Comment on lines +24 to +25
--color-ssa-light-grey: rgba(130, 130, 130);
--color-ssa-light-brown: rgb(150, 128, 85);
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

The way you set these two colours is completely different to how we're currently using hex values. Could you change these two to hex values rather than rgb and rgba to keep the rest of the file consistent.

eventTitle: string
eventDate: string
}

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

current can be undefined if images is empty or currentIndex is out of range so the useEffect at line 51 will then throw on current.url. Add a check like if (!current) return null before the effects.

Comment thread web/src/components/PhotoAlbum.tsx Outdated
}, [currentIndex, total, onNavigate])

useEffect(() => {
const img = new window.Image()
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

new window.Image() causes a second network fetch on top of next/image's fetch, and the modal visibly resizes when the measurement lands. Consider using next/image's onLoad (which exposes naturalWidth/naturalHeight).

Comment thread web/src/components/PhotoAlbum.tsx Outdated
Comment on lines +142 to +146
<div className="flex items-center justify-end mt-4">
<a
href={current.url}
download
className="flex items-center gap-2 px-6 py-2.5 rounded-full bg-ssa-red-light text-white font-averia font-bold hover:bg-ssa-red transition-opacity border-[3px] border-ssa-red"
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

<a href={url} download> only works for same-origin URLs. Once images come from the CMS (likely a different origin), browsers will ignore download and just navigate. Worth noting for the data-integration follow-up.

Copy link
Copy Markdown
Collaborator

@oorjagandhi oorjagandhi left a comment

Choose a reason for hiding this comment

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

Nice work on this!!

For the new components added, could you please move the gallery specific components (GalleryGrid, PhotoAlbum) into the component folder within the events folder? This is because we want to group specific components into their respective folders so it's easier to track the files, rather than having one massive components folder at the root (the root folder should be reserved for components that will be used throughout the app, for example the ViewMoreButton may be reused somewhere else so you can leave it in the current folder).

Another note: on anything that is 'clickable' like the buttons, hovering over the image before viewing it, etc, the cursor should change to a pointer. This can be done by chucking "cursor-pointer" into the in-line Tailwind for the component you want to be made clickable. I left a code comment as an example, could you please update all clickable components to reflect this?

As discussed in the Discrd, there are some minor design refinements so lmk once you add those and I'll re-review

Awesome work! :)

Comment thread web/src/components/GalleryGrid.tsx Outdated
fill
className="object-cover"
/>
<div className="absolute inset-0 bg-black/40 opacity-0 group-hover:opacity-100 transition-opacity duration-300 flex items-center justify-center">
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Suggested change
<div className="absolute inset-0 bg-black/40 opacity-0 group-hover:opacity-100 transition-opacity duration-300 flex items-center justify-center">
<div className="absolute inset-0 bg-black/40 opacity-0 group-hover:opacity-100 transition-opacity duration-300 flex items-center justify-center cursor-pointer">

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

I've implemented all the changes you suggested but regarding the minor design tweaks I'll wait a bit longer until the smaller details are tuned out

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants