ios – FPS drop with Angular Gradient border throughout SwiftUI animation

0
2
ios – FPS drop with Angular Gradient border throughout SwiftUI animation


I’m including a border and blur impact on a form throughout an animation (root view showing on web page) and seeing FPS drops when utilizing an AngularGradient as the colour of the border. I dont see the drops when utilizing a traditional colour. The drop is noticeable when setting a tool to “low battery” mode.

My code is ready up as a customized view modifier, and the border is added as overlays within the form of myShape, the place myShape matches the form of the view/form being modified.

struct BorderBlur: ViewModifier {
    var fillColor: some ShapeStyle {
        AngularGradient(
            colours: [.blue, .purple, .green, .blue],
            middle: .middle)
        .opacity(borderOpacity)
    }
    
    var myShape : some Form {
        RoundedRectangle(cornerRadius:36)
    }
    
    
    let borderWidth : CGFloat
    let blurRadius: CGFloat
    let borderOpacity: CGFloat
    
    init(borderWidth: CGFloat, blurRadius: CGFloat, borderOpacity: CGFloat) {
        self.borderWidth = borderWidth
        self.blurRadius = blurRadius
        self.borderOpacity = borderOpacity
    }
    
    public func physique(content material: Content material) -> some View {
        content material
            .overlay(
                myShape
                    .stroke(lineWidth: borderWidth)
                    .fill(fillColor)
                    .padding(borderWidth)
            )
            .overlay(
                myShape
                    .stroke(lineWidth: borderWidth)
                    .fill(fillColor)
                    .blur(radius: blurRadius)
                    .padding(borderWidth)
            )
            .overlay(
                myShape
                    .stroke(lineWidth: borderWidth)
                    .fill(fillColor)
                    .blur(radius: blurRadius / 2)
                    .padding(borderWidth)
            )
    }
}

extension View {
    public func borderBlur(borderWidth: CGFloat, blurRadius: CGFloat, borderOpacity: CGFloat) -> some View {
        return modifier(BorderBlur(borderWidth: borderWidth, blurRadius: blurRadius, borderOpacity: borderOpacity))
    }
}

struct MyRootView: View {
    
    @State var didAppear = false
    var borderWidth: CGFloat {
        didAppear ? 3 : 0
    }
    var borderBlurRadius: CGFloat {
        didAppear ? 10 : 0
    }
    var borderOpacity: CGFloat {
        didAppear ? 1 : 0
    }
    
    var physique: some View {
        VStack {
            RoundedRectangle(cornerRadius:36).fill(.clear)
                .borderBlur(borderWidth: borderWidth, blurRadius: borderBlurRadius, borderOpacity: borderOpacity)
                .body(width: didAppear ? 300 : 100, peak: didAppear ? 400 : 100)
                .offset(y: didAppear ? 0 : -400)
        }
        .onAppear {
            withAnimation(.linear(length:2.0)) {
                didAppear = true
            }
        }
    }
}

If I alter the fillColor to an ordinary colour like Coloration.blue, I see no FPS drops. Any concepts as to easy methods to make the gradient render extra effectively? I attempted drawingGroup(), which does enhance FPS, however it makes the blur look dangerous, and I additionally need to have the ability to animate blur dimension (+ border width, opacity).

LEAVE A REPLY

Please enter your comment!
Please enter your name here