viewstub应用

前言

我们经常遇到某些view或viewgroup,在一定的条件下才显示,显示的频率比较低,但是view或者viewgroup又比较复杂,比如viewgroup有很多的子view,用普通的VISIABLE,GONE的方法,我们大约需要以下几步操作

1.    把view写到layout内,inflate的时候inflate所有view

2.    findview,找到有可能用到的各个view

3.    把某些view设置为gone(当然你也可以在xml里写,但是对于listview还是必须每次setVisibility,避免复用带来的bug)

 

针对此类场景可以用viewstub,ViewStub是一个没有尺寸大小并且不会在布局中嵌套或渲染任何东西的轻量级的视图。好处就是,我们可以第一步不inflate所有view,对于某些复杂而又显示频率低的view可以放在viewstub内部,暂时不inflate,只inflate一个viewstub。第二部的时候不需要findview所有的view,第三部的时候就没必要setvisibility所有view了

举个例子

我们想要实现一个效果,默认不出现某些视图,点击按钮才出现,这些试图的数量很多,非常复杂(这里举例为viewContent),按钮点击的概率非常低,我们先来看第一种实现方法

方法一

public class MainActivity extends BaseFishActivity {
    View viewContent;
    Button btn;
    TextView tv;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        viewContent=findViewById(R.id.view_content);
        btn = (Button) findViewById(R.id.btn_new);
        tv = (TextView) findViewById(R.id.tv_new);

        viewContent.setVisibility(View.GONE);
        setButtonClick(R.id.btn,new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                viewContent.setVisibility(View.VISIBLE);
            }
        });
    }

}

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
    android:orientation="vertical"
    android:layout_height="match_parent" android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    android:paddingBottom="@dimen/activity_vertical_margin" tools:context=".MainActivity">

    <TextView android:text="@string/hello_world" android:layout_width="wrap_content"
        android:layout_height="wrap_content" />

    <Button
        android:id="@+id/btn"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="点我让viewstub出来"/>


    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:id="@+id/view_content"
        android:background="#00ff77"
        android:orientation="vertical">


        <TextView
            android:id="@+id/tv_new"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="我是新来的" />

        <Button
            android:id="@+id/btn_new"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="我是按钮" />
    </LinearLayout>

</LinearLayout>

这是最初想到的做法,我们再oncreate的时候

        btn = (Button) findViewById(R.id.btn_new);

       tv = (TextView) findViewById(R.id.tv_new);

这里为了demo简单只写了2个view,实际可能十几个,这些view一般都是用不到的,只有在按钮点击之后才会有意义

我们可以稍微优化下,把这些代码移到onClick内部

代码如下

public class MainActivity extends BaseFishActivity {
    View viewContent;
    Button btn;
    TextView tv;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        viewContent=findViewById(R.id.view_content);
        btn = (Button) findViewById(R.id.btn_new);
        tv = (TextView) findViewById(R.id.tv_new);

        viewContent.setVisibility(View.GONE);
        setButtonClick(R.id.btn,new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                if(btn==null){
                    btn = (Button) findViewById(R.id.btn_new);
                    tv = (TextView) findViewById(R.id.tv_new);
                }

                viewContent.setVisibility(View.VISIBLE);
            }
        });
    }

}

其实这里viewcontent可以根本不用渲染,用viewstub来代替,看下面的方案

用viewstub

public class MainActivity extends BaseFishActivity {

    ViewStub vs;
    View viewContent;
    Button btn;
    TextView tv;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        vs = (ViewStub) findViewById(R.id.viewstub);
        setButtonClick(R.id.btn, new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                viewContent = vs.inflate();
                btn = (Button) viewContent.findViewById(R.id.btn_new);
                tv = (TextView) viewContent.findViewById(R.id.tv_new);
            }
        });
    }

}

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#00ff77"
    android:orientation="vertical">

    <TextView
        android:id="@+id/tv_new"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="我是新来的" />

    <Button
        android:id="@+id/btn_new"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="我是按钮" />
</LinearLayout>

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
    android:orientation="vertical"
    android:layout_height="match_parent" android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    android:paddingBottom="@dimen/activity_vertical_margin" tools:context=".MainActivity">

    <TextView android:text="@string/hello_world" android:layout_width="wrap_content"
        android:layout_height="wrap_content" />

    <Button
        android:id="@+id/btn"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="点我让viewstub出来"/>

    <ViewStub
        android:id="@+id/viewstub"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout="@layout/aa"
       />


</LinearLayout>

 

对于现实概率低,结构复杂的viewgroup(超过5个view),比较适合用viewstub来替代。一般来说都是用在viewgroup上的,当然你也可以用在view上,如果这个view比较复杂,渲染成本高的话,比如上面的aa.xml也可以只写一个TextView

<TextView  xmlns:android="http://schemas.android.com/apk/res/android"  
    android:id="@+id/textview"  
     android:layout_width="wrap_content"  
     android:layout_height="wrap_content"  
     android:text="teeee"/>  

 总结

  1. 对于现实概率低,结构复杂的viewgroup(超过5个view),比较适合用viewstub来替代
  2. 只能inflate一次,inflate完毕之后viewstub就变为null了,第二次inflate会崩溃
  3. viewstub的布局参数应当写到viewstub内,比如margin值,写在layout内是无效的 ,但是padding是可以写在layout内的
  4. Viewstub对应的布局中不能用merge

 

http://blog.youkuaiyun.com/androiddevelop/article/details/37556307

 




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值