因?yàn)橹绊?xiàng)目中接觸到很少動(dòng)畫,前幾天面試遇到有人問到關(guān)于動(dòng)畫的東西雌团,所以打算系統(tǒng)的學(xué)習(xí)一下動(dòng)畫燃领,在此記錄一下催促自己學(xué)習(xí)。
下邊開始今天的學(xué)習(xí)內(nèi)容锦援。
做之前先看一下要怎么做猛蔽,看一下這個(gè)圖片步驟。
我們?cè)O(shè)計(jì)好這些步驟灵寺,就可以開始做了:
* 第一步:創(chuàng)建layer
//創(chuàng)建layer? ?
CALayer *layer = [[CALayer alloc]init];? ?
layer.bounds = CGRectMake(0, 0, 200, 200);? ?
//? ? position:默認(rèn)情況下相當(dāng)于UIView的center? ?
layer.position = self.view.center;
//? ? CALayer的內(nèi)容曼库。可以設(shè)置為圖片略板,但是需要橋接毁枯。橋接不需要自己額外設(shè)置,編譯后編譯器會(huì)自動(dòng)提示叮称,讓Xcode自動(dòng)幫我們橋接就可以啦? ?
layer.contents = (__bridge id _Nullable)([UIImage imageNamed:@"clock.jpeg"].CGImage);? ?
//添加到view的layer上? ? [self.view.layer addSublayer:layer];
* 第二步 設(shè)置秒种玛、分藐鹤、時(shí)
秒針、時(shí)針設(shè)置都是一樣相同赂韵,所以只貼出了一個(gè)秒針的創(chuàng)建方法?
//? ? 設(shè)置秒針? ?
secondHand = [[UIView alloc]init];? ?
secondHand.backgroundColor = [UIColor orangeColor];? ?
secondHand.bounds = CGRectMake(0, 0, 1.2, 60);? ?
secondHand.center = self.view.center;?? ?
//? ? 錨點(diǎn)有X娱节、Y組成。錨點(diǎn)的數(shù)值范圍就是0~1右锨。0表示在最左邊或者最上邊括堤,1表示在最右邊或者最下邊。有點(diǎn)模糊是不绍移?再來張圖就更清楚了:?? ?? ?
//修改錨點(diǎn)? ?
secondHand.layer.anchorPoint = CGPointMake(0.5, 1);? ??
[self.view addSubview:secondHand];
* 創(chuàng)建CADisplayLink進(jìn)行每秒刷新悄窃,進(jìn)入秒針走動(dòng)動(dòng)畫(我們一開始想到的辦法就是用定時(shí)器,每一秒鐘刷新一次秒針蹂窖。但是使用了定時(shí)器之后轧抗,有一個(gè)問題。發(fā)現(xiàn)秒針比電腦上的稍微慢一點(diǎn)瞬测。是因?yàn)樗⑿骂l率和電腦不一樣横媚。)
NStimer與CADisplayLink的區(qū)別
*NSTimer占用系統(tǒng)資源較多
*NSTimer使用完后,一定要銷毀月趟,把它設(shè)置成nil灯蝴。
*CADisplayLink本來就在進(jìn)程中,每秒進(jìn)行60次孝宗。
*核心動(dòng)畫的時(shí)候穷躁,最好使用CADisplayLink
//? ? 使用CADisplayLink來刷新時(shí)鐘。
? ? //? ? 創(chuàng)建CADisplayLink
? ? CADisplayLink*link = [CADisplayLinkdisplayLinkWithTarget:selfselector:@selector(clockRunning)];
? ? //? ? 將創(chuàng)建的CADisplayLink加入到主線程中
[linkaddToRunLoop:[NSRunLoop mainRunLoop] forMode:NSDefaultRunLoopMode];
* 進(jìn)入每秒動(dòng)畫因妇,并獲取到當(dāng)前時(shí)間
//獲取本地時(shí)區(qū)
NSTimeZone *tZone = [NSTimeZone localTimeZone];
//? ? 獲取日歷
NSCalendar*calendar = [NSCalendarcurrentCalendar];
//獲取系統(tǒng)當(dāng)前時(shí)間
NSDate*currentDate = [NSDatedate];
//設(shè)置日歷的時(shí)區(qū)
[calendarsetTimeZone:tZone];
//取出當(dāng)前的時(shí)分秒
NSDateComponents *currentTime = [calendar components:NSCalendarUnitSecond|NSCalendarUnitMinute|NSCalendarUnitHour|NSCalendarUnitTimeZone fromDate:currentDate];
*? **下邊就是進(jìn)入到這篇最核心的地方问潭,根據(jù)當(dāng)前時(shí)間計(jì)算時(shí)分秒針弧度,然后讓自己設(shè)置的View進(jìn)行形變**
//? ? CGAffineTransform是一個(gè)用于處理形變的類,其可以改變控件的平移婚被、縮放狡忙、旋轉(zhuǎn)等,其坐標(biāo)系統(tǒng)采用的是二維坐標(biāo)系,即向右為x軸正方向,向下為y軸正方向
? ? CGFloatangle = (M_PI*2/60) * currentTime.second;
? ? secondHand.transform = CGAffineTransformMakeRotation(angle);
? ? CGFloatminuteAngle = (M_PI*2/60) * currentTime.minute;
? ? minuteHand.transform = CGAffineTransformMakeRotation(minuteAngle);
? ? CGFloathourAngle = (M_PI*2/12) * currentTime.hour;
? ? hourHand.transform = CGAffineTransformMakeRotation(hourAngle);
但是這上邊發(fā)現(xiàn)表已經(jīng)可以走了,但是有個(gè)問題址芯,當(dāng)秒針走動(dòng)一圈的時(shí)候灾茁,到最后時(shí)針才會(huì)走動(dòng)一下,我們想讓他每秒都會(huì)走谷炸,怎么做呢北专?
我們只需把下邊的分鐘、時(shí)轉(zhuǎn)換成秒進(jìn)行角度轉(zhuǎn)換就可以了淑廊;
?CGFloatangle = (M_PI*2/60) * currentTime.second;
secondHand.transform = CGAffineTransformMakeRotation(angle);
CGFloatminuteAngle = (M_PI*2/60/60) * (currentTime.minute *60+ currentTime.second);
minuteHand.transform = CGAffineTransformMakeRotation(minuteAngle);
CGFloathourAngle = (M_PI*2/60/60/12) * (currentTime.hour*60*60+currentTime.minute*60+currentTime.second);
//? ? CGFloat hourAccurate = (M_PI * 2 / 12) * currentTime.second / 60 / 60;
hourHand.transform = CGAffineTransformMakeRotation(hourAngle);
到這里我們就把這個(gè)時(shí)鐘最好了!
看下效果:
結(jié)束L嘏亍<境汀录粱!
參考文章:http://www.reibang.com/p/3a96cc95da5c