Ios 从另一个中减去CALayer,混合?

Ios 从另一个中减去CALayer,混合?,ios,swift,core-graphics,core-animation,calayer,Ios,Swift,Core Graphics,Core Animation,Calayer,在下图中,蓝色圆圈仅用于调试目的。我的目标是蓝色圆圈后面的每一层都应该是透明的。我只想让蓝色圆圈外面的东西保持可见 以下是用swift编写的代码: let croissantView = UIView(frame: CGRectMake(100, 100, 100, 100)) croissantView.backgroundColor = UIColor.clearColor() self.view.addSubview(croissantView) l

在下图中,蓝色圆圈仅用于调试目的。我的目标是蓝色圆圈后面的每一层都应该是透明的。我只想让蓝色圆圈外面的东西保持可见

以下是用swift编写的代码:

    let croissantView = UIView(frame: CGRectMake(100, 100, 100, 100))
    croissantView.backgroundColor = UIColor.clearColor()

    self.view.addSubview(croissantView)


    let radius = 50 as CGFloat
    let width = 50 as CGFloat

    let origin = CGPointMake(0, 100)
    let end = CGPointMake(100,100)
    let highAmplitude = CGPointMake(50,180)
    let lowAmplitude = CGPointMake(50,150)

    let quad = UIBezierPath()
    quad.moveToPoint(origin)
    quad.addQuadCurveToPoint(end, controlPoint: highAmplitude)
    quad.closePath()

    let quad2 = UIBezierPath()
    quad2.moveToPoint(origin)
    quad2.addQuadCurveToPoint(end, controlPoint: lowAmplitude)
    quad2.closePath()

    let layer = CAShapeLayer()
    layer.path = quad.CGPath

    layer.strokeColor = UIColor.greenColor().CGColor
    layer.fillColor = UIColor.blackColor().CGColor

    croissantView.layer.addSublayer(layer)

    let anim =  CABasicAnimation(keyPath: "path")
    anim.duration = 3
    anim.repeatCount = 20
    anim.fromValue = quad.CGPath
    anim.toValue = quad2.CGPath
    anim.autoreverses = true
    layer.addAnimation(anim, forKey: "animQuad")


    let animRotate =  CABasicAnimation(keyPath: "transform.rotation")
    animRotate.duration = 5
    animRotate.repeatCount = 20
    animRotate.fromValue = 0
    animRotate.toValue = 360 * CGFloat(M_PI) / 180
    croissantView.layer.addAnimation(animRotate, forKey: "animRotate")


    let circle = UIBezierPath(arcCenter: croissantView.center, radius: 75, startAngle: 0, endAngle: 360 * CGFloat(M_PI) / 180, clockwise: true);
    let circleLayer = CAShapeLayer()
    circleLayer.path = circle.CGPath
    circleLayer.fillColor = UIColor.blueColor().CGColor
    circleLayer.opacity = 0.6
    self.view.layer.addSublayer(circleLayer)
思想
  • 从图层中减去,不知道是否可行
  • 混合,不知道怎么用CALayer做

谢谢!!:)

我有三点建议

  • 将羊角面包视图更改为图层(不确定这是否必要,但我就是这么做的)

  • 为圆形状创建一个可以反转其遮罩的CGPath。为此,可以在圆周围环绕一个外矩形,使路径如下所示:

  • 将圆形图层上的填充规则设置为奇偶:

    circleLayer.fillRule = kCAFillRuleEvenOdd
    
  • 这就是它看起来的样子:

    我修改了你的代码来尝试它,这就是我想到的。您的里程可能会有所不同:

    func applyMask() {
    
        let mainLayer = CALayer()
        mainLayer.bounds = CGRect(x: 0.0, y: 0.0, width: 100.0, height: 100.0)
        mainLayer.position = CGPoint(x: 200.0, y: 200.0)
        // Set the color for debugging
        mainLayer.backgroundColor = UIColor.orangeColor().CGColor
    
        self.view.layer.addSublayer(mainLayer)
    
        let radius = 50 as CGFloat
        let width = 50 as CGFloat
    
        let origin = CGPointMake(0, 100)
        let end = CGPointMake(100,100)
        let highAmplitude = CGPointMake(50,180)
        let lowAmplitude = CGPointMake(50,150)
    
        let quad = UIBezierPath()
        quad.moveToPoint(origin)
        quad.addQuadCurveToPoint(end, controlPoint: highAmplitude)
        quad.closePath()
    
        let quad2 = UIBezierPath()
        quad2.moveToPoint(origin)
        quad2.addQuadCurveToPoint(end, controlPoint: lowAmplitude)
        quad2.closePath()
    
        let layer = CAShapeLayer()
        layer.path = quad.CGPath
    
        layer.strokeColor = UIColor.greenColor().CGColor
        layer.fillColor = UIColor.blackColor().CGColor
    
        mainLayer.addSublayer(layer)
    
        let anim =  CABasicAnimation(keyPath: "path")
        anim.duration = 3
        anim.repeatCount = 20
        anim.fromValue = quad.CGPath
        anim.toValue = quad2.CGPath
        anim.autoreverses = true
        layer.addAnimation(anim, forKey: "animQuad")
    
        let animRotate =  CABasicAnimation(keyPath: "transform.rotation")
        animRotate.duration = 5
        animRotate.repeatCount = 20
        animRotate.fromValue = 0
        animRotate.toValue = 360 * CGFloat(M_PI) / 180
        mainLayer.addAnimation(animRotate, forKey: "animRotate")
    
        // Build a Circle CGPath
        var circlePath = CGPathCreateMutable()
        CGPathAddEllipseInRect(circlePath, nil, CGRectInset(mainLayer.bounds, -20.0, -20.0))
        // Invert the mask by adding a bounding rectangle
        CGPathAddRect(circlePath, nil, CGRectInset(mainLayer.bounds, -100.0, -100.0))
        CGPathCloseSubpath(circlePath)
    
        let circleLayer = CAShapeLayer()
        circleLayer.fillColor = UIColor.blueColor().CGColor
        circleLayer.opacity = 0.6
        // Use the even odd fill rule so that our path gets inverted
        circleLayer.fillRule = kCAFillRuleEvenOdd
        circleLayer.path = circlePath
    
        mainLayer.mask = circleLayer
    
        mainLayer.addSublayer(layer)
    }
    
    以下是我尝试的项目:


    希望这能有所帮助。

    您看过了吗?非常感谢!!它工作得很好!我要玩它,确保能理解一切。