Write, review, or improve SwiftUI code following best practices for state management, view composition, performance, macOS-specific APIs, and iOS 26+ Liquid Glass adoption. Use when building new SwiftUI features, refactoring existing views, reviewing code quality, or adopting modern SwiftUI patterns.
Install with Tessl CLI
npx tessl i github:avdlee/swiftui-agent-skill --skill swiftui-expert-skill94
Does it follow best practices?
Validation for skill structure
Use this skill to build, review, or improve SwiftUI features with correct state management, optimal view composition, and iOS 26+ Liquid Glass styling. Prioritize native APIs, Apple design guidance, and performance-conscious patterns. This skill focuses on facts and best practices without enforcing specific architectural patterns.
references/latest-apis.md to ensure only current, non-deprecated APIs are usedreferences/state-management.md)references/view-structure.md)references/performance-patterns.md)references/list-patterns.md)references/animation-basics.md, references/animation-transitions.md)references/accessibility-patterns.md)references/macos-scenes.md, references/macos-window-styling.md, references/macos-views.md)references/liquid-glass.md)references/latest-apis.md to replace any deprecated APIs with their modern equivalentsreferences/state-management.md)references/view-structure.md)references/performance-patterns.md)references/list-patterns.md)references/animation-basics.md, references/animation-transitions.md)Button over tap gestures, add @ScaledMetric for Dynamic Type (see references/accessibility-patterns.md)references/macos-scenes.md, references/macos-window-styling.md, references/macos-views.md)UIImage(data:) is used (as optional optimization, see references/image-optimization.md)references/latest-apis.md to use only current, non-deprecated APIs for the target deployment versionreferences/state-management.md)references/view-structure.md)references/layout-best-practices.md)references/animation-basics.md, references/animation-transitions.md, references/animation-advanced.md)Button for tappable elements, add accessibility grouping and labels (see references/accessibility-patterns.md)references/macos-scenes.md), window styling (see references/macos-window-styling.md), and views like HSplitView, Table (see references/macos-views.md)references/liquid-glass.md)#available and provide fallbacks@State must be private; use for internal view state@Binding only when a child needs to modify parent state@StateObject when view creates the object; @ObservedObject when injected@State with @Observable classes; use @Bindable for injected observables needing bindingslet for read-only values; var + .onChange() for reactive reads@State or @StateObject — they only accept initial valuesObservableObject doesn't propagate changes — pass nested objects directly; @Observable handles nesting finebody simple and pure (no side effects or complex logic)@ViewBuilder functions only for small, simple sections@ViewBuilder let content: Content over closure-based content properties@Observable state objects in lists to narrow update/dependency scopeonReceive, onChange, scroll handlersLazyVStack/LazyHStack for large listsForEach (never .indices for dynamic content)ForEach elementForEach (prefilter and cache)AnyView in list rowsUIImage(data:) is encountered (as optional optimization)GeometryReader)Self._logChanges() or Self._printChanges() to debug unexpected view updatesShape.path(), visualEffect, Layout, and onGeometryChange closures may run off the main thread — capture values instead of accessing @MainActor state.animation(_:value:) with value parameter (deprecated version without value is too broad)withAnimation for event-driven animations (button taps, gestures)offset, scale, rotation) over layout changes (frame) for performanceAnimatable implementations must have explicit animatableData (or use @Animatable macro on iOS 26+)@Animatable macro to auto-synthesize animatableData; use @AnimatableIgnored to exclude properties.phaseAnimator for multi-step sequences (iOS 17+).keyframeAnimator for precise timing control (iOS 17+).transaction(value:) for reexecutionButton over onTapGesture for tappable elements (free VoiceOver support)@ScaledMetric for custom numeric values that should scale with Dynamic TypeaccessibilityElement(children: .combine) for joined labelsaccessibilityLabel when default labels are unclear or missingaccessibilityRepresentation for custom controls that should behave like native onesOnly adopt when explicitly requested by the user.
glassEffect, GlassEffectContainer, and glass button stylesGlassEffectContainer.glassEffect() after layout and visual modifiers.interactive() only for tappable/focusable elementsglassEffectID with @Namespace for morphing transitions| Wrapper | Use When |
|---|---|
@State | Internal view state (must be private) |
@Binding | Child modifies parent's state |
@StateObject | View owns an ObservableObject |
@ObservedObject | View receives an ObservableObject |
@Bindable | iOS 17+: Injected @Observable needing bindings |
let | Read-only value from parent |
var | Read-only value watched via .onChange() |
// Basic glass effect with fallback
if #available(iOS 26, *) {
content
.padding()
.glassEffect(.regular.interactive(), in: .rect(cornerRadius: 16))
} else {
content
.padding()
.background(.ultraThinMaterial, in: RoundedRectangle(cornerRadius: 16))
}
// Grouped glass elements
GlassEffectContainer(spacing: 24) {
HStack(spacing: 24) {
GlassButton1()
GlassButton2()
}
}
// Glass buttons
Button("Confirm") { }
.buttonStyle(.glassProminent)references/latest-apis.md)@State properties are private@Binding only where child modifies parent state@StateObject for owned, @ObservedObject for injected@State with @Observable, @Bindable for injected@State or @StateObjectObservableObject avoided (or passed directly to child views)references/sheet-navigation-patterns.md).sheet(item:) for model-based sheetsreferences/scroll-patterns.md)ScrollViewReader with stable IDs for programmatic scrollingreferences/view-structure.md)@ViewBuilder let content: Content.compositingGroup() before .clipShape() on layered viewsreferences/performance-patterns.md)body kept simple and pure (no side effects)bodybodyreferences/list-patterns.md).indices)AnyView in list rowsreferences/layout-best-practices.md)references/animation-basics.md, references/animation-transitions.md, references/animation-advanced.md).animation(_:value:) with value parameterwithAnimation for event-driven animationsAnimatable has explicit animatableData (or @Animatable macro on iOS 26+).transaction(value:) for reexecutionreferences/accessibility-patterns.md)Button used instead of onTapGesture for tappable elements@ScaledMetric used for custom values that should scale with Dynamic TypeaccessibilityElement(children:)accessibilityRepresentation when appropriatereferences/macos-scenes.md, references/macos-window-styling.md, references/macos-views.md)Settings scene for preferences (not a custom window)MenuBarExtra for menu bar items (not AppKit NSStatusItem)Commands / CommandGroup / CommandMenu for menu bar menusTable adapts for compact size classes on iOS (first column shows combined info)defaultSize, windowResizability, and frame(minWidth:minHeight:)#if os(macOS) conditionalsNSViewRepresentable with proper makeNSView/updateNSView lifecycleNavigationSplitView (not HSplitView) for sidebar-based navigationHSplitView/VSplitView reserved for IDE-style equal peer panes#available(iOS 26, *) with fallback for Liquid GlassGlassEffectContainer.glassEffect() applied after layout/appearance modifiers.interactive() only on user-interactable elementsreferences/latest-apis.md - Required reading for all workflows. Version-segmented guide of deprecated-to-modern API transitions (iOS 15+ through iOS 26+)references/state-management.md - Property wrappers and data flowreferences/view-structure.md - View composition, extraction, and container patternsreferences/performance-patterns.md - Performance optimization techniques and anti-patternsreferences/list-patterns.md - ForEach identity, stability, Table (iOS 16+), and list best practicesreferences/layout-best-practices.md - Layout patterns, context-agnostic views, and testabilityreferences/accessibility-patterns.md - Accessibility traits, grouping, Dynamic Type, and VoiceOverreferences/animation-basics.md - Core animation concepts, implicit/explicit animations, timing, performancereferences/animation-transitions.md - Transitions, custom transitions, Animatable protocolreferences/animation-advanced.md - Transactions, phase/keyframe animations (iOS 17+), completion handlers (iOS 17+), @Animatable macro (iOS 26+)references/sheet-navigation-patterns.md - Sheet presentation, NavigationSplitView, Inspector, and navigation patternsreferences/scroll-patterns.md - ScrollView patterns and programmatic scrollingreferences/image-optimization.md - AsyncImage, image downsampling, and optimizationreferences/liquid-glass.md - iOS 26+ Liquid Glass APIreferences/macos-scenes.md - macOS scene types: Settings, MenuBarExtra, WindowGroup, Window, UtilityWindow, DocumentGroupreferences/macos-window-styling.md - macOS window configuration: toolbar styles, sizing, positioning, NavigationSplitView, Inspector, Commandsreferences/macos-views.md - macOS views and components: HSplitView, VSplitView, Table, PasteButton, file dialogs, drag & drop, AppKit interopThis skill focuses on facts and best practices, not architectural opinions:
74bc2a0
If you maintain this skill, you can claim it as your own. Once claimed, you can manage eval scenarios, bundle related skills, attach documentation or rules, and ensure cross-agent compatibility.