用一个切出的圆圈掩盖UIView [英] Mask a UIView with a cut-out circle

查看:109
本文介绍了用一个切出的圆圈掩盖UIView的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我创建了一个带有半透明黑色背景的 UIView ,可以放在主应用程序的视图中。我的目标是在 UIView 的某处创建一个切出的圆形,其中看不到半透明的黑色背景,给出了黑色的效果除了圆形区域之外的整个图像上的遮罩(这是为了突出显示该区域中的按钮)。

I’ve created a UIView with a semi-transparent black background to sit across my main app’s view. What I’m aiming for here is to create a cut-out circle shape somewhere in that UIView where the semi-transparent black background is not seen, giving the effect of a black mask over the whole image except the circular area (this is to highlight a button in that area).

我设法使用 CAShapeLayer 创建一个圆形蒙版,但这有相反的效果(即视图的其余部分是清晰的,并且圆圈内部是半透明的黑色。我想要的是除了圆形保持半透明的黑色,然后内部清楚。这是我使用的代码,我将如何使其以相反的方式工作?我的 blackMask 是半透明的黑色视图,我的 buttonCircle 是我希望保持清晰的圈子。

I’ve managed to use CAShapeLayer to create a circular mask, but this has had the opposite effect (i.e. the rest of the view is clear, and INSIDE the circle is the semi-transparent black. What I’d like is everything outside of the circle to keep the semi-transparent black, then what’s inside to be clear. Here’s the code I used, how would I go about making it work in the opposite way? My blackMask is the semi-transparent black view, and my buttonCircle is the circle I’d like to be kept clear.

也许我需要以某种方式反转路径?

Perhaps I need to invert the path, somehow?

CAShapeLayer *maskLayer = [[CAShapeLayer alloc] init];
CGRect maskRect = buttonCircle.frame;
CGPathRef path = CGPathCreateWithEllipseInRect(maskRect, NULL);
maskLayer.path = path;
CGPathRelease(path);
blackMask.layer.mask = maskLayer;

编辑:现在尝试这个,没有看到任何掩码:

Trying this now, not seeing any mask at all with this one:

UIView *circularMaskView = [[UIView alloc] initWithFrame:buttonCircle.frame];
circularMaskView.backgroundColor = [UIColor greenColor];
CAShapeLayer *maskLayer = [[CAShapeLayer alloc] init];

CGPathRef path = CGPathCreateWithEllipseInRect(buttonCircle.frame, NULL);
maskLayer.path = path;
CGPathRelease(path);

circularMaskView.layer.mask = maskLayer;

[blackMask addSubview:circularMaskView];


推荐答案

所以,这就是我的所作所为。我创建了一个名为 BlackoutView 的自定义 UIView 子类,如下所示:

So, here’s what I did. I created a custom UIView subclass called BlackoutView, like so:

BlackoutView.h

#import <UIKit/UIKit.h>

@interface BlackoutView : UIView

@property (nonatomic, retain) UIColor *fillColor;
@property (nonatomic, retain) NSArray *framesToCutOut;

@end

BlackoutView.m

#import "BlackoutView.h"

@implementation BlackoutView

- (void)drawRect:(CGRect)rect
{
    [self.fillColor setFill];
    UIRectFill(rect);

    CGContextRef context = UIGraphicsGetCurrentContext();
    CGContextSetBlendMode(context, kCGBlendModeDestinationOut);

    for (NSValue *value in self.framesToCutOut) {
        CGRect pathRect = [value CGRectValue];
        UIBezierPath *path = [UIBezierPath bezierPathWithOvalInRect:pathRect];
        [path fill];
    }

    CGContextSetBlendMode(context, kCGBlendModeNormal);
}

@end

我然后将其实例化为正常,并将属性设置为我要使用的蒙版的颜色,以及要从蒙版中剪切的帧:

I then instantiate it as normal, and set the properties to the colour of the mask I want to use, and the frames to be cut out of the mask:

[blackMask setFillColor:[UIColor colorWithWhite:0.0f alpha:0.8f]];
[blackMask setFramesToCutOut:@[[NSValue valueWithCGRect:buttonCircleA.frame],
                               [NSValue valueWithCGRect:buttonCircleB.frame]]];

这可以通过允许我切除椭圆形以外的其他形状来改善,但它对我的目的来说很好在这里,很容易适应以后这样做。希望这有助于其他人!

This could be improved by allowing me to cut out other shapes besides ovals, but it’s fine for my purposes here and would be easily adapted to do so later. Hopefully this helps others!

这篇关于用一个切出的圆圈掩盖UIView的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆