Đường viền đứt quanh UIView


Câu trả lời:


131

Bạn có thể đặt đường viền với mẫu này bằng đường dẫn Layer và Bezier như các ví dụ dưới đây.

Mục tiêu-C

CAShapeLayer *yourViewBorder = [CAShapeLayer layer];
yourViewBorder.strokeColor = [UIColor blackColor].CGColor;
yourViewBorder.fillColor = nil;
yourViewBorder.lineDashPattern = @[@2, @2];
yourViewBorder.frame = yourView.bounds;
yourViewBorder.path = [UIBezierPath bezierPathWithRect:yourView.bounds].CGPath;
[yourView.layer addSublayer:yourViewBorder];

Swift 3.1

var yourViewBorder = CAShapeLayer()
yourViewBorder.strokeColor = UIColor.black.cgColor
yourViewBorder.lineDashPattern = [2, 2]
yourViewBorder.frame = yourView.bounds
yourViewBorder.fillColor = nil
yourViewBorder.path = UIBezierPath(rect: yourView.bounds).cgPath
yourView.layer.addSublayer(yourViewBorder)

Bạn cũng có thể đặt các loại thiết kế khác nhau bằng cách sử dụng hình ảnh mẫu như ví dụ dưới đây.

[yourView.layer setBorderWidth:5.0];
[yourView.layer setBorderColor:[[UIColor colorWithPatternImage:[UIImage imageNamed:@"DotedImage.png"]] CGColor]];///just add image name and create image with dashed or doted drawing and add here

Ở đây bạn đã thêm <QuartzCore/QuartzCore>khung trong dự án và nhập nó với dòng dưới đây trong YourViewController.mtệp.

#import <QuartzCore/QuartzCore.h>

2
Đó không phải là một cách hoàn hảo khi nói về iPhone6 ​​plus. Đường chấm chấm có thể trở nên mờ.
Jacky

1
@Jacky: sử dụng hình ảnh có độ phân giải cao hơn. :)
Olie

6
một ví dụ của hình ảnh là gì?
Tom Roggero

1
bạn có thể cho một ví dụ về hình ảnh?
Jonguo

1
Jonguo Ví dụ: nếu bạn thêm bất kỳ hình ảnh nào có độ phân giải phù hợp như giả sử kích thước hình ảnh bình thường của bạn là 120x120 và tên của nó là test.png, sau đó tạo hai hình ảnh khác với tên test@2x.png và test@3x.png với kích thước 240x240 và 360x360 được sử dụng tự động trong tất cả các thiết bị apple với tên liên quan. (ví dụ: test.png được sử dụng trong iPhone 4, test @ 2x sẽ hữu ích cho iPhone 4s, 5, 5s, 6, 6s và twst @ 3x sẽ hữu ích cho iPhone 6 plus, 6s plus.
Paras Joshi

273

Một phương pháp khác nếu bạn thích lớp con. Trong init của chế độ xem tùy chỉnh của bạn, hãy đặt cái này (_border là một ivar):

_border = [CAShapeLayer layer];
_border.strokeColor = [UIColor colorWithRed:67/255.0f green:37/255.0f blue:83/255.0f alpha:1].CGColor;
_border.fillColor = nil;
_border.lineDashPattern = @[@4, @2];
[self.layer addSublayer:_border];

Và trong bố cục của bạn, đặt điều này:

_border.path = [UIBezierPath bezierPathWithRect:self.bounds].CGPath;
_border.frame = self.bounds;

41
Đẹp! Bạn cũng có thể sử dụng một cái gì đó như thế này để tạo hiệu ứng tròn:_border.path = [UIBezierPath bezierPathWithRoundedRect:self.bounds cornerRadius:5.f].CGPath;
Everton Cunha

Lấy làm tiếc! Tôi không hiểu Ví dụ nào? @EvertonCunha
Yi Jiang

3
@VanDuTran Trong đoạn trích đầu tiên,_border.lineWidth = 3
Chris

1
hey tôi đã áp dụng mã này để gắn nhãn trên ô xem bảng nhưng nó cho kích thước nhỏ của đường viền làm thế nào tôi có thể sửa lỗi này.
Chaudhary Ankit Deshwal

3
Swift 3: border = CAShapeLayer() border.strokeColor = yourColor border.fillColor = nil border.lineDashPattern = [4, 2] self.layer.addSublayer(border)
Geek20

71

Đối với những bạn làm việc trong Swift, phần mở rộng lớp học này trên UIView giúp bạn dễ dàng. Điều này được dựa trên câu trả lời của sunlightDev.

extension UIView {
  func addDashedBorder() {
    let color = UIColor.red.cgColor

    let shapeLayer:CAShapeLayer = CAShapeLayer()
    let frameSize = self.frame.size
    let shapeRect = CGRect(x: 0, y: 0, width: frameSize.width, height: frameSize.height)

    shapeLayer.bounds = shapeRect
    shapeLayer.position = CGPoint(x: frameSize.width/2, y: frameSize.height/2)
    shapeLayer.fillColor = UIColor.clear.cgColor
    shapeLayer.strokeColor = color
    shapeLayer.lineWidth = 2
    shapeLayer.lineJoin = CAShapeLayerLineJoin.round
    shapeLayer.lineDashPattern = [6,3]
    shapeLayer.path = UIBezierPath(roundedRect: shapeRect, cornerRadius: 5).cgPath

    self.layer.addSublayer(shapeLayer)
    }
}

Để dùng nó:

anyView.addDashedBorder()

2
Tuyệt vời của mã! Chỉ có một vấn đề, khi tôi áp dụng nó cho UIImageView, nó không nhận ra toàn bộ chiều rộng của nó, nó chiếm khoảng 80%.
arielcr 30/03/2015

1
Tôi nghĩ rằng có lẽ bạn đang gọi addDashBorder quá sớm, hãy thử gọi nó trong didLayoutSubview
Bố già

3
Tôi đã tạo một UIView tùy chỉnh và đặt phần mở rộng này vào bên trong. Sau đó, tôi đã gọi addDashedBorder()trong khi didMoveToSuperview()nghĩ rằng tự động thanh toán sẽ hoàn thành sau đó và kích thước khung hình sẽ chính xác nhưng không được. Chiều rộng của đường viền nét đứt vượt quá chiều rộng của khung nhìn. Bằng cách này, đường đứt nét trông rất tốt! Điều self.frame.sizenày không đúng.
levibostian

self.layer.masksToBound = true Sử dụng cái này nếu nó vượt ra khỏi giới hạn
Ankish Jain

@rmooney hoạt động rất tuyệt vời nhưng vấn đề là khi bạn thêm một lớp con trong một ô động UITableView, lớp được coi là lớp của bảng phân cảnh và nó không hoạt động trong một customcell, nó có kích thước khác nhau nếu chiều rộng của bảng phân cảnh của bạn là 375px. kích thước và nó sẽ không hoạt động trong một thiết bị lớn hơn như 414px, v.v.
Azharhussain Shaikh

18

Swift 3 :

import UIKit

class UIViewWithDashedLineBorder: UIView {

    override func draw(_ rect: CGRect) {

        let path = UIBezierPath(roundedRect: rect, cornerRadius: 0)

        UIColor.purple.setFill()
        path.fill()

        UIColor.orange.setStroke()
        path.lineWidth = 5

        let dashPattern : [CGFloat] = [10, 4]
        path.setLineDash(dashPattern, count: 2, phase: 0)
        path.stroke()
    }
}

Sử dụng trong bảng phân cảnh (dưới dạng lớp tùy chỉnh) hoặc trực tiếp bằng mã:

let v = UIViewWithDashedLineBorder(frame: CGRect(x: 0, y: 0, width: 100, height: 100))

Kết quả:

nhập mô tả hình ảnh ở đây


Bất ngờ rằng không có nhiều sự ủng hộ về điều này. Giải pháp này hoạt động tốt nhất với bố cục tự động so với các câu trả lời khác.
Yuchen Zhong

17

Dựa trên những gì Prasad G đã gợi ý, tôi đã tạo ra một phương thức bên trong lớp UIImage Extras với các mục sau:

- (CAShapeLayer *) addDashedBorderWithColor: (CGColorRef) color {
    CAShapeLayer *shapeLayer = [CAShapeLayer layer];

    CGSize frameSize = self.size;

    CGRect shapeRect = CGRectMake(0.0f, 0.0f, frameSize.width, frameSize.height);
    [shapeLayer setBounds:shapeRect];
    [shapeLayer setPosition:CGPointMake( frameSize.width/2,frameSize.height/2)];

    [shapeLayer setFillColor:[[UIColor clearColor] CGColor]];
    [shapeLayer setStrokeColor:color];
    [shapeLayer setLineWidth:5.0f];
    [shapeLayer setLineJoin:kCALineJoinRound];
    [shapeLayer setLineDashPattern:
     [NSArray arrayWithObjects:[NSNumber numberWithInt:10],
      [NSNumber numberWithInt:5],
      nil]];
    UIBezierPath *path = [UIBezierPath bezierPathWithRoundedRect:shapeRect cornerRadius:15.0];
    [shapeLayer setPath:path.CGPath];

    return shapeLayer;
}

Điều quan trọng là chỉ ra rằng nếu bạn xác định vị trí hình dạng của mình là (0,0), góc dưới cùng của đường viền sẽ được đặt ở giữa hình ảnh, đó là lý do tại sao tôi đặt nó thành: (frameSize. Thong / 2, frameSize .eight / 2)

Sau đó, tôi sử dụng phương thức của mình để có được đường viền nét đứt bằng cách sử dụng UIImage của UIImageView của tôi và thêm CAShapeLayer làm lớp con của lớp UIImageView:

[myImageView.layer addSublayer:[myImageView.image addDashedBorderWithColor:[[UIColor whiteColor] CGColor]]];

16

Sử dụng phương thức CGContextSetLineDash ().

CGFloat dashPattern[]= {3.0, 2};

context =UIGraphicsGetCurrentContext();
CGContextSetRGBStrokeColor(context, 1.0, 1.0, 1.0, 1.0);
// And draw with a blue fill color
CGContextSetRGBFillColor(context, 0.0, 0.0, 1.0, 1.0);
// Draw them with a 2.0 stroke width so they are a bit more visible.
CGContextSetLineWidth(context, 4.0);
CGContextSetLineDash(context, 0.0, dashPattern, 2);

CGContextAddRect(context, self.bounds);

// Close the path
CGContextClosePath(context);

CGContextStrokePath(context);

// Fill & stroke the path
CGContextDrawPath(context, kCGPathFillStroke);

Tôi nghĩ nó sẽ hữu ích cho bạn.


1
Bối cảnh ở đây là gì?
Avinash Sharma

11

Đây là một lớp con UIView có thể hoạt động cho bất kỳ dự án nào, nó cũng hoạt động cho các chế độ xem tròn :

import UIKit

class CustomDashedView: UIView {

    @IBInspectable var cornerRadius: CGFloat = 0 {
        didSet {
            layer.cornerRadius = cornerRadius
            layer.masksToBounds = cornerRadius > 0
        }
    }
    @IBInspectable var dashWidth: CGFloat = 0
    @IBInspectable var dashColor: UIColor = .clear
    @IBInspectable var dashLength: CGFloat = 0
    @IBInspectable var betweenDashesSpace: CGFloat = 0

    var dashBorder: CAShapeLayer?

    override func layoutSubviews() {
        super.layoutSubviews()
        dashBorder?.removeFromSuperlayer()
        let dashBorder = CAShapeLayer()
        dashBorder.lineWidth = dashWidth
        dashBorder.strokeColor = dashColor.cgColor
        dashBorder.lineDashPattern = [dashLength, betweenDashesSpace] as [NSNumber]
        dashBorder.frame = bounds
        dashBorder.fillColor = nil
        if cornerRadius > 0 {
            dashBorder.path = UIBezierPath(roundedRect: bounds, cornerRadius: cornerRadius).cgPath
        } else {
            dashBorder.path = UIBezierPath(rect: bounds).cgPath
        }
        layer.addSublayer(dashBorder)
        self.dashBorder = dashBorder
    }
}

Bằng cách này bạn có thể chỉnh sửa từ Storyboard như thế này:

nhập mô tả hình ảnh ở đây

Một cặp kết quả:

nhập mô tả hình ảnh ở đây

nhập mô tả hình ảnh ở đây


10

Đối với điều này, bạn cần thêm CAShapeLayer cho đối tượng cụ thể đó

 CAShapeLayer * dotborder = [CAShapeLayer layer];
    dotborder.strokeColor = [UIColor redColor].CGColor;//your own color
    dotborder.fillColor = nil;
    dotborder.lineDashPattern = @[@4, @2];//your own patten 
    [codeBtn.layer addSublayer:dotborder];
    dotborder.path = [UIBezierPath bezierPathWithRect:codeBtn.bounds].CGPath;
    dotborder.frame = codeBtn.bounds;

7

Swift 4.2

Dựa trên câu trả lời của rmooney như một UIViewphần mở rộng với các tham số có thể định cấu hình được đặt giá trị mặc định.

Lưu ý điều này không hoạt động nếu chế độ xem có self.translatesAutoresizingMaskIntoConstraints = false

extension UIView {
  func addDashedBorder(_ color: UIColor = UIColor.black, withWidth width: CGFloat = 2, cornerRadius: CGFloat = 5, dashPattern: [NSNumber] = [3,6]) {

    let shapeLayer = CAShapeLayer()

    shapeLayer.bounds = bounds
    shapeLayer.position = CGPoint(x: bounds.width/2, y: bounds.height/2)
    shapeLayer.fillColor = nil
    shapeLayer.strokeColor = color.cgColor
    shapeLayer.lineWidth = width
    shapeLayer.lineJoin = CAShapeLayerLineJoin.round // Updated in swift 4.2
    shapeLayer.lineDashPattern = dashPattern
    shapeLayer.path = UIBezierPath(roundedRect: bounds, cornerRadius: cornerRadius).cgPath

    self.layer.addSublayer(shapeLayer)
  }
}

shapeLayer.lineJoin = CAShapeLayerLineJoin.roundnên làyourViewBorder.lineJoin = kCALineJoinRound
pw2

6

Phiên bản Swift của câu trả lời QuartzCore.

import QuartzCore    

let dottedPattern = UIImage(named: "dottedPattern")
myView.layer.borderWidth = 1
myView.layer.borderColor = UIColor(patternImage: dottedPattern!).CGColor

Cách CAShapeLayertiếp cận hoạt động, nhưng cách tiếp cận QuartzCore tốt hơn trong việc xử lý tải lại Chế độ xem bảng, nếu UIViewnó nằm trong một ô.

Đối với hình ảnh, bạn có thể sử dụng một cái gì đó như thế này (nó thực sự nhỏ):

nhập mô tả hình ảnh ở đây

Tôi có xu hướng thích vectơ hơn PNG khi tôi có thể thoát khỏi nó:

  • Trong Phác thảo, tạo một hình chữ nhật 4 pixel.
  • Tổng cộng bốn trong số này
  • Nhóm chúng thành một màu, xen kẽ các màu
  • Xuất nhóm dưới dạng PDF
  • Bên trong Images.xcassets, tạo một New Image Settên gọi là rải rác
  • Thay đổi Scale FactorsthànhSingle Vector
  • Thả bản PDF của bạn

6

Đối với Xamarin.iOS đường viền đứt nét / chấm.

        dottedLayer = new CAShapeLayer();
        dottedLayer.StrokeColor = UIColor.FromRGB(202, 202, 208).CGColor; 
        dottedLayer.FillColor = null;
        dottedLayer.LineDashPattern = new[] { new NSNumber(4), new NSNumber(2) };

        dottedLayer.Path = UIBezierPath.FromRect(YourView.Bounds).CGPath; //for square
        dottedLayer.Path = UIBezierPath.FromRoundedRect(YourView.Bounds, 5).CGPath; //for rounded corners

        dottedLayer.Frame = YourView.Bounds;
        YourView.Layer.AddSublayer(dottedLayer);

Vui lòng giải thích câu trả lời của bạn một chút thay vì chỉ đặt đoạn mã.
kabirbaidhya

1
Lưu ý cho những người đọc trong tương lai: bạn phải sử dụng không gian tên CoreAnimation để sử dụng hàm tạo CAShapeLayer.
jnel899

6

Trong Swift 3

let border = CAShapeLayer();
border.strokeColor = UIColor.black.cgColor;
border.fillColor = nil;
border.lineDashPattern = [4, 4];
border.path = UIBezierPath(rect: theView.bounds).cgPath
border.frame = theView.bounds;
theView.layer.addSublayer(border);

4

Đây là nếu bạn muốn nó trong Swift 2

func addDashedLineBorderWithColor(color:UIColor) {
    let _ = self.sublayers?.filter({$0.name == "DashedBorder"}).map({$0.removeFromSuperlayer()})
    let  border = CAShapeLayer();
    border.name = "DashedBorder"
    border.strokeColor = color.CGColor;
    border.fillColor = nil;
    border.lineDashPattern = [4, 4];
    border.path = UIBezierPath(rect: self.bounds).CGPath
    border.frame = self.bounds;
    self.addSublayer(border);

}

3

thử mã dưới đây

- (void)drawRect:(CGRect)rect {
    //// Color Declarations
    UIColor* fillColor = [UIColor colorWithRed: 1 green: 1 blue: 1 alpha: 1];
    UIColor* strokeColor = [UIColor colorWithRed: 0.29 green: 0.565 blue: 0.886 alpha: 1];

    //// Rectangle Drawing
    UIBezierPath* rectanglePath = [UIBezierPath bezierPathWithRoundedRect:rect cornerRadius: 6];
    [fillColor setFill];
    [rectanglePath fill];
    [strokeColor setStroke];
    rectanglePath.lineWidth = 1;
    CGFloat rectanglePattern[] = {6, 2, 6, 2};
    [rectanglePath setLineDash: rectanglePattern count: 4 phase: 0];
    [rectanglePath stroke];
    [super drawRect:rect];
}

cho một người dưới đây nhập mô tả hình ảnh ở đây


Các góc không bị cong.
Vivek Tyagi

3

Dành cho Swift 5

extension UIView {
    func addDashBorder() {
        let color = UIColor.white.cgColor

        let shapeLayer:CAShapeLayer = CAShapeLayer()

        let frameSize = self.frame.size
        let shapeRect = CGRect(x: 0, y: 0, width: frameSize.width, height: frameSize.height)

        shapeLayer.bounds = shapeRect
        shapeLayer.name = "DashBorder"
        shapeLayer.position = CGPoint(x: frameSize.width/2, y: frameSize.height/2)
        shapeLayer.fillColor = UIColor.clear.cgColor
        shapeLayer.strokeColor = color
        shapeLayer.lineWidth = 1.5
        shapeLayer.lineJoin = .round
        shapeLayer.lineDashPattern = [2,4]
        shapeLayer.path = UIBezierPath(roundedRect: shapeRect, cornerRadius: 10).cgPath

        self.layer.masksToBounds = false

        self.layer.addSublayer(shapeLayer)
    }
}

Làm thế nào để thêm

vw.addDashBorder()

Làm thế nào để loại bỏ biên giới một lần nữa

let _ = vw.layer.sublayers?.filter({$0.name == "DashBorder"}).map({$0.removeFromSuperlayer()})

2

Tôi đã kết thúc việc tạo một IB Designable bằng cách sử dụng một số triển khai @Chris:

CurvedDashingBorderUIVIew.h:

#import <UIKit/UIKit.h>

IB_DESIGNABLE
@interface CurvedDashedBorderUIVIew : UIView

@property (nonatomic) IBInspectable CGFloat cornerRadius;
@property (nonatomic) IBInspectable UIColor *borderColor;
@property (nonatomic) IBInspectable int dashPaintedSize;
@property (nonatomic) IBInspectable int dashUnpaintedSize;

@property (strong, nonatomic) CAShapeLayer *border;

@end

CurvedDashingBorderUIVIew.m:

#import "CurvedDashedBorderUIVIew.h"

@implementation CurvedDashedBorderUIVIew

- (instancetype)init
{
    self = [super init];
    if (self) {
        [self setup];
    }
    return self;
}

- (instancetype)initWithCoder:(NSCoder *)coder
{
    self = [super initWithCoder:coder];
    if (self) {
        [self setup];
    }
    return self;
}

- (instancetype)initWithFrame:(CGRect)frame
{
    self = [super initWithFrame:frame];
    if (self) {
        [self setup];
    }
    return self;
}

-(void)setup
{
    _border = [CAShapeLayer layer];
    [self.layer addSublayer:_border];
}

-(void)layoutSubviews {
    [super layoutSubviews];
    self.layer.cornerRadius = self.cornerRadius;

    _border.strokeColor = self.borderColor.CGColor;
    _border.fillColor = nil;
    _border.lineDashPattern = @[[NSNumber numberWithInt:_dashPaintedSize],
                                [NSNumber numberWithInt:_dashUnpaintedSize]];
    _border.path = [UIBezierPath bezierPathWithRoundedRect:self.bounds cornerRadius:self.cornerRadius].CGPath;
    _border.frame = self.bounds;
}

@end

sau đó chỉ cần thiết lập nó trong xib / Storyboard:

nhập mô tả hình ảnh ở đây


2

Giải pháp Swift với lớp tùy chỉnh đã làm việc với autolayout

được tùy chỉnh từ @Iain Smith

class DashedBorderView: UIView {

    @IBInspectable var cornerRadius: CGFloat = 4
    @IBInspectable var borderColor: UIColor = UIColor.black
    @IBInspectable var dashPaintedSize: Int = 2
    @IBInspectable var dashUnpaintedSize: Int = 2

    let dashedBorder = CAShapeLayer()

    override init(frame: CGRect) {
        super.init(frame: frame)
        commonInit()
    }

    required init?(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)
        commonInit()
    }

    private func commonInit() {
        //custom initialization
        self.layer.addSublayer(dashedBorder)
        applyDashBorder()
    }

    override func layoutSublayers(of layer: CALayer) {
        super.layoutSublayers(of: layer)
        applyDashBorder()
    }

    func applyDashBorder() {
        dashedBorder.strokeColor = borderColor.cgColor
        dashedBorder.lineDashPattern = [NSNumber(value: dashPaintedSize), NSNumber(value: dashUnpaintedSize)]
        dashedBorder.fillColor = nil
        dashedBorder.cornerRadius = cornerRadius
        dashedBorder.path = UIBezierPath(rect: self.bounds).cgPath
        dashedBorder.frame = self.bounds
    }
}

2

Bạn chỉ có thể tạo một lớp IBDesignable như thế này:

import UIKit

@IBDesignable
class BorderedView: UIView {

    @IBInspectable var cornerRadius: CGFloat = 0

    @IBInspectable var borderWidth: CGFloat = 0

    @IBInspectable var borderColor: UIColor = UIColor.clear

    override func draw(_ rect: CGRect) {
        let path = UIBezierPath(roundedRect: rect, cornerRadius: cornerRadius)
        path.lineWidth = borderWidth

        borderColor.setStroke()

        let dashPattern : [CGFloat] = [10, 4]
        path.setLineDash(dashPattern, count: 2, phase: 0)
        path.stroke()
    }

}

Sau đó, chỉ phân lớp chế độ xem của bạn với BorderedView từ Xcode. Bằng cách này, bạn có thể đặt màu đường viền và độ rộng đường viền rất dễ dàng từ trình tạo giao diện!


2
extension UIView{
func addDashedLineBorder() {
    let color = UIColor.black.cgColor

    let shapeLayer:CAShapeLayer = CAShapeLayer()
    let frameSize = (self.frame.size)
    let shapeRect = CGRect(x: 0, y: 0, width: self.frame.width, height: self.frame.height)

    shapeLayer.bounds = shapeRect
    shapeLayer.position = CGPoint(x: frameSize.width/2, y: frameSize.height/2)
    shapeLayer.fillColor = UIColor.clear.cgColor
    shapeLayer.strokeColor = color
    shapeLayer.lineWidth = 1
    shapeLayer.lineJoin = kCALineJoinRound
    shapeLayer.lineDashPattern = [2,2]
    shapeLayer.path = UIBezierPath(rect: shapeRect).cgPath

    self.layer.addSublayer(shapeLayer)
}

} và gọi hàm này trong viewdidLoad () với độ trễ:

DispatchQueue.main.asyncAfter(deadline: .now() + 0.5) { 
            // Your code with delay
            self.YourView.addDashedBorder()
        }

Điều này sẽ bao gồm một phần 100% quan điểm của bạn.
Ayush Dixit

1

• Swift 5

• Hoạt động với tính năng tự động thanh toán

• Hoạt động với bán kính góc

import UIKit

    class DashedBorderView: UIView {

    private let dashedLineColor = UIColor.black.cgColor
    private let dashedLinePattern: [NSNumber] = [6, 3]
    private let dashedLineWidth: CGFloat = 4

    private let borderLayer = CAShapeLayer()

    init() {
        super.init(frame: CGRect.zero)

        borderLayer.strokeColor = dashedLineColor
        borderLayer.lineDashPattern = dashedLinePattern
        borderLayer.backgroundColor = UIColor.clear.cgColor
        borderLayer.fillColor = UIColor.clear.cgColor
        borderLayer.lineWidth = dashedLineWidth
        layer.addSublayer(borderLayer)
    }

    required init?(coder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }

    override func draw(_ rect: CGRect) {
        borderLayer.frame = bounds
        borderLayer.path = UIBezierPath(roundedRect: rect, cornerRadius: layer.cornerRadius).cgPath
    }
}

0

Trong swift 4 tôi đã tạo một phần mở rộng UIView với chức năng sau:

func borderDash(withRadius cornerRadius: Float, borderWidth: Float, borderColor: UIColor, dashSize: Int) {
    let currentFrame = self.bounds
    let shapeLayer = CAShapeLayer()
    let path = CGMutablePath()
    let radius = CGFloat(cornerRadius)

    // Points - Eight points that define the round border. Each border is defined by two points.
    let topLeftPoint = CGPoint(x: radius, y: 0)
    let topRightPoint = CGPoint(x: currentFrame.size.width - radius, y: 0)
    let middleRightTopPoint = CGPoint(x: currentFrame.size.width, y: radius)
    let middleRightBottomPoint = CGPoint(x: currentFrame.size.width, y: currentFrame.size.height - radius)
    let bottomRightPoint = CGPoint(x: currentFrame.size.width - radius, y: currentFrame.size.height)
    let bottomLeftPoint = CGPoint(x: radius, y: currentFrame.size.height)
    let middleLeftBottomPoint = CGPoint(x: 0, y: currentFrame.size.height - radius)
    let middleLeftTopPoint = CGPoint(x: 0, y: radius)

    // Points - Four points that are the center of the corners borders.
    let cornerTopRightCenter = CGPoint(x: currentFrame.size.width - radius, y: radius)
    let cornerBottomRightCenter = CGPoint(x: currentFrame.size.width - radius, y: currentFrame.size.height - radius)
    let cornerBottomLeftCenter = CGPoint(x: radius, y: currentFrame.size.height - radius)
    let cornerTopLeftCenter = CGPoint(x: radius, y: radius)

    // Angles - The corner radius angles.
    let topRightStartAngle = CGFloat(Double.pi * 3 / 2)
    let topRightEndAngle = CGFloat(0)
    let bottomRightStartAngle = CGFloat(0)
    let bottmRightEndAngle = CGFloat(Double.pi / 2)
    let bottomLeftStartAngle = CGFloat(Double.pi / 2)
    let bottomLeftEndAngle = CGFloat(Double.pi)
    let topLeftStartAngle = CGFloat(Double.pi)
    let topLeftEndAngle = CGFloat(Double.pi * 3 / 2)

    // Drawing a border around a view.
    path.move(to: topLeftPoint)
    path.addLine(to: topRightPoint)
    path.addArc(center: cornerTopRightCenter,
                radius: radius,
                startAngle: topRightStartAngle,
                endAngle: topRightEndAngle,
                clockwise: false)
    path.addLine(to: middleRightBottomPoint)
    path.addArc(center: cornerBottomRightCenter,
                radius: radius,
                startAngle: bottomRightStartAngle,
                endAngle: bottmRightEndAngle,
                clockwise: false)
    path.addLine(to: bottomLeftPoint)
    path.addArc(center: cornerBottomLeftCenter,
                radius: radius,
                startAngle: bottomLeftStartAngle,
                endAngle: bottomLeftEndAngle,
                clockwise: false)
    path.addLine(to: middleLeftTopPoint)
    path.addArc(center: cornerTopLeftCenter,
                radius: radius,
                startAngle: topLeftStartAngle,
                endAngle: topLeftEndAngle,
                clockwise: false)

    // Path is set as the shapeLayer object's path.
    shapeLayer.path = path;
    shapeLayer.backgroundColor = UIColor.clear.cgColor
    shapeLayer.frame = currentFrame
    shapeLayer.masksToBounds = false
    shapeLayer.setValue(0, forKey: "isCircle")
    shapeLayer.fillColor = UIColor.clear.cgColor
    shapeLayer.strokeColor = borderColor.cgColor
    shapeLayer.lineWidth = CGFloat(borderWidth)
    shapeLayer.lineDashPattern = [NSNumber(value: dashSize), NSNumber(value: dashSize)]
    shapeLayer.lineCap = kCALineCapRound

    self.layer.addSublayer(shapeLayer)
    self.layer.cornerRadius = radius;
}

0

Nếu bạn muốn nó hoạt động với angleRadius thì hãy thử nó

tagView.clipsToBounds = YES;
tagView.layer.cornerRadius = 20.0f;
tagView.backgroundColor = [UIColor groupTableViewBackgroundColor];

CAShapeLayer *yourViewBorder = [CAShapeLayer layer];
yourViewBorder.strokeColor = [UIColor blackColor].CGColor;
yourViewBorder.fillColor = nil;
yourViewBorder.lineDashPattern = @[@2, @2];
yourViewBorder.frame = tagView.bounds;

// Create the path for to make circle
UIBezierPath *maskPath = [UIBezierPath bezierPathWithRoundedRect:tagView.bounds
                                               byRoundingCorners:UIRectCornerAllCorners
                                                     cornerRadii:CGSizeMake(20, 20)];


yourViewBorder.path = maskPath.CGPath;

[tagView.layer addSublayer:yourViewBorder];

0

Swift 5+

import UIKit

class DashedBorderView: UIView {

    private let borderLayer = CAShapeLayer()

    init(color: UIColor, width: CGFloat = 1) {
        super.init(frame: CGRect.zero)

        let pattern: [NSNumber] = [NSNumber(value: Float(5 * width)), NSNumber(value: Float(3 * width))]

        borderLayer.backgroundColor = nil
        borderLayer.fillColor = nil
        borderLayer.lineDashPattern = pattern
        borderLayer.lineWidth = width
        borderLayer.strokeColor = color.cgColor

        layer.addSublayer(borderLayer)
    }

    required init?(coder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }

    override func draw(_ rect: CGRect) {
        borderLayer.frame = bounds
        borderLayer.path = UIBezierPath(roundedRect: rect, cornerRadius: layer.cornerRadius).cgPath
    }
}

Cách sử dụng:

// f.e. inside UIViewController

let viewWithDashedBorder = DashedBorderView(color: .red, width: 2)
view.addSubview(viewWithDashedBorder)
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.