Android高仿小米時(shí)鐘

作者簡(jiǎn)介 原創(chuàng)微信公眾號(hào)郭霖 WeChat ID: guolin_blog

本篇是猴菇先生的第二篇投稿忠藤,高度還原了小米時(shí)鐘,效果很不錯(cuò),希望大家喜歡芍殖。

猴菇先生的博客地址:

http://blog.csdn.net/qq_31715429

正文

繼續(xù)練習(xí)自定義View。畢竟熟才能生巧谴蔑。一直覺(jué)得小米的時(shí)鐘很精美豌骏,那這次就搞它~這次除了練習(xí)自定義View,還涉及到使用 Camera 和 Matrix 實(shí)現(xiàn)3D效果隐锭。


一個(gè)這樣的效果窃躲,在繪制的時(shí)候最好選擇一個(gè)方向一步一步的繪制,這里我選擇由外到內(nèi)钦睡、由深到淺的方向來(lái)繪制蒂窒,代碼步驟如下:

1.首先老一套~新建 attrs.xml 文件,編寫(xiě)自定義屬性如時(shí)鐘背景色荞怒、亮色(用于分針洒琢、秒針、漸變終止色)褐桌、暗色(圓弧衰抑、刻度線(xiàn)、時(shí)針荧嵌、漸變起始色)呛踊,新建 MiClockView 繼承 View,重寫(xiě)構(gòu)造方法啦撮,獲取自定義屬性值谭网,初始化 Paint、Path 以及 畫(huà)圓赃春、弧需要的RectF 等東東愉择,重寫(xiě) onMeasure 計(jì)算寬高,這里不再啰嗦~

2.由于 onSizeChanged 方法在構(gòu)造方法、onMeasure 之后薄辅,又在 onDraw 之前要拂,此時(shí)已經(jīng)完成全局變量初始化,也得到了控件的寬高站楚,所以可以在這個(gè)方法中確定一些與寬高有關(guān)的數(shù)值脱惰,比如這個(gè) View 的 半徑啊、padding值 等窿春,方便繪制的時(shí)候計(jì)算大小和位置:

3.準(zhǔn)備工作做的差不多了拉一,那就開(kāi)始繪制,根據(jù)方向我先確定最外層的小時(shí)時(shí)間文本的位置及其旁邊的四個(gè)痪善颉:

注意兩位數(shù)字的寬度和一位數(shù)的寬度是不一樣的蔚润,在計(jì)算的時(shí)候一定要注意:

我計(jì)算文本的寬高一般采用的方法是,new一個(gè) Rect尺栖,然后再繪制時(shí)調(diào)用:

mTextPaint.getTextBounds(timeText,0, timeText.length(), mTextRect);

將這個(gè)文本的范圍賦值給這個(gè) mTextRect嫡纠,此時(shí) mTextRect.width() 就是這段文本的寬,mTextRect.height() 就是這段文本的高延赌。

畫(huà)文本旁邊的四個(gè)怀怠:

計(jì)算圓弧外接矩形的范圍別忘了加上圓弧線(xiàn)寬的一半。

4.再往里是刻度盤(pán)挫以,畫(huà)這個(gè)刻度盤(pán)的思路是現(xiàn)在底層畫(huà)一個(gè) mScaleLength 寬度的圓者蠕,并設(shè)置 SweepGradient 漸變,上面再畫(huà)一圈背景色的刻度線(xiàn)掐松。獲得 SweepGradient 的 Matrix 對(duì)象踱侣,通過(guò)不斷旋轉(zhuǎn) mGradientMatrix 的角度實(shí)現(xiàn)刻度盤(pán)的旋轉(zhuǎn)效果:

這里有一個(gè)全局變量mSecondDegree,即秒針旋轉(zhuǎn)的角度大磺,需要根據(jù)當(dāng)前時(shí)間動(dòng)態(tài)獲嚷站洹:

5.然后就是畫(huà)秒針,用 Path 繪制一個(gè)指向 12點(diǎn)鐘 的三角形杠愧,通過(guò)不斷旋轉(zhuǎn)畫(huà)布實(shí)現(xiàn)秒針的旋轉(zhuǎn):

6.看實(shí)現(xiàn)圖待榔,時(shí)針在分針之下并且比分針顏色淺,那我就先畫(huà)時(shí)針殴蹄,仍然是 Path,并且針頭為圓弧狀猾担,那么就用二階貝賽爾曲線(xiàn)袭灯,路徑為 moveTo( A),lineTo(B),quadTo(C,D),lineTo(E),close.

7.然后是分針,按照時(shí)針的思路:

8.最后由于path是close的绑嘹,所以干脆畫(huà)兩個(gè)圓蓋在上面:

9.終于畫(huà)完了稽荧,onDraw 部分就是這樣:

繪制的時(shí)候,尤其是像這樣圓形view工腋,靈活運(yùn)用:

這一套組合拳可以減少不少三角函數(shù)姨丈、角度弧度相關(guān)的計(jì)算畅卓。

10.辣么接下來(lái)就是如何實(shí)現(xiàn)觸摸使鐘表3D旋轉(zhuǎn)

借助 Camera類(lèi) 和 Matrix類(lèi),在構(gòu)造方法中:

MatrixmCameraMatrix=newMatrix();

CameramCamera=newCamera();

這段代碼除了 camera 的旋轉(zhuǎn)蟋恬、平移翁潘、縮放之類(lèi)的操作之外,剩下的代碼一般是固定的.

全局變量 mCameraRotateX 和 mCameraRotateY 應(yīng)該與此時(shí)手指觸摸坐標(biāo)相關(guān)聯(lián)動(dòng)態(tài)獲燃哒:

解釋一下 camera 旋轉(zhuǎn)角度為啥介么算:

floatrotateX=-(event.getY()-getHeight()/2);

floatrotateY=(event.getX()-getWidth()/2);

是這樣的拜马,當(dāng) camer.rotateX(x) 的 x為正時(shí),圖像繞X軸上半部分向里下半部分向外旋轉(zhuǎn)沐绒,也就是手指觸摸點(diǎn)就要往上移俩莽。這個(gè) x 就會(huì)與 event.getY() 的值有關(guān),x越大乔遮,繞X軸旋轉(zhuǎn)角度越大扮超,以圓心為原點(diǎn),往上 event.getY() - getHeight() / 2 的值為負(fù)蹋肮,故 float rotateX = -(event.getY() - getHeight() / 2)出刷;

而對(duì)于 camer.rotateY(y) 的y為正時(shí),圖像繞Y軸右半部分向里左半部分向外旋轉(zhuǎn)括尸,也就是手指觸摸點(diǎn)就要往右移巷蚪。這個(gè) y 就會(huì)與 event.getX() 的值有關(guān),y越大濒翻,繞Y軸旋轉(zhuǎn)角度越大屁柏,以圓心為原點(diǎn),往上 event.getX() - getWidth() / 2 的值為正有送,故 float rotateY = event.getX() - getWidth() / 2淌喻。

其他情況大家可以試一下,百度一下 camera 的坐標(biāo)以及它的旋轉(zhuǎn)是怎么轉(zhuǎn)的~

11.最后在 onTouchEvent 中松開(kāi)手指時(shí)加一個(gè)復(fù)原并晃動(dòng)的動(dòng)畫(huà)

終于寫(xiě)完了雀摘,這個(gè) MiClockView 適配也做的差不多了裸删,時(shí)間也是同步的手機(jī)時(shí)間,一般可以拿來(lái)就用了~

后來(lái)

額阵赠,經(jīng)過(guò)我的細(xì)心觀(guān)察涯塔。。發(fā)現(xiàn)撥動(dòng)時(shí)鐘時(shí)清蚀,時(shí)針匕荸、分針、秒針和刻度盤(pán)會(huì)有一個(gè)較小的偏移量枷邪,形成有層次的榛搔、近大遠(yuǎn)小的立體偏移效果。。本來(lái)打算用 matrix 和 camera 的 mCamera.translate(x, y, z) 方法改變 z 的值践惑,隨著z值增大腹泌,原先計(jì)算好的大小只會(huì)變小,并不會(huì)層疊偏移尔觉。凉袱。所以就隨著手指移動(dòng)動(dòng)態(tài)計(jì)算位移距離,然后在 onDraw() 的繪制不同零件的方法中不斷 mCanvas.translate(x, y) 達(dá)到類(lèi)似立體偏移的效果穷娱。

源碼地址:

https://github.com/MonkeyMushroom/MiClockView


完绑蔫。。泵额。配深。。嫁盲。篓叶。。羞秤。缸托。。瘾蛋。俐镐。。哺哼。佩抹。。取董。棍苹。。茵汰。

文章原創(chuàng)作者GuoLin 書(shū)籍推薦

郭林大神原創(chuàng)android 書(shū)籍:《第一行代碼 android》

淘寶鏈接: https://s.click.taobao.com/t?e=m%3D2%26s%3DgKUfuKdAZKocQipKwQzePOeEDrYVVa64K7Vc7tFgwiHjf2vlNIV67p2n%2BQBNMyE6Rku8%2Bpj6eJall3bs%2B3NRhNHnsKI%2BqxhyM0iVZhTFBom4YIorMPnmg8G0g2OJi%2FzmXHfenomYtn5EW9vzeG8LzfPUwktUBEmkxg5p7bh%2BFbQ%3D&pvid=10_106.6.161.154_3367_1490163222155

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末枢里,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子蹂午,更是在濱河造成了極大的恐慌栏豺,老刑警劉巖,帶你破解...
    沈念sama閱讀 216,372評(píng)論 6 498
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件豆胸,死亡現(xiàn)場(chǎng)離奇詭異奥洼,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī)配乱,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,368評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門(mén)溉卓,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人搬泥,你說(shuō)我怎么就攤上這事桑寨。” “怎么了忿檩?”我有些...
    開(kāi)封第一講書(shū)人閱讀 162,415評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵尉尾,是天一觀(guān)的道長(zhǎng)。 經(jīng)常有香客問(wèn)我燥透,道長(zhǎng)沙咏,這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,157評(píng)論 1 292
  • 正文 為了忘掉前任班套,我火速辦了婚禮肢藐,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘吱韭。我一直安慰自己吆豹,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,171評(píng)論 6 388
  • 文/花漫 我一把揭開(kāi)白布理盆。 她就那樣靜靜地躺著痘煤,像睡著了一般。 火紅的嫁衣襯著肌膚如雪猿规。 梳的紋絲不亂的頭發(fā)上衷快,一...
    開(kāi)封第一講書(shū)人閱讀 51,125評(píng)論 1 297
  • 那天,我揣著相機(jī)與錄音姨俩,去河邊找鬼蘸拔。 笑死,一個(gè)胖子當(dāng)著我的面吹牛哼勇,可吹牛的內(nèi)容都是我干的都伪。 我是一名探鬼主播,決...
    沈念sama閱讀 40,028評(píng)論 3 417
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼积担,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼陨晶!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起帝璧,我...
    開(kāi)封第一講書(shū)人閱讀 38,887評(píng)論 0 274
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤先誉,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后的烁,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體褐耳,經(jīng)...
    沈念sama閱讀 45,310評(píng)論 1 310
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,533評(píng)論 2 332
  • 正文 我和宋清朗相戀三年渴庆,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了铃芦。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片雅镊。...
    茶點(diǎn)故事閱讀 39,690評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖刃滓,靈堂內(nèi)的尸體忽然破棺而出仁烹,到底是詐尸還是另有隱情,我是刑警寧澤咧虎,帶...
    沈念sama閱讀 35,411評(píng)論 5 343
  • 正文 年R本政府宣布卓缰,位于F島的核電站,受9級(jí)特大地震影響砰诵,放射性物質(zhì)發(fā)生泄漏征唬。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,004評(píng)論 3 325
  • 文/蒙蒙 一茁彭、第九天 我趴在偏房一處隱蔽的房頂上張望总寒。 院中可真熱鬧,春花似錦理肺、人聲如沸偿乖。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,659評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)贪薪。三九已至,卻和暖如春眠副,著一層夾襖步出監(jiān)牢的瞬間画切,已是汗流浹背。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 32,812評(píng)論 1 268
  • 我被黑心中介騙來(lái)泰國(guó)打工囱怕, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留霍弹,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 47,693評(píng)論 2 368
  • 正文 我出身青樓娃弓,卻偏偏與公主長(zhǎng)得像典格,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子台丛,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,577評(píng)論 2 353

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