今天遇到了一個比較讓我頭疼的問題,不過追根揭底只是我對listview理解的不夠透徹罷了,
閑言少敘,說說我遇到的問題吧:
上篇隨筆我寫了關於listview的使用,如果你也已經寫好了列表那么恭喜這一篇對你也有用
當然如果你還沒有搭好可以先去看看我的上一篇(上篇地址:http://www.cnblogs.com/wobeinianqing/p/5064740.html)
相信很多新手都跟我一樣總想這把被點擊的item的內容傳遞給相應對的詳情頁,其實這種想法是很錯誤的
listview的功能只管展示給他的數據並不理會數據的內容的。其監聽方法
mListView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) {
}
}
各部分參數:
//adapterView相當於listview Y適配器的一個指針,可以通過它來獲得Y里裝着的一切東西,再通俗點就是說告訴你,你點的是Y,不是X
// view是你點的b這個view的句柄,就是你可以用這個view,來獲得b里的控件的id后操作控件
// i 是b在Y適配器里的位置(生成listview時,適配器一個一個的做item,然后把他們按順序排好隊,在放到listview里,意思就是這個b是第position號做好的)
// l 是b在listview Y里的第幾行的位置(很明顯是第2行)
可以看出通過這些參數並不能得到對應對的數據的那應該怎么拿到相關數據呢?
其實很簡單如果你是靜態數據(自己在前面整個數組,里面放些數據)可以直接利用postion(就是上面的 i )對應這數組的下標找到相應對的數據
但如果你不是其實也是這么個理論,只要你能拿到數據,再根據postion對應下標就好了
下面細說下:
public class MyAdapter extends BaseAdapter { private LayoutInflater mLayoutInflater; // 映射數據 private List<ItemBean> mDataList; //private long mSumTime; private int id; public MyAdapter(Context context, List<ItemBean> list) { mLayoutInflater = LayoutInflater.from(context); mDataList = list; } // 獲取數據量 @Override public int getCount() { return mDataList.size(); } // 獲取對應ID項對應的Item @Override public Map<String , String> getItem(int position) { ItemBean itemBean = mDataList.get(position); Map<String , String> map = new HashMap<String , String>(); map.put("title" , itemBean.itemTitle); map.put("explain" , itemBean.itemContent); map.put("price" , itemBean.itemPrice); map.put("senderPhone" , itemBean.itemSenderPhone); map.put("sendTime" , itemBean.itemSendTime); map.put("endTime" , itemBean.itenEndtime); map.put("sender" , itemBean.itemSender); map.put("receiver" , itemBean.itemReceiver); return map; } // 獲取對應項ID @Override public long getItemId(int position) { return position; } @Override public View getView(int position, View convertView, ViewGroup parent) { // 文藝式 >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> //獲取納秒時間 更加精確 ViewHolder holder = null; if (convertView == null) { holder = new ViewHolder(); //由於我們只需要將XML轉化為View,並不涉及到具體的布局,所以第二個參數通常設置為null convertView = mLayoutInflater.inflate(R.layout.tasklistitem, null); holder.title = (TextView) convertView.findViewById(R.id.task_title); holder.explain = (TextView) convertView.findViewById(R.id.task_explain); holder.price = (TextView) convertView.findViewById(R.id.task_price); holder.faraway = (TextView) convertView.findViewById(R.id.task_distance); convertView.setTag(holder); } else { holder = (ViewHolder) convertView.getTag(); } // 取出bean對象 ItemBean bean = mDataList.get(position); // 設置控件的數據 holder.title.setText(bean.itemTitle); holder.explain.setText(bean.itemContent); holder.price.setText(bean.itemPrice); holder.faraway.setText(bean.itemFaraway); return convertView; // 文藝式 >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>163258 20 } // ViewHolder用於緩存控件 class ViewHolder{ public TextView title;//標題 public TextView explain;//說明 public TextView price;//價格 public TextView faraway;//距離 } }
// 獲取對應ID項對應的Item @Override public Map<String , String> getItem(int position) { ItemBean itemBean = mDataList.get(position); Map<String , String> map = new HashMap<String , String>(); map.put("title" , itemBean.itemTitle); map.put("explain" , itemBean.itemContent); map.put("price" , itemBean.itemPrice); map.put("senderPhone" , itemBean.itemSenderPhone); map.put("sendTime" , itemBean.itemSendTime); map.put("endTime" , itemBean.itenEndtime); map.put("sender" , itemBean.itemSender); map.put("receiver" , itemBean.itemReceiver); return map; }
我獲取的是服務器數據,在自定義adapter 中實現上面的getitem方法,這個方法是默認都要復寫的方法(繼承baseadapter)繼承baseadapter要實現四個方法:
// 獲取數據量 @Override public int getCount() { return mDataList.size(); } // 獲取對應ID項對應的Item @Override public Object getItem(int position) { return postion; } // 獲取對應項ID @Override public long getItemId(int position) { return position; } @Override public View getView(int position, View convertView, ViewGroup parent) {}
看官方多貼心,我們只要重寫上面的getitem方法改成你需要的數據類型
上面我復寫的方法可以看到我要傳遞的內容較多所以我用了個map。我們還看到
數據是從bean中拿到的所以我貼出bean的代碼:
package com.example.guwie.yaoren.ui.Bean; /** * Created by guwei on 15-12-17. */ public class ItemBean { public String itemTitle; public String itemContent; public String itemPrice; public String itemFaraway; public String itemSenderPhone; public String itemSendTime; public String itenEndtime; public String itemSender; public String itemReceiver; /*** * title 標題 * content 說明 * price 價格 * faraway 距離 * */ public ItemBean(String itemTitle, String itemContent, String itemPrice, String itemFaraway, String itemSenderPhone, String itemSendTime, String itenEndtime, String itemSender, String itemReceiver) { this.itemTitle = itemTitle; this.itemContent = itemContent; this.itemPrice = itemPrice; this.itemFaraway = itemFaraway; this.itemSenderPhone = itemSenderPhone; this.itemSendTime = itemSendTime; this.itenEndtime = itenEndtime; this.itemSender = itemSender; this.itemReceiver = itemReceiver; } }
bean的數據從哪來呢?當然從服務器啦。我們看下獲取代碼:
/*** * 獲取list數據 * * */ public void getTaskList(int pages) { //Toast.makeText(TaskList.this , pages+"" , Toast.LENGTH_SHORT).show(); RequestQueue mreuestQueut = Volley.newRequestQueue(this); JsonObjectRequest jsreq = new JsonObjectRequest(Request.Method.GET, TASK_LIST_DATE+"page="+pages, null, new Response.Listener<JSONObject>() { @Override public void onResponse(JSONObject jsonObject) { Message msg = new Message(); try { int code = jsonObject.getInt("code"); if(code == 200){ int size = jsonObject.getJSONArray("data").length(); for(int i=0; i<size ; i++){ JSONObject dataObject = jsonObject.getJSONArray("data").getJSONObject(i); String title = dataObject.getString("title"); String price = dataObject.getString("fee"); String explain = dataObject.getString("description"); String senderPhone = dataObject.getString("senderPhone"); String sendTime = dataObject.getString("sendTime"); String endTime = dataObject.getString("endTime"); String sender = dataObject.getString("sender"); String receiver = dataObject.getString("receiver"); dataList.add(new ItemBean(title , explain , price , "3km" , senderPhone , sendTime, endTime , sender ,receiver )); } maxpage = ++page; page = page-1; }else if(code == 205){ //已無更多數據 //maxpage = page; page = maxpage; msg.what=0x001; mHandler.sendMessage(msg); }else if(code == 404){ //未找到數據 msg.what = 0x002; mHandler.sendMessage(msg); } } catch (JSONException e) { e.printStackTrace(); Log.i("----------------", "客戶端內部錯誤"); } } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError volleyError) { Log.i("----------------","服務器出錯"+volleyError.toString()); } }); mreuestQueut.add(jsreq); }
使用volley獲取數據請自行百度
獲取的是json數據每次傳5條如下:
{
"code":200,
"message":"ok",
"data":[
{
"id":10,
"title":"qwd",
"description":"qwdqwd",
"type":1,
"fee":31,
"senderPhone":"123123",
"sender":23,
"receiver":null,
"sendTime":"2015-12-16 21:11:01",
"endTime":"2015-12-16 21:11:03",
"longtitude":null,
"latitude":null,
"finished":0
},
{
"id":11,
"title":"eqwrwr",
"description":"werwer",
"type":2,
"fee":32,
"senderPhone":null,
"sender":24,
"receiver":null,
"sendTime":"2015-12-18 11:35:41",
"endTime":"2015-12-18 11:35:43",
"longtitude":null,
"latitude":null,
"finished":0
},
{
"id":12,
"title":"sadfef",
"description":"ewqr",
"type":1,
"fee":21,
"senderPhone":"122113",
"sender":24,
"receiver":26,
"sendTime":"2015-12-18 11:35:27",
"endTime":"2015-12-18 11:35:46",
"longtitude":null,
"latitude":null,
"finished":1
},
{
"id":13,
"title":"而通過了",
"description":"435435",
"type":3,
"fee":12,
"senderPhone":"21215",
"sender":26,
"receiver":null,
"sendTime":"2015-12-18 11:36:40",
"endTime":"2015-12-23 11:37:03",
"longtitude":null,
"latitude":null,
"finished":0
},
{
"id":14,
"title":"wefwef",
"description":"23wef",
"type":2,
"fee":12,
"senderPhone":"213214",
"sender":27,
"receiver":25,
"sendTime":"2015-12-18 16:29:42",
"endTime":"2015-12-18 16:29:44",
"longtitude":null,
"latitude":null,
"finished":1
}
]
}
上面處理json數據 的方法是官方對的解析方法當然還有其他方法。通過循環吧數據每次add給自定義的adapter讓它
將數據組裝給list展示,然后就是對每個item進行監聽了:
/** * item 監聽事件 * * */ mListView.setOnItemClickListener(new AdapterView.OnItemClickListener() { @Override public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) { Map<String ,String> map = new MyAdapter(TaskList.this , dataList).getItem(--i);//不減1會出現錯位現象 Intent intent = new Intent(TaskList.this, MorInformation.class); Bundle bundle = new Bundle(); bundle.putString("title" , map.get("title")); bundle.putString("explain" , map.get("explain")); bundle.putString("price" , map.get("price")); bundle.putString("senderPhone" , map.get("senderPhone")); bundle.putString("sendTime" , map.get("sendTime")); bundle.putString("endTime" , map.get("endTime")); bundle.putString("sender" , map.get("sender")); bundle.putString("receiver" , map.get("receiver")); intent.putExtras(bundle); startActivity(intent); } });
這里看到adapter傳來的map又被我用bundle包了一遍。其實我也沒辦法因為intent 並不能傳遞map 只好借助bundle了
這樣在目標頁面就已經能拿到這些數據了。什么?bundle如何拿數據?看看吧:
/** * 放入相關數據 * * */ private void SetData() { Bundle bundle = this.getIntent().getExtras(); title.setText(bundle.getString("title")); explain.setText(bundle.getString("explain")); price.setText(bundle.getString("price")); phone.setText(bundle.getString("senderPhone")); date.setText(bundle.getString("endTime")); add.setText(bundle.getString("explain")); }
其實很簡單是吧, Bundle bundle = this.getIntent().getExtras(); 獲取bundle對象
然后通過bundle.getString("xxx")的方法來拿相應的數據。
就這么多了