What's the best way to conditionally include/exclude some lines of code for performance profiling?

It seems shadows/blur/round-corner/text-rendering some or all of these things are making my SwiftUI animated view slow and crash (shadows for sure b/c removing all shadows eliminated crash and run much faster).

I want to use SwiftUI or Core Animation Instrument to see what's going on and find out which of those things are slow. So I need to conditionally add or remove various SwiftUI view modifiers to run with instruments. I'm manually commenting different sets of modifiers for now, it's tedious. I want to know if there is better way? Is dong custom compiler flag -DSHADOWS and in code:

#if SHADOWS
    .modifier(Emboss())
#endif

best way? Or is there better way?

For Swift, adding such values as "Active Compilation Conditions" in Xcode would be the best way. Better yet, your own view modifier that lets you switch between sets of modifiers more easily so you don't have #if all over the place.

things are kind of spread out, not inside one modifier..

I wonder, if I change:

view
    .cornerRadius(xyzzy)
struct ConditionalCornerRadius: ViewModifier {
    let r: CGFloat
    func body(content: Content) -> some View {
        content
// comment out for now
//            .cornerRadius(r)
    }
}
...
view
    .modifier(ConditionalCornerRadius(xyz))

If I comment out .cornerRadius(r) inside ConditionalCornerRadius, is it truly no-op? Or there is extra cost still?

That still costs as much as an empty view modifier. I'd say that that's about appropriate.

...then there is no convenient way to completely take out a single modifier. It's either manually comment out or use #if ...?

I mean, if an empty view mod is significantly stalling an application, that'd be very fishy.

I was suggesting you move the modifiers you want to test into a single modifier so you can easily switch between all the toggles. Whether you do that using the compiler conditions or runtime conditions is up to you.

FYI, if you figured out it's the rendering that causes the problem, you may want to put drawingGroup at some appropriate places. Sparingly used, and it could be very performant.

With shadows and blur modifiers in place, adding .drawingGroup() all the shadows and blur effects are gone and it does not seem to make it run any faster.

Only by removing all shadows and blur modifiers things run very fast and no crash on rotate.

I couldn't help much further since I don't see any code. So, best of luck!

That'd be bug-report worthy.

I'm unable to reproduce the problem of .drawingGroup() killing the shadow effects with simplified code. So I would very much appreciated if you can take a look at my actual code and see what's wrong:

If you run it, you can see the shadow effects. Search for .drawingGroup(), uncomment it and run to see shadow effects gone.

Thanks!

I've just faced similiar problem - when using .drawingGroup() blur effect of my view just disappeared (on iOS 13, iOS 14 handled it right). The "problem" was in using cornerRadius modifier - without it, the blur remained.

For me the solution was simple - I was using Rectangle(), so switching to RounderRectangle(cornerRadius: _) solve the problem.

1 Like