用UIBezierPath類自定義視圖

課題:如何來自定義一個(gè)UIView呢巩割?UIKit提供給我們很強(qiáng)大的UIView及它子類,但這些都不能滿足時(shí),我們就應(yīng)該自定義一個(gè)視圖亭珍。

  • 創(chuàng)建一個(gè)工程并創(chuàng)建一個(gè)繼承于UIView的自定義視圖類KNZCustomView
Snip20160928_2.png

Xcode已經(jīng)提供一個(gè)帶- (void)drawRect:(CGRect)rect方法的模板敷钾,我們只能在這個(gè)方法中去自定義視圖,參數(shù)rect就是你視圖繪圖范圍肄梨。

  • 在ViewController.m文件中創(chuàng)建一個(gè)自定義視圖
    <code>
    #import "ViewController.h"
    #import "KNZCustomView.h"
    @interface ViewController ()
    </br>@end
    @implementation ViewController
    - (void)viewDidLoad
    {
    [super viewDidLoad];
    //創(chuàng)建一個(gè)窗口大小的自定義KNZCustomView對(duì)象customView阻荒,并設(shè)置它背景顏色為白色
    KNZCustomView *customView = [[KNZCustomView alloc]initWithFrame:[UIScreen mainScreen].bounds];
    customView.backgroundColor = [UIColor whiteColor];
    self.view = customView;
    }
    @end
    </code>
    運(yùn)行一下,白白一片峭范,啥都沒有财松,因?yàn)槟氵€沒有開始畫圖呀!


    Snip20160928_4.png

我們先來畫一條直線

  1. 在KNZCustomView.m文件中纱控,先創(chuàng)建一個(gè)UIBezierPath路徑對(duì)象path
    <code>UIBezierPath *path = [[UIBezierPath alloc]init];</code>
    路徑就是你畫圖的想法辆毡,然后定義直線的起始點(diǎn)(100,100)
    <code>[path moveToPoint:CGPointMake(100, 100)];</code>
    兩個(gè)點(diǎn)決定一條直線,用另外一個(gè)點(diǎn)確定一條直線:
    <code>[path addLineToPoint:CGPointMake(200, 200)]; </code>
    我們已經(jīng)想好畫一條直線的想法-路徑了甜害,但現(xiàn)在運(yùn)行的話舶掖,還是什么都沒有,因?yàn)槟悻F(xiàn)在只有想法尔店,你還沒去畫出來眨攘。
    我們開始將這個(gè)想法畫出來吧主慰。
    <code>[path stroke];</code>
Snip20160928_6.png

運(yùn)行結(jié)果:


Snip20160928_7.png

終于看到有直線了,又細(xì)又黑的.......但我想要是一條比較粗的紅色的直線呢鲫售?
那我們就要在畫這個(gè)想法時(shí)共螺,再添加多一點(diǎn)想法了
<code>
path.lineWidth = 10;
[[UIColor redColor]setStroke];
[path stroke];
</code>

關(guān)于更加多的想法,你可以看我翻譯的UIBezierPath類文章中的屬性和方法:http://www.reibang.com/p/5f9e047865df

再運(yùn)行

Snip20160928_8.png

一條又紅又粗的直線就畫出來了情竹!Bingo!

使用UIBezierPath思維方式就是先創(chuàng)建一個(gè)UIBezierPath對(duì)象藐不,也就是畫圖的想法,這個(gè)時(shí)候想法為空秦效。然后對(duì)這個(gè)路徑添加畫圖的想法:畫線段雏蛮?畫圓?畫悔逯荨挑秉?畫矩形?什么顏色苔货?多寬犀概?是描邊還是填充?詳細(xì)內(nèi)容還得看UIBezierPath類中的說明夜惭。

我們先來畫一個(gè)內(nèi)切圓形吧阱冶!

  1. 在KNZCustomView.m文件中滥嘴,用UIBezierPath的類方法+ bezierPathWithArcCenter:radius:startAngle:endAngle:clockwise:快速創(chuàng)建路徑對(duì)象path若皱,里面為一個(gè)畫圓的想法镊叁。
Snip20160928_9.png

要求輸入五個(gè)實(shí)參:圓的圓心、半徑走触、開始角度晦譬、終止角度、描繪方向互广。

2.圓心為窗口中心點(diǎn)敛腌,半徑為內(nèi)切圓時(shí)半徑(不是窗口width就是height的長度的一半),開始角度為0惫皱,終止角度為2倍的M_PI(角度單位為弧度像樊,M_PI為一個(gè)π旅敷,一個(gè)圓形為2π),描繪方向?yàn)轫槙r(shí)針方向(設(shè)置YES為順時(shí)針涂滴,NO為逆時(shí)針)友酱。
<code>
CGPoint center =CGPointMake(rect.size.width*0.5,rect.size.height *0.5);
//MIN(A,B)C語言標(biāo)準(zhǔn)函數(shù)柔纵,求A缔杉、B最小那個(gè)
CGFloat radius = MIN(rect.size.width, rect.size.height) * 0.5;
CGFloat startAngle = 0 ;
CGFloat endAngle = M_PI * 2;
UIBezierPath *path = [UIBezierPath bezierPathWithArcCenter:center radius:radius startAngle:startAngle endAngle:endAngle clockwise:YES];
</code>
已經(jīng)想好怎么去畫一個(gè)圓了,我們把它畫出來吧搁料!
<code>[path stroke];</code>
運(yùn)行


Snip20160928_10.png

我想將這個(gè)圓形全部用黃色填充加缘,并不是只畫個(gè)形狀出來而已,那我們就將stroke改為fill就可以簡單地實(shí)現(xiàn)了。
<code>
[[UIColor yellowColor]setFill];
[path fill];
</code>
運(yùn)行

Snip20160928_11.png

整個(gè)畫圖代碼中,沒有出現(xiàn)其它文章寫的難懂的圖形上下文,因?yàn)閁IBezierPath這個(gè)類已經(jīng)幫你封裝好了,你只要stroke或fill一下屉更,就可以將path對(duì)象畫出來树绩,是不是超簡單呢?
蘋果就在將復(fù)雜冗余的低級(jí)類封裝成高級(jí)類讓我們?nèi)ラ_發(fā)app蛛芥,讓我們專注于app用戶體驗(yàn)方面,而不是學(xué)習(xí)難懂的底層框架技術(shù)仅淑。

用UIBezierPath類畫一個(gè)復(fù)雜一點(diǎn)點(diǎn)的自定義View

說復(fù)雜称勋,也不是很復(fù)雜,放心涯竟,很容易懂的

還是在上一篇自定義視圖基礎(chǔ)上畫赡鲜,先創(chuàng)建一個(gè)UIBezierPath路徑對(duì)象
<code>UIBezierPath *path = [[UIBezierPath alloc]init];</code>
接著我想畫一個(gè)外接圓,然后再畫一系列半徑每次減少20的同心圓庐船。
外接圓半徑maxRadius
<code>
CGPoint center = CGPointMake(rect.size.width * 0.5, rect.size.height * 0.5);//圓心
CGFloat maxRadius = hypot(rect.size.width, rect.size.height) * 0.5;//圓半徑</code>

hypot(A,B)為C語言函數(shù)银酬,給出A、B求直角三角形斜邊長

畫一系列同心圓筐钟,第一個(gè)想到用for循環(huán)函數(shù)揩瞪,每一次畫的圓半徑為radius,每次畫完半徑就減少20篓冲,直到半徑小于0才結(jié)束
<code>
for (int radius = maxRadius; radius > 0; radius -= 20) {
[path addArcWithCenter:center radius:radius startAngle:0 endAngle:M_PI *2 clockwise:YES];
}
</code>
畫出來
<code>[path stroke];</code>

Snip20160928_12.png

運(yùn)行


Snip20160928_13.png

感覺已經(jīng)畫出來了李破,但那個(gè)線是怎么回事啊壹将?嗤攻?
原因是你每次畫一個(gè)圓半徑減少20,你沒有告訴path诽俯,我要從新的點(diǎn)開始畫妇菱,他就是自動(dòng)生成從上一個(gè)圓終點(diǎn)到下一個(gè)圓起始點(diǎn)的直線。
解決這個(gè)問題很簡單暴区,你每次還要告訴下一個(gè)圓恶耽,你要從哪個(gè)點(diǎn)開始畫就行了。
<code>[path moveToPoint:CGPointMake(center.x + radius, center.y)];</code>

Snip20160928_14.png

運(yùn)行

Snip20160928_15.png

看到這個(gè)同心圓颜启,暈了嗎偷俭?給它加粗點(diǎn)吧!還要設(shè)為紅色缰盏!


Snip20160928_17.png

再次運(yùn)行

Snip20160928_18.png

好吧涌萤!用UIBezierPath類畫圖就是這么簡單!口猜!

我寫的這個(gè)文章只是一個(gè)入門思想介紹负溪,交流最重要的是讓對(duì)方明白就好了,我自己在看技術(shù)文章時(shí)济炎,發(fā)現(xiàn)你們雖然自己學(xué)懂了川抡,但沒讓其他人都看懂。能讓一個(gè)小學(xué)生都能看懂的文章,才能讓知識(shí)傳播得更遠(yuǎn)崖堤。關(guān)于更加多的畫圖方法請(qǐng)查看我翻譯的UIBezierPath類資料侍咱。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市密幔,隨后出現(xiàn)的幾起案子楔脯,更是在濱河造成了極大的恐慌,老刑警劉巖胯甩,帶你破解...
    沈念sama閱讀 216,843評(píng)論 6 502
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件昧廷,死亡現(xiàn)場離奇詭異,居然都是意外死亡偎箫,警方通過查閱死者的電腦和手機(jī)木柬,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,538評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來淹办,“玉大人眉枕,你說我怎么就攤上這事〗课ǎ” “怎么了?”我有些...
    開封第一講書人閱讀 163,187評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵寂玲,是天一觀的道長塔插。 經(jīng)常有香客問我,道長拓哟,這世上最難降的妖魔是什么想许? 我笑而不...
    開封第一講書人閱讀 58,264評(píng)論 1 292
  • 正文 為了忘掉前任,我火速辦了婚禮断序,結(jié)果婚禮上流纹,老公的妹妹穿的比我還像新娘。我一直安慰自己违诗,他們只是感情好漱凝,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,289評(píng)論 6 390
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著诸迟,像睡著了一般茸炒。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上阵苇,一...
    開封第一講書人閱讀 51,231評(píng)論 1 299
  • 那天壁公,我揣著相機(jī)與錄音,去河邊找鬼绅项。 笑死紊册,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的快耿。 我是一名探鬼主播囊陡,決...
    沈念sama閱讀 40,116評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼芳绩,長吁一口氣:“原來是場噩夢(mèng)啊……” “哼!你這毒婦竟也來了关斜?” 一聲冷哼從身側(cè)響起示括,我...
    開封第一講書人閱讀 38,945評(píng)論 0 275
  • 序言:老撾萬榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎痢畜,沒想到半個(gè)月后垛膝,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,367評(píng)論 1 313
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡丁稀,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,581評(píng)論 2 333
  • 正文 我和宋清朗相戀三年吼拥,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片线衫。...
    茶點(diǎn)故事閱讀 39,754評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡凿可,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出授账,到底是詐尸還是另有隱情枯跑,我是刑警寧澤,帶...
    沈念sama閱讀 35,458評(píng)論 5 344
  • 正文 年R本政府宣布白热,位于F島的核電站敛助,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏屋确。R本人自食惡果不足惜纳击,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,068評(píng)論 3 327
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望攻臀。 院中可真熱鬧焕数,春花似錦、人聲如沸刨啸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,692評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽设联。三九已至加匈,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間仑荐,已是汗流浹背雕拼。 一陣腳步聲響...
    開封第一講書人閱讀 32,842評(píng)論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留粘招,地道東北人啥寇。 一個(gè)月前我還...
    沈念sama閱讀 47,797評(píng)論 2 369
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親辑甜。 傳聞我的和親對(duì)象是個(gè)殘疾皇子衰絮,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,654評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容

  • 18- UIBezierPath官方API中文翻譯(待校對(duì)) ----------------- 華麗的分割線 -...
    醉臥欄桿聽雨聲閱讀 1,065評(píng)論 1 1
  • UIBezierPath Class Reference 譯:UIBezierPath類封裝了Core Graph...
    鋼鉄俠閱讀 1,723評(píng)論 0 3
  • Quartz2D以及drawRect的重繪機(jī)制字?jǐn)?shù)1487 閱讀21 評(píng)論1 喜歡1一、什么是Quartz2D Q...
    PurpleWind閱讀 771評(píng)論 0 3
  • 基礎(chǔ)知識(shí) 使用UIBezierPath可以創(chuàng)建基于矢量的路徑磷醋,此類是Core Graphics框架關(guān)于路徑的封裝猫牡。...
    十里桃花不及你閱讀 855評(píng)論 0 5
  • 文|zj當(dāng)年明月 在多年的實(shí)際教學(xué)中淌友,最令老師和家長頭疼的事莫過“孩子作業(yè)拖拉,磨蹭的壞毛病”骇陈。 “孩子作業(yè)寫的太...
    阿jing閱讀 927評(píng)論 3 12