掌上快递之主界面篇(1)

本文涉及的产品
云解析 DNS,旗舰版 1个月
全局流量管理 GTM,标准版 1个月
公共DNS(含HTTPDNS解析),每月1000万次HTTP解析
简介:

概述

整体是通过2个Fragment+FragmentTabHost组合而成,本节主要针对Fragment1做一个总结,该Fragment主要实现以下功能

【1】输入快递单号或者扫描二维码 查询快递信息

【2】侧滑栏集成的百度地图可以显示附近快递点,方便选择合适自己的地点

本篇只总结主界面架构和功能1,先上图有个直观感受


1、主界面结构

Fragment+FragmentTabHost组合而成,其中整体的布局文件是在LinearLayout(vertical)的布局中嵌入了FrameLayout,上图显示的文字和背景都在直接代码中加入的,main_tab_layout.xml具体布局如下

[html]  view plain  copy
  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  3.     xmlns:baiduadsdk="http://schemas.android.com/apk/res/com.weimeijing.feigeshudi"  
  4.     android:layout_width="fill_parent"  
  5.     android:layout_height="fill_parent"  
  6.     android:orientation="vertical" >  
  7.   
  8.     <FrameLayout  
  9.         android:id="@+id/realtabcontent"  
  10.         android:layout_width="fill_parent"  
  11.         android:layout_height="0dip"  
  12.         android:layout_weight="1" />  
  13.   
  14.     <android.support.v4.app.FragmentTabHost  
  15.         android:id="@android:id/tabhost"  
  16.         android:layout_width="fill_parent"  
  17.         android:layout_height="wrap_content"  
  18.         android:background="@drawable/maintab_toolbar_bg" >  
  19.   
  20.         <FrameLayout  
  21.             android:id="@android:id/tabcontent"  
  22.             android:layout_width="0dp"  
  23.             android:layout_height="0dp"  
  24.             android:layout_weight="0" />  
  25.     </android.support.v4.app.FragmentTabHost>  
  26.   
  27. </LinearLayout>  


框架MainTabActivity主要使用FragmentTabHost来管理,这里将俩个Fragment放入一个数组中

[java]  view plain  copy
  1. // 定义数组来存放Fragment界面  
  2.   
  3.     private Class fragmentArray[] = { MainActivity.class,  
  4.             MyExpressActivity.class };  
然后// 将Tab按钮添加进Tab选项卡中 mTabHost.addTab(tabSpec, fragmentArray[i], null);

具体代码如下

[java]  view plain  copy
  1. package com;  
  2.   
  3. import android.os.Bundle;  
  4. import android.support.v4.app.FragmentActivity;  
  5. import android.support.v4.app.FragmentTabHost;  
  6. import android.view.LayoutInflater;  
  7. import android.view.View;  
  8. import android.widget.ImageView;  
  9. import android.widget.TabHost.TabSpec;  
  10. import android.widget.TextView;  
  11.   
  12. import com.baidu.mapapi.map.BaiduMap;  
  13. import com.weimeijing.feigeshudi.R;  
  14.   
  15. /** 
  16.  * @author xsfelvis 功能描述:自定义TabHost 
  17.  */  
  18. public class MainTabActivity extends FragmentActivity {  
  19.     // 定义FragmentTabHost对象  
  20.     private FragmentTabHost mTabHost;  
  21.   
  22.     // 定义一个布局  
  23.     private LayoutInflater layoutInflater;  
  24.   
  25.     // 定义数组来存放Fragment界面  
  26.   
  27.     private Class fragmentArray[] = { MainActivity.class,  
  28.             MyExpressActivity.class };  
  29.   
  30.     // 定义数组来存放按钮图片  
  31.     private int mImageViewArray[] = { R.drawable.tab_square_btn,  
  32.             R.drawable.tab_home_btn };  
  33.     // Tab选项卡的文字  
  34.     private String mTextviewArray[] = { "快递追踪""我的收藏" };  
  35.   
  36.     public void onCreate(Bundle savedInstanceState) {  
  37.         super.onCreate(savedInstanceState);  
  38.         setContentView(R.layout.main_tab_layout);  
  39.   
  40.         initView();  
  41.     }  
  42.   
  43.     /** 
  44.      * 初始化组件 
  45.      */  
  46.     private void initView() {  
  47.         // 实例化布局对象  
  48.         layoutInflater = LayoutInflater.from(this);  
  49.   
  50.         // 实例化TabHost对象,得到TabHost  
  51.         mTabHost = (FragmentTabHost) findViewById(android.R.id.tabhost);  
  52.         mTabHost.setup(this, getSupportFragmentManager(), R.id.realtabcontent);  
  53.   
  54.         // 得到fragment的个数  
  55.         int count = fragmentArray.length;  
  56.   
  57.         for (int i = 0; i < count; i++) {  
  58.             // 为每一个Tab按钮设置图标、文字和内容  
  59.             TabSpec tabSpec = mTabHost.newTabSpec(mTextviewArray[i])  
  60.                     .setIndicator(getTabItemView(i));  
  61.             // 将Tab按钮添加进Tab选项卡中  
  62.             mTabHost.addTab(tabSpec, fragmentArray[i], null);  
  63.             // 设置Tab按钮的背景  
  64.             mTabHost.getTabWidget().getChildAt(i)  
  65.                     .setBackgroundResource(R.drawable.selector_tab_background);  
  66.         }  
  67.     }  
  68.   
  69.     /** 
  70.      * 给Tab按钮设置图标和文字 
  71.      */  
  72.     private View getTabItemView(int index) {  
  73.         View view = layoutInflater.inflate(R.layout.tab_item_view, null);  
  74.   
  75.         ImageView imageView = (ImageView) view.findViewById(R.id.imageview);  
  76.         imageView.setImageResource(mImageViewArray[index]);  
  77.   
  78.         TextView textView = (TextView) view.findViewById(R.id.textview);  
  79.         textView.setText(mTextviewArray[index]);  
  80.   
  81.         return view;  
  82.     }  
  83. }  

框架部分其实还是很简单的,注释比较详细就不赘述了


2 、Fragment 快递追踪

2.1、布局文件

这里的布局文件非常重要,因为Fragment1里面实际包含了2部分 快递追踪+侧滑(来自github的开源控件开源控件)下一篇讲侧滑模块再详细介绍,布局文件中activity_main.xml其中 <include layout="@layout/left_slide" />是侧滑的布局文件,这里我们暂不考虑,

【1】使用了SlidingMenu,整个布局要在其中包含跟一般的布局文件不一样,这里需要导入slidingmenu_library才可以使用

【2】要注意由于要包含侧滑部分,因此整个LinearLayout属性使用"horizontal",而不是Vertical的

布局文件代码如下:

[html]  view plain  copy
  1. <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  2.     xmlns:tools="http://schemas.android.com/tools"  
  3.     xmlns:baiduadsdk="http://schemas.android.com/apk/res/com.weimeijing.feigeshudi"  
  4.     xmlns:xsf="http://schemas.android.com/apk/res/com.weimeijing.feigeshudi"  
  5.     android:layout_width="match_parent"  
  6.     android:layout_height="match_parent"  
  7.     tools:context=".MainActivity" >  
  8.   
  9.   <span style="color:#009900;">  <com.leftside.SlidingMenu  
  10.         android:id="@+id/id_menu"  
  11.         android:layout_width="match_parent"  
  12.         android:layout_height="match_parent"  
  13.         android:background="@drawable/img_frame_background"  
  14.         xsf:rightPadding="80dp" ></span>  
  15.   
  16.         <LinearLayout  
  17.             android:layout_width="wrap_content"  
  18.             android:layout_height="match_parent"  
  19.             android:orientation="horizontal" >  
  20.   
  21.            <span style="color:#006600;"> <include layout="@layout/left_slide" /></span>  
  22.   
  23.             <LinearLayout  
  24.                 android:layout_width="fill_parent"  
  25.                 android:layout_height="fill_parent"  
  26.                 android:background="@drawable/main_banner2"  
  27.                 android:orientation="vertical"  
  28.                 tools:context=".MainActivity" >  
  29.   
  30.                 <LinearLayout  
  31.                     android:id="@+id/ll_main_container"  
  32.                     android:layout_width="match_parent"  
  33.                     android:layout_height="match_parent"  
  34.                     android:layout_below="@+id/iv_main_banner"  
  35.                     android:focusable="true"  
  36.                     android:focusableInTouchMode="true"  
  37.                     android:orientation="vertical"  
  38.                     android:paddingLeft="15dp"  
  39.                     android:paddingRight="15dp"  
  40.                     android:paddingTop="60dp" >  
  41.   
  42.                     <RelativeLayout  
  43.                         android:layout_width="match_parent"  
  44.                         android:layout_height="wrap_content" >  
  45.   
  46.                         <EditText  
  47.                             android:id="@+id/tv_main_express_name"  
  48.                             android:layout_width="match_parent"  
  49.                             android:layout_height="wrap_content"  
  50.                             android:layout_alignParentRight="true"  
  51.                             android:background="@drawable/edittext_selector"  
  52.                             android:focusable="false"  
  53.                             android:hint="快递公司"  
  54.                             android:textSize="25dp" />  
  55.   
  56.                         <ImageView  
  57.                             android:layout_width="wrap_content"  
  58.                             android:layout_height="wrap_content"  
  59.                             android:layout_alignParentRight="true"  
  60.                             android:layout_centerVertical="true"  
  61.                             android:gravity="center|center_vertical"  
  62.                             android:src="@drawable/image_search_arrow" />  
  63.                     </RelativeLayout>  
  64.   
  65.                     <TextView  
  66.                         android:id="@+id/tv_main_banner_text"  
  67.                         android:layout_width="match_parent"  
  68.                         android:layout_height="wrap_content"  
  69.                         android:gravity="right|center_vertical"  
  70.                         android:paddingRight="10dp"  
  71.                         android:text="@string/banner_text"  
  72.                         android:textColor="#FFFAFAFA"  
  73.                         android:textSize="8pt" />  
  74.   
  75.                     <RelativeLayout  
  76.                         android:layout_width="match_parent"  
  77.                         android:layout_height="wrap_content" >  
  78.   
  79.                         <EditText  
  80.                             android:id="@+id/tv_main_express_number"  
  81.                             android:layout_width="wrap_content"  
  82.                             android:layout_height="wrap_content"  
  83.                             android:layout_alignParentLeft="true"  
  84.                             android:layout_alignParentRight="true"  
  85.                             android:background="@drawable/edittext_selector"  
  86.                             android:clickable="true"  
  87.                             android:hint="快递单号"  
  88.                             android:inputType="number"  
  89.                             android:textSize="25dp" />  
  90.   
  91.                         <ImageView  
  92.                             android:id="@+id/scane_express_number"  
  93.                             android:layout_width="wrap_content"  
  94.                             android:layout_height="wrap_content"  
  95.                             android:layout_alignParentRight="true"  
  96.                             android:layout_marginRight="10dp"  
  97.                             android:layout_marginTop="2dp"  
  98.                             android:clickable="true"  
  99.                             android:src="@drawable/button_selector_scane" />  
  100.                     </RelativeLayout>  
  101.   
  102.                     <LinearLayout  
  103.                         android:layout_width="match_parent"  
  104.                         android:layout_height="wrap_content"  
  105.                         android:orientation="horizontal" >  
  106.   
  107.                         <Button  
  108.                             android:id="@+id/btn_main_search"  
  109.                             android:layout_width="wrap_content"  
  110.                             android:layout_height="wrap_content"  
  111.                             android:layout_marginTop="20dp"  
  112.                             android:layout_weight="3"  
  113.                             android:background="@drawable/button_selector_search"  
  114.                             android:text="查询"  
  115.                             android:textColor="#FFfcfcfc" />  
  116.   
  117.                         <TextView  
  118.                             android:layout_width="wrap_content"  
  119.                             android:layout_height="wrap_content"  
  120.                             android:layout_weight="1" />  
  121.   
  122.                         <Button  
  123.                             android:id="@+id/btn_main_reset"  
  124.                             android:layout_width="wrap_content"  
  125.                             android:layout_height="wrap_content"  
  126.                             android:layout_marginTop="20dp"  
  127.                             android:layout_weight="3"  
  128.                             android:background="@drawable/button_selector_reset"  
  129.                             android:text="重置"  
  130.                             android:textColor="#FFfcfcfc" />  
  131.                     </LinearLayout>  
  132.                 </LinearLayout>  
  133.             </LinearLayout>  
  134.         </LinearLayout>  
  135.    <span style="color:#006600;"> </com.leftside.SlidingMenu></span>  
  136.   
  137. </RelativeLayout>  

2.2、MainTabActivity.java总结

这里对该代码中一些要点做下总结:

【1】使用fragment与Activity通信

因为所有的Fragment都是依附于Activity的,所以通信起来并不复杂,大概归纳为:
a、如果你Activity中包含自己管理的Fragment的引用,可以通过引用直接访问所有的Fragment的public方法

b、如果Activity中未保存任何Fragment的引用,那么没关系,每个Fragment都有一个唯一的TAG或者ID,可以通过getFragmentManager.findFragmentByTag()或者findFragmentById()获得任何Fragment实例,然后进行操作。

c、在Fragment中可以通过getActivity得到当前绑定的Activity的实例,然后进行操作。


【2】使用Fragment时 onCreateView()参数详解

[java]  view plain  copy
  1. /* 实现fragment需要使用Fragment时,需要继承Fragment或者Fragment的子类 */  
  2.     // onCreateView()中container参数代表该Fragment在Activity中的父控件;savedInstanceState提供了上一个实例的数据  
  3.     // 为Fragment加载布局时调用  
  4.     @Override  
  5.     public View onCreateView(LayoutInflater inflater, ViewGroup container,  
  6.             Bundle savedInstanceState) {  
  7.   
  8.         // 为这个 fragment加载 activity_main布局文件  
  9.         /* 
  10.          * 第一个是resource ID,指明了当前的Fragment对应的资源文件;第二个参数是父容器控件; 
  11.          * 第三个布尔值参数表明是否连接该布局和其父容器控件 
  12.          * ,在这里的情况设置为false,因为系统已经插入了这个布局到父控件,设置为true将会产生多余的一个View Group。 
  13.          */  
  14.         return inflater.inflate(R.layout.activity_main, null);  
  15.   
  16.     }  

【3】startActivityForResult与startActivity区别 

1、startActivity( )
仅仅是跳转到目标页面,若是想跳回当前页面,则必须再使用一次startActivity( )。
2、startActivityForResult( )
可 以一次性完成这项任务,当程序执行到这段代码的时候,假若从T1Activity跳转到下一个Text2Activity,而当这个 Text2Activity调用了finish()方法以后(必须调用该方法!),程序会自动跳转回T1Activity,并调用前一个T1Activity中的 onActivityResult( )方法。通过requestCode来判断执行
相关函数:
startActivityForResult(Intent intent, Int requestCode)
setResut(int resultCode, Intent intent)
onActivityResult(int requestCode, int resultCode, Intent intent)

本项中通过俩种形式手动输入快递号requestCode=1,扫描二维码requestCode=0

[java]  view plain  copy
  1. startActivityForResult(openCameraIntent, 0); // 扫描二维码触发  
[java]  view plain  copy
  1. startActivityForResult(intent, 1);//手动输入快递单号  

然后在回调函数onActivityResult是这样处理的

[java]  view plain  copy
  1. /** 
  2.      * onActivityResult接收返回的数据/结果的处理函数 
  3.      * 这里的requestCode就是startActivityForResult的requestCode, 
  4.      * resultCode就是setResult里面的resultCode, 返回的数据在data里面。 
  5.      */  
  6.     @Override  
  7.     public void onActivityResult(int requestCode, int resultCode, Intent data) {  
  8.         if (data == null) {  
  9.             return;  
  10.         }  
  11.         super.onActivityResult(requestCode, resultCode, data);  
  12.         if (requestCode == 1) { // 说明是快递选择触发的  
  13.             /* 
  14.              * 处理ExpressList回传来的点击选择的对应的code/name 将回传信息填写到对应的文本控件中 
  15.              */  
  16.             code = data.getStringExtra("code");  
  17.             String name = data.getStringExtra("name");  
  18.             tv_main_express_name.setText(name);  
  19.             tv_main_express_number.setText("");  
  20.   
  21.         } else if (requestCode == 0) { // 扫描按钮触发的  
  22.             Bundle bundle = data.getExtras();  
  23.             String scanResult = bundle.getString("result");  
  24.             tv_main_express_number.setText(scanResult);  
  25.         }  
  26.   
  27.     }  


【4】这里在最开始就让MainActivity继承了 Fragment类 实现了 OnClickListener,以便通过switch统一处理监听对象,这种方式处理起来很简洁

[java]  view plain  copy
  1. /* 将监听放在一起统一处理 */  
  2. public void onClick(View v) {  
  3.   
  4.     switch (v.getId()) {  
  5.     // 获取视图的ID进行判断从而做出相应的跳转,获取name参数  
  6.     case R.id.scane_express_number:  
  7.         Intent openCameraIntent = new Intent(getActivity(),  
  8.                 CaptureActivity.class);  
  9.         startActivityForResult(openCameraIntent, 0); // 0跟下面的onActivityResult方法对应,表明触发类型  
  10.   
  11.     case R.id.btn_main_reset:  
  12.         // 重置按钮,将快递单号重置为空  
  13.         tv_main_express_number.setText("");  
  14.         break;  
  15.     case R.id.tv_main_express_name:  
  16.         // 跳转到快递公司选择界面Activity,获取name参数  
  17.         /* 
  18.          * ExpressList中通过getResources()获取string_city_code.xml文件中的定义好的快递公司名称数组 
  19.          * 监听listview的选项item,获取快递公司名称name和对应拼音code封装在intent中回传过来 
  20.          * 在onActivityResult根据其requestcode处理提取 
  21.          */  
  22.         Intent intent = new Intent(getActivity(), ExpressList.class);  
  23.         startActivityForResult(intent, 1);  
  24.         break;  
  25.   
  26.     case R.id.btn_main_search:  
  27.         // 装化成为字符串进行比较判断  
  28.         String name = tv_main_express_name.getText().toString();  
  29.         if (name.equals("")) {  
  30.             Toast.makeText(getActivity(), "请选择快递公司", Toast.LENGTH_SHORT)  
  31.                     .show();  
  32.         } else {  
  33.             String number = tv_main_express_number.getText().toString();  
  34.             if (number.equals("")) {  
  35.                 Toast.makeText(getActivity(), "快递号码不能为空",  
  36.                         Toast.LENGTH_SHORT).show();  
  37.             } else {  
  38.                 // searchForJson(number,name);  
  39.                 // 在对应activity中创建ProgressDialog  
  40.                 progressDialog = new ProgressDialog(getActivity());  
  41.                 // 核心所在!!!  
  42.                 /* 
  43.                  * 输入参数含义分别为: number:快递单号 name:快递名称 code:快递拼音名称 
  44.                  * getActivity()当前Activity/fragment progressDialog控件的名称 
  45.                  */  
  46.                 /* 
  47.                  * 使用Xutil框架中的HttpUtils 
  48.                  * 解析爱查快递提供信息使用Parcelable序列化方式将data和context保存到listInfo 
  49.                  * ,使用intent跳转到ExpressInfoActivity 
  50.                  */  
  51.             <span style="color:#33CC00;"> <span style="color:#006600;">QueryExpressUtil.queryExpressForNumber(number, name, code,  
  52.                         getActivity(), progressDialog);</span></span>  
  53.             }  
  54.   
  55.         }  
  56.             break;  
  57.       default:  
  58.             break;  
  59.     }  
  60. }  


【5】关键处理函数QueryExpressUtil.queryExpressForNumber

QueryExpressUtil.queryExpressForNumber(number, name, code,getActivity(), progressDialog); 

    * 输入参数含义分别为: number:快递单号 name:快递名称 code:快递拼音名称
    * getActivity()当前Activity/fragment progressDialog控件的名称
 整体核心函数主要做了以下几件事情:             
    (1)使用Xutil框架中的HttpUtils通过Get的请求方式,GET请求的数据会附在URL之后(就是 把数据放置在HTTP协议头中),以?分割URL和传输数据,参数之间以&相连(对比下post)

[java]  view plain  copy
  1.               String url;  
  2. url = "http://api.ickd.cn/?id=102616&secret=16135ea51cb60246eff620f130a005bd&com=";  
  3. url += code;  
  4. url += "&nu=";  
  5. url += number;  
  6. url += "&type=json&encode=utf8&ord=asc";  
  7. Log.v("tag", url);// 测试log  
  8. // HttpUtils使用方法:使用普通get方法  
  9. HttpUtils http = new HttpUtils();  
  10. http.send(HttpRequest.HttpMethod.GET, url, new RequestCallBack<String>()   

    (2) 解析爱查快递提供信息使用Parcelable序列化方式将data和context保存到listInfo其中ExpressInfo为序列化数据模型

[java]  view plain  copy
  1. /*将快递信息序列化*/  
  2. public class ExpressInfo implements Parcelable {    //声明实现接口Parcelable  
  3.     public String time;  
  4.     public String context;  
  5.   
  6.      //实例化静态内部对象CREATOR实现接口Parcelable.Creator  
  7.     public static final Parcelable.Creator<ExpressInfo> CREATOR = new Creator<ExpressInfo>() {  
  8.   
  9.         @Override  
  10.          //从Parcel容器中读取传递数据值,封装成Parcelable对象返回逻辑层  
  11.         public ExpressInfo createFromParcel(Parcel source) {  
  12.               
  13.             //先读取time,再读取context   
  14.             ExpressInfo expressInfo = new ExpressInfo();  
  15.             expressInfo.time = source.readString();  
  16.             expressInfo.context = source.readString();  
  17.               
  18.             return expressInfo;  
  19.         }  
  20.   
  21.         @Override  
  22.         //创建一个类型为T,长度为size的数组,仅一句话(return new T[size])即可。方法是供外部类反序列化本类数组使用。  
  23.         public ExpressInfo[] newArray(int size) {  
  24.               
  25.             return new ExpressInfo[size];  
  26.         }  
  27.   
  28.     };  
  29.     //内容接口描述,默认返回0就可以;  
  30.     @Override  
  31.     public int describeContents() {  
  32.         return 0;  
  33.     }  
  34.     //该方法将类的数据写入外部提供的Parcel中.即打包需要传递的数据到Parcel容器保存,以便从parcel容器获取数据  
  35.     @Override  
  36.     public void writeToParcel(Parcel dest, int flags) {  
  37.           
  38.            //先写入time,再写入context  
  39.         dest.writeString(time);  
  40.         dest.writeString(context);  
  41.           
  42.     }  
  43. }  

这里从服务器返回快递信息的是Json格式的数据,过程在Xutil框架中HttpUtils模块onSuccess函数中处理

[java]  view plain  copy
  1. @Override  
  2. public void onSuccess(ResponseInfo<String> responseInfo) {  
  3. try {  
  4.     JSONObject all = new JSONObject(responseInfo.result);// 获取所有的json对象  
  5.     String status = all.getString("status");// 快递状态信息  
  6.                                                                     // 0失败,1正常,2派送中,3已签收,4退回  
  7.   
  8.     if (status.equals(STATE_FAIL)) { // 0代表查找失败  
  9.     String message = all.getString("message"); // message中存储着错误消息  
  10.     Toast.makeText(context, message,  
  11.               Toast.LENGTH_LONG).show();  
  12.     // 关闭ProgressDialog  
  13.     progressDialog.dismiss();  
  14.     return;  
  15.         }  
  16.          // 通过inflate加载aty_express_info文件的控件  
  17.   
  18.        // jsonArray按照爱查快递解析出来data(time/context)其中context就是最重要的快递中转信息  
  19.     JSONArray jsonArray = all.getJSONArray("data");  
  20.     int length = jsonArray.length();  
  21.     Log.v("tag""长度是" + length);  
  22.     <span style="color:#006600;">// !!!!!!!定义调转意图为快递详细信息Activity  
  23.     Intent intent = new Intent(context,ExpressInfoActivity.class);</span>  
  24.   
  25.     // 将快递信息封装到序列化的对象信息中  
  26.     ArrayList<ExpressInfo> infoList = new ArrayList<ExpressInfo>();  
  27.     /* 
  28.     * 扫描数据信息,按照json格式读取快递时间和快递信息,填入到infoList中, 
  29.     * ExpressInfo采用android常用的Parcelable来进行序列化 
  30.     * 将序列化的数据存放到infolist中 
  31.     */  
  32.     for (int i = 0; i < length; i++) {  
  33.     ExpressInfo expressInfo = new ExpressInfo();  
  34.     String time = jsonArray.getJSONObject(i).getString("time");  
  35.     String context = jsonArray.getJSONObject(i).getString("context");  
  36.   
  37.     expressInfo.time = time;  
  38.     expressInfo.context = context;  
  39.   
  40.     infoList.add(expressInfo);  
  41.     }  
  42.   
  43.     // 利用Bundle回传数据  
  44.     Bundle bundle = new Bundle();  
  45.     bundle.putParcelableArrayList("infos", infoList);// intent中传递序列化对象  
  46.   
  47.     intent.putExtras(bundle);// 将序列化的bundle信息放入intent中进行传递  
  48.     intent.putExtra("state", status);// 快递状态  
  49.     intent.putExtra("name", name);// 快递名  
  50.     intent.putExtra("number", number);// 快递编号  
  51.     intent.putExtra("code", code);// 快递拼音  
  52.     // 关闭ProgressDialog  
  53.     progressDialog.dismiss();  
  54.   
  55.     <span style="color:#009900;">// 将回传数据  
  56.     context.startActivity(intent);// 跳转到ExpressInfoActivity.class</span>  
  57.   
  58.     } catch (JSONException e) {  
  59.         e.printStackTrace();  
  60.                 }  
  61.     }  

2.3、使用intent跳转到ExpressInfoActivity

该Activity用来提取序列化的消息并将其显示(ListView)
  

[java]  view plain  copy
  1. /* QueryExpressUtil中带有参数intent跳转 */  
  2.         // 提取序列化info对象  
  3.         infoList = getIntent().getExtras().getParcelableArrayList("infos");  
  4.         // 存储快递实时信息listview  
  5.         lv_express_info = (ListView) findViewById(R.id.lv_express_info_list);  
  6.         // 设置适配器,这里的listView对  
  7.         lv_express_info.setAdapter(<span style="color:#009900;">new ExpressInfoAdapter(this, infoList)</span>);  
  8.         //  
  9.   
  10.         // 获取上一个跳转Activity的Intent参数,快递单号,拼音,快递名称  
  11.         number = getIntent().getStringExtra("number");  
  12.         code = getIntent().getStringExtra("code");  
  13.         name = getIntent().getStringExtra("name");  
  14.         expressState = getIntent().getStringExtra("state");  
  15.         // 根据状态设置信息显示侧栏的动作  
  16.         if (expressState.equals(STATE_RECEIVED)) {  
  17.             // 快递已经签收  
  18.             /* 
  19.              * ((TextView) findViewById(R.id.follow_textview)) 
  20.              * .setCompoundDrawablesWithIntrinsicBounds(0, 0, 
  21.              * R.drawable.icon_success, 0); 
  22.              */  
  23.             findViewById(R.id.colorLine).setBackgroundResource(  
  24.                     R.drawable.red_line_green);  
  25.             findViewById(R.id.dot_full).setVisibility(View.VISIBLE);  
  26.         }  
  27.         if (expressState.equals(STATE_ON_PASSAGE)) {  
  28.             // 快递正在派送中  
  29.             findViewById(R.id.colorLine).setBackgroundResource(  
  30.                     R.drawable.red_line_blue);  
  31.         }  

这里面在加载消息时还使用了Listview的优化,lv_express_info.setAdapter(new ExpressInfoAdapter(this, infoList))

在 ExpressInfoAdapter中,主要使用了ViewHolder/convertView来优化ListView

ViewHolder不是Android的开发API,而是一种设计方法,就是设计个静态类,缓存一下,省得Listview更新的时候,还要重新操作;

convertView 在API中的解释是The old view to reuse, if possible, 第一次getView时还没有convertView,这时你便创建了一个新的view,下次getView时就有这个“旧的”convertView 了  setTag的作用才是把查找的view通过ViewHolder封装好缓存起来方便多次重用,当需要时可以getTag拿出来  ;

[java]  view plain  copy
  1. @Override  
  2.     public View getView(int position, View convertView, ViewGroup parent) {  
  3.         //优化listview的操作使用ViewHolder,将缓存的那些view封装好  
  4.          ViewHolder holder;  
  5.          //第一次创建时缓存起来  
  6.          if (convertView == null) {  
  7.              //得到LayoutInflater实例之后就可以用它来加载方法  
  8.              convertView = mInflater.inflate(R.layout.list_express_info_item,parent, false);  
  9.              //静态加载的viewHolder  
  10.              holder = new ViewHolder();  
  11.              holder.time = (TextView) convertView.findViewById(R.id.tv_info_time);  
  12.              holder.context = (TextView) convertView.findViewById(R.id.tv_info_context);  
  13.              //setTag的作用才是把查找的view通过ViewHolder封装好缓存起来方便多次重用,当需要时可以getTag拿出来  
  14.              convertView.setTag(holder);  
  15.         } else {  
  16.             holder = (ViewHolder) convertView.getTag();  
  17.         }  
  18.         holder.time.setText(lists.get(position).time);  
  19.         holder.context.setText(lists.get(position).context);  
  20.           
  21.         return convertView;  
  22.     }  


2.4 知识点总结

【1】使用fragment与Activity通信(见上)

【2】startActivityForResult与startActivity区别(见上)

【3】Parcelable序列化

Android中实现序列化有两个选择:一是实现Serializable接口 (是JavaSE本身就支持的),一是实现Parcelable接口(Android特有功能,效率比实现Serializable接口高效,可用于 Intent数据传递,也可以用于进程间通信(IPC))。实现Serializable接口非常简单,声明一下就可以了,而实现Parcelable接 口稍微复杂一些(实例化静态内部对象CREATOR实现接口Parcelable.Creator),但效率更高,推荐用这种方法提高性能。
注:Android中Intent传递对象有两种方法:一是 Bundle.putSerializable(Key,Object),另一种是Bundle.putParcelable(Key,Object)。 当然这些Object是有一定的条件的,前者是实现了Serializable接口,而后者是实现了Parcelable接口。
选择序列化方法的原则
1)在使用内存的时候,Parcelable比Serializable性能高,所以推荐使用Parcelable。
2)Serializable在序列化的时候会产生大量的临时变量,从而引起频繁的GC。
3)Parcelable不能使用在要将数据存储在磁盘上的情况,因为Parcelable不能很好的保证数据的持续性在外界有变化的情况下。尽管Serializable效率低点,但此时还是建议使用Serializable 。

【4】Json解析

json一共有两种数据结构,一种是以 (key/value)对形式存在的无序的jsonObject对象,一个对象以“{”(左花括号)开始,“}”(右花括号)结束。每个“名称”后跟一个“:”(冒号);“‘名称/值’ 对”之间使用“,”(逗号)分隔;

另一种数据格式就是有序的value的集合,这种形式被称为是jsonArray,数组是值(value)的有序集合。一个数组以“[”(左中括号)开始,“]”(右中括号)结束。值之间使用“,”(逗号)分隔。

详细的网上有很多,推荐一篇json

【5】Xutil框架

【6】ListView的优化(见上)


转载:http://blog.csdn.net/xsf50717/article/details/47206939

目录
相关文章
|
小程序
【带源码】基于微信小程序的旅游订票旅游预订小程序酒店预订项目
重要的事情说三遍,可白嫖,可白嫖,可白嫖!!! 源码下载链接:docs.qq.com/doc/DYm5DSlBWZEplalBP 随着移动互联网的迅速发展,人们对于旅游信息获取和旅行订票的需求也逐渐增加。传统的旅游指南和订票方式往往不够便捷和灵活,而微信作为一种广泛使用的社交媒体平台,拥有巨大的用户群体和强大的社交属性,成为了传递信息和服务的重要渠道。
|
网络协议 测试技术 Go
家庭收支软件需求和界面|学习笔记
快速学习家庭收支软件需求和界面
家庭收支软件需求和界面|学习笔记
好客租房175-获取当前小区被点击房源数据
好客租房175-获取当前小区被点击房源数据
112 0
好客租房175-获取当前小区被点击房源数据
J3
|
前端开发 数据库
快捷餐饮之店家后台厨艺秀实现
快捷餐饮之店家后台厨艺秀实现
J3
130 0
快捷餐饮之店家后台厨艺秀实现
J3
快捷餐饮之店家后台系统管理实现
快捷餐饮之店家后台系统管理实现
J3
151 0
快捷餐饮之店家后台系统管理实现
J3
快捷餐饮之店家后台员工管理实现
快捷餐饮之店家后台员工管理实现
J3
109 0
快捷餐饮之店家后台员工管理实现
J3
快捷餐饮之店家后台订单管理实现
快捷餐饮之店家后台订单管理实现
J3
145 0
快捷餐饮之店家后台订单管理实现
J3
快捷餐饮之店家后台评论管理及餐桌管理实现
快捷餐饮之店家后台评论管理及餐桌管理实现
J3
174 0
快捷餐饮之店家后台评论管理及餐桌管理实现
|
供应链 API
在平台上添加发快递上门取件的功能-快递物流上门取件API对接
上门取件,是电商平台为寄件用户提供的通过一键下单到快递员,并在2小时上门取件的寄件服务。适用于散客在线寄件、电商退货上门取件等业务场景;通过API指令由系统自动将消息发送给物流公司和快递员,由快递员上门取货揽件与在线收款; 快递鸟上门预约取件api接口 解决寄件客户不用线下找快递员、不用苦苦等待,通过上门取件服务让客户可以轻松选择约定时间、地点完成寄件需求。
1786 0
在平台上添加发快递上门取件的功能-快递物流上门取件API对接