解析layout_weight

UI布局是Android项目非常重要的一部分内容,我们知道Android一共包括五中布局方式:1.LinearLayout(线性布局);2.RelativeLayout(相对布局);3.TableLayout(表格布局);4.AbsoluteLayout(绝对布局);5.FrameLayout(帧布局)。但在实际项目当中,我们基本上只用到LinearLayout和RelativeLayout。现在我们一起了解一下LinearLayout中的一个非常重要的属性:layout_weight

android:layout_weight是指LinearLayout先给里面的控件分配完大小之后剩余空间的权重,这块可能大家不是特别好理解。不用着急,首先我们初学者要明白一个概念,那就是布局文件并不一定都要放在屏幕当中,例如下面一个例子:

<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:id="@+id/textView1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="@string/hello_world" />

     <TextView
        android:id="@+id/textView2"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="@string/hello_world" />

</LinearLayout></span>

两个TextView,textView1填满父元素,textView2也是填满父元素,其实是这样分布,textView2是放在屏幕外面的:

其次,很多初学者都以为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:id="@+id/textView1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="天气"
        android:background="#fff123" />

     <TextView
        android:id="@+id/textView2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="北京天安门"
        android:background="#123fff"/>

</LinearLayout></span>

运行结果:

可以看到两个TextView的宽度都是包裹内容,那么layout_weight的作用就是分配剩余白色空间的大小,比如我们都给两个控件的layout_weight设置成1,意思就是每个控件分配剩下白色区域的1/2:

<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:id="@+id/textView1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="天气"
        android:layout_weight="1"
        android:background="#fff123" />

     <TextView
        android:id="@+id/textView2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="北京天安门"
        android:layout_weight="1"
        android:background="#123fff"/>

</LinearLayout></span>

运行结果:

可以看到,每个控间都设置成包裹内容,然后给每个控件都设置了权重为1,但是两个控件的宽度明显不同,说明layout_weight属性确实分配的是剩余空间的大小。首先textView1得到了包裹它内容的宽度,然后再加上布置完所有控件剩余部分中自己所占的比例,就是自己的实际宽度;textView2同样也是如此。

以上我们设置的控件宽度都是包裹内容,那如果我们把控件的宽度设置成fill_parent会是如何呢

<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:id="@+id/textView1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="天气"
        android:layout_weight="1"
        android:background="#fff123" />

     <TextView
        android:id="@+id/textView2"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="北京天安门"
        android:layout_weight="1"
        android:background="#123fff"/>

</LinearLayout></span>

运行结果:

可以看到两个控件占的空间大小是相同的,如何解释呢:textView1和textView2的宽度都是fill_parent,那么剩余的宽度=屏幕的宽度(1 个fill_parent)-textView1的宽度(1个fill_parent)-textView2的宽度(1个fill_parent)=-1个fill_parent的宽度,因为我们给两个控件都设置了权重为1,那么textView1的宽度=1个fill_parent的宽度(自身的宽度)+1/2(-1个fill_parent的宽度)【layout_weight为其分配的权重所占的空间大小】=1/2个fill_parent的宽度,也就是屏幕的一半宽度,同样textView2也是这样。所以搞清楚剩余空间的大小是搞清楚laytou_weight作用的关键。这里我们可以这样总结一下:

剩余空间的大小=LinearLayout(权重所在的线性布局的大小)-我们给其中每一个控件分配的大小空间

这里剩余空间的大小并不都是正数,这一点大家要注意,明白剩余空间的概念,相信我们很容易就能按我们的需要给每个控件分配权重大小。

-------------------------------------------------------------------分割性---------------------------------------------------------------------------

下面是几个我常见的例子:

1.我们往往不会为了实现上面的效果,而让每个控件的大小都fill_parent,也就是说我们如何实现在控件为wrap_content的情况下实现如上那样等比例分配空间大小,而不会根据里面内容多少而获得不同的空间大小(如上上个效果图)。其实很简单:

<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:id="@+id/textView1"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:text="天气"
        android:layout_weight="1"
        android:background="#fff123" />

     <TextView
        android:id="@+id/textView2"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:text="北京天安门"
        android:layout_weight="1"
        android:background="#123fff"/>

</LinearLayout></span>

我们给每一个控件的宽度都设为0dp,这样剩余空间的大小=1个fill_parent的大小-textView1的大小(0)-textView2的大小(0)=1个fill_parent的大小,然后textView1的大小=0dp+1/2(1个fill_parent)=1/2fill_parent,也就是屏幕的一半,textView2同样.

2.我们在实际项目中会经常遇到这样一种布局样式

一个控件在屏幕的最左边,另一个控件在屏幕的最右边,如果不了解LinearLayout的layout_weight属性,我们会用RelativeLayout来实现这样的效果,那么现在我们了解了layout_weight,我们用layout_weitght非常容易就能实现这样的效果

<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:id="@+id/textView1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="天气"
        android:layout_weight="1"
        android:background="#fff123" />

     <TextView
        android:id="@+id/textView2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="设置"
        android:background="#123fff"/>

</LinearLayout></span>

可以看到,我们给textView1控件设置了layout_weight为1,没有为textView2设置权重,而且两个控件的宽度都是包裹内容,用我们上面的公式分析,textView1把剩余的空间全部占了,所以就把textView2控件挤到了屏幕的右边。

3.最后,我们看一个稍微简复杂点的例子

我们如何让第二列的对其方式符合上面的样子

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal">
        <TextView
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:text="1"/>
        <TextView
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:text="2"/>
        <TextView
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:text="3"/>
        <TextView
            android:layout_width="0dp"
            android:layout_weight="1"
            android:layout_height="wrap_content"
            android:text="4"/>
        <TextView
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:text="5"/>
    </LinearLayout>

    <LinearLayout
	        android:layout_width="match_parent"
	        android:layout_height="wrap_content"
	        android:orientation="horizontal">
	        <TextView
	            android:layout_width="match_parent"
	            android:layout_height="wrap_content"
	            android:layout_weight="3"
	            android:text="1"/>
	       <TextView
	            android:layout_width="match_parent"
	            android:layout_height="wrap_content"
	            android:layout_weight="4"
	            android:text="2"/>
	        <TextView
	            android:layout_width="match_parent"
	            android:layout_height="wrap_content"
	            android:layout_weight="4"
	            android:text="3"/>
	        <TextView
	            android:layout_width="match_parent"
	            android:layout_weight="4"
	            android:layout_height="wrap_content"
	            android:text="4"/>
    </LinearLayout>

</LinearLayout></span>

我们可以看到第二列的宽度都是fill_parent,权重是3:4:4:4,那么我们再来一起分析一下这个权重是如何得来的,首先我们计算第二列的剩余空间的大小=1个fill_parent(LinearLayout的宽度)-4个fill_parent(4个控件的宽度都为fill_parent,所以是4个fill-parent)=-3个fill_parent,那么根据我们所需textView1的宽度占屏幕的2/5,我们设textView1的权重为x,也就是1个fill_parent+(x/4)*(-3个fill_parent)=2/5fill_parent,得到x=4/5;同样的方法textView2,设其权重为y,1个fill_parent+(x/4)*(-3个fill_parent)=1/5fill_parent,得到y=16/15
,剩下的权重都为16/15,所以权重比应该是4/5:16/15:16/15:16/15,也就是3:4:4:4.

ok,到此位置layout_weight的总结全部结束!

时间: 2024-12-28 14:46:52

解析layout_weight的相关文章

layout_weight 全解析

[layout_weight 全解析] 参考:http://www.cnblogs.com/net168/p/4227144.html

Android技术14:Android中layout_weight属性解析

为了更好的对空间进行布局,在LinearLayout中使用layout_weight,然后对于这一属性,在有些书上或者Android的初学者直接认为layout_weight值越大,控件权重就越大,所占用的空间就越大或者layout_wight值越小,控件空间就越大.这两种都是片面的,没有真正认识到layout_weight含义以及如何布局.下面首先演示使用代码为什么会有这两种感觉. 1.演示权重成反比 LinearLayout设置水平布局,然后里面空间宽度为fill_parent,layout

Android 布局之layout_weight解析

Android 布局之layout_weight解析 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_paren

layout_weight及常见属性解析

我们看一下下面的代码 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:

android:layout_weight 属性解析

1.一个LinearLayout中有多个Textview,其中一个textview是多行时.它们会第一行对齐(根据父类方法基线对齐), 在LinearLayout中设置baselineAligned = "false" 可使控件对齐. 2.在横向的LinearLayout中使用layout_weight时,一般设置 layout_width = "0dp", 如下图就是先分配了"111111111111"的宽度后,再把剩余的宽度按1:2:3分别分

【FastDev4Android框架开发】实例解析之SwipeRefreshLayout+RecyclerView+CardView(三十五)

转载请标明出处: http://blog.csdn.net/developer_jiangqq/article/details/50087873 本文出自:[江清清的博客] (一).前言: 作为Android L开始,Google更新了新控件RecyclerView和CardView,这两个控件在之前的文章中已经做了详细介绍和使用,同时在前面还对下拉刷新组件SwipeRefreshLayout进行相关讲解.本来该专题不在更新了,正好昨天有一个群友问到了怎么样结合SwipeRefreshLayou

ChrisRenke/DrawerArrowDrawable源码解析

转载请注明出处http://blog.csdn.net/crazy__chen/article/details/46334843 源码下载地址http://download.csdn.net/detail/kangaroo835127729/8765757 这次解析的控件DrawerArrowDrawable是一款侧拉抽屉效果的控件,在很多应用上我们都可以看到(例如知乎),控件的github地址为https://github.com/ChrisRenke/DrawerArrowDrawable

chenglei1986/DatePicker源码解析(一)

DatePicker在android其实是有提供的一个控件,相信有不少的人使用过它,但是这个控件的外观我们只能做一些简单的设定(原生的),如果我们有更高需求,希望能自定义我们的datepicker的外观,希望赋予它更多的功能,我们就需要自定义一个datepciker控件. 在github上,我发现了一个chenglei1986/DatePicker的项目,可以实现上面的需求.地址是https://github.com/chenglei1986/DatePicker 这个自定义控件非常灵活,通过学

Android之ProgressBar读取文件进度解析

ProgressBar进度条, 分为旋转进度条和水平进度条,进度条的样式根据需要自定义,之前一直不明白进度条如何在实际项目中使用,网上演示进度条的案例大多都是通过Button点 击增加.减少进度值,使用方法incrementProgressBy(int),最简单的做法是在xml布局文件中放置ProgressBar空间,然 后再MainActivity中触发事件后执行incrementProgressBy(int),代码如下: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15