如果在这样一个视图中使用的代码添加视图的边界
self.layer.borderColor = [UIColor yellowColor].CGColor;
self.layer.borderWidth = 2.0f;
边框是类似下面的视图中添加:
正确的观点是原来的观点,你可以看到,镶上视图的黑色区域是比原来少一个。 但我希望得到的是原来的观点,这样的外边框: 。 黑色的面积等于原来的,我怎么能实现呢?
如果在这样一个视图中使用的代码添加视图的边界
self.layer.borderColor = [UIColor yellowColor].CGColor;
self.layer.borderWidth = 2.0f;
边框是类似下面的视图中添加:
正确的观点是原来的观点,你可以看到,镶上视图的黑色区域是比原来少一个。 但我希望得到的是原来的观点,这样的外边框: 。 黑色的面积等于原来的,我怎么能实现呢?
不幸的是,不是简单的,你可以设置边框对齐到外面一点点财产。 因为UIViews默认绘图操作其边界内绘制它吸引对准里面。
我想到的最简单的解决办法是通过应用边框时边框宽度的尺寸扩大的UIView:
CGFloat borderWidth = 2.0f;
self.frame = CGRectInset(self.frame, -borderWidth, -borderWidth);
self.layer.borderColor = [UIColor yellowColor].CGColor;
self.layer.borderWidth = borderWidth;
好了,已经有一个公认的答案,但我认为这是一个更好的方式来做到这一点,你就必须比你的观点来了一个新的层有点大,并且不要将屏蔽对视图的层的边界(实际上是默认行为)。 下面是示例代码:
CALayer * externalBorder = [CALayer layer];
externalBorder.frame = CGRectMake(-1, -1, myView.frame.size.width+2, myView.frame.size.height+2);
externalBorder.borderColor = [UIColor blackColor].CGColor;
externalBorder.borderWidth = 1.0;
[myView.layer addSublayer:externalBorder];
myView.layer.masksToBounds = NO;
当然,这是如果你想你的边界是1个团结大,如果你想要更多的你适应的borderWidth
和层的相应的框架。 这比使用第二视图位作为一个更大更好CALayer
是比轻UIView
和你没有做修改的框架myView
,这是很好的,例如,如果myView
是一个UIImageView
注:对我来说,结果是不完美的模拟器(该层是不完全在正确的位置,使该层为一侧较厚有时),但到底是什么要求就实际设备。
编辑
其实我在NB谈论这个问题只是因为我已经减少了模拟器的屏幕上正常大小也绝对没有问题
希望能帮助到你
通过上述公认的最佳答案我有这样不是很好的结果和难看的边缘制作经验:
因此,我会分享我的UIView 斯威夫特扩展和你在一起,使用一个UIBezierPath代替边境轮廓-没有难看的边缘(灵感@Fattie ):
// UIView+BezierPathBorder.swift
import UIKit
extension UIView {
fileprivate var bezierPathIdentifier:String { return "bezierPathBorderLayer" }
fileprivate var bezierPathBorder:CAShapeLayer? {
return (self.layer.sublayers?.filter({ (layer) -> Bool in
return layer.name == self.bezierPathIdentifier && (layer as? CAShapeLayer) != nil
}) as? [CAShapeLayer])?.first
}
func bezierPathBorder(_ color:UIColor = .white, width:CGFloat = 1) {
var border = self.bezierPathBorder
let path = UIBezierPath(roundedRect: self.bounds, cornerRadius:self.layer.cornerRadius)
let mask = CAShapeLayer()
mask.path = path.cgPath
self.layer.mask = mask
if (border == nil) {
border = CAShapeLayer()
border!.name = self.bezierPathIdentifier
self.layer.addSublayer(border!)
}
border!.frame = self.bounds
let pathUsingCorrectInsetIfAny =
UIBezierPath(roundedRect: border!.bounds, cornerRadius:self.layer.cornerRadius)
border!.path = pathUsingCorrectInsetIfAny.cgPath
border!.fillColor = UIColor.clear.cgColor
border!.strokeColor = color.cgColor
border!.lineWidth = width * 2
}
func removeBezierPathBorder() {
self.layer.mask = nil
self.bezierPathBorder?.removeFromSuperlayer()
}
}
例:
let view = UIView(frame: CGRect(x: 20, y: 20, width: 100, height: 100))
view.layer.cornerRadius = view.frame.width / 2
view.backgroundColor = .red
//add white 2 pixel border outline
view.bezierPathBorder(.white, width: 2)
//remove border outline (optional)
view.removeBezierPathBorder()
那么有没有直接的方法来做到这一点你可以考虑一些解决方法。
如果你不需要一个明确的边界(皆伐边界),那么你可以依靠阴影为目的
[view1 setBackgroundColor:[UIColor blackColor]]; UIColor *color = [UIColor yellowColor]; view1.layer.shadowColor = [color CGColor]; view1.layer.shadowRadius = 10.0f; view1.layer.shadowOpacity = 1; view1.layer.shadowOffset = CGSizeZero; view1.layer.masksToBounds = NO;
对于斯威夫特的实现,您可以将其添加为一个UIView扩展。
extension UIView {
struct Constants {
static let ExternalBorderName = "externalBorder"
}
func addExternalBorder(borderWidth: CGFloat = 2.0, borderColor: UIColor = UIColor.whiteColor()) -> CALayer {
let externalBorder = CALayer()
externalBorder.frame = CGRectMake(-borderWidth, -borderWidth, frame.size.width + 2 * borderWidth, frame.size.height + 2 * borderWidth)
externalBorder.borderColor = borderColor.CGColor
externalBorder.borderWidth = borderWidth
externalBorder.name = Constants.ExternalBorderName
layer.insertSublayer(externalBorder, atIndex: 0)
layer.masksToBounds = false
return externalBorder
}
func removeExternalBorders() {
layer.sublayers?.filter() { $0.name == Constants.ExternalBorderName }.forEach() {
$0.removeFromSuperlayer()
}
}
func removeExternalBorder(externalBorder: CALayer) {
guard externalBorder.name == Constants.ExternalBorderName else { return }
externalBorder.removeFromSuperlayer()
}
}
加入边界之前增加视图的与边框宽度帧的宽度和高度:
float borderWidth = 2.0f
CGRect frame = self.frame;
frame.width += borderWidth;
frame.height += borderWidth;
self.layer.borderColor = [UIColor yellowColor].CGColor;
self.layer.borderWidth = 2.0f;
其实有一个非常简单的解决方案。 只需设置他们两个这样的:
view.layer.borderWidth = 5
view.layer.borderColor = UIColor(red: 1, green: 1, blue: 1, alpha: 0.5).cgColor
view.backgroundColor = UIColor(red: 1, green: 1, blue: 1, alpha: 0.25).cgColor
我喜欢@picciano的解决方案,如果你想爆炸圆的而不是方将其替换addExternalBorder功能:
func addExternalBorder(borderWidth: CGFloat = 2.0, borderColor: UIColor = UIColor.white) {
let externalBorder = CALayer()
externalBorder.frame = CGRect(x: -borderWidth, y: -borderWidth, width: frame.size.width + 2 * borderWidth, height: frame.size.height + 2 * borderWidth)
externalBorder.borderColor = borderColor.cgColor
externalBorder.borderWidth = borderWidth
externalBorder.cornerRadius = (frame.size.width + 2 * borderWidth) / 2
externalBorder.name = Constants.ExternalBorderName
layer.insertSublayer(externalBorder, at: 0)
layer.masksToBounds = false
}
我喜欢@picciano&@Maksim Kniazev的解决方案。 我们也可以创建环形边框与以下内容:
func addExternalAnnularBorder(borderWidth: CGFloat = 2.0, borderColor: UIColor = UIColor.white) {
let externalBorder = CALayer()
externalBorder.frame = CGRect(x: -borderWidth*2, y: -borderWidth*2, width: frame.size.width + 4 * borderWidth, height: frame.size.height + 4 * borderWidth)
externalBorder.borderColor = borderColor.cgColor
externalBorder.borderWidth = borderWidth
externalBorder.cornerRadius = (frame.size.width + 4 * borderWidth) / 2
externalBorder.name = Constants.ExternalBorderName
layer.insertSublayer(externalBorder, at: 0)
layer.masksToBounds = false
}