agents/skills/swift-animations/SKILL.md
# SwiftUI & AppKit Animation Best Practices Comprehensive animation guide for Apple platform interfaces, adapted from Emil Kowalski's web animation principles and Framer Motion best practices. Contains 80 rules across 10 categories targeting iOS 17+, prioritized by impact. ## When to Apply Reference these guidelines when: - Adding animations to SwiftUI views - Choosing easing curves, springs, or timing values - Implementing gesture-based interactions (drag, tap, long press) - Building transit
npx skillsauth add por/dotfiles agents/skills/swift-animationsInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
Comprehensive animation guide for Apple platform interfaces, adapted from Emil Kowalski's web animation principles and Framer Motion best practices. Contains 80 rules across 10 categories targeting iOS 17+, prioritized by impact.
Reference these guidelines when:
matchedGeometryEffect for shared element transitionsPhaseAnimator or KeyframeAnimatoraccessibilityReduceMotion| Priority | Category | Impact | Prefix |
|----------|----------|--------|--------|
| 1 | Timing Curves & Easing | CRITICAL | ease- |
| 2 | Duration & Timing | CRITICAL | timing- |
| 3 | Animation Properties | HIGH | props- |
| 4 | Transforms & Effects | HIGH | transform- |
| 5 | Gesture & Interaction | HIGH | gesture- |
| 6 | Transitions & Navigation | MEDIUM-HIGH | transition- |
| 7 | Scroll & Parallax | MEDIUM | scroll- |
| 8 | Strategic Animation | MEDIUM | strategy- |
| 9 | Accessibility & Polish | MEDIUM | polish- |
| 10 | AppKit Specific | LOW-MEDIUM | appkit- |
ease-prefer-easeout - Use easeOut as your default easingease-avoid-linear - Avoid linear easing for UI animationsease-spring-default - Prefer springs for natural motionease-spring-ios17 - Use iOS 17 Spring struct with bounce/durationease-custom-timing-curve - Create custom curves with timingCurveease-ease-in-for-exits - Use easeIn for exit animationsease-ease-inout-for-emphasis - Use easeInOut for emphasis motionease-spring-response - Configure spring response for duration feelease-spring-damping - Configure spring damping for bounceease-match-context - Match easing to animation contexttiming-200ms-default - Use 200ms as default UI animation durationtiming-100ms-micro - Use 100ms for micro-interactionstiming-300ms-emphasis - Keep emphasis animations under 300mstiming-stagger-children - Stagger child animations for orchestrationtiming-delay-strategic - Use delay strategically for sequencingprops-opacity-scale - Prefer opacity and scale for performanceprops-avoid-size-animate - Avoid animating frame size directlyprops-transform-origin - Set anchor points for transformsprops-drawing-group - Use drawingGroup for complex hierarchiesprops-animation-disable - Use animation(nil) to prevent animationsprops-explicit-animation - Use withAnimation for explicit controlprops-implicit-animation - Use .animation modifier for implicit animationstransform-scale-subtle - Use subtle scale values (0.95-0.98)transform-rotation-purposeful - Apply rotation with purposetransform-translate-direction - Translate in meaningful directionstransform-3d-perspective - Use rotation3DEffect for depthtransform-order-matters - Modifier order affects outputtransform-anchor-point - Set anchor for rotation/scale origintransform-combine-effects - Combine transforms purposefullygesture-tap-feedback - Provide immediate tap feedbackgesture-long-press - Animate long press statesgesture-drag-basic - Implement smooth drag interactionsgesture-drag-constraints - Constrain drag within boundsgesture-drag-velocity - Use velocity for momentum effectsgesture-gesture-state - Use @GestureState for transient valuesgesture-updating-modifier - Use .updating for live feedbackgesture-simultaneous-vs-exclusive - Choose gesture compositiongesture-magnify-gesture - Implement pinch-to-zoomgesture-rotation-gesture - Implement rotation gesturesgesture-hover-macos - Handle hover on macOSgesture-sensory-feedback - Pair gestures with hapticsgesture-spring-on-release - Spring back on gesture endgesture-cancellation - Handle gesture cancellation gracefullytransition-builtin-types - Use built-in transition typestransition-asymmetric - Use asymmetric for different enter/exittransition-combined - Combine transitions for richer effectstransition-custom-modifier - Create custom transition modifierstransition-matched-geometry - Use matchedGeometryEffect properlytransition-namespace-scope - Manage @Namespace lifecycletransition-navigation-transitions - Customize navigation transitionstransition-sheet-presentations - Animate sheet presentationstransition-id-for-replacement - Use .id() for view replacementtransition-content-transition - Use contentTransition for textscroll-geometry-reader - Use GeometryReader for scroll positionscroll-preference-key - Use PreferenceKey for scroll datascroll-parallax-effect - Create parallax scroll effectsscroll-sticky-header - Implement animated sticky headersscroll-scroll-transition - Use iOS 17 scrollTransition modifierscroll-visual-effect - Use iOS 17 visualEffect modifierstrategy-purposeful-motion - Every animation needs purposestrategy-hierarchy-emphasis - Use motion to show hierarchystrategy-state-communication - Animate state changes clearlystrategy-spatial-continuity - Maintain spatial relationshipsstrategy-brand-expression - Express brand through motionpolish-reduce-motion - Respect accessibilityReduceMotionpolish-phase-animator - Use PhaseAnimator for sequencespolish-keyframe-animator - Use KeyframeAnimator for complex pathspolish-animation-completions - Handle animation completionpolish-interruptible-animations - Make animations interruptiblepolish-animation-debugging - Debug animations effectivelypolish-performance-profiling - Profile animation performancepolish-symbol-effects - Use SF Symbol effectspolish-text-animations - Animate text with contentTransitionpolish-haptic-pairing - Pair animations with haptic feedbackappkit-nsanimation-context - Use NSAnimationContext for groupingappkit-core-animation - Use Core Animation layersappkit-layer-backed-views - Enable layer backing for performanceappkit-implicit-animations - Leverage implicit layer animationsappkit-spring-animation - Create spring animations in AppKitappkit-animator-proxy - Use animator proxy for view animations| Value | Usage |
|-------|-------|
| .spring(duration: 0.3, bounce: 0.2) | Standard iOS 17 spring animation |
| .spring(response: 0.3, dampingFraction: 0.7) | Classic spring configuration |
| .easeOut(duration: 0.2) | Standard UI transition |
| scaleEffect(0.97) | Button press feedback |
| scaleEffect(0.95) | Minimum enter scale (never scale to 0) |
| 0.2 seconds | Default micro-interaction duration |
| 0.3 seconds | Maximum duration for UI animations |
| 0.5 seconds | Sheet/drawer animation duration |
| Web Concept | SwiftUI Equivalent |
|-------------|-------------------|
| ease-out | .easeOut or Animation.easeOut(duration:) |
| cubic-bezier(a,b,c,d) | .timingCurve(a, b, c, d, duration:) |
| Framer Motion spring | .spring(duration:bounce:) (iOS 17+) |
| transform: scale(0.97) | .scaleEffect(0.97) |
| transform-origin | .scaleEffect(anchor: .topLeading) |
| useMotionValue | @State / @GestureState |
| AnimatePresence | .transition() + .id() |
| layoutId | .matchedGeometryEffect(id:in:) |
| useScroll | GeometryReader + PreferenceKey |
| whileHover/whileTap | .onHover {} / gesture modifiers |
| dragConstraints | DragGesture with onChange bounds |
| prefers-reduced-motion | @Environment(\.accessibilityReduceMotion) |
| File | Description | |------|-------------| | references/_sections.md | Category definitions and ordering | | assets/templates/_template.md | Template for new rules | | metadata.json | Version and reference information |
development
Test-driven development with red-green-refactor loop. Use when user wants to build features or fix bugs using TDD, mentions "red-green-refactor", wants integration tests, or asks for test-first development.
development
Implement, review, or improve SwiftUI features using the iOS 26+ Liquid Glass API. Use when asked to adopt Liquid Glass in new SwiftUI UI, refactor an existing feature to Liquid Glass, or review Liquid Glass usage for correctness, performance, and design alignment.
development
Write, review, or improve SwiftUI code following best practices for state management, view composition, performance, modern APIs, Swift concurrency, and iOS 26+ Liquid Glass adoption. Use when building new SwiftUI features, refactoring existing views, reviewing code quality, or adopting modern SwiftUI patterns.
tools
Draft and create a conventional commit based on the current git diff.