Summary
On Android in native/Fuse mode, grid cells can show stale conditional styling after selection changes.
I am building a calendar which consists of a LazyVGrid of tappable day cells with a shared @State selectedDate. Each cell receives an isSelected boolean. Logs confirm that after each tap, exactly one cell renders with isSelected == true, but visually the newly selected cell and previously tapped cells intermittently blink together. This does not happen on iOS.
Environment
- Android device: Samsung SM-G973F, Android 12
- Build: release, minified
- Mode: native / Skip Fuse
- Reproduces with:
- skip-fuse-ui 1.18.1
- skip-ui 1.59.1
- Last known working in our released app:
- skip-fuse-ui 1.13.0
- skip-ui 1.53.1
Minimal POC
import SwiftUI
struct CalendarBugRepro: View {
@State var selectedDate = Date()
private let calendar = Calendar(identifier: .gregorian)
var body: some View {
LazyVGrid(
columns: Array(repeating: GridItem(.flexible(), spacing: 0), count: 7),
spacing: 4
) {
ForEach(days, id: \.self) { date in
Button {
selectedDate = date
} label: {
ReproDayCell(
day: calendar.component(.day, from: date),
isSelected: calendar.isDate(date, inSameDayAs: selectedDate)
)
}
.buttonStyle(.plain)
}
}
.padding()
}
private var days: [Date] {
let first = calendar.date(from: DateComponents(year: 2026, month: 9, day: 1))!
return (0..<30).compactMap { calendar.date(byAdding: .day, value: $0, to: first) }
}
}
struct ReproDayCell: View {
let day: Int
let isSelected: Bool
var body: some View {
Text("\(day)")
.font(.system(size: 14, weight: isSelected ? .bold : .regular))
.foregroundStyle(isSelected ? .white : .primary)
.frame(width: 32, height: 32)
.background(Circle().fill(isSelected ? Color.accentColor : .clear))
.frame(height: 44)
}
}
Expected
Only the selected day is highlighted.
Actual
Previously selected days blink together, even though only one cell has isSelected == true.
Workaround
Keeping the view tree stable and toggling opacity avoids the issue:
.background {
Circle()
.fill(Color.accentColor)
.opacity(isSelected ? 1 : 0)
}
So the issue seems related to conditional styling like:
.background(Circle().fill(isSelected ? Color.accentColor : .clear))
.foregroundStyle(isSelected ? .white : .primary)
Summary
On Android in native/Fuse mode, grid cells can show stale conditional styling after selection changes.
I am building a calendar which consists of a
LazyVGridof tappable day cells with a shared@State selectedDate. Each cell receives anisSelectedboolean. Logs confirm that after each tap, exactly one cell renders withisSelected == true, but visually the newly selected cell and previously tapped cells intermittently blink together. This does not happen on iOS.Environment
Minimal POC
Expected
Only the selected day is highlighted.
Actual
Previously selected days blink together, even though only one cell has
isSelected == true.Workaround
Keeping the view tree stable and toggling opacity avoids the issue:
So the issue seems related to conditional styling like: