亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 學院 > 開發設計 > 正文

Quartz2d繪圖

2019-11-14 18:29:57
字體:
來源:轉載
供稿:網友

今天看了一下Quartz 2D繪圖,我只想說:不要把繪圖和動畫那些東西當做一個很復雜的東西,其實只要你認真看還是可以理解的。他們并不難。啰嗦了幾句,現在直接進入正題:

前提是我們必須新建一個singleviewapplication。具體新建就不多說了,然后我們自己寫一個UIView的子類,然后創建子類加載到故事板中。(你也可以直接把故事板中的ViewControler的view的父類定義為你自己創建的類),然后我們的操作都是在drawRectangular:方法中實現的:(我采用的是直接修改View的父類為我自定義的類)

下面的就是代碼:我們一個一個來跟著代碼理解:

1、首先是最簡單的填充顏色:

- (void)drawRect:(CGRect)rect {//       setFill設置填充的顏色        [[UIColor redColor] setFill];   //隨后需要填充的顏色設置        UIRectFill(rect);  //用當前的顏色進行填充}

其中:

setFill方法:它的作用就是設置隨后填充操作用到的顏色。

UIRectFill():該方法就是用剛才設置的顏色進行填充。

結果如下:

我們沒有在ViewController中的修改任何屬性,這只是在自定義的View中完成的。

2、使用UIRectFrame畫一個矩形:

- (void)drawRect:(CGRect)rect {        //setStroke設置描邊的顏色        [[UIColor redColor] setStroke];        CGRect frame = CGRectMake(20, 30, 100, 300);        UIRectFrame(frame);}

其中:

setStroke:是設置隨后描邊用到的顏色

UIRectFrame():根據指定的rect畫一個框架。

結果如下:

3、然后是NSString類的繪制文本方法:

- (void)drawRect:(CGRect)rect {        NSString *s = [NSString stringWithFormat:@"zhangsan"];        //這里面drawAtPoint就是繪制文本的方法        [s drawAtPoint:CGPointMake(100, 300) withAttributes:@{NSFontAttributeName:[UIFont boldSystemFontOfSize:34]}];}

運行效果如下:

其中主要用的的方法就是drawAtPoint:那個方法

另外還有drawInRect方法。具體的方法介紹就不做過多介紹了。

4、畫三角形

- (void)drawRect:(CGRect)rect {    CGContextRef context = UIGraphicsGetCurrentContext();  //創建圖形上下文
  CGContextSaveGState(context); //保存當前圖形上下文設置 CGContextMoveToPoint(context, 20, 20); CGContextAddLineToPoint(context, 40, 100); CGContextAddLineToPoint(context, 160, 20); CGContextClosePath(context); [[UIColor redColor] setFill]; [[UIColor blackColor] setStroke]; CGContextDrawPath(context, kCGPathFillStroke);
  CGContextRestoreGState(context); //恢復圖形上下文設置}

效果如下:

其中遇到了新的東西:CGContextRef。不要害怕遇到CG,其實很簡單。

首先,一句

 CGContextRef context = UIGraphicsGetCurrentContext();  //創建圖形上下文

創建了上下文,什么是上下文?????你可以直接把他理解成一個Quartz 2D的繪畫環境。

就是對每個的繪畫操作都需要一個繪畫環境,然后才能進行繪畫操作。而UIGraphicsGetCurrentContext()就是獲取當前的繪畫環境,

然后里面有:

CGContextMoveToPoint:就是繪畫的起始點。

CGContextAddLineToPoint:就是從剛才繪畫起始點到你在這個函數中指定的點。

最后用CGContextClosePath去封閉這三個點組成的圖形。這樣一個三角形就出來。

NO,NO,還需要CGContextDrawPath來進行操作哦。它的作用是繪制當前路徑用提供的繪制模型:這里用的kCGPathFillStroke,就是描邊填充模型,其他的模型讀者可以自己查看。

忘了,忘了。還有兩個方法沒介紹:

CGContextSaveGState(context):它的作用是為當前的上下文保存一個復制。官方介紹是壓一份復制的當前繪畫狀態到繪畫狀態棧中。也就是壓棧操作。

CGContextRestoreGState(context):設置當前繪畫狀態 為最近保存的一份狀態??梢岳斫鉃槌鰲2僮?。

使用這兩個函數的原因:有事后需要多次改變圖形上下文對象的參數,這樣兩次繪制就可能相互影響,這就好像拿著蠟筆畫畫,每一次只能拿一個。為了防止相互影響所以要保存上下文設置,繪制完成后我們在用restore那個函數回復圖形上下文。

5、Quartz路徑

Core Graphics中有4種基本圖元用于描述路徑:點、線、弧和貝塞爾(Bezier)曲線。前兩種都不用介紹了都見過,后面的貝塞爾曲線和弧需要說一下。

?。嚎梢杂蓤A心點、半徑、起始角和結束角描述。圓是弧的一個特例。只需要這只起始角度為0,結束角度為360就可以了。

貝塞爾曲線:任何一條曲線都可以通過與他相切的控制線兩端的點的位置定義。具體我也不太理解,先沒看就。如果你理解的深刻可以給我說一下。

6、坐標變換

首先要理解:在Quartz 2D中的坐標系和UIKit坐標系是相反的。什么意思勒?就是

Quartz 2D坐標系原點在左下角,x向右為正方向,y向上為正方向

UIKit坐標系原點在左上角,x向右為正方向,y向下為正方向。

現在就讓我們繼續看看坐標變換把。

--------------------------------為了書寫方便下面的方法我直接提取出來了,只需要在drawRect:方法里面調用就行了--------------------------------

7、畫一張圖片:

//反向image- (void)drawImage {    /*     圖形的另一種操作就是變換:包括評議、縮放和旋轉等形式的變換     Quartz 2D坐標系和UIKit坐標系是相反的。     */    CGContextRef context = UIGraphicsGetCurrentContext();    UIImage *image = [UIImage imageNamed:@"test"];    CGImageRef cgImage = image.CGImage;    CGRect rect = CGRectMake(0, 0, image.size.width, image.size.height);    CGContextDrawImage(context, rect, cgImage);    //由于坐標系相反,所以圖形是返回來的。}

運行一下看看:

這圖片怎么長這樣,我開始也納悶,后來知道了,原來它是倒著放的。因為什么呢?因為Quartz 2D坐標系和UIKit的相反,所以會造成這種情況。

先不管反正了。反正畫了一個圖片到view上??纯创a。應該不用過多介紹了。CGContextDrawImage和剛才的CGContextDrawPath類似,只不過畫的東西不一樣罷了。里面要說下CGImageRef:它是一個結構體:封裝了位圖圖像的信息。而UIImaged的CGImage就是返回的這樣的實例。其他不說了。

8、2D圖形基本變換:

有平移變換、縮放變換、旋轉變換、x軸對稱變換、y軸對稱變換、坐標原點對稱變換。具體的都不詳細介紹了。應該都能理解那些變換的意思。

9、CTM變換矩陣

不要看著CTM幾個字母就害怕,其實它就是current transformation matrix的簡稱。就是當前矩陣變換。Quartz 2D提供了多種形式的變換,其中主要是CTM和仿射(Affine)變換??匆幌翪TM吧。

CTM主要涉及的函數有:

CGContextRotateCTM:旋轉變換

CGContextScaleCTM:縮放變換

CGContextTranslateCTM:平移變換

舉個簡單栗子:

- (void)tanslateImage {    CGContextRef context = UIGraphicsGetCurrentContext();    CGContextSaveGState(context);      UIImage *image = [UIImage imageNamed:@"test"];    CGImageRef cgImage = image.CGImage;//    CGContextTranslateCTM(context, 0, image.size.height);//    CGContextScaleCTM(context, -1, 1);    CGContextTranslateCTM(context, 50, 50);   //移動它的位置到100,50//    CGContextRotateCTM(context, 360);    CGRect rect = CGRectMake(0, 0, image.size.width, image.size.height);    CGContextDrawImage(context, rect, cgImage);    CGContextRestoreGState(context);}

看看結果:

使用了CGContextTranslateCTM,我們可以進行位置調整。這里我把位置向右向下移動了50.就成這樣了。哪些旋轉和縮小就不說了,自己嘗試一把。

這里給出來代碼,可以試試:

/**旋轉變換*/

#define radians(x) (x*M_PI/180)

- (void)rotateImage {    CGContextRef context = UIGraphicsGetCurrentContext();    CGContextSaveGState(context);    UIImage *image = [UIImage imageNamed:@"test"];    CGImageRef cgImage = image.CGImage;    CGContextRotateCTM(context, radians(-45.));    CGRect rect = CGRectMake(0, 0, image.size.width, image.size.height);    CGContextDrawImage(context, rect, cgImage);    CGContextRestoreGState(context);}
/**縮小變換*/- (void)scaleImage {    CGContextRef context = UIGraphicsGetCurrentContext();    CGContextSaveGState(context);    UIImage *image = [UIImage imageNamed:@"test"];    CGImageRef cgImage = image.CGImage;    CGContextScaleCTM(context, .2, .40);   //設置縮小大小    CGRect rect = CGRectMake(0, image.size.height, image.size.width, image.size.height);    CGContextDrawImage(context, rect, cgImage);}

最后再給出一個比較厲害的讓你的圖片旋轉過來的方法:

//正向image- (void)drawNormalImage {    CGContextRef context = UIGraphicsGetCurrentContext();    CGContextSaveGState(context);    //保留初始上下文    UIImage *image = [UIImage imageNamed:@"test"];    CGImageRef cgImage = image.CGImage;        CGContextTranslateCTM(context, 0, image.size.height);  //先做平移變換    CGContextScaleCTM(context, 1, -1);   //縮放變換x不變,y相反    CGRect rect = CGRectMake(0, 0, image.size.width, image.size.height);    CGContextDrawImage(context, rect, cgImage);    CGContextRestoreGState(context);   //還原初始上下文//    CGContextScaleCTM(context, -1, 1); //    CGContextDrawImage(context, rect, cgImage);    }

其實讓圖片正過來很簡單,先做了平移變換,然后又縮放了一把,就0k了。

------------------------------------------------看累了嗎?繼續看。馬上完--------------------------------

仿射變換(Affine)

也是一種2D變換,他可以重用變換,經過多次變換,每一種變換都可以用矩陣表示,通過多次矩陣相乘得到最后結果。(矩陣太難了。。。。。。。。。沒關系,理解就行了)

下面是一些訪射變換函數:

CGAffineMakeRotation:創建新的旋轉變換矩陣

CGAffineMakeScale:創建新的 縮放矩陣函數

CGAffineMakeTranslation:創建新的平移矩陣

CGAffineTransformRotate:旋轉矩陣

CGAffineTransformScale:縮放矩陣

CGAffineTransformTranslate:平移矩陣

CGContextConcatCTM:連接到CTM變換。

這么多函數。這么多函數。這么多函數。太難了。。。。。。不過沒事??纯聪旅娴睦幽銘摼涂梢岳斫饬?。

- (void)normalImageByAffine {    UIImage *image = [UIImage imageNamed:@"test"];    CGImageRef cgImage = image.CGImage;    CGContextRef context = UIGraphicsGetCurrentContext();    CGContextSaveGState(context);    CGAffineTransform myAffine = CGAffineTransformMakeTranslation(0, image.size.height);            myAffine = CGAffineTransformScale(myAffine, 1, -1);    CGContextConcatCTM(context, myAffine);    CGRect rect = CGRectMake(0, 0, image.size.width, image.size.height);    CGContextDrawImage(context, rect, cgImage);    CGContextRestoreGState(context);}

這個方法是通過仿射變換把剛剛倒過來的圖形放正??梢钥匆幌拢?/p>

CGAFffineTransform就是一個結構體,可以用來接收CGAffineTransformMakeTranslate創建的仿射(平移)矩陣。

然后又CGAffineTransformScale:通過里面的參數來設置縮放矩陣.然后用CGContextConcatCTM連接到CTM變換。這樣就實現了圖像的正過來。drawNormalImage方法實現的效果是一樣的。

----------------------------------------------------這里是結束----------------------------------------------------

沒有了,這里就是結束了。

給個代碼把?好的好的。下面就是源碼:寫的比較亂,能看懂就行了。

http://pan.baidu.com/s/1kTMUyX5

謝謝百度網盤給的空間。


發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb
国产一区二区三区免费视频| 欧美一区二区视频97| 视频直播国产精品| 中文字幕亚洲一区二区三区五十路| 亚洲男人天堂网站| 国产成人福利网站| 欧美猛交免费看| 亚洲欧美精品suv| 亚洲小视频在线| 欧美大片免费观看| 久久久噜噜噜久久久| 久久综合免费视频影院| 国产精品成人品| 日韩电影免费观看在线| 日韩免费电影在线观看| 亚洲天堂网站在线观看视频| 色综合久综合久久综合久鬼88| 不卡在线观看电视剧完整版| 91久热免费在线视频| 亚洲成人黄色在线观看| 日韩电影在线观看永久视频免费网站| 国产成人中文字幕| 欧美激情乱人伦| 91沈先生在线观看| 51ⅴ精品国产91久久久久久| 精品国产一区二区三区久久久| 欧美成人免费小视频| 正在播放亚洲1区| 欧美日韩国产色| 亚洲色图狂野欧美| 成人激情免费在线| 奇米四色中文综合久久| 美女啪啪无遮挡免费久久网站| 国产一区二区三区视频免费| 动漫精品一区二区| 激情久久av一区av二区av三区| 综合网日日天干夜夜久久| 亚洲综合自拍一区| 国产成人在线一区二区| 国产精品视频免费在线| 91精品国产高清久久久久久久久| 色综合久久精品亚洲国产| 国产精品久久久久久久久久三级| 亚洲第一中文字幕在线观看| 国产九九精品视频| 久久深夜福利免费观看| 精品国产91久久久| 三级精品视频久久久久| 成人免费看吃奶视频网站| 清纯唯美亚洲激情| 成人亚洲欧美一区二区三区| 成人观看高清在线观看免费| 久久精品99国产精品酒店日本| 亚洲视频欧洲视频| 538国产精品一区二区免费视频| 国产日韩在线免费| 中文字幕不卡在线视频极品| 日韩最新中文字幕电影免费看| 久久99青青精品免费观看| 91亚洲一区精品| 欧美中文在线观看| 久久影视电视剧免费网站| 国产精品自产拍高潮在线观看| 亚洲专区在线视频| 欧美精品在线免费观看| 亚洲91精品在线| 孩xxxx性bbbb欧美| 粉嫩老牛aⅴ一区二区三区| 97视频在线观看视频免费视频| 欧美成人免费网| 97视频在线观看网址| 国产精品影院在线观看| 欧美亚洲国产视频小说| 亚洲综合精品一区二区| 毛片精品免费在线观看| 亚洲人成在线免费观看| 久久99久久亚洲国产| 久久精品亚洲精品| 欧美大片大片在线播放| 中文字幕亚洲第一| 精品久久久国产精品999| 欧美在线视频一二三| 成人性生交大片免费看视频直播| 亚洲欧洲在线视频| 国模吧一区二区三区| 中文字幕一区日韩电影| 国产美女被下药99| 国产极品精品在线观看| 最近日韩中文字幕中文| 国产成人a亚洲精品| 久久男人av资源网站| 奇门遁甲1982国语版免费观看高清| 国产福利视频一区二区| 国产精品爽爽ⅴa在线观看| 欧美日韩中文字幕| 欧美日韩中文在线| 黄色精品一区二区| 精品久久久视频| 不用播放器成人网| 国产精品第3页| 在线一区二区日韩| 久久琪琪电影院| 国产日产亚洲精品| 2019av中文字幕| 亚洲精品资源在线| 日韩精品视频在线观看免费| 操人视频在线观看欧美| 欧美午夜女人视频在线| 久久精品成人欧美大片古装| 亚洲第一精品久久忘忧草社区| 中文字幕久久精品| 国产成人精品免费视频| 亚洲一区二区在线| 日韩精品在线播放| 热re91久久精品国99热蜜臀| 久久久久久久999精品视频| 亚洲男人天堂网| 久久精品国产精品亚洲| 日韩国产一区三区| 成人福利网站在线观看| 亚州国产精品久久久| 亚洲欧美精品在线| 国产精品99久久久久久白浆小说| 色噜噜久久综合伊人一本| 国产一区二区久久精品| 日韩美女免费观看| 久久久国产精品免费| 国产国产精品人在线视| 国产精品99久久久久久久久久久久| 国产亚洲精品一区二区| 久久免费视频网| 成年无码av片在线| 国产91成人在在线播放| 日韩av网站导航| 久久视频在线直播| 2023亚洲男人天堂| 欧美日韩国产激情| 青青久久av北条麻妃海外网| 欧美电影免费在线观看| 国产91网红主播在线观看| 国产成人精品免费久久久久| 亚洲欧美制服综合另类| 黑人精品xxx一区一二区| 国产精品扒开腿做爽爽爽的视频| 日韩精品中文字幕在线| 精品久久久久久久久久久| 成人黄色在线观看| 欧美一区在线直播| 亚洲深夜福利网站| 色综合久久精品亚洲国产| 欧美美女15p| 欧美夫妻性视频| 国产91色在线播放| 中文字幕av一区中文字幕天堂| 亚洲精品日韩欧美| 按摩亚洲人久久| 综合激情国产一区| 中文字幕亚洲一区| 亚洲高清一二三区| 色99之美女主播在线视频| 中文字幕日韩在线观看| 欧美一区二区三区四区在线| 日本亚洲欧洲色α| 日韩国产高清污视频在线观看|