From e179aa17431ed5730f75896588a7c68ed9196f1e Mon Sep 17 00:00:00 2001 From: itsfinniii <102350242+itsfinniii@users.noreply.github.com> Date: Wed, 25 Mar 2026 22:14:32 +0100 Subject: [PATCH] Add reviews to the website --- astro/src/components/web/Reviews.astro | 50 +++++++++++++ .../web/subcomponents/StarRating.astro | 71 +++++++++++++++++++ astro/src/components/webpage/Webpage.astro | 2 + 3 files changed, 123 insertions(+) create mode 100644 astro/src/components/web/Reviews.astro create mode 100644 astro/src/components/web/subcomponents/StarRating.astro diff --git a/astro/src/components/web/Reviews.astro b/astro/src/components/web/Reviews.astro new file mode 100644 index 0000000..6d22091 --- /dev/null +++ b/astro/src/components/web/Reviews.astro @@ -0,0 +1,50 @@ +--- +import StarRating from './subcomponents/StarRating.astro'; + +interface Props { + reviews: ReviewListComponent; +} + +const reviews = Astro.props.reviews; + +let totalStars: number = 0; +const totalReviews: number = reviews.reviews.length; + +reviews.reviews.forEach((review) => { + totalStars = totalStars + review.stars; +}); + +const averageStars = Math.round((totalStars / totalReviews) * 10) / 10; +const reviewsToShow = reviews.reviews.slice(0, 5); +--- + +
+
+
+

{reviews.title}

+
{reviews.text}
+
+ +
+ +

{averageStars} stars out of {totalReviews} {totalReviews === 1 ? "review" : "reviews"}.

+
+
+ +
+ { reviewsToShow.map((review) => ( +
+
+

{review.name}

+
+ +
+
+ +
+ { review.review } +
+
+ )) } +
+
diff --git a/astro/src/components/web/subcomponents/StarRating.astro b/astro/src/components/web/subcomponents/StarRating.astro new file mode 100644 index 0000000..10be01b --- /dev/null +++ b/astro/src/components/web/subcomponents/StarRating.astro @@ -0,0 +1,71 @@ +--- +interface Props { + stars: number; + size: "big" | "small"; +} + +function roundToCustomHalf(value: number) { + const whole = Math.floor(value); + const decimal = value - whole; + + if (decimal < 0.25) return whole; + if (decimal < 0.75) return whole + 0.5; + return whole + 1; +} + +const stars = roundToCustomHalf(Astro.props.stars); +const totalStars = 5; +--- + +
+ {Array.from({ length: totalStars }).map((_, i) => { + const starValue = i + 1; + let type = "empty"; + + if (stars >= starValue) { + type = "full"; + } else if (stars >= starValue - 0.5) { + type = "half"; + } + + return ( + + {type === "full" && ( + + )} + + {type === "half" && ( + <> + + + + + + + + + )} + + {type === "empty" && ( + + )} + + ); + })} +
+ diff --git a/astro/src/components/webpage/Webpage.astro b/astro/src/components/webpage/Webpage.astro index a0e7ba1..195b134 100644 --- a/astro/src/components/webpage/Webpage.astro +++ b/astro/src/components/webpage/Webpage.astro @@ -5,6 +5,7 @@ import TextWithImage from '../web/TextWithImage.astro'; import UpcomingEvents from '../web/UpcomingEvents.astro'; import WallOfText from '../web/WallOfText.astro'; import EquipmentTable from '../web/EquipmentTable.astro'; +import Reviews from '../web/Reviews.astro'; interface Props { webpage: WebpageComponent[]; @@ -24,6 +25,7 @@ console.log(Astro.props.webpage); { component.component === "UpcomingEvents" && } { component.component === "FrequentlyAskedQuestions" && } { component.component === "EquipmentTable" && } + { component.component === "Reviews" && } )) }