Quartz 2D簡單介紹

1、什麼是Quartz2D框架

 Quartz 2D是⼀個二維繪圖引擎,同時支持iOS和Mac系統。dom

咱們可使用Quartz 2D  API 來實現許多功能,如基本路徑的繪製、透明度、描影、繪製陰影、透明層、顏色管理、反鋸齒、PDF文檔生成和PDF元數據訪問。在須要的時候,Quartz 2D還能夠藉助圖形硬件的功能。ide

 Quartz 2D能完成的工做:函數

  繪製圖形 : 線條\三角形\矩形\圓\弧等atom

  繪製文字spa

  繪製\生成圖片(圖像).net

  讀取\生成PDFcode

  截圖\裁剪圖片orm

  自定義UI控件 繼承

  

  塗鴉\畫板

  手勢解鎖

2、Quartz2D在iOS開發中的價值

爲了便於搭建美觀的UI界面,iOS提供了UIKit框架,⾥⾯有各類各樣的UI控件 

UILabel:顯⽰文字
UIImageView:顯示圖片
UIButton:同時顯示圖片和⽂字(能點擊)

利⽤UIKit框架提供的控件,拼拼湊湊,能搭建和現實一些簡單、常見的UI界⾯

可是,有些UI界面極其複雜、⽽且⽐較個性化,⽤普通的UI控件沒法實現,這時能夠利用Quartz2D技術將控件內部的結構畫出來,自定義控件的樣子

其實,iOS中⼤部分控件的內容都是經過Quartz2D畫出來的
所以,Quartz2D在iOS開發中很重要的⼀個價值是:自定義view(自定義UI控件)

 

三.Quartz2D須知

Quartz2D的API是純C語⾔言的

Quartz2D的API來自於Core Graphics框架

須要導入CoreGraphics.framework

數據類型和函數基本都以CG做爲前綴

CGContextRef
CGPathRef
CGContextStrokePath(ctx); 

4、圖形上下文

圖形上下文(Graphics Context):是一個CGContextRef類型的數據

圖形上下文的做用:

(1)保存繪圖信息、繪圖狀態
(2)決定繪製的輸出目標(繪製到什麼地⽅去?) (輸出目標能夠是PDF⽂文件、Bitmap或者顯示器的窗口上)

相同的⼀套繪圖序列,指定不一樣的Graphics Context,就可將相同的圖像繪製到不一樣的目標上 


5、自定義view

如何利用Quartz2D⾃定義view?(⾃定義UI控件)

首先,得有圖形上下文,由於它能保存繪圖信息,而且決定着繪製到什麼地方去

其次,那個圖形上下⽂必須跟view相關聯,才能將內容繪製到view上面

⾃定義view的步驟:

(1)新建⼀個類,繼承自UIView

(2)實現-(void)drawRect:(CGRect)rect⽅法.而後在這個⽅方法中 :

1)取得跟當前view相關聯的圖形上下文;

2)繪製相應的圖形內容

3)利用圖形上下文將繪製的全部內容渲染顯示到view上面 

6、補充說明

1.drawRect:

(1)爲何要實現drawRect:⽅法才能繪圖到view上?

由於在drawRect:⽅法中才能取得跟view相關聯的圖形上下文

(2)drawRect:⽅法在何時被調用?

當view第一次顯示到屏幕上時(被加到UIWindow上顯示出來)

調用view的setNeedsDisplay或者setNeedsDisplayInRect:時 

2.drawRect:中取得的上下⽂

在drawRect:方法中取得上下文後,就能夠繪製東西到view上

View內部有個layer(圖層)屬性,drawRect:方法中取得的是一個Layer Graphics Context,所以,繪製的東西實際上是繪製到view的layer上去了

View之因此能顯示東西,徹底是由於它內部的layer 

7、Demo

1.餅狀圖Demo


- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event{

// 執行重繪

    [self setNeedsDisplay];

}


- (void)drawRect:(CGRect)rect {

  

    NSArray *data = @[ @30, @15, @5 , @17 , @3, @10, @20];

    

//  設置圓心

    CGPoint center = CGPointMake(rect.size.width / 2, rect.size.height / 2);

    

//  設置半徑

    CGFloat r = MIN(rect.size.width, rect.size.height) / 2;

    

//  起始弧度    結束弧度

    CGFloat start = 0;

    CGFloat end = 0;

    for (NSInteger i = 0; i <data.count; i++) {

//  結束弧度

        end = [data[i]floatValue ] / 100 * 2 * M_PI + start ;

//  建立路徑

        UIBezierPath *path = [UIBezierPath bezierPathWithArcCenter:center radius:r startAngle:start endAngle:end clockwise:YES];

        

//  鏈接圓心

        [path addLineToPoint:center];

        

//  設置餅的顏色

        [[self randomColor] set];

//   渲染

        [path fill];

        

       

        start = end;

        

    }

    

  }


// 隨機餅的顏色

- (UIColor *)randomColor{

    UIColor *color = [UIColor colorWithRed:(arc4random_uniform(256)/255.0) green:(arc4random_uniform(256)/255.0) blue:(arc4random_uniform(256)/255.0) alpha:1];

    return color;


}



}


二、柱狀圖Demo

- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event{

    [self setNeedsDisplay];

}

- (void)drawRect:(CGRect)rect {

    NSArray *data = @[@300, @150.65, @55.3, @507.7, @95.8, @700, @650.65];


    CGFloat w = rect.size.width / (data.count * 2 - 1) ;

    

    for (NSInteger i = 0; i < data.count; i++) {


        CGFloat x = i *2 * w;

        

        CGFloat h = [data[i]floatValue] / 1000 * rect.size.height;

        CGFloat y = rect.size.height - h;

        UIBezierPath *path = [UIBezierPath bezierPathWithRect:CGRectMake(x,y, w,h)];

        

        [[self randomColor]set];

        [path fill];

        

        

    }


}


- (UIColor *)randomColor{

    UIColor *color = [UIColor colorWithRed:(arc4random_uniform(256)/255.0) green:(arc4random_uniform(256)/255.0) blue:(arc4random_uniform(256)/255.0)alpha:1];

    return color;


}


3.進度條Demo

//思路:

//在控制器中將slider的值傳遞給自定義view

//在自定義View中,根據傳遞過來的值繪製弧

//建立一個與自定義view同樣大小的label來顯示下載進度


#import "CZView.h"


@interface CZView ()

@property(nonatomic, strong) UILabel *progressLabel;


@end

@implementation CZView


//重寫setProgress方法

- (void)setProgress:(CGFloat)progress{

    _progress = progress;

    

// 執行重繪。它不斷的根據你的滑塊的進度, 改變我扇形的面積,

    [self setNeedsDisplay];

//label 賦值

    self.progressLabel.text = [NSString stringWithFormat:@"已下載%.2f%%",self.progress * 100];


}


- (void)drawRect:(CGRect)rect {

    // Drawing code

    CGPoint center = CGPointMake(rect.size.width / 2, rect.size.height / 2);

    CGFloat r = MIN(rect.size.width, rect.size.height)/ 2;

    CGFloat start = -M_PI_2;

    CGFloat end = 2 * M_PI * self.progress + start;

    

    UIBezierPath *path = [UIBezierPath bezierPathWithArcCenter:center radius:r startAngle:start endAngle:end clockwise:YES];

    

    [path addLineToPoint:center];

    [[UIColor blueColor]set];

    

    [path fill];

    

}


//懶加載label

- (UILabel *)progressLabel{

    if(_progressLabel == nil){

        _progressLabel = [[UILabel alloc] init];

        _progressLabel.font = [UIFont systemFontOfSize:24.0];

        _progressLabel.textColor = [UIColor whiteColor];

        _progressLabel.textAlignment = NSTextAlignmentCenter;

        

        [self addSubview:_progressLabel];

        

    }

    return _progressLabel;

}


//設置frame

- (void)layoutSubviews{

    [super layoutSubviews];


    self.progressLabel.frame = CGRectMake(0, 0, self.bounds.size.width, self.bounds.size.height);


}

相關文章
相關標籤/搜索