Skip to main content

How to make SwiftUI modifiers safer to use with @warn_unqualified_access

About 2 minSwiftSwiftUIArticle(s)bloghackingwithswift.comcrashcourseswiftswiftuixcodeappstore

How to make SwiftUI modifiers safer to use with @warn_unqualified_access 관련

SwiftUI by Example

Back to Home

How to make SwiftUI modifiers safer to use with @warn_unqualified_access | SwiftUI by Example

How to make SwiftUI modifiers safer to use with @warn_unqualified_access

Updated for Xcode 15

Every SwiftUI makes the same mistake at some point, and sadly it’s something you’ll do more than once: rather than writing .someModifier() you write someModifier(), and it causes your app to completely freeze or crash with EXC_BAD_ACCESS.

First I’ll show you the how to solve the problem, then I’ll explain what the underlying problem is. The solution is to use Swift’s @warn_unqualified_access attribute, which means you can’t access properties or methods without using a variable name or similar.

For example, if we had a titleStyle() method that added a bunch of modifiers to a view to make it matching a custom theme, we’d use @warn_unqualified_access before the method signature, like this:

extension View {
    @warn_unqualified_access
    func titleStyle() -> some View {
        self
            .font(.largeTitle)
            .fontWeight(.black)
            .padding()
            .background(.blue)
            .foregroundStyle(.white)
            .cornerRadius(10)
    }
}

When we use that, we’d write the same SwiftUI code we always did:

struct ContentView: View {
    var body: some View {
        Text("Welcome")
            .titleStyle()
    }
}

That works exactly as expected – the extra attribute hasn’t made the method behave differently at all in normal circumstances.

However, take a look at this code:

struct ContentView: View {
    var body: some View {
        Text("Welcome")
            titleStyle()
    }
}

That’s subtly different: I removed the dot before titleStyle(), which is an unqualified access – I haven’t said where I’m calling titleStyle(), so SwiftUI assumes I’m actually calling it on ContentView. This means it’s actually calling self.padding(), so we have an infinitely recursive view and ultimately a crash.

Sadly, SwiftUI doesn’t use @warn_unqualified_access with its own modifiers, but you can at least add it for the custom ones you build.

Similar solutions…
How to create custom modifiers | SwiftUI by Example

How to create custom modifiers
How to create modifiers for a UIViewRepresentable struct | SwiftUI by Example

How to create modifiers for a UIViewRepresentable struct
How to stack modifiers to create more advanced effects | SwiftUI by Example

How to stack modifiers to create more advanced effects
SwiftUI tips and tricks | SwiftUI by Example

SwiftUI tips and tricks
All SwiftUI property wrappers explained and compared | SwiftUI by Example

All SwiftUI property wrappers explained and compared

이찬희 (MarkiiimarK)
Never Stop Learning.