最新消息:欢迎访问Android开发中文站!商务联系微信:loading_in

Android UI布局问题总结

开发进阶 AndroidChina 6153浏览 0评论

在做新行程项目期间,遇到了很多关于UI布局的问题,这里总结一部分,都是一些小细节,希望能加深理解,以后少走弯路。

一 页面唤起后view创建完成的时间

Activity的生命周期为下图所示:

Activity在onCreate中使用setContentView()方法中载入xml布局,那么布局中的view是在何时完成创建的呢?在父布局中添加一个TextView,使用getLeft()、getRight()方法获取TextView在父布局中的左右边界的位置,打印出来可以看到

在onResume方法中获取的位置依然为0,按下home键后,将应用置为后台运行,可以看到


在onPause方法中打印出了位置,所以Activity中view创建完成的时间是在调用OnResume()方法返回之后,在此之前是无法获取view的位置信息的,fragment也是类似的,fragment的生命周期如图:

同样在布局中添加一个TextView,页面启动后打印TextView的位置,可以看到

在OnResume方法中也并没有打印出TextView得位置,按下home键,可以看到

打印出了TextView得位置,所以Fragment中view从创建完成到可见也是在OnResume()方法返回之后。那么如何才能知道activity已经完全加载,view已经可见了呢,可以根据OnWindowFocusChange()回调方法来判断。
OnWindowFocusChange()在OnResume()或者OnPause()方法调用完成之后被调用,可以保证activity已经完全加载,如图所示

二 复用View时避免之前View的属性的影响

在使用RecyclerView,ListView或者GridView时,为了节省内存,android系统将新创建的view直接复用上一个同类型的、当前已不可见的view,以RecyclerView为例,设置RecyclerView的item布局为一个ImageView加一个TextView,在adapter的

OnBindViewHolder()中设置第一个item的字体颜色为红色,代码如下:

@Override
    public void onBindViewHolder(MyViewHolder holder, int position) {
        String url = mUrlList.get(position);
        Picasso.with(mContext).load(url).into(holder.mIvPic);
        holder.mTvText.setText("这是第 " + position + "个");
        if(position == 0){
            holder.mTvText.setTextColor(Color.parseColor("#ff0000"));
        }
    }

运行效果如图所示:

咋看起来满足了要求,只有第一个item的字体标红了,但是上下滚动几次,使得别的view能够复用第一个view,可以看到

别的item也出现了字体被标红的效果,这是由于在view复用的时候,只是对特殊情况进行了处理,并没有对正常情况进行处理,简单来说就是只设置第一个位红色,没有设置非第一个为黑色,没有做到有if就有else,重写onBindViewHolder方法为:

    @Override
    public void onBindViewHolder(MyViewHolder holder, int position) {
        String url = mUrlList.get(position);
        Picasso.with(mContext).load(url).into(holder.mIvPic);
        holder.mTvText.setText("这是第 " + position + "个");
        if(position == 0){
            holder.mTvText.setTextColor(Color.parseColor("#ff0000"));
        }else{
            holder.mTvText.setTextColor(Color.parseColor("#000000"));
        }
    }

这样就不会出现非0个view字体标红的情况了,如图:

与此类似,当使用RecyclerView、ListView或者GridView时,要注意上一个view对之后view复用的影响,对于特殊属性的处理,要做到有if就要有else,避免属性不同的影响。

三 .9图片的可绘制区域

Android使用9patch处理图片以保证图片不会随着屏幕尺寸的变化而失真,如图:

背景图片会随着文字内容的变化动态调整大小而不会失真,在使用.9图片时候需要注意可操作区域的大小,每条边都要设置操作区域,如果设置.9图片的拉伸区域为:

那么在尖角上面的区域就是不可操作的区域,如图:

文本只存在于下方可操作区域内,上面的空间就无法使用了,正确的设置方法为:

保证可编辑区域的大小范围满足要求。

总结

还有一些小细节,比如RelativeLayout使用wrap_content属性,如果其内部View使用alignParentBottom或者alignParentRight等需要依赖父布局位置时,RelativeLayout就会撑满全屏等,都是一些小细节,陆续还会总结,以便加深记忆,提高效率。

该文章来自于阿里巴巴技术协会(ATA)

作者:萧锁

转载请注明:Android开发中文站 » Android UI布局问题总结

您必须 登录 才能发表评论!