【原】iOS學習之Quartz2D(1),ios學習quartz2d
什麼是Quartz2D
1、Quartz 2D 是一個二維繪圖引擎,同時支援iOS和Mac系統
2、Quartz 2D 能完成的工作:
繪製圖形 : 線條\三角形\矩形\圓\弧等
繪製文字
繪製\產生圖片(映像)
讀取\產生PDF
\裁剪圖片
自訂UI控制項
圖形上下文
1、圖形上下文(Graphics Context):是一個 CGContextRef 類型的資料
2、圖形內容相關的作用:
儲存繪圖資訊、繪圖狀態
決定繪製的輸出目標(繪製到什麼地方去?)
相同的一套繪圖序列,指定不同的 Graphics Context,就可將相同的映像繪製到不同的目標上
3、Quartz2D 提供了以下幾種類型的 Graphics Context:
BitmapGraphics Context
PDFGraphics Context
WindowGraphics Context
LayerGraphics Context
PrinterGraphics Context
自訂view
1、如何利用 Quartz2D 繪製東西到 view 上?
2、自訂view的步驟
3、為什麼要在 drawRect 裡面繪圖
只有在這個方法裡面才能擷取到跟 View 的 layer 相關聯的圖形上下文
當這個View要顯示的時候才會調用drawRect繪製圖形
注意:rect是當前控制項的bounds
畫線
1、步驟:
2、直線
方式1:(最原始的繪圖方式)
// 1.擷取圖形上下文 // 目前我們所用的上下文都是以UIGraphics // CGContextRef Ref:引用 CG:目前使用到的類型和函數 一般都是CG開頭 CoreGraphics CGContextRef ctx = UIGraphicsGetCurrentContext(); // 2.描述路徑 // 建立路徑 CGMutablePathRef path = CGPathCreateMutable(); // 設定起點 // path:給哪個路徑設定起點 CGPathMoveToPoint(path, NULL, 0, 250); // 添加一根線到某個點 CGPathAddLineToPoint(path, NULL, 250, 0); // 3.把路徑添加到上下文 CGContextAddPath(ctx, path); // 4.渲染上下文 CGContextStrokePath(ctx);
方式2:(原生)
// 擷取上下文 CGContextRef ctx = UIGraphicsGetCurrentContext(); // 描述路徑 // 設定起點 CGContextMoveToPoint(ctx, 0, 0); CGContextAddLineToPoint(ctx, 250, 250); // 渲染上下文 CGContextStrokePath(ctx);
方式3:貝瑟爾路徑
// UIKit已經封裝了一些繪圖的功能 // 貝瑟爾路徑 // 建立路徑 UIBezierPath *path = [UIBezierPath bezierPath]; // 設定起點 [path moveToPoint:CGPointMake(0, 125)]; // 添加一根線到某個點 [path addLineToPoint:CGPointMake(250, 125)]; // 繪製路徑 [path stroke];
3、線的相關操作
原生
// 擷取上下文 CGContextRef ctx = UIGraphicsGetCurrentContext(); // 描述路徑 //起點 CGContextMoveToPoint(ctx, 50, 50); CGContextAddLineToPoint(ctx, 100, 50); // 設定起點 CGContextMoveToPoint(ctx, 80, 60); // 預設下一根線的起點就是上一根線終點 CGContextAddLineToPoint(ctx, 100, 200); // 設定繪圖狀態,一定要在渲染之前 // 顏色 [[UIColor redColor] setStroke]; // 線寬 CGContextSetLineWidth(ctx, 5); // 設定串連樣式 CGContextSetLineJoin(ctx, kCGLineJoinBevel); // 設定頂角樣式 CGContextSetLineCap(ctx, kCGLineCapRound); // 渲染上下文 CGContextStrokePath(ctx);
貝瑟爾路徑
UIBezierPath *path = [UIBezierPath bezierPath]; [path moveToPoint:CGPointMake(50, 50)]; [path addLineToPoint:CGPointMake(200, 200)]; // 線寬 path.lineWidth = 10; // 顏色 [[UIColor redColor] set]; [path stroke]; UIBezierPath *path1 = [UIBezierPath bezierPath]; [path1 moveToPoint:CGPointMake(0, 0)]; [path1 addLineToPoint:CGPointMake(30, 60)]; [[UIColor greenColor] set]; path1.lineWidth = 3; [path1 stroke];
比較:
從代碼中可以看出,原生的線操作只能將線繪製為一種樣式,但是貝瑟爾路徑的對線的操作可以根據路徑的不同來繪製不同樣式的線條
3、曲線
方式1(原生)
// 原生繪製方法 // 擷取上下文 CGContextRef ctx = UIGraphicsGetCurrentContext(); // 描述路徑 // 設定起點 CGContextMoveToPoint(ctx, 150, 50); // CGContextAddQuadCurveToPoint(CGContextRef cg_nullable c, CGFloat cpx, CGFloat cpy, CGFloat x, CGFloat y) // cpx:控制點的x // cpy:控制點的y // x, y 為線結束的點的座標 CGContextAddQuadCurveToPoint(ctx, 50, 50, 50, 150); // 渲染上下文 CGContextStrokePath(ctx);
方式2(貝瑟爾路徑)
// 圓弧 // + (instancetype)bezierPathWithArcCenter:(CGPoint)center radius:(CGFloat)radius startAngle:(CGFloat)startAngle endAngle:(CGFloat)endAngle clockwise:(BOOL)clockwise; // Center:圓心 // radius:半徑 // startAngle:開始角度 // endAngle:結束角度 // clockwise:YES:順時針 NO:逆時針 CGPoint center = CGPointMake(125, 125); UIBezierPath *path = [UIBezierPath bezierPathWithArcCenter:center radius:100 startAngle:0 endAngle:M_PI_2 clockwise:YES]; [path stroke];
4、扇形
未填充
// 扇形 CGPoint center = CGPointMake(125, 125); UIBezierPath *path = [UIBezierPath bezierPathWithArcCenter:center radius:100 startAngle:0 endAngle:M_PI_2 clockwise:YES]; // 添加一根線到圓心 [path addLineToPoint:center]; // 封閉路徑,關閉路徑:從路徑的終點到起點 [path closePath]; [path stroke];
代碼:
填充
// 扇形 CGPoint center = CGPointMake(125, 125); UIBezierPath *path = [UIBezierPath bezierPathWithArcCenter:center radius:100 startAngle:0 endAngle:M_PI_2 clockwise:YES]; // 添加一根線到圓心 [path addLineToPoint:center]; // 填充:必須是一個完整的封閉路徑,預設就會自動關閉路徑 [path fill];
代碼:
5、圓角矩形
// 圓角矩形 // + (instancetype)bezierPathWithRoundedRect:(CGRect)rect cornerRadius:(CGFloat)cornerRadius; // cornerRadius:圓角的弧度,當值為邊長的一半時,畫出來的映像為圓形 UIBezierPath *path = [UIBezierPath bezierPathWithRoundedRect:CGRectMake(20, 20, 200, 200) cornerRadius:50]; [path stroke]; // 填充:必須是一個完整的封閉路徑,預設就會自動關閉路徑// [path fill];
代碼:
相關操作同貝塞爾路徑的相關操作類似,大家可以試試,對以上內容有什麼建議的可以直接聯絡我,O(∩_∩)O謝謝!