Android开发—电商系列】(二):仿淘宝商品属性标签页

一睹为快     这里写图片描述

需求

1.动态加载属性,如尺码,颜色,款式等

  由于每件商品的属性是不确定的,有的商品的属性是颜色和尺码,有的是口味,有的是大小,所以这些属性不能直接写死到页面上。

2.动态加载属性下的标签

  每个属性下的标签个数也不是一定的,比如有的商品的尺码是是S,M,XL,有的是均码,也就是每种属性的具体的内容是不一定的。

技术点

自定义ViewGroup,使其中的TextView可以依据内容长短自动换行,如下图所示

     这里写图片描述

实现

布局

通过ListView来显示商品所有属性,每种属性作为ListView的Item。

?
1
<span style= "font-family: Arial, Verdana, sans-serif;" >自定义ViewGroup</span>

普通的LinearLayout只能横向和纵向显示控件,但是当一行显示不够时,无法自动换行,需要我们自定义布局容器。

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
<code class = "hljs java" > package jczb.shoping.common;
 
import android.content.Context;
import android.util.AttributeSet;
import android.util.Log;
import android.view.View;
import android.view.ViewGroup;
 
public class MyViewGroup extends ViewGroup {
 
      private final static int VIEW_MARGIN= 15 ;
 
      public MyViewGroup(Context context, AttributeSet attrs){
          super (context, attrs);
      }
 
      public MyViewGroup(Context context) {
          super (context);
      }
      @Override
      protected void onMeasure( int widthMeasureSpec, int heightMeasureSpec) {
         int stages = 1 ;
         int stageHeight = 0 ;
         int stageWidth = 0 ;
 
         int wholeWidth = MeasureSpec.getSize(widthMeasureSpec);
 
         for ( int i = 0 ; i < getChildCount(); i++) {
             final View child = getChildAt(i);
             // measure
             measureChild(child, widthMeasureSpec, heightMeasureSpec);
             stageWidth += (child.getMeasuredWidth() + VIEW_MARGIN);
             stageHeight = child.getMeasuredHeight();
             if (stageWidth >= wholeWidth) {
                 stages++;
                 //reset stageWidth
                 stageWidth = child.getMeasuredWidth();
             }
 
 
         }
 
 
 
         int wholeHeight = (stageHeight + VIEW_MARGIN) * stages;
 
         // report this final dimension
         setMeasuredDimension(resolveSize(wholeWidth, widthMeasureSpec),
                 resolveSize(wholeHeight, heightMeasureSpec));
      }
      private int jiange = 10 ; //按钮之间的间隔
      @Override
      protected void onLayout( boolean arg0, int arg1, int arg2, int arg3, int arg4) {
 
          final int count = getChildCount();
          int row= 0 ; // which row lay you view relative to parent
          int lengthX=arg1 ;    // right position of child relative to parent
          int lengthY=arg2;    // bottom position of child relative to parent
          for ( int i= 0 ;i<count;i++){ final = "" view= "" child= "this.getChildAt(i);" int = "" width= "child.getMeasuredWidth();" height= "child.getMeasuredHeight();" if (i= "=" 0 ){= "" lengthx+= "width+VIEW_MARGIN;//第一个的时候不需要加" } else {= "" +jiange;= "" 按钮之间的间隔= "" }= "" lengthy= "row*(height+VIEW_MARGIN)+VIEW_MARGIN+height+arg2;" if = "" it= "" can't= "" drawing= "" on= "" a= "" same= "" line= "" ,= "" skip= "" to= "" next= "" if (lengthx= "" >arg3){
                  lengthX=width+VIEW_MARGIN+arg1;
                  row++;
                  lengthY=row*(height+VIEW_MARGIN)+VIEW_MARGIN+height+arg2;
              }
              child.layout(lengthX-width, lengthY-height, lengthX, lengthY);
          }
      }
}
</code>

ListView的Adapter

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
<code class = "hljs java" > package jczb.shoping.adapter;
 
import java.util.ArrayList;
import java.util.HashMap;
 
import jczb.shoping.common.MyViewGroup;
import jczb.shoping.ui.R;
import android.content.Context;
import android.graphics.Color;
import android.graphics.drawable.Drawable;
import android.os.Handler;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.Button;
import android.widget.LinearLayout;
import android.widget.LinearLayout.LayoutParams;
import android.widget.TableLayout;
import android.widget.TextView;
 
public class PropertyAdapter extends BaseAdapter {
 
     private Context mContext;
     private ArrayList<hashmap<string,object>> mList;
     private ArrayList<hashmap<string,textview[]>> mViewList;
     private Drawable drawableNormal ;
     private Drawable drawablePressed;
     private Handler mHandler;
 
     //用于保存用户的属性集合
     private HashMap<string,string> selectProMap= new HashMap<string, string= "" >();
     /**
      * 返回选中的属性
      * @return
      */
     public HashMap<string, string= "" > getSelectProMap() {
         return selectProMap;
     }
 
 
 
 
     public void setSelectProMap(HashMap<string, string= "" > selectProMap) {
         this .selectProMap = selectProMap;
     }
 
 
 
 
     public PropertyAdapter(Handler handler,Context context,ArrayList<hashmap<string,object>> list){
         super ();
         this .mHandler=handler;
         this .mContext=context;
         this .mList=list;
         mViewList= new ArrayList<hashmap<string,textview[]>>();
         drawableNormal=mContext.getResources().getDrawable(R.drawable.tv_property_label);
     }
 
     @Override
     public int getCount() {
         // TODO Auto-generated method stub
         return mList.size();
     }
 
     @Override
     public Object getItem( int position) {
         // TODO Auto-generated method stub
         return mList.get(position);
     }
 
     @Override
     public long getItemId( int position) {
         // TODO Auto-generated method stub
         return position;
     }
 
     @Override
     public View getView( int position, View convertView, ViewGroup parent) {
         ViewHolder holder = null ;
         if (convertView == null ) {
             // 获取list_item布局文件的视图
             convertView = LayoutInflater.from( this .mContext).inflate(R.layout.lv_property_item, null , true );
             holder = new ViewHolder();
 
             // 获取控件对象
             holder.tvPropName= (TextView) convertView
                     .findViewById(R.id.tv_property_name);
             //holder.llPropContents=(LinearLayout)convertView.findViewById(R.id.ll_property_content);
             //holder.tlPropContents=(TableLayout)convertView.findViewById(R.id.ll_property_content);
             // 设置控件集到convertView
             holder.vgPropContents= (MyViewGroup) convertView.findViewById(R.id.myviewgroup);
             convertView.setTag(holder);
         } else {
             holder = (ViewHolder) convertView.getTag();
         }
         if ( this .mList != null ) {
             //HashMap<string,textview[]> mapView=new HashMap<string,>();
             ArrayList<string> lables = (ArrayList<string>) this .mList.get(position).get( "lable" );
             String type = (String) this .mList.get(position).get(
                     "type" );
             holder.tvPropName.setText(type); //规格名称
             //动态加载标签
             //判断布局中的子控件是否为0,如果不为0,就不添加了,防止ListView滚动时重复添加
             if (holder.vgPropContents.getChildCount()== 0 ){
                 TextView[]  textViews = new TextView[lables.size()];
                 //设置每个标签的文本和布局
                 //TableRow tr=new TableRow(mContext);
 
                  for ( int i = 0 ; i < lables.size(); i++) {
                      TextView textView = new TextView(mContext);                     textView.setGravity( 17 );
                      textView.setPadding( 25 , 15 , 25 , 15 );              
                      textViews[i] = textView;
                      textViews[i].setBackgroundResource(R.drawable.tv_property_label);
                      textViews[i].setText(lables.get(i));
                      textViews[i].setTag(i);
 
                      //textViews[i].setBackgroundColor(Color.parseColor("#EE5500"));
                      //tr.addView(textViews[i]);
                     // holder.llPropContents.addView(textViews[i]);
                      holder.vgPropContents.addView(textViews[i]);
                  }
                  //holder.tlPropContents.addView(tr);
                  //绑定标签的Click事件
                  for ( int j= 0 ;j<textviews.length;j++){ string= "" void = "" viewholder= "" view= "" v= "(TextView)" tv= "(TextView)v;" this .type= "type;" textviews= "(TextView[])v.getTag();" textview= "" tablelayout= "" return = "" public = "" private = "" override= "" new = "" myviewgroup= "" linearlayout= "" lableclicklistener= "" int = "" implements = "" i= "0;i<textViews.length;i++){" h= "0;h<holder.vgPropContents.getChildCount();h++){" code= "" ></textviews.length;j++){></string></string></string,></string,textview[]></hashmap<string,textview[]></hashmap<string,object></string,></string,></string,></string,string></hashmap<string,textview[]></hashmap<string,object></code>

总结

  这里关键就是实现自定义的ViewGroup,重写onMeasure和onLayout方法,判断新添加的控件有没有超出屏幕的宽度来决定是否要换行。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值