安卓listview加载来自json的数据

来源:互联网 发布:盲僧皮肤龙的传人淘宝 编辑:程序博客网 时间:2024/05/16 07:41

你将会学到如何在安卓中从URL加载数据,如何定义安卓ListView和如何在安卓ListView组件中使用JSON格式。你将会见到如何在一个使用多线程的异步方法中从URL下载数据,如何提取一个使用开放的json库JSON格式数据和如何定义一个定制ListView的adapter.

布局设计

让我们来创建一个新的安卓工程。
activity_main.xml 布局中添加ListView组件

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"    xmlns:tools="http://schemas.android.com/tools"    android:layout_width="match_parent"    android:layout_height="match_parent" >    <ListView        android:layout_width="match_parent"        android:layout_height="match_parent"        android:id="@+id/list"     /></RelativeLayout>

现在创建一个新的安卓XML文件,命名为cell.xml ,它将会被用在定制ListView单元定义。插入两个TextView组件。

<?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="match_parent"    android:orientation="vertical" >    <TextView         android:layout_width="wrap_content"        android:layout_height="50dp"        android:id="@+id/name"        android:layout_alignParentStart="true"        android:gravity="center_vertical"          android:paddingStart="10dp"    />    <TextView         android:layout_width="wrap_content"        android:layout_height="50dp"        android:id="@+id/code"        android:gravity="center_vertical"          android:layout_alignParentEnd="true"        android:paddingEnd="10dp"    /></RelativeLayout>

从URL中加载数据

确保在androidmanifest.xml 中你已经添加访问网络权限。

<uses-permission android:name=”android.permission.INTERNET”></uses-permission>

现在让我们来创建一个将会在后台下载数据的类。创建一个新类,命名为Download_data
在顶端,这个类名被定义的地方,确保写上implements Runnable。这让我们定义一个定制线程类并用来执行后台处理。

package com.kaleidosstudio.listview_load_data_from_json;import java.io.BufferedReader;import java.io.InputStreamReader;import java.net.HttpURLConnection;import java.net.URL;import android.os.Bundle;import android.os.Handler;import android.os.Message;public class Download_data implements Runnable  {    public download_complete caller;    public interface download_complete    {        public void get_data(String data);    }       Download_data(download_complete caller) {                 this.caller = caller;    }    private String link;    public void download_data_from_link(String link)    {        this.link = link;        Thread t = new Thread(this);        t.start();    }    public void run() {        threadMsg(download(this.link));     }     private void threadMsg(String msg) {         if (!msg.equals(null) && !msg.equals("")) {             Message msgObj = handler.obtainMessage();             Bundle b = new Bundle();             b.putString("message", msg);             msgObj.setData(b);             handler.sendMessage(msgObj);         }     }     private final Handler handler = new Handler() {         public void handleMessage(Message msg) {             String Response = msg.getData().getString("message");             caller.get_data(Response);         }     };public static String download(String url) {         URL website;         StringBuilder response = null;        try {            website = new URL(url);            HttpURLConnection connection = (HttpURLConnection) website.openConnection();            connection.setRequestProperty("charset", "utf-8");            BufferedReader in = new BufferedReader(                 new InputStreamReader(                     connection.getInputStream()));            response = new StringBuilder();            String inputLine;            while ((inputLine = in.readLine()) != null)                 response.append(inputLine);            in.close();        } catch (Exception  e) {            return "";        }         return response.toString();     }}

Download_data类定义:

download_data_from_link 作用是提供一个输入链接地址用来下载和启动后台进程。
download 作用是从url下载数据,返回响应数据本身作为一个字符串和运行缺省的线程类进程。
Download_data 有一个构造方法允许定义caller 类和一个接口让后台进程尽可能快地调用caller 类,当数据已经从URL下载下来。

ListView适配器

现在让我们来为ListView定义适配器类,这个类让我们为列表定义定制cell

import android.content.Context;import android.view.LayoutInflater;import android.view.View;import android.view.ViewGroup;import android.widget.BaseAdapter;import android.widget.TextView;public class ListAdapter extends BaseAdapter {    MainActivity main;    ListAdapter(MainActivity main)    {        this.main = main;    }    @Override    public int getCount() {        return  main.countries.size();    }    @Override    public Object getItem(int position) {        return null;    }    @Override    public long getItemId(int position) {        return 0;    }    static class ViewHolderItem {        TextView name;        TextView code;    }    @Override    public View getView(int position, View convertView, ViewGroup parent){        ViewHolderItem holder = new ViewHolderItem();        if (convertView == null) {         LayoutInflater inflater = (LayoutInflater) main.getSystemService(Context.LAYOUT_INFLATER_SERVICE);            convertView = inflater.inflate(R.layout.cell, null);            holder.name = (TextView) convertView.findViewById(R.id.name);            holder.code = (TextView) convertView.findViewById(R.id.code);            convertView.setTag(holder);        }        else        {             holder = (ViewHolderItem) convertView.getTag();        }        holder.name.setText(this.main.countries.get(position).name);        holder.code.setText(this.main.countries.get(position).code);        return convertView;    }}

MainActivity定义 和结构定义

import java.util.ArrayList;import com.kaleidosstudio.listview_load_data_from_json.Download_data.download_complete;import android.app.Activity;import android.os.Bundle;import android.widget.ListView;public class MainActivity extends Activity implements download_complete {    public ListView list;    public ArrayList<Countries> countries = new ArrayList<Countries>();    public ListAdapter adapter;    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_main);        list = (ListView) findViewById(R.id.list);                  adapter = new ListAdapter(this);        list.setAdapter(adapter);        Download_data download_data = new Download_data((download_complete) this);        download_data.download_data_from_link("http://www.kaleidosblog.com/tutorial/tutorial.json");    }    public void get_data(String data)    {    }}

MainActivity 类将会调用download_data 方法,然后会等待数据尽可能快的准备好。这个类将实现download_complete接口中的get_data 方法。

创建一个新类,命名为Countries.java,这个类是我们保存JSON提取的数据而定义的结构。

public class Countries {  String name;  String code;}

安卓json listview:一起来提取数据咯

为了执行json数据的提取,我使用java-json.jar库。这是一个免费的库允许你去做许多json格式操作。保证你也加入了这个库,下图是我的导入方法:
这里写图片描述
现在让我们执行json数据提取。json格式允许发送对象通过数据序列化。
主要的json类型是:数组(Array)对象(Object)
数据定义在[……]中括号中,对象定义在{……}大括号中。
在例子中我提供给你的简单json数据结构是由一个对象数组(an array of objects)组成的。正如下面你看到的结构:
Array[0….N]{ country ; code }

现在让我们来完成get_data 接口功能,只要数据准备好就调用:

public void get_data(String data)    {        try {            JSONArray data_array=new JSONArray(data);            for (int i = 0 ; i < data_array.length() ; i++)            {                JSONObject obj=new JSONObject(data_array.get(i).toString());                Countries add=new Countries();                add.name = obj.getString("country");                add.code = obj.getString("code");                countries.add(add);            }            adapter.notifyDataSetChanged();        } catch (JSONException e) {            e.printStackTrace();        }}

效果如图:
这里写图片描述

0 1
原创粉丝点击