Android知識點剖析系列:深入了解layout_weight屬性

前言

  Android中layout_weight這個屬性對于經常搗鼓UI的我們來說,肯定不會陌生。但是我們在真正使用這個屬性時,經常會出現一些莫名奇妙的布局效果;如果僅僅知其然而不知其所以然,一些意外的布局效果一定讓我們頗為頭疼。在本文中,將對layout_weight這個屬性詳細剖析。

正文

從代碼講起:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="match_parent"android:orientation="vertical"><Button android:layout_width="match_parent"android:layout_height="wrap_content"android:text="button1"/><Button android:layout_width="match_parent"android:layout_height="wrap_content"android:text="button2"/><Button android:layout_width="match_parent"android:layout_height="wrap_content"android:text="button3"/>
</LinearLayout>

效果圖如下:

我們可以發現這三個button并沒有將整個屏幕占據,而是根據內容適配大小。

我們在button2里面添加一個屬性 ?android:layout_weight="1" ,發現布局變成這樣了:

我們發現這次屏幕被三個button占據了,而且第一個和第三個button還是保持與內容適配大小,而第二個button而占據了剩余屏幕空間。

我們對上面的情況進行講解:

1、我們只有在button2使用了layout_weight屬性,并賦值為1;但是button1和button2并沒有使用這個屬性,根據API可以知道,他們的layout_weight屬性等于0。

2、LinearLayout如果顯式包含layout_weight屬性時,會measure兩次;第一次將正常計算三個button的寬高,第二次將結合layout_weight的值分配剩余的空間。

  通俗點來總結:Android系統先按照你設置的3個Button高度Layout_height=wrap_content,給你分配好他們3個的高度,然后會把剩下來的屏幕空間全部賦給Button2,因為只有他的權重值是1,這也是為什么Button2占了那么大的一塊空間。

這么講解大概大家也對layout_weight屬性有了比較清晰的認識了吧。

再來看看下面的代碼:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="match_parent"android:orientation="horizontal"><TextView android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_weight="1"android:text="1"android:background="#ff0000"/><TextView android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_weight="2"android:text="2"android:background="#00ff00"/><TextView android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_weight="3"android:text="3"android:background="#0000ff"/>
</LinearLayout>

在我們對這三個TextView的layout_width都設置為wrap_content時,我們會得到以下布局:

這個布局很符合我們上面的分析:

系統先給3個TextView分配他們的寬度值wrap_content(寬度足以包含他們的內容1,2,3即可),然后會把剩下來的屏幕空間按照1:2:3的比列分配給3個textview,所以就出現了上面的圖像。

如果我們將上面三個TextView的layout_width都設置為match_parent,分別給三個TextView設置他們的Layout_weight為1、2、2的話,會出現一個相反的布局效果:

我們大概可以分辨出,他們所占的寬的比例為3:1:1。這樣就出現一個另外一個效果:weight權重越大,控件所占的空間越小。

所以網上就有人這么總結:

在layout_width設置為match_parent的時候,layout_weight所代表的是你的控件要優先盡可能的大,但這個大是有限度的,即match_parent。
在layout_width設置為wrap_content的時候,layout_weight所代表的是你的控件要優先盡可能的小,但這個大是有限度的,即wrap_content。

這是對于這種僅僅記住怎么用而不是為什么這么用的做法,作為一個有追求有理想的程序員是不會茍同的,因為說不定哪天,咱們又忘了口訣,所以我們要從原理上理解為啥是這個樣子的。

?

依照上面的理解,這個現象的出現在于layout_width="fill_parent"這個原因導致的;開始下面的分析:

1、系統先給3個TextView分配他們所要的寬度match_parent,也就指定了每一個TextView都是填滿他的父控件,這里就是整個屏幕的寬度。

2、由于如果包含layout_width這個屬性,LinearLayout將會進行第二次measure,此時將會根據權重分配剩余的空間,在這里剩余空間=1個parent_width-3個parent_width=-2個parent_width (parent_width指的是屏幕寬度?)。

3、第一個TextView的實際所占寬度=parent_width(match_parent的寬度) + 1/5(他所占剩余空間的權重比列) * 剩余空間大小(-2 parent_width)=3/5parent_width

同理第二個TextView的實際所占寬度=parent_width + 2/5*(-2parent_width)=1/5parent_width;

第三個TextView的實際所占寬度=parent_width + 2/5*(-2parent_width)=1/5parent_width

由此我們就可以知道為什么是按3:1:1的這個比例顯示了。

?

如果我們將Layout_weight為1、2、3呢?第三個TextView直接消失了有木有!

我們可以按照上面的方法算一次就得出答案了:

1、系統先給3個TextView分配他們所要的寬度match_parent,也就指定了每一個TextView都是填滿他的父控件,這里就是整個屏幕的寬度。

2、由于如果包含layout_width這個屬性,LinearLayout將會進行第二次measure,此時將會根據權重分配剩余的空間,在這里剩余空間=1個parent_width-3個parent_width=-2個parent_width (parent_width指的是屏幕寬度?)。

3、第一個TextView的實際所占寬度=parent_width(match_parent的寬度)?+ 1/6(他所占剩余空間的權重比列)?* 剩余空間大小(-2 parent_width)=2/3parent_width

同理第二個TextView的實際所占寬度=parent_width + 2/6*(-2parent_width)=1/3parent_width;

第三個TextView的實際所占寬度=parent_width + 3/6*(-2parent_width)=0parent_width

所以三個TextView的顯示比例應該為2:1:0,第三個TextView就消失了,因為根據計算,都沒有空間可以分配給他了。

看到這里大家都清楚了解了這個計算原理,相信對于設計UI布局有所幫助,對于match_parent和wrap_content混合使用的UI布局也可以通過這個方法進行計算設計。

?

接下來順帶著也給大家說另外一個跟Layout_weight相關的屬性:weightSum

顧名思義,就是制定權重的總值,如果不指定weightSum,系統會將各個Layout_weight的值相加得出的總數作為權重總值,當然我們也可以在這里顯式指定,這里也方便我們布局所用,我就在下面舉一個關于weightSum屬性的應用:

?參見這樣一個效果,一個總是占據一半屏幕的Button

其實XML代碼很簡單:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="match_parent"android:gravity="center"android:weightSum="2"android:orientation="horizontal"><Button android:layout_width="0dp"android:layout_height="wrap_content"android:layout_weight="1"android:text="button"/>
</LinearLayout>

  開發文檔中對layout_weight屬性的有如下描述:定義weight總和的最大值。如果未指定該值,以所有子視圖的layout_weight屬性的累加值作為總和的最大值。一個典型的案例是:通過指定子視圖的layout_weight屬性為0.5,并設置LinearLayout的weightSum屬性為1.0,實現子視圖占據可用寬度的50。

  從上面的xml中我們可以知道我們設置了weightSum為2,而對于button設置了layout_width為0且layout_weight為1(也就是weightSum的一半),我們就可以得出上面一個效果,使得Button保持占據屏幕的一半,而不用通過硬編碼去實現。

?

代碼比較簡單,這里就不上demo了哈。

?

作者:enjoy風鈴
出處:http://www.cnblogs.com/net168/
本文版權歸作者和博客園共有,歡迎轉載,但未經作者同意必須保留此段聲明,且在文章頁面明顯位置給出原文連接,否則下次不給你轉載了

轉載于:https://www.cnblogs.com/net168/p/4227144.html

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/259495.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/259495.shtml
英文地址,請注明出處:http://en.pswp.cn/news/259495.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

C++ 中explicit的使用

C提供了關鍵字explicit&#xff0c;可以阻止不應該允許的經過轉換構造函數進行的隱式轉換的發生。聲明為explicit的構造函數不能在隱式轉換中使用。 C中&#xff0c; 一個參數的構造函數(或者除了第一個參數外其余參數都有默認值的多參構造函數)&#xff0c; 承擔了兩個角色。1…

BZOJ 1026 windy數 (數位DP)

題意 區間[A,B]上&#xff0c;總共有多少個不含前導零且相鄰兩個數字之差至少為2的正整數&#xff1f; 思路 狀態設計非常簡單&#xff0c;只需要pos、limit和一個前驅數pre就可以了&#xff0c;每次枚舉當前位時判斷是否與上一位相差2即可。一個需要注意的地方是第一位不用比較…

oracle診斷,Oracle?診斷事件列表

Oracle 診斷事件列表(2013-03-26 18:05:26)標簽&#xff1a;oracle診斷事件itORA-10000: controlfile debug event, name control_fileORA-10001: controlfile crash event1ORA-10002: controlfile crash event2ORA-10003: controlfile crash event3ORA-10004: controlfile cra…

考研數學:【以錯補錯】 降低做題出錯率

考研數學&#xff1a;以錯補錯 降低做題出錯率  眾所周知&#xff0c;數學需要做題&#xff0c;需要通過做題來鞏固掌握&#xff0c;但很多同學卻陷入了題海戰術&#xff0c;把所有的精力都放在數學練習上&#xff0c;一門心思做題&#xff0c;可幾個月下來卻沒有進展&#x…

treeview右鍵添加新節點

private void advTree1_MouseDown(object sender, MouseEventArgs e){if (e.Button MouseButtons.Right)//判斷你點的是不是右鍵{Point ClickPoint new Point(e.X, e.Y);Node CurrentNode advTree1.GetNodeAt(ClickPoint);if (CurrentNode ! null)//判斷你點的是不是一個節點…

RPM方式安裝MySQL5.6

RPM方式安裝MySQL5.6 rpm -ivh MySQL-server-5.6.25-1.linux_glibc2.5.x86_64.rpm rpm -ivh MySQL-client-5.6.25-1.linux_glibc2.5.x86_64.rpm rpm -ivh MySQL-devel-5.6.25-1.linux_glibc2.5.x86_64.rpm rpm -ivh MySQL-embedded-5.6.25-1.linux_glibc2.5.x86_64.rpm rpm -iv…

centos7靜默搭建oracle11g,Linux靜默安裝Oracle方法(centos7+oracle11g)

1、 增加虛擬內存ddif/dev/zero of/swapadd bs1024 count2006424mkswap /swapaddswapon /swapadd2、 檢查依賴包rpm -q binutils compat-libstdc-33 elfutils-libelf elfutils-libelf-devel gcc gcc-c glibc-2.5 glibc-common glibc-devel glibc-headers ksh libaio libaio-dev…

Ms SQL Server 約束和規則

一、SQL約束 約束定義關于列中允許值的規則&#xff0c;是強制完整性的標準機制。 使用約束優先于使用觸發器、規則和默認值。查詢優化器也使用約束定義生成高性能的查詢執行計劃。 1&#xff1a;類型 約束的類型一共分三種 域約束&#xff1a; 涉及一個或多個列&#xf…

Qt 獨立運行時伴隨CMD命令窗口

用Qt寫了一個小軟件&#xff0c;在把程序release后&#xff0c;打包分裝后&#xff0c;發現程序運行的時候會伴隨cmd命令窗口&#xff0c;可把我愁懷了 不過功夫不負有心人&#xff0c;在老師和我網友的幫助下&#xff0c;終于搞完了 CONFIG&#xff1a;指定工程配置和編譯參數…

Intellij IDEA 快捷鍵整理(dyCopy)

原文&#xff1a;http://www.cnblogs.com/tonycody/p/3257601.html【常規】CtrlShift Enter&#xff0c;語句完成“&#xff01;”&#xff0c;否定完成&#xff0c;輸入表達式時按 “&#xff01;”鍵CtrlE&#xff0c;最近的文件CtrlShiftE&#xff0c;最近更改的文件ShiftC…

長豎線及長括號

轉載&#xff1a;http://blog.sina.com.cn/s/blog_6005d4af0101861l.html 文章修改中要求把花括號和豎線變長&#xff0c;查了下發現下面的幾種方法&#xff1a; 1.花括號“{ }”變長&#xff1a; $\left\{...\right\}$&#xff1b; 或者用 $\Big\{...\Big\}$; 2.豎線“|”變長…

php 加入日志功能,php怎么寫一個日志功能的函數

我們要寫一個寫日志的函數,首先需要了解需求,我們一般怎么用日志函數呢?例如,程序執行到某一步,我希望把這個變量(地址)$user_address的值打印到日志,我們希望日志里是這么寫的:xx-xx-xx xx:xx $user_address : 上海市楊浦區xxxxx然后每一條日志都要換行,都有日期時間,假設 函…

Ant簡單工程的構建

1.在Ant的官方網站http://ant.apache.org/bindownload.cgi下載Ant最新版本&#xff08;我下載的是apache-ant-1.8.2-bin.zip&#xff09;&#xff0c;Ant無需安裝&#xff0c;直接解壓后設置環境變量即可。 2.測試Ant是否安裝成功&#xff0c;在控制臺運行ant命令&#xff0c;出…

MVC學習四

第七節 講述了增加model中類的屬性&#xff0c;由于數據庫中已存在表&#xff0c;表中沒有存在新加的列&#xff0c;所以可以刪除數據庫或者在數據庫中新增一列&#xff0c;另可以在controller中新增一個數據庫初始化的類&#xff0c;并在Global.asax添加初始化數據庫的代碼 …

mysqlpump 備份文件壓縮對比

mysqldump&#xff0c;使用single-transaction&#xff0c;通過管道使用gzip壓縮&#xff0c;20G單數據庫備份real8m15.291suser8m39.617ssys0m16.675s備份文件1.43Gmysqlpump&#xff0c;4線程&#xff0c;使用single-transaction&#xff0c;通過管道使用gzip壓縮&#xff0c…

如何讓Latex公式字體變小

轉載&#xff1a;http://blog.sina.com.cn/s/blog_5e16f1770100gdxh.html 第一種方法&#xff1a;用比較笨的方法&#xff0c;一個一個公式用 \begin{small} \begin{equation} \ldots \end{equation} \end{small} 第二種方法&#xff1a;定義新的變量環境 在開始 \newenvironme…

php 正則表達式驗證金額,php 正則表達式驗證數字

非負浮點數(正浮點數 0)&#xff1a;^d(.d)?$正浮點數 ^(([0-9].[0-9]*[1-9][0-9]*)|([0-9]*[1-9][0-9]*.[0-9])|([0-9]*[1-9][0-9]*))$非正浮點數(負浮點數 0) ^((-d(.d)?)|(0(.0)?))$負浮點數 ^(-(([0-9].[0-9]*[1-9][0-9]*)|([0-9]*[1-9][0-9]*.[0-9])|([0-9]*[1-9]…

ASP.NET MVC:會導致鎖定的會話

背景 一直沒有意識到會話的訪問會導致會話鎖定&#xff0c;現在想想這樣設計是非常合理的&#xff0c;不過某些情況下這樣會導致同一個會話的并發訪問非常低&#xff08;只能串行化&#xff09;&#xff0c;好在MS提供了機制讓我們控制這種鎖。 測試 A頁面&#xff1a;緩存寫入…

.NET重構(四):窗體繼承+模板方法,完美實現組合查詢

導讀&#xff1a;在機房重構中&#xff0c;有好些個查詢都是大同小異&#xff0c;最為顯著的就是組合查詢了。怎樣給自己省事兒&#xff0c;相同的東西能不能重復利用&#xff0c;就成了一個現實的問題。第一遍做機房的時候&#xff0c;使用的更多的是&#xff1a;復制粘貼。學…

github常見操作和常見錯誤!錯誤提示:fatal: remote origin already exists.

原文鏈接&#xff1a;http://blog.csdn.net/dengjianqiang2011/article/details/9260435 如果輸入$ git remote add origin gitgithub.com:djqiang&#xff08;github帳號名&#xff09;/gitdemo&#xff08;項目名&#xff09;.git 提示出錯信息&#xff1a;fatal: remote or…