Créer un rectangle avec seulement deux coins arrondis dans swift?

J'ai besoin de créer un rectangle qui n'a que deux coins arrondis dans swift (code Objective C aussi ok).

En ce moment, mon code crée deux rectangles avec

CGPathCreateWithRoundedRect(CGRectMake(0, 0, 30, 60), 5, 5, nil); 

et

 CGPathCreateWithRoundedRect(CGRectMake(0, 0, 30, 60), 0, 0, nil); 

et les merge (avoir deux coins à angle droit et deux coins arrondis) mais je ne suis pas content du code et je suis à peu près sûr qu'il devrait y avoir de bien meilleures façons de le faire.

Je suis nouveau sur iOS et le développement graphique et rapide.

Dans Swift 2.3, vous pouvez le faire en

 let maskPath = UIBezierPath(roundedRect: anyView.bounds, byRoundingCorners: [.BottomLeft, .BottomRight], cornerRadii: CGSize(width: 10.0, height: 10.0)) let shape = CAShapeLayer() shape.path = maskPath.CGPath view.layer.mask = shape 

En Objective-C, vous pouvez utiliser la méthode de class UIBezierPath

 bezierPathWithRoundedRect:byRoundingCorners:cornerRadii: 

Exemple de mise en œuvre

 // set the corner radius to the specified corners of the passed container - (void)setMaskTo:(UIView*)view byRoundingCorners:(UIRectCorner)corners { UIBezierPath *rounded = [UIBezierPath bezierPathWithRoundedRect:view.bounds byRoundingCorners:corners cornerRadii:CGSizeMake(10.0, 10.0)]; CAShapeLayer *shape = [[CAShapeLayer alloc] init]; [shape setPath:rounded.CGPath]; view.layer.mask = shape; } 

et appelez la méthode ci-dessus

 [self setMaskTo:anyView byRoundingCorners:UIRectCornerBottomLeft | UIRectCornerBottomRight]; 

Voici une extension rapide Swift 3 que vous pouvez utiliser pour faire des arrondis et des bordures optionnelles.

Remarque: si vous utilisez la layout automatique, vous devrez peut-être l'appeler dans l'un des callbacks du cycle de vie de la vue, tels que viewDidLayoutSubviews ou layoutSubviews après que la vue ait été contrainte.

 import UIKit extension UIView { /** Rounds the given set of corners to the specified radius - parameter corners: Corners to round - parameter radius: Radius to round to */ func round(corners: UIRectCorner, radius: CGFloat) { _ = _round(corners: corners, radius: radius) } /** Rounds the given set of corners to the specified radius with a border - parameter corners: Corners to round - parameter radius: Radius to round to - parameter borderColor: The border color - parameter borderWidth: The border width */ func round(corners: UIRectCorner, radius: CGFloat, borderColor: UIColor, borderWidth: CGFloat) { let mask = _round(corners: corners, radius: radius) addBorder(mask: mask, borderColor: borderColor, borderWidth: borderWidth) } /** Fully rounds an autolayout view (eg one with no known frame) with the given diameter and border - parameter diameter: The view's diameter - parameter borderColor: The border color - parameter borderWidth: The border width */ func fullyRound(diameter: CGFloat, borderColor: UIColor, borderWidth: CGFloat) { layer.masksToBounds = true layer.cornerRadius = diameter / 2 layer.borderWidth = borderWidth layer.borderColor = borderColor.cgColor; } } private extension UIView { @discardableResult func _round(corners: UIRectCorner, radius: CGFloat) -> CAShapeLayer { let path = UIBezierPath(roundedRect: bounds, byRoundingCorners: corners, cornerRadii: CGSize(width: radius, height: radius)) let mask = CAShapeLayer() mask.path = path.cgPath self.layer.mask = mask return mask } func addBorder(mask: CAShapeLayer, borderColor: UIColor, borderWidth: CGFloat) { let borderLayer = CAShapeLayer() borderLayer.path = mask.path borderLayer.fillColor = UIColor.clear.cgColor borderLayer.strokeColor = borderColor.cgColor borderLayer.lineWidth = borderWidth borderLayer.frame = bounds layer.addSublayer(borderLayer) } } 

Voici ce que vous faites dans Swift 2.0

 var maskPath = UIBezierPath(roundedRect: anyView.bounds, byRoundingCorners: [.BottomLeft, .BottomRight], cornerRadii: CGSize(width: 10.0, height: 10.0)) 

En plus de l'excellente réponse de Sanjay, j'ai écrit une extension rapide de CALayer pour Swift 2.3, au cas où vous auriez besoin de faire ce genre de chose "seulement dans certains coins" plus d'une fois.

 extension CALayer { func roundCorners(corners: UIRectCorner, radius: CGFloat) { let maskPath = UIBezierPath(roundedRect: bounds, byRoundingCorners: corners, cornerRadii: CGSize(width: radius, height: radius)) let shape = CAShapeLayer() shape.path = maskPath.CGPath mask = shape } } 

Usage:

 myView.layer.roundCorners([.TopLeft, .TopRight], radius: myCornerRadius) 

Swift 3.0 (Dans cet exemple, les limites proviennent de la vue et non de la couche.À l'aide des limites de la vue, ce code fonctionne avec les vues dans un UITableViewCell.):

 func roundCorners(corners: UIRectCorner, radius: CGFloat, viewBounds: CGRect) { let maskPath = UIBezierPath(roundedRect: viewBounds, byRoundingCorners: corners, cornerRadii: CGSize(width: radius, height: radius)) let shape = CAShapeLayer() shape.path = maskPath.cgPath mask = shape } 

Usage:

 myView.layer.roundCorners(corners: [.topLeft, .topRight], radius: myCornerRadius, viewBounds: bounds) 

Swift 3 – Extension UIView utile lorsque vous devez arrondir certains coins de certaines vues:

 extension UIView { func round(corners: UIRectCorner, radius: CGFloat) { let path = UIBezierPath(roundedRect: bounds, byRoundingCorners: corners, cornerRadii: CGSize(width: radius, height: radius)) let mask = CAShapeLayer() mask.path = path.cgPath self.layer.mask = mask } } 

alors utilisez-le comme ceci:

 someView.round(corners: [.topLeft, .topRight], radius: 5) 

2017 …

entrez la description de l'image ici

 @IBDesignable class RoundedEnds: UIView { override func layoutSubviews() { setup() } // "layoutSubviews" is best func setup() { let r = self.bounds.size.height / 2 let path = UIBezierPath(roundedRect: self.bounds, cornerRadius:r) let mask = CAShapeLayer() mask.path = path.cgPath self.layer.mask = mask } } 

Pour seulement quelques coins, changez simplement en:

entrez la description de l'image ici

 roundedRect: self.bounds, byRoundingCorners: [.topLeft, .topRight], cornerRadii: CGSize(width: r, height: r) 

Notez que, comme d'habitude, il y a eu de nombreux petits changements dans Swift, par exemple la capitalisation des constantes, etc.

Version Objective-C de la réponse d'iWasRobbed:

UIView + RoundCorners.h

 #import <UIKit/UIKit.h> @interface UIView (RoundCorners) /** Rounds the given set of corners to the specified radius - parameter corners: Corners to round - parameter radius: Radius to round to */ - (void)roundCorners:(UIRectCorner)corners radius:(CGFloat)radius; /** Rounds the given set of corners to the specified radius with a border - parameter corners: Corners to round - parameter radius: Radius to round to - parameter borderColor: The border color - parameter borderWidth: The border width */ - (void)roundCorners:(UIRectCorner)corners radius:(CGFloat)radius borderColor:(UIColor *)borderColor borderWidth:(CGFloat)borderWidth; /** Fully rounds an autolayout view (eg one with no known frame) with the given diameter and border - parameter diameter: The view's diameter - parameter borderColor: The border color - parameter borderWidth: The border width */ - (void)fullyRoundWithDiameter:(CGFloat)diameter borderColor:(UIColor *)borderColor borderWidth:(CGFloat)borderWidth; @end 

UIView + RoundCorners.m

 #import "UIView+RoundCorners.h" @implementation UIView (RoundCorners) - (void)roundCorners:(UIRectCorner)corners radius:(CGFloat)radius { [self _roundCorners:corners radius:radius]; } - (void)roundCorners:(UIRectCorner)corners radius:(CGFloat)radius borderColor:(UIColor *)borderColor borderWidth:(CGFloat)borderWidth { CAShapeLayer *mask = [self _roundCorners:corners radius:radius]; [self addBorderWithMask:mask borderColor:borderColor borderWidth:borderWidth]; } - (void)fullyRoundWithDiameter:(CGFloat)diameter borderColor:(UIColor *)borderColor borderWidth:(CGFloat)borderWidth { self.layer.masksToBounds = YES; self.layer.cornerRadius = diameter / 2; self.layer.borderWidth = borderWidth; self.layer.borderColor = borderColor.CGColor; } - (CAShapeLayer *)_roundCorners:(UIRectCorner)corners radius:(CGFloat)radius { UIBezierPath *path = [UIBezierPath bezierPathWithRoundedRect:self.bounds byRoundingCorners:corners cornerRadii:CGSizeMake(radius, radius)]; CAShapeLayer *mask = [CAShapeLayer layer]; mask.path = path.CGPath; self.layer.mask = mask; return mask; } - (void)addBorderWithMask:(CAShapeLayer *)mask borderColor:(UIColor *)borderColor borderWidth:(CGFloat)borderWidth { CAShapeLayer *borderLayer = [CAShapeLayer layer]; borderLayer.path = mask.path; borderLayer.fillColor = UIColor.clearColor.CGColor; borderLayer.strokeColor = borderColor.CGColor; borderLayer.lineWidth = borderWidth; borderLayer.frame = self.bounds; [self.layer addSublayer:borderLayer]; } @end 

Réponse d'iWasRobbed mise à jour pour travailler avec la version Swift 3.0 GM:

 import UIKit extension UIView { /** Rounds the given set of corners to the specified radius - parameter corners: Corners to round - parameter radius: Radius to round to */ func round(corners: UIRectCorner, radius: CGFloat) { _round(corners: corners, radius: radius) } /** Rounds the given set of corners to the specified radius with a border - parameter corners: Corners to round - parameter radius: Radius to round to - parameter borderColor: The border color - parameter borderWidth: The border width */ func round(corners: UIRectCorner, radius: CGFloat, borderColor: UIColor, borderWidth: CGFloat) { let mask = _round(corners: corners, radius: radius) addBorder(mask: mask, borderColor: borderColor, borderWidth: borderWidth) } /** Fully rounds an autolayout view (eg one with no known frame) with the given diameter and border - parameter diameter: The view's diameter - parameter borderColor: The border color - parameter borderWidth: The border width */ func fullyRound(diameter: CGFloat, borderColor: UIColor, borderWidth: CGFloat) { layer.masksToBounds = true layer.cornerRadius = diameter / 2 layer.borderWidth = borderWidth layer.borderColor = borderColor.cgColor; } } private extension UIView { @discardableResult func _round(corners: UIRectCorner, radius: CGFloat) -> CAShapeLayer { let path = UIBezierPath(roundedRect: bounds, byRoundingCorners: corners, cornerRadii: CGSize(width: radius, height: radius)) let mask = CAShapeLayer() mask.path = path.cgPath self.layer.mask = mask return mask } func addBorder(mask: CAShapeLayer, borderColor: UIColor, borderWidth: CGFloat) { let borderLayer = CAShapeLayer() borderLayer.path = mask.path borderLayer.fillColor = UIColor.clear.cgColor borderLayer.strokeColor = borderColor.cgColor borderLayer.lineWidth = borderWidth borderLayer.frame = bounds layer.addSublayer(borderLayer) } } 

Swift 4:

  let maskPath = UIBezierPath(roundedRect: view.bounds, byRoundingCorners: [.allCorners], cornerRadii: CGSize(width: 10.0, height: 10.0)) let shape = CAShapeLayer() shape.path = maskPath.cgPath cell.layer.mask = shape return cell