国产精品电影_久久视频免费_欧美日韩国产激情_成年人视频免费在线播放_日本久久亚洲电影_久久都是精品_66av99_九色精品美女在线_蜜臀a∨国产成人精品_冲田杏梨av在线_欧美精品在线一区二区三区_麻豆mv在线看

深入解析Android的自定義布局

移動開發 Android
這篇文章是前Firefox Android工程師(現在跳槽去Facebook了) Lucas Rocha所寫,文中對Android中常用的四種自定義布局方案進行了很好地分析,并結合這四種Android自定義布局方案所寫的示例項目講解了它們各自的優劣以及四種方案之間的比較。

[[124174]]

寫在前面的話:

這篇文章是前Firefox Android工程師(現在跳槽去Facebook了) Lucas Rocha所寫,文中對Android中常用的四種自定義布局方案進行了很好地分析,并結合這四種Android自定義布局方案所寫的示例項目講解了它們各自的優劣以及四種方案之間的比較。看完這篇文章,也讓我對Android 自定義布局有了進一步的了解,于是趁著興頭,我把它翻譯成中文,原文鏈接在此

只要你寫過Android程序,你肯定使用過Android平臺內建的幾個布局——RelativeLayout, LinearLayout, FrameLayout等等。 它們能幫助我們很好的構建Android UI。

這些內建的布局已經提供了很多方便的構件,但很多情況下你還是需要來定制自己的布局。

總結起來,自定義布局有兩大優點:

  1. 通過減少view的使用和更快地遍歷布局元素讓你的UI顯示更加有效率;
  2. 可以構建那些無法由已有的view實現的UI。

在這篇博文中,我將實現四種不同的自定義布局,并對它們的優缺點進行比較。它們分別是: composite view, custom composite view, flat custom view, 和 async custom views。

這些代碼實現可以在我的github上的 android-layout-samples 項目里找到。這個app使用上面說到的四種自定義布局實現了相同的UI效果。它們使用 Picasso 來加載圖片。這個app的UI只是twitter timeline的簡化版本——沒有交互,只有布局。

好啦,我們先從最常見的自定義布局開始吧: composite view。

Composite View

Composite views (也被稱為 compound views) 是眾多將多個view結合成為一個可重用UI組件的方法中最簡單的。這種方法的實現過程是這樣的:

  1. 繼承相關的內建的布局。
  2. 在構造函數里面填充一個 merge 布局。
  3. 初始化成員變量并通過 findViewById()指向內部view。
  4. 添加自定義的API來查詢和更新view的狀態。

TweetCompositeViewcode 就是一個 composite view。它繼承于 RelativeLayout,并填充了 tweet_composite_layout.xmlcode 布局文件,***向外界暴露了 update()方法來更新它在adaptercode里面的狀態。

Custom Composite View

上面提到的TweetCompositeView 這種實現方式能滿足大部分的情況。但是碰到某些情況就不靈了。假設你現在想要減少子視圖的數量,讓布局元素的便利更加有效。

這個時候我們可以回過頭來看看,盡管 composite views 實現起來比較簡單,但是使用這些內建的布局還是有不少的開銷的——特別是 LinearLayout 和RelativeLayout這種比較復雜的容器。由于Android平臺內建布局的實現,在一次布局元素遍歷中,系統需要處理許多布局的結合和子視圖的多次測量——LinearLayout的 layout_weight 的屬性就是常見例子。

因此你可以為你的app量身定做一套子視圖的計算和定位邏輯,這樣的話你就可以極大的優化你的UI了。這種做法就是我接下來要介紹的 custom composite view.

顧名思義,一個 custom composite view 就是一個重寫了onMeasure() 和onLayout() 方法的 composite view 。因此相比之前的composite view繼承了 RelativeLayout,現在我們需要更進一步——繼承更抽象的ViewGroup。

TweetLayoutViewcode 就是通過這種技術實現的。注意現在這個實現不像 TweetComposiveView 繼承了LinearLayout ,這也就避免了 layout_weightcode這個屬性的使用了。

這個大費周折的過程通過ViewGroup’s 的measureChildWithMargins() 方法和背后的 getChildMeasureSpec() 方法計算出了每個子視圖的 MeasureSpec 。

TweetLayoutView 不能正確地處理所有可能的 layout 組合但是它也不必這樣。我們肯定需要根據特定需求來優化我們的自定義布局,這種方式可以讓我們寫出簡單高效的布局代碼。

Flat Custom View

如你所見,custom composite views 可以簡單地通過使用ViewGroup 的API就可以實現了。大部分時候,這種實現是可以滿足我們的需求的。

然而我們想更進一步的話——優化我們應用中的關鍵部分UI,比如 ListViews ,ViewPager等等。如果我們把所有的 TweetLayoutView 子視圖合并成一個單一的自定義視圖然后統一管理會怎么樣呢?這就是我們接下來要討論的 flat custom view——參看下面的圖片。

layouts

左邊為CUSTOM COMPOSITE VIEW ,右邊是FLAT CUSTOM VIEW

flat custom view 就是一個完全自定義的 view ,它完全負責內部的子視圖的計算,位置安排,繪制。所以它就直接繼承了View 而不是 ViewGroup。

如果你想找找現實生活中app是否存在這樣的例子,很簡單——開啟你手機“開發者模式”里面的 “顯示布局邊界”選項,然后打開 Twitter, Gmail, 或者 Pocket這些app,它們在列表UI里面都采用了 flat custom view。

使用 flat custom view最主要的好處就是可以極大地壓縮app 的視圖層級,進而可以進行更快的布局元素遍歷,最終可以減少內存占用。

Flat custom view 可以給你***的自由,就好像你在一張白紙上面作畫。但是這樣的自由是有代價的:你不能使用已有的那些視圖元素了,比如 TextView 和 ImageView。沒錯,在 Canvas 上面描繪文本 的確很簡單,但要你實現 ellipsizing(就是對過長的文本截斷)呢?同樣, 在 Canvas 上面 描繪圖片確很簡單,但是如何縮放呢?這些限制同樣適用于touch events, accessibility, keyboard navigation等等。

所以使用flat custom view的底線就是:只將flat custom view應用于你的app的UI核心部分,其他的就直接依賴Android平臺提供的view了。

TweetElementViewcode 就是 flat custom view。為了更容易的實現它,我創建了一個小小的自定義視圖框架叫做UIElement。你可以在  canvascode 這個包里找到它。

UIElement 提供了和Android平臺類似的 measure/layout API 。它包含了沒有圖像界面的 TextView 和 ImageView ,這兩個元素包含了幾個必需的特性——分別參看 TextElementcode 和ImageElementcode 。它還擁有自己的 inflatercode ,幫助從 布局資源文件code里面實例化UIElement  。

注意: UIElement 還處于非常早期的開發階段,所以還有很多缺陷,不過將來隨著不斷的改進UIElement 可能會變得非常有用。

你可能覺得TweetElementView 的代碼看起來很簡單,這是因為實際代碼都在 TweetElementcode里面——實際上TweetElementView 扮演托管的角色code

TweetElement  里面的布局代碼和TweetLayoutView‘非常類似,但是它使用 Picasso 請求圖片時卻不一樣code ,因為TweetElement  沒有使用ImageView。

Async Custom View

總所周知,Android UI 框架時單線程的 。 這樣的單線程會帶來一些限制。比如,你不能在主線程之外遍歷布局元素——然而這對復雜、動態的UI是很有益處的。

假如你的app 在一個ListView 中很布局比較復雜的條目(就像大多數社交app一樣),那么你在滑動ListView 就很有可能出現跳幀的現象,因為ListView 需要為列表中即將出現的新內容計算它們的視圖大小code和布局code。同樣的問題也會出現在GridViews,ViewPagers等等。

如果我們可以在主線程之外的線程上面對那些還沒有出現的子視圖進行布局遍歷是不是就可以解決上面的問題了?也就是說,在子視圖上面調用 measure() 和layout() 方法都不會占用主線程的時間了。

所以 async custom view 就是一個允許子視圖布局遍歷過程發生在主線程之外的實驗,這個idea是受到Facebook的Paperteam async node framework 這個視頻激發所想到的。

既然我們在主線程之外永遠接觸不到Android平臺的UI組件,因此我們需要一個API在不能直接接觸到這個視圖的前提下對這個視圖的內容進行測量、布局。這恰恰就是 UIElement 框架提供給我的功能。

AsyncTweetViewcode 就是一個 async custom view。它使用了一個線程安全的 AsyncTweetElementcode 工廠類code 來定義它的內容。具體過程是一個 Smoothie 子項加載器code 在一個后臺線程上對暫時不可見的AsyncTweetElement 進行創建、預測量和緩存(在內存里面,以便后來直接使用)。

當然在實現這個異步UI的過程中我還是妥協了一些,因為你不知道如何顯示任意高度的布局占位符。比如,當布局異步傳遞過來的時候你只能在后臺線程對它們的大小進行一次更改。因此當一個 AsyncTweetView 就要顯示的時候卻無法在內存里面找到合適的AsyncTweetElement ,這個時候框架就會強制在主線程上面創建一個AsyncTweetElement code

還有,預先加載的邏輯和內存緩存過期時間設置都需要比較好的實現來保證在主線程盡可能多地利用內存里面的緩存布局。比如,這個方案中使用 LRU 緩存code 就不是一個明智的選擇。

盡管還存在這些限制,但是使用 async custom view 的得到的初步結果還是很有前途的。當然我也會通過重構這個UIElement  框架和使用其他類別的UI在這個領域繼續探索。讓我們靜觀其變吧。

總結

在我們涉及到布局的時候,我們自定義的越深,我們能從Android平臺所能獲得的依賴就越少。所以我們也要避免過早優化,只在確實能實實在在改善app質量和性能的區域進行完全的布局自定義。

這不是一個非黑即白的決定。在使用平臺提供的UI元素和完全自定義的兩種極端之間還有很多方案——從簡單的composite views 到復雜的 async views。實際項目中,你可能會結合文中的幾種方案寫出優秀的app。

責任編輯:閆佳明 來源: greenrobot.me
相關推薦

2010-08-11 09:01:41

Flex4布局

2016-12-26 15:25:59

Android自定義View

2016-11-16 21:55:55

源碼分析自定義view androi

2021-08-16 14:45:38

鴻蒙HarmonyOS應用

2013-04-01 14:35:10

Android開發Android自定義x

2024-02-22 08:06:45

JSON策略解析器

2017-05-19 10:03:31

AndroidBaseAdapter實踐

2016-04-12 10:07:55

AndroidViewList

2010-02-07 14:02:16

Android 界面

2017-05-18 12:36:16

android萬能適配器列表視圖

2012-12-24 14:42:48

iOS自定義狀態欄

2025-01-10 09:28:25

2016-08-18 13:56:33

AndroidExecutorsubmit

2011-04-27 10:31:38

Java

2015-02-12 15:33:43

微信SDK

2010-07-22 09:25:21

Symbian開發

2021-11-30 11:17:23

自定義配置插件

2015-01-14 15:06:48

定義相機

2018-07-06 15:58:34

SpringSchemaJava

2013-01-09 17:22:38

Android開發Camera
點贊
收藏

51CTO技術棧公眾號

欧美插天视频在线播放| 韩国久久久久| 99福利在线观看| 涩爱av在线播放一区二区| 日韩激情欧美| 在线观看av一区二区| 精品三级国产| 欧美午夜无遮挡| 三上悠亚一区二区三区| 不卡电影一区二区三区| 2020国产在线| 国产欧美不卡| 精品国产一区二区三区久久狼5月| 国产在线观看不卡| 视频在线国产| 亚洲视频高清| 中文字幕视频在线免费欧美日韩综合在线看| 中文字幕第一页亚洲| www 久久久| 日本韩国视频一区二区| xxxx影院| 24小时成人在线视频| 国产欧美丝袜| 欧美日韩国产综合一区二区| h片在线播放| 日韩写真福利视频在线| 久草在线网址| 国产精品拍拍拍| 爱情岛论坛成人| 久久aⅴ国产欧美74aaa| 欧美高清视频看片在线观看| 久久亚洲精品小早川怜子66| 亚洲一区欧美激情| 亚洲精品视频99| 成年无码av片在线| 免费久久99精品国产自在现线| 欧美大片在线播放| 亚洲日韩欧美视频一区| 亚州av乱码久久精品蜜桃| 亚洲一区日韩精品| 免费91在线视频| 久久午夜电影网| 欧美日韩破处视频| 久久久影院一区二区三区| 免费高清在线一区| 搡女人真爽免费午夜网站| 亚洲成人网在线观看| 欧美视频日韩视频| 少妇av在线| 神马影院午夜我不卡影院| 神马久久桃色视频| 自拍偷在线精品自拍偷无码专区| 日韩午夜电影网| 久久毛片亚洲| 黄色www在线观看| 精品99一区二区三区| 日韩精品国产精品| 日韩电影毛片| 国产精品69页| 国产日产欧美一区二区三区| 2021国产在线| 国产91在线亚洲| 久久夜色精品国产| 亚洲欧洲性图库| 欧美日本一区二区高清播放视频| 特级毛片在线| 亚洲色欲久久久综合网东京热| 99精品欧美| 秋霞午夜在线观看| 久草资源站在线观看| 91av在线影院| 日韩亚洲在线观看| 精品一区二区三区不卡| 91在线导航| 日韩av电影院| 欧美视频在线看| 北岛玲heyzo一区二区| 99青草视频在线播放视| 日本最黄一级片免费在线| 精品一区在线| 盗摄系列偷拍视频精品tp| 成人自拍视频| 日本不卡电影| 羞羞影院欧美| 精品一区二区三区中文字幕视频| av中文在线资源| 精品处破学生在线二十三| 成人免费高清观看| 男人c女人视频| 久久久综合av| 色婷婷综合五月| 日本女优北野望在线电影| 亚洲午夜视频在线| 欧美性三三影院| 7777奇米亚洲综合久久| 国产精品视频二| 在线观看免费高清完整| 精品久久亚洲| 亚洲成aⅴ人片久久青草影院| 香蕉久久网站| 91夜夜蜜桃臀一区二区三区| 亚洲高清毛片| 久久精品日产第一区二区 | 亚洲图片激情小说| 欧美日韩在线视频首页| 古典武侠综合av第一页| 国产三级三级看三级| 中文字幕4区| 午夜成年人在线免费视频| 国产亚洲精aa在线看| 久热成人在线视频| 国产乱码精品| 国产免费久久精品| 亚洲第一综合天堂另类专| 337p亚洲精品色噜噜| 亚洲一区二区三区四区在线免费观看 | 国产爆乳无码一区二区麻豆| 欧美大片在线看| 亚洲国产免费av| 日韩av一区二区在线观看| 色综合久久天天| 日韩一区二区在线观看视频| 色综合久久综合网97色综合| 99久久99久久免费精品蜜臀| 91精品丝袜国产高跟在线| 福利视频午夜| 日韩中文一区二区| 一本色道69色精品综合久久| 第四色成人网| 一本大道久久a久久精品综合| 成人动漫视频在线观看免费| 精品99999| 综合电影一区二区三区| 日韩影院精彩在线| 亚洲午夜久久| 午夜欧美巨大性欧美巨大| 亚洲做受高潮| 国产精品videosex极品| 一本色道久久综合亚洲精品不卡| 精品一区二区三区欧美| 亚洲综合丝袜美腿| 在线免费观看不卡av| 在线观看欧美日韩| 成人av动漫在线| 久久久久久**毛片大全| 国产欧美精品在线观看| 岛国成人毛片| 精品久久免费观看| 国产精品www网站| 在线观看亚洲专区| 不卡电影一区二区三区| 自由日本语亚洲人高潮| 欧美美女被草| 在线国产网址| 91视频最新入口| 久久久久久a亚洲欧洲aⅴ| 欧美一区二区三区精品电影| 亚洲人成电影网站色xx| 欧美日韩一区在线观看| 精品三级av| 国产欧美日韩视频| 久久婷婷国产麻豆91天堂| 91精品黄色片免费大全| 欧美日韩国产精品一区二区不卡中文 | 免费yellow网站| 欧美色18zzzzxxxxx| 日韩精选视频| 国产精品av久久久久久麻豆网| 日韩欧美成人免费视频| 国产91免费视频| 欧美一区二区网站| 日韩欧美国产高清91| 亚洲精品老司机| 国产日韩欧美高清| av在线一区二区| 韩国v欧美v日本v亚洲v| 欧美aaaaaa午夜精品| 亚洲乱亚洲高清| 日韩av高清在线播放| 一级视频在线观看视频在线啦啦 | 国产精品永久免费视频| 视频一区二区在线观看| 欧美黑人巨大| 在线日本成人| 亚洲欧美区自拍先锋| 18性欧美xxxⅹ性满足| 吴梦梦av在线| 金瓶狂野欧美性猛交xxxx| 欧美久久久久| 亚洲精品久久久久| 国产欧美成人| 欧美日韩精品一区二区三区四区| 中文字幕日韩高清| 久久日韩精品| 中文字幕在线永久在线视频| 福利欧美精品在线| 欧美日韩一级二级三级| 国产在线日韩在线| 免费高清成人| 希岛爱理av免费一区二区|