Now liveThe Skillselion MCP - thousands of ranked skills, loaded into your agent mid-task. No install.Get it →
rshankras avatar

Swiftui Debugging

  • 82 installs
  • 591 repo stars
  • Updated July 24, 2026
  • rshankras/claude-code-apple-skills

Helps with debugging tasks.

About

swiftui-debugging is a Claude Code skill for debugging. It helps solo builders move faster with AI-assisted development.

  • swiftui-debugging
  • Debugging
  • AI-coding skill

Swiftui Debugging by the numbers

  • 82 all-time installs (skills.sh)
  • +1 installs in the week ending Jul 26, 2026 (Skillselion tracking)
  • Ranked #255 of 596 Debugging skills by installs in the Skillselion catalog
  • Data as of Aug 5, 2026 (Skillselion catalog sync)
npx skills add https://github.com/rshankras/claude-code-apple-skills --skill swiftui-debugging

Add your badge

Show developers this skill is listed on Skillselion. Paste this into your README.

Listed on Skillselion
Installs82
repo stars591
Last updatedJuly 24, 2026
Repositoryrshankras/claude-code-apple-skills

What it does

Helps with debugging tasks.

Files

SKILL.mdMarkdownGitHub ↗

SwiftUI Performance Debugging

Systematic guide for diagnosing and fixing SwiftUI performance problems: unnecessary view re-evaluations, identity issues, expensive body computations, and lazy loading mistakes.

When This Skill Activates

Use this skill when the user:

  • Reports slow or janky SwiftUI views
  • Sees excessive view re-renders or body re-evaluations
  • Asks about Self._printChanges() or view debugging
  • Has scrolling performance issues with lists or grids
  • Asks why a view keeps updating when nothing changed
  • Mentions @Observable or ObservableObject performance differences
  • Wants to understand SwiftUI view identity or diffing
  • Uses AnyView and asks about performance implications
  • Has a hang or stutter traced to SwiftUI rendering

Decision Tree

What SwiftUI performance problem are you seeing?
|
+- Views re-render when they should not
|  +- Read body-reevaluation.md
|     +- Self._printChanges() to identify which property changed
|     +- @Observable vs ObservableObject observation differences
|     +- Splitting views to narrow observation scope
|
+- Scrolling is slow / choppy (lists, grids)
|  +- Read lazy-loading.md
|     +- VStack vs LazyVStack, ForEach without lazy container
|     +- List prefetching, grid cell reuse
|
+- Views lose state unexpectedly / animate when they should not
|  +- Read view-identity.md
|     +- Structural vs explicit identity
|     +- .id() misuse, conditional view branching
|
+- Known pitfall (AnyView, DateFormatter in body, etc.)
|  +- Read common-pitfalls.md
|     +- AnyView type erasure, object creation in body
|     +- Over-observation, expensive computations
|
+- General "my SwiftUI app is slow" (unknown cause)
|  +- Start with body-reevaluation.md, then common-pitfalls.md
|  +- Use Instruments SwiftUI template (see Debugging Tools below)

API Availability

API / TechniqueMinimum VersionReference
Self._printChanges()iOS 15body-reevaluation.md
@ObservableiOS 17 / macOS 14body-reevaluation.md
@ObservableObjectiOS 13body-reevaluation.md
LazyVStack / LazyHStackiOS 14lazy-loading.md
LazyVGrid / LazyHGridiOS 14lazy-loading.md
.id() modifieriOS 13view-identity.md
Instruments SwiftUI templateXcode 14+SKILL.md
os_signpostiOS 12SKILL.md

Top 5 Mistakes -- Quick Reference

#MistakeFixDetails
1Large ForEach inside VStack or ScrollView without lazy containerWrap in LazyVStack -- eager VStack creates all views upfrontlazy-loading.md
2Using AnyView to erase typesUse @ViewBuilder, Group, or concrete generic types -- AnyView defeats diffingcommon-pitfalls.md
3Creating objects in body (DateFormatter(), NumberFormatter())Use static let shared instances or @State for mutable objectscommon-pitfalls.md
4Observing entire model when only one property is neededSplit into smaller @Observable objects or extract subviewsbody-reevaluation.md
5Unstable .id() values causing full view recreation every renderUse stable identifiers (database IDs, UUIDs), never array indices or random valuesview-identity.md

Debugging Tools

Self._printChanges()

Add to any view body to see what triggered re-evaluation:

var body: some View {
    let _ = Self._printChanges()
    // ... view content
}

Output reads: ViewName: @self, @identity, _propertyName changed. See body-reevaluation.md for full interpretation guide.

Instruments SwiftUI Template

1. Xcode > Product > Profile (Cmd+I) 2. Choose SwiftUI template (includes View Body, View Properties, Core Animation Commits) 3. Record, reproduce the slow interaction, stop 4. View Body lane shows which views had their body evaluated and how often 5. View Properties lane shows which properties changed

os_signpost for Custom Measurement

import os

private let perfLog = OSLog(subsystem: "com.app.perf", category: "SwiftUI")

var body: some View {
    let _ = os_signpost(.event, log: perfLog, name: "MyView.body")
    // ... view content
}

View in Instruments with the os_signpost instrument to count body evaluations per second.

Review Checklist

View Identity

  • [ ] No unstable .id() values (random, Date(), array index on mutable arrays)
  • [ ] Conditional branches (if/else) do not cause unnecessary view destruction
  • [ ] ForEach uses stable, unique identifiers from the model

Body Re-evaluation

  • [ ] Views observe only the properties they actually use
  • [ ] @Observable classes preferred over ObservableObject (iOS 17+)
  • [ ] No unnecessary @State changes that trigger body re-evaluation
  • [ ] Large views split into smaller subviews to narrow observation scope

Lazy Loading

  • [ ] Large collections use LazyVStack / LazyHStack, not VStack / HStack
  • [ ] List or lazy stack used for 50+ items
  • [ ] No .frame(maxHeight: .infinity) on children inside lazy containers (defeats laziness)

Common Pitfalls

  • [ ] No AnyView type erasure (use @ViewBuilder or Group)
  • [ ] No object allocation in body (DateFormatter, NSPredicate, view models)
  • [ ] Expensive computations moved to background with task { } or Task.detached
  • [ ] Images use AsyncImage or .resizable() with proper sizing, not raw UIImage decoding in body

Reference Files

FileContent
view-identity.mdStructural vs explicit identity, .id() usage, conditional branching
body-reevaluation.mdWhat triggers body, _printChanges(), @Observable vs ObservableObject
lazy-loading.mdLazy vs eager containers, List, ForEach, grid performance
common-pitfalls.mdAnyView, object creation in body, over-observation, expensive computations
../profiling/SKILL.mdGeneral Instruments profiling (Time Profiler, Memory, Energy)

Related skills

Debuggingtesting

This week in AI coding

Five minutes, every Monday - the tools, releases and tactics for developers.

unsubscribe anytime.