ios – How do I get a mixing mode to use to my ScrollView whereas not affecting the background on newest SwiftUI?


The masking method might work for scroll views too, for those who monitor the frames of every subview of the scroll view. You could possibly use a struct like this:

struct ScrollContentFrame: Identifiable {
    let id: AnyHashable
    let body: Anchor
    let form: AnyShape
}

I am maintaining issues very common right here by utilizing AnyHashable and AnyShape. If that is only a one-off impact you need to do, I’d suggest utilizing an applicable ID kind, and if the form is understood and fixed, take away form.

Subsequent, write a desire key that collects an array of those,

struct ScrollContentFramesKey: PreferenceKey {
    static var defaultValue: [ScrollContentFrame] { [] }
    
    static func scale back(worth: inout [ScrollContentFrame], nextValue: () -> [ScrollContentFrame]) {
        worth.append(contentsOf: nextValue())
    }
}

Set the desire key utilizing an anchorPreference,

.anchorPreference(key: ScrollContentFramesKey.self, worth: .bounds) { anchor in
    [
        ScrollContentFrame(
            id: i,
            frame: anchor,
            shape: AnyShape(RoundedRectangle(cornerRadius: 16))
        )
    ]
}

The colour-blended linear gradient could be added as an overlayPreferenceValue as a substitute of ZStack.

.overlayPreferenceValue(ScrollContentFramesKey.self) { scrollContentFrames in
    LinearGradient(
        colours: [.blue, .orange],
        startPoint: .topLeading,
        endPoint: .bottomTrailing
    )
    .allowsHitTesting(false)
    .masks {
        GeometryReader { proxy in
            ForEach(scrollContentFrames) { content material in
                let body = proxy[content.frame]
                content material.form
                    .body(width: body.width, top: body.top)
                    .place(x: body.midX, y: body.midY)
            }
        }
    }
    .blendMode(.coloration)
    .ignoresSafeArea()
}

Full code for the view:

struct ContentView: View {
    var physique: some View {
        ZStack {
            LinearGradient(
                colours: [.purple, .pink],
                startPoint: .high,
                endPoint: .backside
            )
            .ignoresSafeArea()
            ScrollView {
                LazyVStack(spacing: 20) {
                    ForEach(0..<10) { i in
                        RoundedRectangle(cornerRadius: 16)
                            .fill(.white)
                            .body(top: 120)
                            .overlay(
                                Textual content("Card (i)")
                                    .font(.headline)
                                    .foregroundColor(.crimson)
                            )
                            .anchorPreference(key: ScrollContentFramesKey.self, worth: .bounds) { anchor in
                                [
                                    ScrollContentFrame(
                                        id: i,
                                        frame: anchor,
                                        shape: AnyShape(RoundedRectangle(cornerRadius: 16))
                                    )
                                ]
                            }
                            .padding(.horizontal)
                    }
                }
                .padding(.vertical, 50)
            }
            .background(Shade.clear)
            .overlayPreferenceValue(ScrollContentFramesKey.self) { scrollContentFrames in
                LinearGradient(
                    colours: [.blue, .orange],
                    startPoint: .topLeading,
                    endPoint: .bottomTrailing
                )
                .allowsHitTesting(false)
                .masks {
                    GeometryReader { proxy in
                        ForEach(scrollContentFrames) { content material in
                            let body = proxy[content.frame]
                            content material.form
                                .body(width: body.width, top: body.top)
                                .place(x: body.midX, y: body.midY)
                        }
                    }
                }
                .blendMode(.coloration)
                .ignoresSafeArea()
            }
        }
    }
}

Related Articles

LEAVE A REPLY

Please enter your comment!
Please enter your name here

Latest Articles