Skip to content
Snippets Groups Projects

Style saving overview

Merged Agnethe Kval-Engstad requested to merge style-saving-overview into development
1 file
+ 44
179
Compare changes
  • Side-by-side
  • Inline
@@ -25,7 +25,7 @@ import {
onMounted,
onUnmounted,
computed,
onBeforeMount,
onBeforeMount,
} from "vue";
import Sparti from "@/components/Sparti.vue";
import { Chart, registerables } from 'chart.js';
@@ -33,8 +33,10 @@ import MainLayout from "@/components/MainLayout.vue";
import { useSavingGoalsStore } from "@/stores/savingGoals.js";
import { useThemeStore } from "@/stores/theme.js";
import {useUserStore} from "@/stores/user.js";
import { useSavingChallengeStore } from "@/stores/savingChallenge.js";
import { useTransactionsStore } from "@/stores/transactions";
import {useSavingChallengeStore} from "@/stores/savingChallenge.js";
const transactionsStore = useTransactionsStore();
const savingChallengeStore = useSavingChallengeStore();
const challenges = computed(() => savingChallengeStore.savingChallenges);
@@ -42,99 +44,12 @@ const challenges = computed(() => savingChallengeStore.savingChallenges);
const savingGoalsStore = useSavingGoalsStore();
const savingGoals = computed(() => savingGoalsStore.savingGoals);
const transactionsStore = useTransactionsStore();
const completedSavings = savingGoalsStore.completedSavingGoals;
/**
* Registers the chart.js components.
*/
Chart.register(...registerables);
//TODO: Delete when backend is connected.
const savings = [
{
id: 1,
goal: "Ferie",
deadline: "01.06.2022",
amount: "10 000 kr",
status: "completed",
},
{
id: 2,
goal: "Bolig",
deadline: "01.01.2023",
amount: "50 000 kr",
status: "active",
},
{
id: 3,
goal: "Lån bil",
deadline: "01.01.2024",
amount: "13 000 kr",
status: "completed",
},
]
//TODO: Delete when backend is connected.
//TODO: Delete when backend is connected.
const otherSavings = [
{
id: 1,
description: "Sparekonto",
date: "02.07.2022",
amount: "500 kr",
},
{
id: 2,
description: "Aksjer",
date: "29.11.2023",
amount: "3 500 kr",
},
{
id: 3,
description: "Fond",
date: "03.04.2024",
amount: "400 kr",
},
]
/**
* Filtering out the completed saving goals from all the saving goals.
*/
/**
* Counting the completed saving goals.
*/
const completedSavingsGoals = completedSavings.length;
/**
* Counting the completed saving challenges.
*/
const completedChallenges = challenges.filter(challenge => challenge.status === 'completed').length;
/**
* Filtering out the active saving goals from all the saving goals.
*/
const activeSavingsGoals = savings.filter(saving => saving.status === 'active');
/**
* Filtering out the active challenges from all the challenges.
*/
const activeChallenges = challenges.filter(challenge => challenge.status === 'active');
/**
* Filtering out the failed saving goals from all the saving goals.
*/
const failedSavingsGoals = savings.filter(saving => saving.status === 'failed');
/**
* Filtering out the failed challenges from all the challenges.
*/
const failedChallenges = challenges.filter(challenge => challenge.status === 'failed');
/**
* References to the three chart canvases.
@@ -168,9 +83,9 @@ watchEffect(() => {
const savingsChartData = {
labels: ['Fullførte', 'Aktive', 'Feilede'],
datasets: [{
data: [savingGoalsStore.completedSavingGoals, savingGoalsStore.activeSavingGoalsCount,
data: [savingGoalsStore.completedSavingGoalsCount, savingGoalsStore.activeSavingGoalsCount,
savingGoalsStore.failedSavingGoalsCount],
backgroundColor: [primaryColor, primaryLightColor, primaryDarkColor],
backgroundColor: [completedColor, activeColor, failedColor],
}]
};
@@ -196,7 +111,7 @@ watchEffect(() => {
datasets: [{
data: [savingChallengeStore.completedChallengesCount, savingChallengeStore.activeChallengesCount,
savingChallengeStore.failedChallengesCount],
backgroundColor: [primaryColor, primaryLightColor, primaryDarkColor],
backgroundColor: [completedColor, activeColor, failedColor],
}]
};
@@ -211,51 +126,8 @@ watchEffect(() => {
});
/**
* Calculate the total savings per month.
* Groups the savings by month and calculates the total savings for each month cumulatively.
*/
const calculateTotalSavingsPerMonth = (savingsArray) => {
const savingsPerMonth = {};
let cumulativeTotal = 0;
const groupedSavings = savingsArray.reduce((acc, saving) => {
const date = saving.deadline ? saving.deadline : saving.date;
const monthYear = date.split('.').slice(1).reverse().join('-');
const amount = parseInt(saving.amount.replace(/\s/g, '').replace('kr', ''));
if (!acc[monthYear]) {
acc[monthYear] = [];
}
acc[monthYear].push(amount);
return acc;
}, {});
Object.keys(groupedSavings).sort((a, b) => new Date(a) - new Date(b)).forEach(monthYear => {
groupedSavings[monthYear].forEach(amount => {
cumulativeTotal += amount;
});
savingsPerMonth[monthYear] = cumulativeTotal;
});
return savingsPerMonth;
};
/**
* Calculate the total savings per month.
*/
const totalSavingsPerMonth = calculateTotalSavingsPerMonth([...completedSavings, ...otherSavings]);
/**
* Chart labels.
*/
const totalSavingsChartLabels = Object.keys(totalSavingsPerMonth);
/**
* Watchers for the total savings data.
* Updates the area line chart when the data changes.
* Watchers for the transaction data.
* Updates the chart when the data changes.
*/
watchEffect(() => {
if (totalSavingsChartRef.value) {
@@ -297,24 +169,7 @@ watchEffect(() => {
}
})
/**
* Calculate the total of other savings.
*/
const otherSavingsTotal = otherSavings.reduce((acc, saving) => {
return acc + parseInt(saving.amount.replace(" ", ""));
}, 0);
/**
* Calculate the total of saving goals.
*/
const savingGoalsTotal = completedSavings.reduce((acc, saving) => {
return acc + parseInt(saving.amount.replace(" ", ""));
}, 0);
/**
* Calculate the total savings.
*/
const totalSavings = otherSavingsTotal + savingGoalsTotal;
/**
* Checks if the screen is large.
@@ -364,6 +219,7 @@ const displayName = computed(() => {
const savingsTransactions = computed(() => transactionsStore.$state.savingsTransactions);
const totalSaved = computed(() => transactionsStore.getTotalSaved);
const totalSavedOnlyFromSavingGoals = computed(() => transactionsStore.getTotalSavedWithSavingGoal);
/**
* Computed property for the formatted deadline.
*/
@@ -378,6 +234,13 @@ function formattedDeadline(time) {
return `${formattedDate}`;
}
const totalSavings = transactionsStore.getTotalSaved;
const totalActiveSavingGoals = savingGoalsStore.activeSavingGoalsCount;
const totalOtherSavings = totalSavings - totalSavedOnlyFromSavingGoals;
</script>
<template>
@@ -386,27 +249,29 @@ function formattedDeadline(time) {
<h1 class="text-stroke">MINE SPARINGER</h1>
<div class="flex flex-col md:flex-row justify-center gap-6">
<Sparti :theme="theme" class="md:w-5/12">
<span v-if="totalSavings === 0">
Hmm <strong>{{ displayName }}</strong>,<br />
ser ut som du ikke har spart noe enda.<br />
<span v-if="totalSavings === 0 && totalActiveSavingGoals===0">
Hmm <strong>{{ displayName }}</strong>,<br/>
ser ut som du ikke har spart noe enda.<br/>
Kanskje det er på tide å sette seg noen sparemål?
</span>
<span v-if="savingGoalsTotal === 0 && otherSavingsTotal > 0">
Psst <strong>{{ displayName }}</strong>!<br />
Med sparesti har du klart å spare opp <strong>{{ totalSaved }} kr.</strong> i annen sparing.<br />
<span v-if="totalActiveSavingGoals === 0 && totalOtherSavings > 0">
Psst <strong>{{ displayName }}</strong>!<br/>
Med sparesti har du klart å spare opp <strong>{{ totalOtherSavings }} kr.</strong> i annen sparing.<br/>
Det er supert, men kanskje er det på tide å sette seg noen sparemål?
</span>
<span v-if="otherSavingsTotal === 0 && savingGoalsTotal > 0">
Psst <strong>{{ displayName }}</strong>!<br />
Med sparesti har du klart å spare opp <strong>{{ totalSavedOnlyFromSavingGoals }} kr.</strong> med sparemål.<br />
<span v-if="totalOtherSavings === 0 && totalSavedOnlyFromSavingGoals > 0">
Psst <strong>{{ displayName }}</strong>!<br/>
Med sparesti har du klart å spare opp <strong>{{ totalSavedOnlyFromSavingGoals }} kr.</strong> med sparemål.<br/>
Flott!
</span>
<span v-if="totalActiveSavingGoals > 0 && totalOtherSavings === 0 && totalSavedOnlyFromSavingGoals=== 0">
ser ut som du ikke har spart noe enda.
</span>
<span v-else>
Psst <strong>{{ displayName }}</strong>!<br />
Med Sparesti har du klart å spare opp <strong>{{ totalSaved }} kr.</strong><br />
<strong>{{ totalSavedOnlyFromSavingGoals }} kr</strong> med sparemål<br />
og <strong>{{ totalSaved - totalSavedOnlyFromSavingGoals }} kr</strong> i annen sparing.<br />
Imponerende!
Psst <strong>{{ displayName }}</strong>!<br/>
Med Sparesti har du klart å spare opp <strong>{{ totalSaved }} kr.</strong><br/>
<strong>{{ totalSavedOnlyFromSavingGoals }} kr</strong> med sparemål<br/>
og <strong>{{ totalSaved - totalSavedOnlyFromSavingGoals }} kr</strong> i annen sparing.
</span>
</Sparti>
<div class="flex flex-col p-4 gap-4 md:gap-1 text-left">
@@ -414,7 +279,7 @@ function formattedDeadline(time) {
Totalt spart siste året: {{ totalSaved }} kr
</p>
<Card class="md:w-[400px] bg-white border-2 border-primary-dark">
<canvas ref="totalSavingsChartRef" class="md:w-full md:h-full" />
<canvas ref="totalSavingsChartRef" class="md:w-full md:h-full"/>
</Card>
</div>
</div>
@@ -455,13 +320,13 @@ function formattedDeadline(time) {
</TableCell>
<TableCell>
<div v-if="savingGoal.status === 'ACTIVE'" title="Aktiv">
<SquareMinus size="20" :color="primaryLightColor"/>
<SquareMinus size="30" :color="activeColor"/>
</div>
<div v-if="savingGoal.status === 'COMPLETED'" title="Fullført">
<SquareCheck size="20" :color="primaryColor"/>
<SquareCheck size="30" :color="completedColor"/>
</div>
<div v-if="savingGoal.status === 'FAILED'" title="Feilet">
<SquareX size="20" :color="primaryDarkColor"/>
<SquareX size="30" :color="failedColor"/>
</div>
</TableCell>
<TableCell>{{ formattedDeadline(savingGoal.deadline) }}</TableCell>
@@ -491,7 +356,7 @@ function formattedDeadline(time) {
<Card class="mb-6 border-standard">
<div class="flex flex-row justify-between table-container overflow-y-auto max-h-[auto] bg-standard">
<Card class="bg-white border-2 border-primary-dark md:overflow-auto md:max-h-[300px]">
<Table >
<Table>
<TableHeader>
<TableRow>
<TableHead class="w-[100px]">UTFORDRING</TableHead>
@@ -503,21 +368,21 @@ function formattedDeadline(time) {
<TableBody class="overflow-auto">
<TableRow v-for="challenge in challenges" :key="challenge.id">
<TableCell class="flex flex-row items-center justify-start">
{{ challenge.goal }}
{{ challenge.title }}
</TableCell>
<TableCell>
<div v-if="challenge.status === 'ACTIVE'" title="Aktiv">
<SquareMinus size="20" :color="primaryLightColor" />
<SquareMinus size="30" :color="activeColor"/>
</div>
<div v-if="challenge.status === 'COMPLETED'" title="Fullført">
<SquareCheck size="20" :color="primaryColor" />
<SquareCheck size="30" :color="completedColor"/>
</div>
<div v-if="challenge.status === 'FAILED'" title="Feilet">
<SquareX size="20" :color="primaryDarkColor" />
<SquareX size="30" :color="failedColor"/>
</div>
</TableCell>
<TableCell>{{ challenge.deadline }}</TableCell>
<TableCell class="text-right">{{ challenge.amount }}</TableCell>
<TableCell>{{ formattedDeadline(challenge.deadline) }}</TableCell>
<TableCell class="text-right">{{ challenge.goal }}</TableCell>
</TableRow>
</TableBody>
</Table>
Loading