iOS:带边框的圆形矩形出血颜色
我正在绘制头像图片,只需将iOS:带边框的圆形矩形出血颜色,ios,uiimageview,calayer,Ios,Uiimageview,Calayer,我正在绘制头像图片,只需将cornerRadius应用到UIImageView的图层,并通过borderWith和borderColor添加边框。像这样: self.layer.masksToBounds = YES; self.layer.cornerRadius = imageDimension / 2.f; self.layer.borderWidth = 1.f; self.layer.borderColor = borderColor.CGColor; 这非常有效,除了边界外的内容有
cornerRadius
应用到UIImageView
的图层,并通过borderWith
和borderColor
添加边框。像这样:
self.layer.masksToBounds = YES;
self.layer.cornerRadius = imageDimension / 2.f;
self.layer.borderWidth = 1.f;
self.layer.borderColor = borderColor.CGColor;
这非常有效,除了边界外的内容有微小但明显的出血,如:
有没有一种方法可以只在边界的开头加上几个1/10点,或者插入比边界更多的内容
解决方案 多亏了FelixLam,我想出了一个很好的解决方案,并将把它留在这里,留给后世:
@interface MMRoundImageViewWithBorder : UIView
- (id)initWithImage:(UIImage *)image borderWidth:(CGFloat)borderWidth;
@property (strong, nonatomic) UIImageView *imageView;
@property (assign, nonatomic) CGFloat borderWidth;
@property (strong, nonatomic) UIColor *borderColor;
@end
@implementation MMRoundImageViewWithBorder
- (id)initWithImage:(UIImage *)image borderWidth:(CGFloat)borderWidth {
if (self = [super init]) {
self.borderWidth = borderWidth;
self.borderColor = UIColor.whiteColor;
self.imageView = [[UIImageView alloc] initWithImage:image];
[self addSubview:self.imageView];
self.imageView.layer.masksToBounds = YES;
self.layer.masksToBounds = YES;
}
return self;
}
- (void)setBorderColor:(UIColor *)borderColor {
_borderColor = borderColor;
self.backgroundColor = borderColor;
}
- (void)layoutSubviews {
[super layoutSubviews];
[self refreshDimensions];
}
- (void)refreshDimensions {
self.layer.cornerRadius = CGRectGetWidth(self.bounds) / 2.f;
self.imageView.frame = CGRectInset(self.bounds, _borderWidth, _borderWidth);
self.imageView.layer.cornerRadius = CGRectGetWidth(self.imageView.bounds) / 2.f;
}
- (void)setBorderWidth:(CGFloat)borderWidth {
_borderWidth = borderWidth;
[self refreshDimensions];
}
- (void)setFrame:(CGRect)frame {
[super setFrame:frame];
[self refreshDimensions];
}
@end
您可以尝试使用带有圆形路径的
CAShapelayer
作为层的遮罩,而不是使用角半径
或者,您可以将图像视图放置在有边框且大一/两像素的容器中。尝试设置:
[self setClipToBounds:YES]
正如在评论中所说,您可以向图像添加透明边框,这样就可以了。 下面是执行此操作的一段代码(UIImageView的一个类别):
我也有同样的问题,想要一个解决方案,可以很好地与故事板。我所做的是将图像放置在视图中,然后将两者设置为控制行为的自定义类。我现在可以完全从故事板控制设计 我已经把代码放在GitHub上了 它所做的是为UIButton和常规UIView覆盖UIView中的drawRect函数,以便可以处理多个视图。包装器视图还用于控制边框颜色和宽度。我只需确保包装视图和superview之间有一定的间距,并将其差值用作边框宽度。superview的背景色将成为边框颜色。现在,我可以在故事板中的许多场景中快速进行这些更改,而无需对每个实例进行自定义编码
- (void)drawRect:(CGRect)rect {
// round view and superview with a border using the background color of the superview
self.layer.cornerRadius = CGRectGetWidth(self.frame) / 2;
self.layer.masksToBounds = YES;
if ([self.superview isKindOfClass:[SSTCircleWrapperView class]]) {
self.superview.layer.cornerRadius = CGRectGetWidth(self.superview.frame) / 2;
self.superview.layer.masksToBounds = YES;
self.superview.layer.borderColor = self.superview.backgroundColor.CGColor;
self.superview.layer.borderWidth = (CGRectGetWidth(self.superview.frame) - CGRectGetWidth(self.frame)) / 2;
}
}
OP的解决方案是不必要的复杂。更简单、更清洁的解决方案。创建UIView、剪裁到边界、遮罩、边界和角半径(如上所述),然后添加UIIAMGEEVIEW作为该UIView的子视图。UIIAMGEEVIEW将被父视图剪裁,您将不会有出血问题。My
UIButton
需要圆角半径,这会导致锯齿状边缘。将borderStyle
设置为。roundedRect
修复了它
button.borderStyle = .roundedRect
button.layer.cornerRadius = 4
button.layer.borderWidth = 1
button.layer.borderColor = .red.cgColor
下面是解决此问题的
UIImageView
的子类
,它添加了一个圆角CAShapeLayer
,其边框宽度和拐角半径比“想要的”大1倍。它的帧从CGPoint(x:1,y:1)
开始,高度比图像视图的高度大2px。这样,它就覆盖了出血通道
Swift 3+解决方案
子类:
class BorderedRoundedImageView: UIImageView {
let borderLayer = CALayer()
var borderWidth: CGFloat!
var borderColor: UIColor!
func setUp() {
borderLayer.borderWidth = borderWidth + 1
borderLayer.borderColor = borderColor.cgColor
layer.addSublayer(borderLayer)
}
override func layoutSubviews() {
super.layoutSubviews()
borderLayer.cornerRadius = layer.cornerRadius + 1
borderLayer.frame = CGRect(x: -1, y: -1, width: frame.width + 2, height: frame.height + 2)
}
}
@IBOutlet weak var imageView: UIImageView!
[...]
imageView.layer.cornerRadius = 20
imageView.borderWidth = 2
imageView.borderColor = .lightGray
imageView.setUp()
用法:
class BorderedRoundedImageView: UIImageView {
let borderLayer = CALayer()
var borderWidth: CGFloat!
var borderColor: UIColor!
func setUp() {
borderLayer.borderWidth = borderWidth + 1
borderLayer.borderColor = borderColor.cgColor
layer.addSublayer(borderLayer)
}
override func layoutSubviews() {
super.layoutSubviews()
borderLayer.cornerRadius = layer.cornerRadius + 1
borderLayer.frame = CGRect(x: -1, y: -1, width: frame.width + 2, height: frame.height + 2)
}
}
@IBOutlet weak var imageView: UIImageView!
[...]
imageView.layer.cornerRadius = 20
imageView.borderWidth = 2
imageView.borderColor = .lightGray
imageView.setUp()
结果:
class BorderedRoundedImageView: UIImageView {
let borderLayer = CALayer()
var borderWidth: CGFloat!
var borderColor: UIColor!
func setUp() {
borderLayer.borderWidth = borderWidth + 1
borderLayer.borderColor = borderColor.cgColor
layer.addSublayer(borderLayer)
}
override func layoutSubviews() {
super.layoutSubviews()
borderLayer.cornerRadius = layer.cornerRadius + 1
borderLayer.frame = CGRect(x: -1, y: -1, width: frame.width + 2, height: frame.height + 2)
}
}
@IBOutlet weak var imageView: UIImageView!
[...]
imageView.layer.cornerRadius = 20
imageView.borderWidth = 2
imageView.borderColor = .lightGray
imageView.setUp()
您可以尝试在图像文件中添加一个透明的1像素边框,这样您的图像将更宽、更高2像素,这将有助于混合,因为这与
self.layer.masksToBounds=YES不同代码>这是次优解决方案。如果从缓存中获取或刷新图像,则必须始终重新生成图像。在图像周围绘制边框是一个渲染问题,而不是内容问题。当有9种方法达到目标时,不要选择一种不好的方法。否则你的代码库很快就会腐烂。谢谢你的想法!我选择了第二个选项,看起来很棒:)谢谢。我的解决方案在故事板中不起作用吗(我真的不在乎)?另外,在两个层上都将shoulldrasterize
设置为YES
,否则性能将显著降低。屏蔽似乎非常昂贵。这是滥用draw rect,大多数这类事情应该只在帧发生变化时发生。嗯,这正是我的代码所做的,还是我忽略了什么?