refactor: update routing paths in app.vue, enhance AnnualBudget component layout, and streamline dashboard and budget pages for improved user experience
This commit is contained in:
parent
09d8794d72
commit
864a81065c
23 changed files with 3211 additions and 1978 deletions
|
|
@ -141,6 +141,16 @@ export const useMembersStore = defineStore(
|
|||
const member = members.value.find((m) => m.id === memberId);
|
||||
if (member) {
|
||||
member.capacity = { ...member.capacity, ...capacity };
|
||||
// Recalculate monthly pay based on new capacity
|
||||
recalculateMemberPay(memberId);
|
||||
}
|
||||
}
|
||||
|
||||
function recalculateMemberPay(memberId, equalWage = 25) {
|
||||
const member = members.value.find((m) => m.id === memberId);
|
||||
if (member) {
|
||||
const targetHours = member.capacity?.targetHours || 0;
|
||||
member.monthlyPayPlanned = targetHours * equalWage;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -197,18 +207,47 @@ export const useMembersStore = defineStore(
|
|||
}
|
||||
|
||||
// Coverage calculations for individual members
|
||||
function getMemberCoverage(memberId) {
|
||||
function getMemberCoverage(memberId, equalWage = 25) {
|
||||
const member = members.value.find((m) => m.id === memberId);
|
||||
if (!member) return { coveragePct: undefined };
|
||||
if (!member) return { minPct: 0, targetPct: 0 };
|
||||
|
||||
return coverage(
|
||||
member.minMonthlyNeeds || 0,
|
||||
member.monthlyPayPlanned || 0
|
||||
);
|
||||
// Calculate what they're getting paid based on their hours
|
||||
const minHours = member.capacity?.minHours || 0;
|
||||
const targetHours = member.capacity?.targetHours || 0;
|
||||
|
||||
// Current monthly pay planned
|
||||
const monthlyPay = member.monthlyPayPlanned || 0;
|
||||
|
||||
// Calculate coverage percentages
|
||||
const minMonthlyPay = minHours * equalWage;
|
||||
const targetMonthlyPay = targetHours * equalWage;
|
||||
|
||||
const minPct = minMonthlyPay > 0 ? Math.min(100, (monthlyPay / minMonthlyPay) * 100) : 0;
|
||||
const targetPct = targetMonthlyPay > 0 ? Math.min(100, (monthlyPay / targetMonthlyPay) * 100) : 0;
|
||||
|
||||
return { minPct, targetPct };
|
||||
}
|
||||
|
||||
// Team-wide coverage statistics
|
||||
const teamStats = computed(() => teamCoverageStats(members.value));
|
||||
// Team-wide coverage statistics - accepts equalWage parameter
|
||||
function getTeamStats(equalWage = 25) {
|
||||
const coverageValues = members.value.map(m => {
|
||||
const coverage = getMemberCoverage(m.id, equalWage);
|
||||
return coverage.minPct;
|
||||
}).filter(v => v !== undefined);
|
||||
|
||||
if (coverageValues.length === 0) {
|
||||
return { under100: 0, median: 0 };
|
||||
}
|
||||
|
||||
const sorted = [...coverageValues].sort((a, b) => a - b);
|
||||
const median = sorted[Math.floor(sorted.length / 2)];
|
||||
const under100 = coverageValues.filter(v => v < 100).length;
|
||||
|
||||
return { under100, median };
|
||||
}
|
||||
|
||||
// Computed team stats (using default wage)
|
||||
const teamStats = computed(() => getTeamStats());
|
||||
|
||||
// Pay policy configuration
|
||||
const payPolicy = ref({
|
||||
|
|
@ -258,6 +297,8 @@ export const useMembersStore = defineStore(
|
|||
setMonthlyNeeds,
|
||||
setPlannedPay,
|
||||
getMemberCoverage,
|
||||
getTeamStats,
|
||||
recalculateMemberPay,
|
||||
// Legacy actions
|
||||
addMember,
|
||||
updateMember,
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue