summaryrefslogtreecommitdiff
path: root/DomainDigWidget/DomainDigPortfolioWidget.swift
diff options
context:
space:
mode:
authorChristian Cleberg <[email protected]>2026-07-21 20:47:34 -0500
committerChristian Cleberg <[email protected]>2026-07-21 21:40:44 -0500
commitc220e26bb496e455a5bdb6a8dc22abf09ecfed5f (patch)
tree1709346960c291f9f7c304724c89432e7194affa /DomainDigWidget/DomainDigPortfolioWidget.swift
parentdc479a3ba0d27fe86509d0eb2d27b01132c2b37f (diff)
downloaddomain-dig-c220e26bb496e455a5bdb6a8dc22abf09ecfed5f.tar.gz
domain-dig-c220e26bb496e455a5bdb6a8dc22abf09ecfed5f.tar.bz2
domain-dig-c220e26bb496e455a5bdb6a8dc22abf09ecfed5f.zip
feat(a11y): color independence, reduce motion, reduce transparency (#21 phase 5)
Audit unchanged at 11 dark / 14 light — expected, as none of these settings are exercised by performAccessibilityAudit, and simctl can toggle only Increase Contrast, not Differentiate Without Color, Reduce Motion, or Reduce Transparency. Correct by construction and build-clean; runtime behaviour is verified in the Phase 6 manual pass. Color independence: - Widget status is now an SF Symbol (checkmark.circle.fill / exclamationmark.triangle.fill / exclamationmark.octagon.fill), the same vocabulary as the in-app badges, replacing a silent colour-only dot on both the domain rows and the small-view count pills. Status now survives greyscale and reads consistently across surfaces. - Under accessibilityDifferentiateWithoutColor: the Dashboard summary-card dot becomes a per-filter symbol, the selected quick-filter chip gains a checkmark and a border (selection was fill-colour only, and also gains the .isSelected trait), and LabeledValueRow prefixes a warning/failure symbol. All gated on the setting so the default UI stays uncluttered. Reduce motion: all five withAnimation/.animation sites now pass nil under accessibilityReduceMotion — AppCopyButton's check cross-fade, CollapsibleSectionView's expand/collapse, TimelineDiffView's scroll, and WatchlistView's list reorder. Reduce transparency: the single .thinMaterial capsule falls back to an opaque AppSurfaceElevated fill under accessibilityReduceTransparency. The SweepActivityController item from the plan is dropped: it is pure ActivityKit lifecycle with no animation, confirmed back in the issue triage.
Diffstat (limited to 'DomainDigWidget/DomainDigPortfolioWidget.swift')
-rw-r--r--DomainDigWidget/DomainDigPortfolioWidget.swift29
1 files changed, 21 insertions, 8 deletions
diff --git a/DomainDigWidget/DomainDigPortfolioWidget.swift b/DomainDigWidget/DomainDigPortfolioWidget.swift
index 66002c5..45772e3 100644
--- a/DomainDigWidget/DomainDigPortfolioWidget.swift
+++ b/DomainDigWidget/DomainDigPortfolioWidget.swift
@@ -97,16 +97,18 @@ struct DomainDigWidgetView: View {
Spacer(minLength: 0)
HStack(spacing: 10) {
- countPill(data.healthyCount, Color(.statusPositive), "healthy")
- countPill(data.warningCount, Color(.statusWarning), "warning")
- countPill(data.criticalCount, Color(.statusCritical), "critical")
+ countPill(data.healthyCount, .healthy, "healthy")
+ countPill(data.warningCount, .warning, "warning")
+ countPill(data.criticalCount, .critical, "critical")
}
}
}
- private func countPill(_ value: Int, _ color: Color, _ label: String) -> some View {
+ private func countPill(_ value: Int, _ status: DomainDigWidgetStatus, _ label: String) -> some View {
HStack(spacing: 3) {
- Circle().fill(color).frame(width: 7, height: 7)
+ Image(systemName: symbol(for: status))
+ .font(.caption2)
+ .foregroundStyle(color(for: status))
Text("\(value)").font(.caption).fontWeight(.medium)
}
// A coloured dot and a number say nothing on their own.
@@ -163,9 +165,9 @@ struct DomainDigWidgetView: View {
private func domainRow(_ domain: DomainDigWidgetDomain) -> some View {
HStack(spacing: 6) {
- Circle()
- .fill(color(for: domain.status))
- .frame(width: 8, height: 8)
+ Image(systemName: symbol(for: domain.status))
+ .font(.caption2)
+ .foregroundStyle(color(for: domain.status))
if domain.isPinned {
Image(systemName: "pin.fill")
.font(.caption2)
@@ -219,4 +221,15 @@ struct DomainDigWidgetView: View {
case .critical: return Color(.statusCritical)
}
}
+
+ /// Same symbol vocabulary as the in-app badges, so status survives without
+ /// colour (Differentiate Without Color, greyscale, colour-blind viewers) and
+ /// reads consistently across surfaces.
+ private func symbol(for status: DomainDigWidgetStatus) -> String {
+ switch status {
+ case .healthy: return "checkmark.circle.fill"
+ case .warning: return "exclamationmark.triangle.fill"
+ case .critical: return "exclamationmark.octagon.fill"
+ }
+ }
}