zoukankan      html  css  js  c++  java
  • Android布局设计之ExpandableList绑定XML数据构成级联、item布局页面的控件查找及配置child事件,自定义适配显示内容

    研究了N久,Google,百度了找到些靠谱的和过滤了N多不靠谱,总算实现了ExpandableList绑定XML数据构成级联、item布局页面控件查找配置事件,自定义适配内容的功能,现在就分享给各个同学。

    效果:

     

     

    布局:

    main:

     

    <?xml version="1.0" encoding="utf-8"?>
    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:background="#ffffff"
        android:orientation="vertical" >
    
       
        <LinearLayout
            android:layout_width="fill_parent"
            android:layout_height="fill_parent"
            android:layout_below="@id/title" >
    
            <ExpandableListView
                android:id="@id/android:list"
                android:layout_width="fill_parent"
                android:layout_height="fill_parent"
                android:cacheColorHint="#ffffffff"
                android:drawSelectorOnTop="false" />
    
            <TextView
                android:id="@id/android:empty"
                android:layout_width="fill_parent"
                android:layout_height="fill_parent"/>
        </LinearLayout>
    
    </RelativeLayout>

    group:

    <?xml version="1.0" encoding="UTF-8"?>
    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_gravity="center_vertical"
        android:padding="5dp" >
    
        <ImageView
            android:id="@+id/group_image"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:paddingLeft="30dp" />
    
        <TextView
            android:id="@+id/group_txt"
            android:layout_width="fill_parent"
            android:layout_height="fill_parent"
            android:paddingLeft="65dp"
            android:textColor="#000000"
            android:textSize="35sp" />
    
    </RelativeLayout>

    child:

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:paddingLeft="20dp" >
    
        <ImageView
            android:id="@+id/child_image"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:paddingLeft="30dp"
            android:paddingTop="4dp" />
    
        <LinearLayout
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:orientation="vertical" >
    
            <TextView
                android:id="@+id/child_name"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="中国"
                android:textSize="30sp" />
    
            <TextView
                android:id="@+id/child_address"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="地址:xx省xx市xx" />
        </LinearLayout>
    
        <TextView
            android:id="@+id/child_id"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="地址:xx省xx市xx" />
    
    </LinearLayout>

    XML数据:

    商铺类型:

    <?xml version="1.0" encoding="UTF-8"?>
    <shoptypes>
        <shoptype id="1">
            <name>快餐店</name>
        </shoptype>
        <shoptype id="2">
            <name>小卖部</name>
        </shoptype>
        <shoptype id="3">
            <name>网吧</name>
        </shoptype>
        <shoptype id="4">
            <name>电器店</name>
        </shoptype>
        <shoptype id="5">
            <name>银行</name>
        </shoptype>
    </shoptypes>

    商铺:

    <?xml version="1.0" encoding="UTF-8"?>
    <shops>
        <shop id="1">
            <typeid>1</typeid>
            <name>好食膳</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="2">
            <typeid>1</typeid>
            <name>好食膳</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="3">
            <typeid>1</typeid>
            <name>好食膳</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="4">
            <typeid>2</typeid>
            <name>实践部</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="5">
            <typeid>2</typeid>
            <name>实践部</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="6">
            <typeid>2</typeid>
            <name>实践部</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="7">
            <typeid>2</typeid>
            <name>网络部</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="8">
            <typeid>3</typeid>
            <name>网络部</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="9">
            <typeid>3</typeid>
            <name>网络部</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="10">
            <typeid>3</typeid>
            <name>卡狄工作室</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="11">
            <typeid>4</typeid>
            <name>魔舟工作室</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="12">
            <typeid>4</typeid>
            <name>魔舟工作室</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="13">
            <typeid>4</typeid>
            <name>魔舟工作室</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="14">
            <typeid>5</typeid>
            <name>好食膳</name>
            <adress>福州市XXX</adress>
        </shop>
        <shop id="15">
            <typeid>5</typeid>
            <name>好食膳</name>
            <adress>福州市XXX</adress>
        </shop>
    </shops>

    java:

    main:

    /**
     * 
     */
    package com.clshf.android.classify;
    
    import java.util.ArrayList;
    import java.util.HashMap;
    import java.util.List;
    import java.util.Map;
    import com.clshf.android.R;
    import com.clshf.android.domain.Shop;
    import com.clshf.android.domain.ShopType;
    import com.clshf.android.services.AppXmlPaseService;
    import com.clshf.android.services.ExpandableListAdapterService;
    
    import android.app.ExpandableListActivity;
    import android.graphics.drawable.Drawable;
    import android.os.Bundle;
    import android.view.View;
    import android.widget.ExpandableListView;
    import android.widget.ImageView;
    import android.widget.TextView;
    import android.widget.Toast;
    
    /**
     * 作用:分类窗体 创建时间:2012-8-3 上午10:29:53 修改时间:2012年8月10日17:02:16
     * 
     * @author Hzl520
     */
    public class ClassifyActivity extends ExpandableListActivity {
        
        private static final String GROUPPCITURE = "grouppciture";
    
        private static final String GROUPNAME = "groupname";
    
        private ExpandableListAdapterService exListAdapter = null;
    
        private static final String SUBCLASSNAMEID = "subclassid";
    
        private static final String SUBCLASSPICTURE = "subclasspicture";
    
        private static final String SUBCLASSNAME = "subclassname";
    
        private static final String SUBCLASSADDRESS = "subclassaddress";
    
     /*
         * 作用:窗体初始化.. 步骤:看注释 创建时间:2012-8-7 下午5:24:20 修改时间:2012-8-10 下午4:19:33
         * 
         * @param savedInstanceState
         */
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.classifyview);
    /** ==============配置风琴数据=============== **/ AppXmlPaseService appXmlPaseService = new AppXmlPaseService(); try { List<ShopType> shopTypes = appXmlPaseService.getPersons(this, "xml/shops/shoptype.xml"); List<Map<String, Object>> groupData = new ArrayList<Map<String, Object>>();// 父类数据 List<List<Map<String, Object>>> childData = new ArrayList<List<Map<String, Object>>>();// 子类数据 // 嵌套循环遍历数据填充至风琴列表中 for (ShopType shoptype : shopTypes) { HashMap<String, Object> curGroupMap = new HashMap<String, Object>(); groupData.add(curGroupMap); curGroupMap.put(GROUPPCITURE, R.drawable.iv_1);// 填充图片,这个随意放。 curGroupMap.put(GROUPNAME, shoptype.getName());// 填充XML中的名称 // 循环遍历子数据 List<Shop> shops = appXmlPaseService.getShops(this, "xml/shops/shop.xml"); List<Map<String, Object>> children = new ArrayList<Map<String, Object>>(); for (Shop shop : shops) { HashMap<String, Object> curChildMap = new HashMap<String, Object>(); int shoptypeid = shoptype.get_id(); if (shoptypeid != 0) { if (shoptypeid == shop.getTypeid()) { curChildMap.put(SUBCLASSPICTURE, R.drawable.iv_1); curChildMap.put(SUBCLASSNAMEID, shop.get_id() .toString()); curChildMap.put(SUBCLASSNAME, shop.getName()); curChildMap.put(SUBCLASSADDRESS, shop.getAddress()); children.add(curChildMap); } else { continue; } } } childData.add(children); } // 配置风琴列表数据 exListAdapter = new ExpandableListAdapterService( ClassifyActivity.this, groupData, R.layout.classify_group, new String[] { GROUPPCITURE, GROUPNAME }, new int[] { R.id.group_image, R.id.group_txt }, childData, R.layout.classify_child, new String[] { SUBCLASSPICTURE, SUBCLASSNAME, SUBCLASSADDRESS, SUBCLASSNAMEID }, new int[] { R.id.child_image, R.id.child_name, R.id.child_address, R.id.child_id }); // 设置风琴列表数据 setListAdapter(exListAdapter); } catch (Exception e) { e.printStackTrace(); } // 对图片ID进行处理 exListAdapter .setViewBinder(new ExpandableListAdapterService.ViewBinder() { /* * 作用:处理图片问题 步骤:看注释 创建时间:2012-8-10 下午4:19:29 修改时间:2012-8-10 * 下午4:19:29 * * @param view * * @param data * * @param textRepresentation * * @return */ @Override public boolean setViewValue(View view, Object data, String textRepresentation) { switch (view.getId()) { case R.id.group_image: { if (view instanceof ImageView) { ImageView _view = (ImageView) view; if (data instanceof Integer) { _view.setImageResource((Integer) data); } else if (data instanceof Drawable) { _view.setImageDrawable((Drawable) data); } else { throw new IllegalArgumentException( "The Data is Not a Drawable Or Resource Id!"); } } return true; } case R.id.child_image: { if (view instanceof ImageView) { ImageView _view = (ImageView) view; if (data instanceof Integer) { _view.setImageResource((Integer) data); } else if (data instanceof Drawable) { _view.setImageDrawable((Drawable) data); } else { throw new IllegalArgumentException( "The Data is Not a Drawable Or Resource Id!"); } } return true; } } return false; } }); } /* * 作用:处理子菜单点击事件 * 步骤:看注释 * 创建时间:2012-8-11 上午11:48:53 * 修改时间:2012-8-11 上午11:48:53 * @param parent * @param v * @param groupPosition * @param childPosition * @param id * @return */ @Override public boolean onChildClick(ExpandableListView parent, View v, int groupPosition, int childPosition, long id) { HashMap<String,String> map=(HashMap<String,String>)exListAdapter.getChild(groupPosition, childPosition); String sid=map.get(SUBCLASSNAMEID); Toast.makeText(this, "child--->"+sid,1).show(); return true; } }


    xml数据解析:

    /**
     * 
     */
    package com.clshf.android.services;
    
    import java.io.InputStream;
    import java.util.ArrayList;
    import java.util.List;
    
    import org.xmlpull.v1.XmlPullParser;
    
    import com.clshf.android.domain.Shop;
    import com.clshf.android.domain.ShopType;
    
    import android.content.Context;
    import android.util.Xml;
    
    
    /**
     * 作用:应用的XML数据解析处理
     * 创建时间:2012-8-10 上午10:34:30
     * 修改时间:2012-8-10 上午10:34:30
     * @author Hzl520
     */
    public class AppXmlPaseService {
    
    
        /**
         * 作用:获取assets文件中的shop数据
         * 步骤:看注释
         * 创建时间:2012-8-10 下午5:31:10
         * 修改时间:2012-8-10 下午5:31:10
         * @param context
         * @param assetspath
         * @return List<Shop>
         * @throws Exception
         */
        public  List<Shop> getShops(Context context,String assetspath ) throws Exception {
            //获取xml文件流对象
            InputStream inputStream=context.getAssets().open(assetspath);
            List<Shop> shops=null;
            Shop shop=null;
            XmlPullParser parser=Xml.newPullParser();
            parser.setInput(inputStream, "UTF-8");
            //获取解析事件,和SAX类似
            int eventType=parser.getEventType();
            //使用各个事件解析XML
            while(eventType!=XmlPullParser.END_DOCUMENT){
                switch (eventType) {
                case XmlPullParser.START_DOCUMENT:
                    //开始遍历节点的时候实例化集合
                    shops=new ArrayList<Shop>();
                    break;
                case XmlPullParser.START_TAG:
                    String name=parser.getName();
                    if(name.equals("shop")){
                        shop=new Shop();
                        shop.set_id(new Integer(parser.getAttributeValue(0)));
                    }
                    if (shop!=null) {
                        if (name.equals("typeid")) {
                            shop.setTypeid(new Integer(parser.nextText()));
                        }else if (name.equals("name")) {
                            shop.setName(parser.nextText());
                        }
                        else if (name.equals("adress")) {
                            shop.setAddress(parser.nextText());
                        }
                    }
                    break;
                case XmlPullParser.END_TAG:
                    if(parser.getName().equals("shop")){
                        shops.add(shop);
                        shop=null;
                        }
                    break;
                }
                //遍历下一个节点
                eventType=parser.next();
            }
            return shops;
        }
    
    
        /**
         * 作用:从XML中获取商店类型信息
         * 步骤:看注释
         * 创建时间:2012-7-14 上午10:31:25
         * 修改时间:2012-7-14 上午10:31:25
         * @param inputStream
         * @return
         * @throws Exception 
         */
        public  List<ShopType> getPersons(Context context,String assetspath ) throws Exception {
            //获取xml文件流对象
            InputStream inputStream=context.getAssets().open(assetspath);
            List<ShopType> shoptypes=null;
            ShopType shoptype=null;
            XmlPullParser parser=Xml.newPullParser();
            parser.setInput(inputStream, "UTF-8");
            //获取解析事件,和SAX类似
            int eventType=parser.getEventType();
            //使用各个事件解析XML
            while(eventType!=XmlPullParser.END_DOCUMENT){
                switch (eventType) {
                case XmlPullParser.START_DOCUMENT:
                    //开始遍历节点的时候实例化集合
                    shoptypes=new ArrayList<ShopType>();
                    break;
                case XmlPullParser.START_TAG:
                    String name=parser.getName();
                    if(name.equals("shoptype")){
                        shoptype=new ShopType();
                        shoptype.set_id(new Integer(parser.getAttributeValue(0)));
                    }
                    if (shoptype!=null) {
                        if (name.equals("name")) {
                            shoptype.setName(parser.nextText());
                        }
                    }
                    break;
                case XmlPullParser.END_TAG:
                    if(parser.getName().equals("shoptype")){
                        shoptypes.add(shoptype);
                        shoptype=null;
                        }
                    break;
                }
                //遍历下一个节点
                eventType=parser.next();
            }
            return shoptypes;
        }
        
    }

    ExpandableList数据适配器:

    package com.clshf.android.services;
    
    import android.content.Context;
    import android.view.LayoutInflater;
    import android.view.View;
    import android.view.ViewGroup;
    import android.widget.BaseExpandableListAdapter;
    import android.widget.TextView;
    
    import java.util.List;
    import java.util.Map;
    
    /**
     * 作用:自定义处理ExpandableListAdapter数据
     * 创建时间:2012-8-10 下午3:30:09
     * 修改时间:2012-8-10 下午3:30:09
     * @author Hzl520
     */
    public class ExpandableListAdapterService extends BaseExpandableListAdapter {
        private ViewBinder mViewBinder;
    
        private List<? extends Map<String, ?>> mGroupData;
        private int mExpandedGroupLayout;
        private int mCollapsedGroupLayout;
        private String[] mGroupFrom;
        private int[] mGroupTo;
    
        private List<? extends List<? extends Map<String, ?>>> mChildData;
        private int mChildLayout;
        private int mLastChildLayout;
        private String[] mChildFrom;
        private int[] mChildTo;
    
        private LayoutInflater mInflater;
    
        public ExpandableListAdapterService(Context context, List<? extends Map<String, ?>> groupData,
                int groupLayout, String[] groupFrom, int[] groupTo,
                List<? extends List<? extends Map<String, ?>>> childData, int childLayout,
                String[] childFrom, int[] childTo) {
            this(context, groupData, groupLayout, groupLayout, groupFrom, groupTo, childData,
                    childLayout, childLayout, childFrom, childTo);
        }
    
        public ExpandableListAdapterService(Context context, List<? extends Map<String, ?>> groupData,
                int expandedGroupLayout, int collapsedGroupLayout, String[] groupFrom, int[] groupTo,
                List<? extends List<? extends Map<String, ?>>> childData, int childLayout,
                String[] childFrom, int[] childTo) {
            this(context, groupData, expandedGroupLayout, collapsedGroupLayout, groupFrom, groupTo,
                    childData, childLayout, childLayout, childFrom, childTo);
        }
    
        public ExpandableListAdapterService(Context context, List<? extends Map<String, ?>> groupData,
                int expandedGroupLayout, int collapsedGroupLayout, String[] groupFrom, int[] groupTo,
                List<? extends List<? extends Map<String, ?>>> childData, int childLayout,
                int lastChildLayout, String[] childFrom, int[] childTo) {
            mGroupData = groupData;
            mExpandedGroupLayout = expandedGroupLayout;
            mCollapsedGroupLayout = collapsedGroupLayout;
            mGroupFrom = groupFrom;
            mGroupTo = groupTo;
    
            mChildData = childData;
            mChildLayout = childLayout;
            mLastChildLayout = lastChildLayout;
            mChildFrom = childFrom;
            mChildTo = childTo;
    
            mInflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        }
    
        public Object getChild(int groupPosition, int childPosition) {
            return mChildData.get(groupPosition).get(childPosition);
        }
    
        public long getChildId(int groupPosition, int childPosition) {
            return childPosition;
        }
    
        /**
         * Instantiates a new View for a child.
         * @param isLastChild Whether the child is the last child within its group.
         * @param parent The eventual parent of this new View.
         * @return A new child View
         */
        public View newChildView(boolean isLastChild, ViewGroup parent) {
            return mInflater.inflate((isLastChild) ? mLastChildLayout : mChildLayout, parent, false);
        }
    
        public int getChildrenCount(int groupPosition) {
            return mChildData.get(groupPosition).size();
        }
    
        public Object getGroup(int groupPosition) {
            return mGroupData.get(groupPosition);
        }
    
        public int getGroupCount() {
            return mGroupData.size();
        }
    
        public long getGroupId(int groupPosition) {
            return groupPosition;
        }
    
        /**
         * Instantiates a new View for a group.
         * @param isExpanded Whether the group is currently expanded.
         * @param parent The eventual parent of this new View.
         * @return A new group View
         */
        public View newGroupView(boolean isExpanded, ViewGroup parent) {
            return mInflater.inflate((isExpanded) ? mExpandedGroupLayout : mCollapsedGroupLayout,
                    parent, false);
        }
    
        public boolean isChildSelectable(int groupPosition, int childPosition) {
            return true;
        }
    
        public boolean hasStableIds() {
            return true;
        }
    
        // --------------------------------------------------------------------------------------//
    
        private void bindView(View view, Map<String, ?> data, String[] from, int[] to) {
            int len = to.length;
    
            boolean isBound = false;
            for (int i = 0; i < len; i++) {
    
                final View v = view.findViewById(to[i]);
    
                if (v!=null) {
                    final Object _data = data.get(from[i]);
                    String text = _data == null ? "" : data.toString();
                    if (text == null) {
                        text = "";
                    }
                    
                    if (mViewBinder != null) {//如果Binder不为空,使用Binder进行处理
                        isBound = mViewBinder.setViewValue(v, data.get(from[i]), text);
                    }
                    
                    if (!isBound) {//如果Binder跳过,使用原来的方法进行处理
                        TextView _v = (TextView)v;
                        _v.setText((String)data.get(from[i]));
                    }                
                }
            }
        }
    
        public View getGroupView(int groupPosition, boolean isExpanded, View convertView,
                ViewGroup parent) {
            View v;
            if (convertView == null) {
                v = newGroupView(isExpanded, parent);
            } else {
                v = convertView;
            }
    
            bindView(v, mGroupData.get(groupPosition), mGroupFrom, mGroupTo);
            return v;
        }
    
        public View getChildView(int groupPosition, int childPosition, boolean isLastChild,
                View convertView, ViewGroup parent) {
            View v;
            if (convertView == null) {
                v = newChildView(isLastChild, parent);
            } else {
                v = convertView;
            }
    
            bindView(v, mChildData.get(groupPosition).get(childPosition), mChildFrom, mChildTo);
            return v;
        }
    
        public void setViewBinder(ViewBinder mViewBinder) {
            this.mViewBinder = mViewBinder;
        }
    
        /**
         * 作用:提供视图渲染的绑定器 
         * 创建时间:2012-8-10 下午3:29:45
         * 修改时间:2012-8-10 下午3:29:45
         * @author Hzl520
         */
        public static interface ViewBinder {
            boolean setViewValue(View view, Object data, String textRepresentation);
        }
    
    }

    转载请注明:http://www.cnblogs.com/hzl512/archive/2012/08/11/2633664.html

  • 相关阅读:
    Leetcode 811. Subdomain Visit Count
    Leetcode 70. Climbing Stairs
    Leetcode 509. Fibonacci Number
    Leetcode 771. Jewels and Stones
    Leetcode 217. Contains Duplicate
    MYSQL安装第三步报错
    .net 开发WEB程序
    JDK版本问题
    打开ECLIPSE 报failed to load the jni shared library
    ANSI_NULLS SQL语句
  • 原文地址:https://www.cnblogs.com/hzl512/p/2633664.html
Copyright © 2011-2022 走看看