SnowInJune
SnowInJune

Reputation: 21

How to make Scratch Card effect in SwiftUI?

I've tried to use mask to make scratch card effect. It can't work. Maybe I use wrong function. Can someone tell me ? Here is the code.

struct ScratchCardView: View {
    @State var points: [CGPoint] = []
    var body: some View {
        ZStack {
            Text("Text")
                .font(.largeTitle)
            
            GeometryReader(content: { geometry in
                Rectangle()
                    .foregroundColor(.blue)
                    .mask(MaskView(in: CGRect(origin: .zero, size: geometry.size)))
                    .gesture(
                        DragGesture()
                            .onChanged { value in
                                points.append(value.location)
                            }
                    )
            })
        }
    }
    func MaskView(in rect: CGRect) -> some View {
        var path = Rectangle().path(in: rect)
        for point in points {
            path.addPath(Circle().path(in: CGRect(origin: point, size: CGSize(width: 30, height: 30)))
            )
        }
        return path.fill(style: FillStyle(eoFill: true))
    }
}

Upvotes: 2

Views: 491

Answers (1)

Duncan C
Duncan C

Reputation: 131436

I suggest you create a CALayer using you're view's bounds as its frame. Install the layer as your view's layer's mask.

Then install an image that's fully transparent in the mask's contents property. As the user drags with their finger, draw in any opaque color along the path of the user's finger with a series of circles at touch position. Turning part the image opaque will cause the mask to reveal that part of the image.

If instead you want a covering image that hides the content underneath, reverse the above. Create a UIImageView that covers the view you want to reveal (let's call it coverView.) Install a CALayer as that image view's mask, with a fully opaque image as its contents. As the user drags around, draw with UIColor.clear (transparent) into the mask's image. That will cause the coverView to be masked in those areas, revealing the image underneath.

Upvotes: 2

Related Questions