Đưa ra các góc tròn UIView


577

Chế độ xem đăng nhập của tôi có một lượt xem có UIActivityViewmột UILabelcâu nói "Đăng nhập vào". Subview này có các góc không được làm tròn. Làm thế nào tôi có thể làm cho chúng tròn?

Có cách nào để làm điều đó trong xib của tôi không?


6
Làm một cái gì đó như thế này trong IB sẽ yêu cầu một hình ảnh được kết xuất sẵn với các góc được làm tròn
Ed Marty

9
Không nhất thiết là @ ed-marty, Câu trả lời này từ @Gujamin xứng đáng nhận được một số tín dụng hơn vì nó chỉ ra cách áp dụng thuộc cornerRadiustính cho bảng chỉ bằng Trình tạo giao diện, mà không phải sử dụng hình ảnh được kết xuất trước hoặc đặt mã vào mã.
djskinner

Câu trả lời:


1219

Thử cái này

#import <QuartzCore/QuartzCore.h> // not necessary for 10 years now  :)

...

view.layer.cornerRadius = 5;
view.layer.masksToBounds = true;

Lưu ý: Nếu bạn đang cố gắng áp dụng các góc tròn cho UIViewControllerchế độ xem của nó, thì nó không nên được áp dụng trong hàm tạo của trình điều khiển khung nhìn, mà thay vào đó -viewDidLoad, sau khi viewthực sự được khởi tạo.


6
Lưu ý rằng thuộc tính chỉ tồn tại trong iPhone 3.0, không phải phiên bản cũ hơn.
Kendall Helmstetter Gelner

5
Tôi chỉ cần nói rằng đây là một trong những câu trả lời thỏa mãn nhất mà tôi từng thấy trên SO. Kiểm tra ở đây trước tiên chỉ giúp tôi tiết kiệm được một giờ chiến đấu với trình chỉnh sửa hình ảnh và sẽ khiến cho quan điểm của tôi trở nên dễ vỡ hơn đối với các thay đổi màu sắc / kích thước. Cảm ơn!
Justin Searls

20
Lưu ý liên quan: bất kỳ ai quan tâm đến các tính năng trực quan hơn (ví dụ như bóng) để dễ dàng áp dụng cho UIView nên kiểm tra tham chiếu lớp CALayer. Hầu hết mọi thứ đều dễ dàng như đặt một hoặc hai giá trị thuộc tính, như câu trả lời ở trên: developer.apple.com/mac/l
Library / documentation / GraphicsImaging / Lỗi

6
@Ben Collins (hoặc bất kỳ ai khác có vấn đề này), hãy đảm bảo rằng chế độ xem của bạn đã được đặt "clip xem trước". Bạn có thể kiểm tra điều này trong trình xây dựng giao diện.
zem

2
điều này hoạt động rất tốt NHƯNG nếu bạn có nhiều góc tròn trong bất kỳ chế độ xem cuộn hoặc hoạt hình nào (tôi đã thử sử dụng chúng trong UITableView), hiệu suất của bạn sẽ bị ảnh hưởng rất nhiều. Chế độ xem bảng cuộn đẹp mắt nhanh chóng trở nên dễ vỡ :(
Slee

261

Bạn cũng có thể sử dụng tính năng Thuộc tính Thời gian chạy do Người dùng Xác định của trình tạo giao diện để đặt đường dẫn chính layer.cornerRadiusthành giá trị. Hãy chắc chắn rằng bạn bao gồm QuartzCorethư viện mặc dù.

Thủ thuật này cũng hoạt động để thiết lập layer.borderWidth tuy nhiên nó sẽ không hoạt động layer.borderColorvì điều này mong đợi CGColorkhông phải là a UIColor.

Bạn sẽ không thể thấy các hiệu ứng trong bảng phân cảnh vì các tham số này được đánh giá khi chạy.

Sử dụng Trình xây dựng giao diện để đặt bán kính góc


10
nhớ kiểm tra Clip Subviewstùy chọn để xem IB nữa
Peter

2
(hoặc) thêm Đường dẫn chính: layer.masksToBound, Loại: boolean: Đã kiểm tra
Amitabh

64

Bây giờ bạn có thể sử dụng danh mục nhanh chóng trong UIView (mã dưới ảnh) với @IBInspectable để hiển thị kết quả tại bảng phân cảnh (Nếu bạn đang sử dụng danh mục, chỉ sử dụng angleRadius chứ không phải layer.cornerRadius làm đường dẫn chính.

extension UIView {
    @IBInspectable var cornerRadius: CGFloat {
        get {
            return layer.cornerRadius
        }
        set {
            layer.cornerRadius = newValue
            layer.masksToBounds = newValue > 0
        }
    }
}

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


Và nếu bạn đang sử dụng một lớp con tùy chỉnh, hãy đảm bảo gắn thẻ nó @IBDesignableđể có bản xem trước trực tiếp trong IB! (Xem thêm tại nshipster.com/ibinspectable-ibdesignable )
clozach

56

Nhanh

Câu trả lời ngắn:

myView.layer.cornerRadius = 8
myView.layer.masksToBounds = true  // optional

Bổ sung trả lời

Nếu bạn đã đi đến câu trả lời này, có lẽ bạn đã thấy đủ để giải quyết vấn đề của mình. Tôi đang thêm câu trả lời này để đưa ra một lời giải thích trực quan hơn một chút về lý do tại sao mọi thứ làm những gì họ làm.

Nếu bạn bắt đầu với một thường xuyên, UIViewnó có góc vuông.

let blueView = UIView()
blueView.frame = CGRect(x: 100, y: 100, width: 100, height: 50)
blueView.backgroundColor = UIColor.blueColor()
view.addSubview(blueView)

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

Bạn có thể cung cấp cho nó các góc tròn bằng cách thay đổi thuộc cornerRadiustính của chế độ xem layer.

blueView.layer.cornerRadius = 8

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

Giá trị bán kính lớn hơn cho các góc tròn hơn

blueView.layer.cornerRadius = 25

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

và các giá trị nhỏ hơn cho các góc tròn ít hơn.

blueView.layer.cornerRadius = 3

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

Điều này có thể đủ để giải quyết vấn đề của bạn ngay tại đó. Tuy nhiên, đôi khi một khung nhìn có thể có một khung nhìn phụ hoặc một lớp con đi ra ngoài giới hạn của khung nhìn. Ví dụ: nếu tôi thêm một chế độ xem phụ như thế này

let mySubView = UIView()
mySubView.frame = CGRect(x: 20, y: 20, width: 100, height: 100)
mySubView.backgroundColor = UIColor.redColor()
blueView.addSubview(mySubView)

hoặc nếu tôi thêm một lớp con như thế này

let mySubLayer = CALayer()
mySubLayer.frame = CGRect(x: 20, y: 20, width: 100, height: 100)
mySubLayer.backgroundColor = UIColor.redColor().CGColor
blueView.layer.addSublayer(mySubLayer)

Sau đó tôi sẽ kết thúc với

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

Bây giờ, nếu tôi không muốn mọi thứ treo ngoài giới hạn, tôi có thể làm điều này

blueView.clipsToBounds = true

hoặc cái này

blueView.layer.masksToBounds = true

đưa ra kết quả này:

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

Cả hai clipsToBoundsmasksToBoundsđều tương đương . Nó chỉ là cái đầu tiên được sử dụng với UIViewvà thứ hai được sử dụng với CALayer.

Xem thêm


4
Tôi cũng muốn thêm rằng việc đặt bán kính góc thành một nửa cạnh ngắn hơn (trong trường hợp này blueView.frame.size.height/2) dẫn đến một góc được làm tròn hoàn hảo.
Johann Burgess

44

Một cách tiếp cận khác với cách mà Ed Marty đã làm:

#import <QuartzCore/QuartzCore.h>

[v.layer setCornerRadius:25.0f];
[v.layer setMasksToBounds:YES];

Bạn cần setM taskToBound cho nó để tải tất cả các đối tượng từ IB ... tôi gặp vấn đề khi chế độ xem của tôi bị làm tròn, nhưng không có các đối tượng từ IB: /

Điều này đã sửa nó = D hy vọng nó sẽ giúp!


48
Nó khác biệt như thế nào? khác với việc không sử dụng cú pháp dấu chấm?
user102008

3
[v.layer setM taskToBound: CÓ]; Dòng này là ma thuật, nó giải quyết vấn đề lớn của tôi
Cullen SUN

3
Tôi đã viết điều này khi tôi bắt đầu phát triển iOS và không biết có sự khác biệt giữa cú pháp dấu chấm và cú pháp dấu ngoặc. Vì vậy, tôi đã viết nó là "khác nhau". Mã của tôi cũng bao gồm nhập <> mà Ed Marty không có trong phản hồi ban đầu của anh ấy (sau này được chỉnh sửa) và do đó câu trả lời của tôi giúp mọi người khắc phục vấn đề của họ (còn gọi là không nhập).
Kristian Flatheim Jensen 8/03/2015

28

Như được mô tả trong bài đăng trên blog này , đây là một phương pháp để làm tròn các góc của UIView:

+(void)roundView:(UIView *)view onCorner:(UIRectCorner)rectCorner radius:(float)radius
{
    UIBezierPath *maskPath = [UIBezierPath bezierPathWithRoundedRect:view.bounds
                                                   byRoundingCorners:rectCorner
                                                         cornerRadii:CGSizeMake(radius, radius)];
    CAShapeLayer *maskLayer = [[CAShapeLayer alloc] init];
    maskLayer.frame = view.bounds;
    maskLayer.path = maskPath.CGPath;
    [view.layer setMask:maskLayer];
    [maskLayer release];
}

Phần thú vị của nó là bạn có thể chọn những góc bạn muốn làm tròn lên.


6
Thay vì chỉ cung cấp một liên kết đến một trang web bên ngoài, chúng tôi muốn các câu trả lời được khép kín ở đây, vì vậy tôi đã mang mã liên quan từ bài đăng blog được liên kết vào câu trả lời của bạn. Mọi người có thể truy cập bài đăng trên blog để biết thêm chi tiết, nhưng điều này đảm bảo rằng nội dung sẽ tồn tại nếu bài đăng trong câu hỏi biến mất. Ngoài ra, bạn đã đăng câu trả lời này cho một số câu hỏi khác nhau mà không thực sự hỏi điều tương tự. Những câu hỏi đã bị xóa và một câu hỏi đã được đóng lại như một bản sao của câu hỏi này. Chúng tôi muốn có câu trả lời được tạo ra để phù hợp với từng câu hỏi.
Brad Larson

5
Tiên tri. Bài viết trên blog là 404 bây giờ.
Anthony C

Cách tiếp cận này là Clean nhưng nó sẽ ẩn bất kỳ hiệu ứng bóng nào trên khung nhìn.
điển

19

Bạn cần nhập tệp tiêu đề đầu tiên <QuartzCore/QuartzCore.h>

 #import QuartzCore/QuartzCore.h>

[yourView.layer setCornerRadius:8.0f];
yourView.layer.borderColor = [UIColor redColor].CGColor;
yourView.layer.borderWidth = 2.0f;
[yourView.layer setMasksToBounds:YES];

Đừng bỏ lỡ để sử dụng - setMasksToBounds, nếu không, hiệu ứng có thể không được hiển thị.


2
Không cần nhập "QuartzCore / QuartzCore.h"
Sudhir Kumar

Có bạn cần phải nhập khẩu.
Lord Zsolt

3
@LordZsolt Có thể họ đã thay đổi điều đó với iOS7, nhưng bạn không cần nhập QuartzCore nữa.
Marc

14

Bạn có thể sử dụng UIViewlớp tùy chỉnh sau đây cũng có thể thay đổi màu và độ rộng đường viền. Vì đây là IBDesignalbeBạn cũng có thể thay đổi các thuộc tính trong trình tạo giao diện.

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

import UIKit

@IBDesignable public class RoundedView: UIView {

    @IBInspectable var borderColor: UIColor = UIColor.white {
        didSet {
            layer.borderColor = borderColor.cgColor
        }
    }

    @IBInspectable var borderWidth: CGFloat = 2.0 {
        didSet {
            layer.borderWidth = borderWidth
        }
    }

    @IBInspectable var cornerRadius: CGFloat = 0.0 {
        didSet {
            layer.cornerRadius = cornerRadius
        }
    }

}

6
UIView *view = [[UIView alloc] initWithFrame:CGRectMake(20, 50, 200, 200)];

view.layer.backgroundColor = [UIColor whiteColor].CGColor;
view.layer.cornerRadius = 20.0;
view.layer.frame = CGRectInset(v.layer.frame, 20, 20);

view.layer.shadowOffset = CGSizeMake(1, 0);
view.layer.shadowColor = [[UIColor blackColor] CGColor];
view.layer.shadowRadius = 5;
view.layer.shadowOpacity = .25;

[self.view addSubview:view];
[view release];

Áp dụng setM taskToBound rất quan trọng. Thiết lập màu nền và bóng đổ là không.
djskinner

3

Swift 4 - Sử dụng IBDesignable

   @IBDesignable
    class DesignableView: UIView {
    }

    extension UIView
    {

        @IBInspectable
        var cornerRadius: CGFloat {
            get {
                return layer.cornerRadius
            }
            set {
            layer.cornerRadius = newValue
        }
    }
}

Tôi xin lỗi, nhưng là một người mới phát triển iOS. Làm thế nào để giải pháp ngăn chặn layer.cornerRadiustrở lại trạng thái ban đầu? (ei làm thế nào để bảng phân cảnh của xcode biết cách đặt cornerRadiuschỉ sau khi bản gốc UIViewđược khởi tạo)?
AlanSTACK


3

- SwiftUI

Trong SwiftUI, bạn có thể sử dụng công cụ cornerRadiussửa đổi trực tiếp trên bất kỳ thứ gì Viewbạn muốn. Ví dụ về câu hỏi này:

Text("Signing In…")
    .padding(16)
    .background(Color.red)
    .cornerRadius(50)

Xem trước

Lưu ý rằng không có nhiều kim cương như bán kính, vì vậy ngay cả khi bạn đặt gócRadius hơn một nửa chiều cao , nó sẽ tròn một cách trơn tru.

Kiểm tra câu trả lời này để biết cách làm tròn các góc cụ thể trong SwiftUI


2

Vui lòng nhập Quartzcore frameworksau đó bạn phải đặt setMaskToBoundsthànhTRUE dòng này rất quan trọng.

Sau đó: [[yourView layer] setCornerRadius:5.0f];


2
UIView* viewWithRoundedCornersSize(float cornerRadius,UIView * original)
{
    // Create a white border with defined width
    original.layer.borderColor = [UIColor yellowColor].CGColor;
    original.layer.borderWidth = 1.5;

    // Set image corner radius
    original.layer.cornerRadius =cornerRadius;

    // To enable corners to be "clipped"
    [original setClipsToBounds:YES];
    return original;
}

2

Làm điều này theo chương trình trong obj c

UIView *view = [[UIView alloc] initWithFrame:CGRectMake(20, 50,    200, 200)];

view.layer.backgroundColor = [UIColor whiteColor].CGColor;
view.layer.cornerRadius = 20.0;
view.layer.frame = CGRectInset(v.layer.frame, 20, 20);

[view.layer.shadowOffset = CGSizeMake(1, 0);
view.layer.shadowColor = [[UIColor blackColor] CGColor];
view.layer.shadowRadius = 5;
view.layer.shadowOpacity = .25;][1]

[self.view addSubview:view];

Chúng tôi cũng có thể làm điều này từ stoaryboard.

 layer.cornerRadius  Number  5

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


2

nếu góc tròn không hoạt động trong viewDidload () thì tốt hơn là viết mã trong viewDidLayoutSubview ()

-(void)viewDidLayoutSubviews
{
    viewTextfield.layer.cornerRadius = 10.0 ;                                               
    viewTextfield.layer.borderWidth = 1.0f;
    viewTextfield.layer.masksToBounds =  YES;
    viewTextfield.layer.shadowRadius = 5;
    viewTextfield.layer.shadowOpacity = 0.3;
    viewTextfield.clipsToBounds = NO;
    viewTextfield.layer.shadowOffset = CGSizeMake(0.0f, 0.0f);
}

Hi vọng điêu nay co ich!


0

Bạn cũng có thể sử dụng một hình ảnh:

UIImage *maskingImage = [UIImage imageNamed:@"bannerBarBottomMask.png"];
CALayer *maskingLayer = [CALayer layer];
maskingLayer.frame = CGRectMake(-(self.yourView.frame.size.width - self.yourView.frame.size.width) / 2
                                , 0
                                , maskingImage.size.width
                                , maskingImage.size.height);
[maskingLayer setContents:(id)[maskingImage CGImage]];
[self.yourView.layer setMask:maskingLayer];

0

đặt góc Thuộc tính hấp dẫn cho chế độ xem vòng

đặt maskToBound Giá trị Boolean cho hình ảnh sẽ vẫn không được vẽ bên ngoài ranh giới bán kính góc

view.layer.cornerRadius = 5;

view.layer.masksToBounds = YES;

0

Sử dụng tiện ích mở rộng UIView:

extension UIView {    

func addRoundedCornerToView(targetView : UIView?)
{
    //UIView Corner Radius
    targetView!.layer.cornerRadius = 5.0;
    targetView!.layer.masksToBounds = true

    //UIView Set up boarder
    targetView!.layer.borderColor = UIColor.yellowColor().CGColor;
    targetView!.layer.borderWidth = 3.0;

    //UIView Drop shadow
    targetView!.layer.shadowColor = UIColor.darkGrayColor().CGColor;
    targetView!.layer.shadowOffset = CGSizeMake(2.0, 2.0)
    targetView!.layer.shadowOpacity = 1.0
}
}

Sử dụng:

override func viewWillAppear(animated: Bool) {

sampleView.addRoundedCornerToView(statusBarView)

}

0

Trong Swift 4.2 và Xcode 10.1

let myView = UIView()
myView.frame = CGRect(x: 200, y: 200, width: 200, height: 200)
myView.myViewCorners()
//myView.myViewCorners(width: myView.frame.width)//Pass View width
view.addSubview(myView)

extension UIView {
    //If you want only round corners
    func myViewCorners() {
        layer.cornerRadius = 10
        layer.borderWidth = 1.0
        layer.borderColor = UIColor.red.cgColor
        layer.masksToBounds = true
    }
    //If you want complete round shape, enable above comment line
    func myViewCorners(width:CGFloat) {
        layer.cornerRadius = width/2
        layer.borderWidth = 1.0
        layer.borderColor = UIColor.red.cgColor
        layer.masksToBounds = true
    }
}

-4

TRÊN Xcode 6 Hãy thử

     self.layer.layer.cornerRadius = 5.0f;

hoặc là

    self.layer.layer.cornerRadius = 5.0f;
    self.layer.clipsToBounds = YES;
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.