Adding functionality to recommendations page

This commit is contained in:
Khalim Conn-Kowlessar 2023-07-27 17:41:36 +01:00
parent 057978f50c
commit ac6ecf3299
7 changed files with 122 additions and 1 deletions

View file

@ -199,6 +199,12 @@ export default function RecommendationCard({
<td>{cardComponent.newUValue}</td>
</tr>
)}
{cardComponent.sapPoints && (
<tr>
<td className="font-medium">SAP Points:</td>
<td>{cardComponent.sapPoints}</td>
</tr>
)}
</tbody>
</table>
<RecommendationModal

View file

@ -14,6 +14,7 @@ export interface PropertyMeta {
yearBuilt: number;
tenure: string;
currentEpcRating: string;
currentSapPoints: number;
}
export type Rating = "Very good" | "Good" | "Poor" | "Very poor" | "N/A";

View file

@ -5,6 +5,7 @@ export interface ComponentRecommendation {
estimatedCost: number;
default: boolean;
newUValue?: number;
sapPoints: number;
}
export interface Recommendation {

View file

@ -27,6 +27,7 @@ export default function DashboardLayout({
yearBuilt: 1990,
tenure: "Rented (social)",
currentEpcRating: "C",
currentSapPoints: 78,
};
if (!propertyId && propertyId !== 0) {
throw Error("Invalid propertyId");

View file

@ -26,6 +26,7 @@ export default function BuildingPassportHome() {
yearBuilt: 1990,
tenure: "Rented (social)",
currentEpcRating: "C",
currentSapPoints: 78,
};
return (

View file

@ -1,7 +1,30 @@
import { Recommendation } from "@/app/db/schema/recommendations";
import {
ComponentRecommendation,
Recommendation,
} from "@/app/db/schema/recommendations";
import RecommendationCard from "@/app/components/building-passport/RecommendationCard";
import { formatNumber, sapToEpc } from "@/app/utils";
import { PropertyMeta } from "@/app/db/schema/property";
export default function Recommendations() {
const propertyMeta: PropertyMeta = {
id: 1,
address: "123 Fake Street",
postcode: "AB1 2CD",
hasPreConditionReport: true,
hasRecommendations: true,
createdAt: "2023-07-12 11:51:31.000 +0100",
propertyType: "House",
builtForm: "Detached",
localAuthority: "Birmingham",
constituency: "Birmingham",
numberOfRooms: 5,
yearBuilt: 1990,
tenure: "Rented (social)",
currentEpcRating: "C",
currentSapPoints: 78,
};
const recommendations: Recommendation = {
Walls: [
{
@ -11,6 +34,7 @@ export default function Recommendations() {
estimatedCost: 9_450,
default: true,
newUValue: 0.29,
sapPoints: 11,
},
{
id: 2,
@ -19,6 +43,7 @@ export default function Recommendations() {
estimatedCost: 10_135,
default: false,
newUValue: 0.28,
sapPoints: 12,
},
{
id: 3,
@ -28,6 +53,7 @@ export default function Recommendations() {
estimatedCost: 13_450,
default: false,
newUValue: 0.25,
sapPoints: 14,
},
],
Ventilation: [
@ -37,6 +63,7 @@ export default function Recommendations() {
description: "Two decentralised mechanical ventilation units",
estimatedCost: 750,
default: true,
sapPoints: -2,
},
],
Floor: [
@ -47,6 +74,7 @@ export default function Recommendations() {
estimatedCost: 3_450,
default: true,
newUValue: 0.24,
sapPoints: 7,
},
{
id: 5,
@ -55,13 +83,74 @@ export default function Recommendations() {
estimatedCost: 4_120,
default: true,
newUValue: 0.24,
sapPoints: 7,
},
],
};
const defaultWallsRecommendations = recommendations.Walls?.find(
(rec: ComponentRecommendation) => rec.default
) || { estimatedCost: 0, sapPoints: 0 };
const defaultFloorRecommendations = recommendations.Floor?.find(
(rec: ComponentRecommendation) => rec.default
) || { estimatedCost: 0, sapPoints: 0 };
const defaultVentiliationRecommendations = recommendations.Ventilation?.find(
(rec: ComponentRecommendation) => rec.default
) || { estimatedCost: 0, sapPoints: 0 };
const totalEstimatedCost =
(defaultWallsRecommendations.estimatedCost || 0) +
(defaultFloorRecommendations.estimatedCost || 0) +
(defaultVentiliationRecommendations.estimatedCost || 0);
const totalSapPoints =
(defaultWallsRecommendations.sapPoints || 0) +
(defaultFloorRecommendations.sapPoints || 0) +
(defaultVentiliationRecommendations.sapPoints || 0);
const currentEpcRating = propertyMeta.currentEpcRating;
const currentSapPoints = propertyMeta.currentSapPoints;
const expectedSapPoints = currentSapPoints + totalSapPoints;
const expectedEpcRating = sapToEpc(expectedSapPoints);
return (
<div className="leading-loose tracking-wider">
<div className="flex py-8 text-lg">Recommendations</div>
<div className="mb-4 flex flex-col grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-4 items-stretch">
<table className="text-left bg-gray-600 rounded-md text-gray-100">
<tbody>
<tr>
<td className="font-medium pl-4 py-2">Total Cost:</td>
<td>{"£" + formatNumber(totalEstimatedCost)}</td>
</tr>
<tr>
<td className="font-medium pl-4 py-2">
Total SAP Points Improvement:
</td>
<td>{totalSapPoints}</td>
</tr>
</tbody>
</table>
<table className="text-left bg-gray-600 rounded-md text-gray-100">
<tbody>
<tr>
<td className="font-medium pl-4 py-2">Current EPC Rating:</td>
<td className="font-bold">{currentEpcRating}</td>
</tr>
<tr>
<td className="font-medium pl-4 py-2">Expected EPC Rating:</td>
<td className="font-bold">{expectedEpcRating}</td>
</tr>
</tbody>
</table>
</div>
<div className="flex flex-col grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-4 items-stretch">
{Object.entries(recommendations).map(
([componentType, recommendationData], idx) => {

View file

@ -1,3 +1,25 @@
export function sapToEpc(sapPoints: number): string {
if (sapPoints <= 0 || sapPoints > 100) {
throw new Error("SAP points should be between 1 and 100.");
}
if (sapPoints > 91) {
return "A";
} else if (sapPoints > 80) {
return "B";
} else if (sapPoints > 69) {
return "C";
} else if (sapPoints > 55) {
return "D";
} else if (sapPoints > 39) {
return "E";
} else if (sapPoints > 21) {
return "F";
} else {
return "G";
}
}
export function formatDateTime(dateTimeString: string): string {
// Create a new Date object
const dateTime = new Date(dateTimeString);