fix: KPI card counts match feed — exclusive buckets + filter reset on click
- reminderService: dueThisWeek/dueThisMonth use exclusive day ranges (1-7, 8-30) matching getHorizon() buckets; schattenmarktReadyCount counts by type=SCHATTENMARKT_RELEASE (same criteria as the feed filter) - ReminderKpiBar: clicking a horizon card resets filterType to ALL; clicking Pre-Market card resets filterHorizon to ALL — ensures the number shown on the card always equals the number of rows displayed below Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -75,11 +75,21 @@ export function ReminderKpiBar() {
|
|||||||
)
|
)
|
||||||
|
|
||||||
function toggleHorizon(h: FilterHorizon) {
|
function toggleHorizon(h: FilterHorizon) {
|
||||||
setFilterHorizon(filterHorizon === h ? 'ALL' : h)
|
if (filterHorizon === h) {
|
||||||
|
setFilterHorizon('ALL')
|
||||||
|
} else {
|
||||||
|
setFilterHorizon(h)
|
||||||
|
setFilterType('ALL') // clear type filter so count matches
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function togglePreMarket() {
|
function togglePreMarket() {
|
||||||
setFilterType(filterType === ReminderType.SCHATTENMARKT_RELEASE ? 'ALL' : ReminderType.SCHATTENMARKT_RELEASE)
|
if (filterType === ReminderType.SCHATTENMARKT_RELEASE) {
|
||||||
|
setFilterType('ALL')
|
||||||
|
} else {
|
||||||
|
setFilterType(ReminderType.SCHATTENMARKT_RELEASE)
|
||||||
|
setFilterHorizon('ALL') // clear horizon filter so count matches
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isLoading) {
|
if (isLoading) {
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import { MockupReminderProvider } from '../provider/MockupReminderProvider'
|
import { MockupReminderProvider } from '../provider/MockupReminderProvider'
|
||||||
import type { Reminder } from '../domain/reminder'
|
import type { Reminder } from '../domain/reminder'
|
||||||
import { ReminderPriority, ReminderStatus, ShadowMarketRisk } from '../domain/reminder'
|
import { ReminderPriority, ReminderStatus, ReminderType } from '../domain/reminder'
|
||||||
|
|
||||||
const provider = MockupReminderProvider
|
const provider = MockupReminderProvider
|
||||||
|
|
||||||
@@ -27,25 +27,19 @@ export const reminderService = {
|
|||||||
|
|
||||||
const urgentCount = active.filter(r => r.priority === ReminderPriority.URGENT).length
|
const urgentCount = active.filter(r => r.priority === ReminderPriority.URGENT).length
|
||||||
|
|
||||||
const endOfWeek = new Date(MOCK_TODAY)
|
// Counts match getHorizon() in ReminderFeed — exclusive, non-overlapping buckets
|
||||||
endOfWeek.setDate(endOfWeek.getDate() + 7)
|
|
||||||
const dueThisWeek = active.filter(r => {
|
const dueThisWeek = active.filter(r => {
|
||||||
const d = daysDiff(r.dueDate)
|
const d = daysDiff(r.dueDate)
|
||||||
return d >= 0 && d <= 7
|
return d >= 1 && d <= 7
|
||||||
}).length
|
}).length
|
||||||
|
|
||||||
const endOfMonth = new Date(MOCK_TODAY)
|
|
||||||
endOfMonth.setDate(endOfMonth.getDate() + 30)
|
|
||||||
const dueThisMonth = active.filter(r => {
|
const dueThisMonth = active.filter(r => {
|
||||||
const d = daysDiff(r.dueDate)
|
const d = daysDiff(r.dueDate)
|
||||||
return d >= 0 && d <= 30
|
return d >= 8 && d <= 30
|
||||||
}).length
|
}).length
|
||||||
|
|
||||||
const schattenmarktReadyCount = reminders.filter(
|
const schattenmarktReadyCount = active.filter(
|
||||||
r =>
|
r => r.type === ReminderType.SCHATTENMARKT_RELEASE,
|
||||||
r.status === ReminderStatus.ACTIVE &&
|
|
||||||
!r.schattenmarktEnabled &&
|
|
||||||
(r.shadowMarketRisk === ShadowMarketRisk.HIGH),
|
|
||||||
).length
|
).length
|
||||||
|
|
||||||
const overdueCount = active.filter(r => daysDiff(r.dueDate) <= 0).length
|
const overdueCount = active.filter(r => daysDiff(r.dueDate) <= 0).length
|
||||||
|
|||||||
Reference in New Issue
Block a user