zoukankan      html  css  js  c++  java
  • 自定义组合控件

    1.将已经编写好的布局文件,抽取到一个类中去做管理,下次还需要使用此布局结构的时候,直接使用组合控件对应的对象.

    2.将组合控件的布局,抽取到单独的一个xml中

    3.通过一个单独的类,去加载此段布局文件.

    4.checkBox是否选中,决定SettingItemView是否开启,isCheck(){return checkbox.isCheck()}方法

    5.提供一个SettingItemView,切换选中状态的方法setCheck(boolean isCheck)

    自定义属性,(设置中心,有多个条目,在复用SettingItemView的时候,每一个条目对应的标示,描述内容都不一致)
    1.查看源码,定义属性时候做法
    sdk所在目录platformsandroid-16data esvaluesattrs.xml

      <resource>
        <declare-styleable name="TextView">
          <attr name="text" format="string"/>
        </declare-styleable>
      <resource>
    2.给SettingItemView定义属性,工程resvaluesattrs.xml
      <resource>
        <declare-styleable name="SettingItemView全类名">
          <attr name="destitle" format="string"/>
          <attr name="desoff" format="string"/>
          <attr name="deson" format="string"/>
        </declare-styleable>
      <resource>
    3.自定义属性的使用
    定义名空间namespace
    mobilesafe替换掉原有android
    com.itheima.mobilesafe74必须这样编写,替换掉了android,代表当前应用自定义属性
    xmlns:mobilesafe="http://schemas.android.com/apk/res/com.itheima.mobilesafe74"

    <com.itheima.mobilesafe74.view.SettingItemView
      xmlns:mobilesafe="http://schemas.android.com/apk/res/com.itheima.mobilesafe74"
      android:id="@+id/siv_update"
      android:layout_width="match_parent"
      android:layout_height="wrap_content"
      mobilesafe:destitle="自动更新设置"
      mobilesafe:desoff="自动更新已关闭"
      mobilesafe:deson="自动更新已开启">
    4.获取属性值
      mobilesafe:destitle="自动更新设置"
      mobilesafe:desoff="自动更新已关闭"
      mobilesafe:deson="自动更新已开启"
    以上的是哪个属性都需要给自定义组合控件(SettingItemView)内部的两个TextView去使用,获取属性值

    //通过属性索引获取属性名称&属性值
    for(int i=0;i<attrs.getAttributeCount();i++){
      Log.i(tag, "name = "+attrs.getAttributeName(i));
      Log.i(tag, "value = "+attrs.getAttributeValue(i));
      Log.i(tag, "分割线 ================================= ");
    }
    //通过属性获取属性名称&名空间
    mDestitle = attrs.getAttributeValue(NAMESPACE, "destitle");
    mDesoff = attrs.getAttributeValue(NAMESPACE, "desoff");
    mDeson = attrs.getAttributeValue(NAMESPACE, "deson");

    5.将获取的属性值,设置给title,des
    des根据是否点中决定
    true deson
    false desoff

    activity_setting.xml

    <?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:orientation="vertical" >
        <TextView 
            style="@style/TitleStyle"
            android:text="设置中心"/>
        <!-- 将以下的相对布局,抽取到单独的一个类中去做管理,以后只需要在布局文件中添加此类,即可达到以下效果-->
       <!--  <RelativeLayout 
            android:padding="5dp"
            android:layout_width="match_parent"
            android:layout_height="wrap_content">
            <TextView 
                android:id="@+id/tv_title"
                android:text="自动更新设置"
                android:textColor="#000"
                android:textSize="18sp"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"/>
            <TextView 
                android:id="@+id/tv_des"
                android:layout_below="@id/tv_title"
                android:text="自动更新已关闭"
                android:textColor="#000"
                android:textSize="18sp"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"/>
            <CheckBox 
                android:id="@+id/cb_box"
                android:layout_alignParentRight="true"
                android:layout_centerVertical="true"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"/>
            <View
                android:background="#000"
                android:layout_below="@id/tv_des"
                android:layout_width="match_parent"
                android:layout_height="1dp"/>
        </RelativeLayout> -->
        <com.itheima.mobilesafe74.view.SettingItemView
            xmlns:mobilesafe="http://schemas.android.com/apk/res/com.itheima.mobilesafe74"
            android:id="@+id/siv_update"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            mobilesafe:destitle="自动更新设置"
            mobilesafe:desoff="自动更新已关闭"
            mobilesafe:deson="自动更新已开启">
        </com.itheima.mobilesafe74.view.SettingItemView>
        <!-- <com.itheima.mobilesafe74.view.SettingItemView
            xmlns:mobilesafe="http://schemas.android.com/apk/res/com.itheima.mobilesafe74"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            mobilesafe:destitle="电话归属地的显示设置"
            mobilesafe:desoff="归属地的显示已关闭"
            mobilesafe:deson="归属地的显示已开启">
        </com.itheima.mobilesafe74.view.SettingItemView> -->
        <!-- SettingItemView需要在构建布局的时候指定title和des字符串内容 -->
        <!-- 自定义属性 -->
        <!-- <com.itheima.mobilesafe74.view.SettingItemView
            android:layout_width="match_parent"
            android:layout_height="wrap_content">
        </com.itheima.mobilesafe74.view.SettingItemView> -->
    </LinearLayout>

    setting_item_view.xml

    <?xml version="1.0" encoding="utf-8"?>
    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" >
        <RelativeLayout 
            android:padding="5dp"
            android:layout_width="match_parent"
            android:layout_height="wrap_content">
            <TextView 
                android:id="@+id/tv_title"
                android:textColor="#000"
                android:textSize="18sp"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"/>
            <TextView 
                android:id="@+id/tv_des"
                android:layout_below="@id/tv_title"
                android:textColor="#000"
                android:textSize="18sp"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"/>
            <!-- android:clickable="false"
                android:focusable="false"
                android:focusableInTouchMode="false"
                                  让当前的 CheckBox不能被点击,即不能响应事件-->
            <CheckBox 
                android:id="@+id/cb_box"
                android:clickable="false"
                android:focusable="false"
                android:focusableInTouchMode="false"
                android:layout_alignParentRight="true"
                android:layout_centerVertical="true"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"/>
            <View
                android:background="#000"
                android:layout_below="@id/tv_des"
                android:layout_width="match_parent"
                android:layout_height="1dp"/>
        </RelativeLayout>
    </RelativeLayout>

    SettingItemView.java

    public class SettingItemView extends RelativeLayout {
        private static final String NAMESPACE = "http://schemas.android.com/apk/res/com.itheima.mobilesafe74";
        private static final String tag = "SettingItemView";
        private CheckBox cb_box;
        private TextView tv_des;
        private String mDestitle;
        private String mDesoff;
        private String mDeson;
    
        public SettingItemView(Context context) {
            this(context,null);
        }
    
        public SettingItemView(Context context, AttributeSet attrs) {
            this(context, attrs,0);
        }
    
        public SettingItemView(Context context, AttributeSet attrs, int defStyle) {
            super(context, attrs, defStyle);
            //xml--->view    将设置界面的一个条目转换成view对象,直接添加到了当前SettingItemView对应的view中
            View.inflate(context, R.layout.setting_item_view, this);
    
            //等同于以下两行代码
            /*View view = View.inflate(context, R.layout.setting_item_view, null);
            this.addView(view);*/
            
            //自定义组合控件中的标题描述
            TextView tv_title = (TextView) findViewById(R.id.tv_title);
            tv_des = (TextView) findViewById(R.id.tv_des);
            cb_box = (CheckBox) findViewById(R.id.cb_box);
            
            //获取自定义以及原生属性的操作,写在此处,AttributeSet attrs对象中获取
            initAttrs(attrs);
            //获取布局文件中定义的字符串,赋值给自定义组合控件的标题
            tv_title.setText(mDestitle);
        }
        
        /**
         * 返回属性集合中自定义属性属性值
         * @param attrs    构造方法中维护好的属性集合
         */
        private void initAttrs(AttributeSet attrs) {
            /*//获取属性的总个数
            Log.i(tag, "attrs.getAttributeCount() = "+attrs.getAttributeCount());
            //获取属性名称以及属性值
            for(int i=0;i<attrs.getAttributeCount();i++){
                Log.i(tag, "name = "+attrs.getAttributeName(i));
                Log.i(tag, "value = "+attrs.getAttributeValue(i));
                Log.i(tag, "分割线 ================================= ");
            }*/
            
            //通过名空间+属性名称获取属性值
            
            mDestitle = attrs.getAttributeValue(NAMESPACE, "destitle");
            mDesoff = attrs.getAttributeValue(NAMESPACE, "desoff");
            mDeson = attrs.getAttributeValue(NAMESPACE, "deson");
            
            Log.i(tag, mDestitle);
            Log.i(tag, mDesoff);
            Log.i(tag, mDeson);
        }
    
        /**
         * 判断是否开启的方法
         * @return    返回当前SettingItemView是否选中状态    true开启(checkBox返回true)    false关闭(checkBox返回true)
         */
        public boolean isCheck(){
            //由checkBox的选中结果,决定当前条目是否开启
            return cb_box.isChecked();
        }
    
        /**
         * @param isCheck    是否作为开启的变量,由点击过程中去做传递
         */
        public void setCheck(boolean isCheck){
            //当前条目在选择的过程中,cb_box选中状态也在跟随(isCheck)变化
            cb_box.setChecked(isCheck);
            if(isCheck){
                //开启
                tv_des.setText(mDeson);
            }else{
                //关闭
                tv_des.setText(mDesoff);
            }
        }
        
    }

    SettingActivity.java

    public class SettingActivity extends Activity {
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_setting);
            
            initUpdate();
        }
    
        /**
         * 版本更新开关
         */
        private void initUpdate() {
            final SettingItemView siv_update = (SettingItemView) findViewById(R.id.siv_update);
            
            //获取已有的开关状态,用作显示
            boolean open_update = SpUtil.getBoolean(this, ConstantValue.OPEN_UPDATE, false);
            //是否选中,根据上一次存储的结果去做决定
            siv_update.setCheck(open_update);
            
            siv_update.setOnClickListener(new OnClickListener() {
                @Override
                public void onClick(View v) {
                    //如果之前是选中的,点击过后,变成未选中
                    //如果之前是未选中的,点击过后,变成选中
                    
                    //获取之前的选中状态
                    boolean isCheck = siv_update.isCheck();
                    //将原有状态取反,等同上诉的两部操作
                    siv_update.setCheck(!isCheck);
                    //将取反后的状态存储到相应sp中
                    SpUtil.putBoolean(getApplicationContext(), ConstantValue.OPEN_UPDATE,!isCheck);
                }
            });
        }
    
    }

    /res/values/attrs.xml

    <?xml version="1.0" encoding="utf-8"?>
    <resources>
        <declare-styleable name="com.itheima.mobilesafe74.view.SettingItemView">
            <attr name="destitle" format="string"/>
            <attr name="desoff" format="string"/>
            <attr name="deson" format="string"/>
        </declare-styleable>
    </resources>
  • 相关阅读:
    volley框架使用
    Insert Interval
    candy(贪心)
    Best Time to Buy and Sell Stock
    Best Time to Buy and Sell Stock III
    distinct subsequences
    edit distance(编辑距离,两个字符串之间相似性的问题)
    trapping rain water
    word break II(单词切分)
    sudoku solver(数独)
  • 原文地址:https://www.cnblogs.com/xufengyuan/p/6227241.html
Copyright © 2011-2022 走看看