feat(progress): add progress tracking enhancements

- Enable zoom/pan on progress map with reset button
- Add visit count badges to stadium chips
- Create GamesHistoryView with year grouping and sport filters
- Create StadiumVisitHistoryView for viewing all visits to a stadium
- Add VisitListCard and GamesHistoryRow components
- Add "See All" navigation from Recent Visits to Games History
- Add tests for map interactions, visit lists, and games history

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
Trey t
2026-01-12 21:34:33 -06:00
parent ed526cabeb
commit 89167c01d7
11 changed files with 979 additions and 16 deletions

View File

@@ -261,7 +261,8 @@ struct ProgressTabView: View {
ForEach(viewModel.visitedStadiums) { stadium in
StadiumChip(
stadium: stadium,
isVisited: true
isVisited: true,
visitCount: viewModel.stadiumVisitStatus[stadium.id]?.visitCount ?? 1
) {
selectedStadium = stadium
}
@@ -368,9 +369,24 @@ struct ProgressTabView: View {
private var recentVisitsSection: some View {
VStack(alignment: .leading, spacing: Theme.Spacing.sm) {
Text("Recent Visits")
.font(.title2)
.foregroundStyle(Theme.textPrimary(colorScheme))
HStack {
Text("Recent Visits")
.font(.title2)
.foregroundStyle(Theme.textPrimary(colorScheme))
Spacer()
NavigationLink {
GamesHistoryView()
} label: {
HStack(spacing: 4) {
Text("See All")
Image(systemName: "chevron.right")
}
.font(.subheadline)
.foregroundStyle(Theme.warmOrange)
}
}
ForEach(viewModel.recentVisits) { visitSummary in
if let stadiumVisit = visits.first(where: { $0.id == visitSummary.id }) {
@@ -418,6 +434,7 @@ struct ProgressStatPill: View {
struct StadiumChip: View {
let stadium: Stadium
let isVisited: Bool
var visitCount: Int = 1
let action: () -> Void
@Environment(\.colorScheme) private var colorScheme
@@ -432,10 +449,22 @@ struct StadiumChip: View {
}
VStack(alignment: .leading, spacing: 2) {
Text(stadium.name)
.font(.subheadline)
.foregroundStyle(Theme.textPrimary(colorScheme))
.lineLimit(1)
HStack(spacing: 4) {
Text(stadium.name)
.font(.subheadline)
.foregroundStyle(Theme.textPrimary(colorScheme))
.lineLimit(1)
// Visit count badge (if more than 1)
if visitCount > 1 {
Text("\(visitCount)")
.font(.caption2.bold())
.foregroundStyle(.white)
.padding(.horizontal, 6)
.padding(.vertical, 2)
.background(Theme.warmOrange, in: Capsule())
}
}
Text(stadium.city)
.font(.caption)