zoukankan      html  css  js  c++  java
  • 异步任务下载图片,通过自定义适配器显示在列表

    1.设计

    2.java代码

    下载网络资源工具类

    public class HttpUtils {
    
        // 获取网络上的json字符串
        // 输入String(url)
        // 返回String(jsonStr)
        public static String getHttpStr(String url) {
            HttpClient httpClient = new DefaultHttpClient(); // Http客户端
            HttpGet httpGet = new HttpGet(url); // GET请求
            try {
                HttpResponse response = httpClient.execute(httpGet); // 发起请求
                if(response.getStatusLine().getStatusCode() == 200) {
                    // 200表示连接成功
                    HttpEntity entity = response.getEntity(); // Http实体(有效信息)
                    InputStream is = entity.getContent(); // 通过实体获取网络资源的内容(InputStream)
                    //  开始下载数据
                    ByteArrayOutputStream baos = new ByteArrayOutputStream(); // 输出缓冲流(把全部的网络资源保存起来)
                    byte[] buffer = new byte[1024]; // 缓冲区
                    int ret;
                    while(true) {
                        ret = is.read(buffer);
                        if(ret < 0) {
                            break;
                        }
                        baos.write(buffer, 0, buffer.length); // 每次把缓冲区的内容写入换冲流(缓冲区的内容每次都会不同)
                    }
                    return baos.toString(); // boas中的内容就是我们需要的数据了
                }
            } catch (ClientProtocolException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }
            return null;
        }
        
        // 获取网络上的图片
        // 输入String(url)
        // 返回Bitmap(图片)
        public static Bitmap getHttpBitmap(String url) {
            HttpClient httpClient = new DefaultHttpClient(); // Http客户端
            HttpGet httpGet = new HttpGet(url); // GET请求
            try {
                HttpResponse response = httpClient.execute(httpGet); // 发起请求
                if(response.getStatusLine().getStatusCode() == 200) {
                    // 200表示连接成功
                    HttpEntity entity = response.getEntity(); // Http实体(有效信息)
                    InputStream is = entity.getContent(); // 通过实体获取网络资源的内容(InputStream)
                    //  开始下载数据
                    ByteArrayOutputStream baos = new ByteArrayOutputStream(); // 输出缓冲流(把全部的网络资源保存起来)
                    byte[] buffer = new byte[1024]; // 缓冲区
                    int ret;
                    while(true) { // 屌丝的代码 大神请忽略
                        ret = is.read(buffer);
                        if(ret < 0) {
                            break;
                        }
                        baos.write(buffer, 0, buffer.length); // 每次把缓冲区的内容写入换冲流(缓冲区的内容每次都会不同)
                    }
                    byte[] byteArr = baos.toByteArray(); // boas中的内容就是我们需要的数据了 先转换成字节数组
                    // 把字节数组的内容转换成图片
                    return BitmapFactory.decodeByteArray(byteArr, 0, byteArr.length);
                }
            } catch (ClientProtocolException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }
            return null;
        }
    }

    解析JSON工具类

    public class JSONUtils {
        
        // 格式为 
        // {"person":[{"address":"ServerForJSON/frjj.jpg","id":1001,"name":"Rose"},
        // {"address":"ServerForJSON/frjj2.jpg","id":1002,"name":"Jack"}]} 
        public static List<Person> parsePersonJSONStr(String jsonStr) {
            
            try {
                List<Person> list = new ArrayList<Person>();
                // 最外层的{}(JSONObject) 表示"所有人"
                JSONObject jsonObject = new JSONObject(jsonStr);
                // 根据key="person"获取value(JSONArray)
                JSONArray jsonArray = (JSONArray) jsonObject.get("person");
                // 遍历jsonArray中每一个人 (JSONObject)
                for(int i = 0; i < jsonArray.length(); i++) {
                    // 获取每个人的json对象
                    JSONObject jsonObject2 = (JSONObject) jsonArray.get(i);
                    // 对于每一个人 分别获取address、id、name
                    String address = (String) jsonObject2.get("address");
                    int id = (Integer) jsonObject2.get("id");
                    String name = (String) jsonObject2.get("name");
                    // 通过地址下载并生成图片
                    Bitmap bitmap = HttpUtils.getHttpBitmap(MainActivity.URL+address);
                    // 生成Person的对象
                    Person person = new Person(id, name, address, bitmap);
                    list.add(person); // 添加到list列表中
                }
                return list; // 返回人的列表
            } catch (JSONException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            return null;
        }
    }

    自定义适配器

    public class MyAdapter extends BaseAdapter {
        private List<Person> list;
        private Context context;
        // 通过构造器传递参数 List<Person>、Context
        public MyAdapter(List<Person> list, Context context) {
            this.list = list;
            this.context = context;
        }
        // 获取数据的大小数量(List<Person>)
        @Override
        public int getCount() {
            return list.size();
        }
        // 根据下标获取列表中具体的数据
        @Override
        public Object getItem(int position) {
            return list.get(position);
        }
        // 根据下标获取ID(下标)
        @Override
        public long getItemId(int position) {
            return position;
        }
        // 根据下标获取对应的视图
        @Override
        public View getView(int position, View convertView, ViewGroup parent) {
            View view = null;
            ViewHolder holder = null;
            if(convertView == null) {
                // 1. 首次加载时 没有缓冲的view 只能创建View
                LayoutInflater inflater = LayoutInflater.from(context);
                view = inflater.inflate(R.layout.item, null);
                // 2. 创建holder 并在view中查找holder中的视图(查找是很耗时间的)
                holder = new ViewHolder();
                holder.image = (ImageView) view.findViewById(R.id.image); // 图片
                holder.textview1 = (TextView) view.findViewById(R.id.textview1); // id
                holder.textview2 = (TextView) view.findViewById(R.id.textview2); // 姓名
                // 3. 绑定view和holder
                view.setTag(holder);
            } else {
                // 1. 后面加载时 已经有缓存的view 可复用
                view = convertView;
                // 2. 直接拿来使用
                holder = (ViewHolder) view.getTag();
            }
            // 4. 给image、textview1、textview2赋值
            Person person = list.get(position); // 具体的人
            Bitmap bitmap = person.getBitmap(); // 得到TA的图片
            holder.image.setImageBitmap(bitmap);
            int id = person.getId(); // 得到TA的id
            holder.textview1.setText(id+"");
            String name = person.getName(); // 得到TA的name
            holder.textview2.setText(name);
            // 5. 返回view
            return view;
        }
        // ViewHolder内部类 把视图包装在一起
        public class ViewHolder {
            public ImageView image;// 图片
            public TextView textview1; // id
            public TextView textview2; // 姓名
        }
    }

    异步任务类

    public class MyTask extends AsyncTask<String, Void, List<Person>> {
        private Context context; // 上下文
        private ListView listview; // 列表视图
        // 通过构造器传递参数 context、listview
        public MyTask(Context context, ListView listview) {
            this.context = context;
            this.listview = listview;
        }
    
        // 执行下载、解析json字符串的功能(子线程)
        @Override
        protected List<Person> doInBackground(String... params) {
            String url = params[0]; // 获得输入的url
            // 通过url下载json字符串
            String jsonStr = HttpUtils.getHttpStr(url);
            // 通过json字符串获取人的列表
            List<Person> list = JSONUtils.parsePersonJSONStr(jsonStr);
            // 调试中……测试成功
            Log.i("MyTask", jsonStr);
            for(Person p : list) {
                Log.i("MyTask", p.toString());
            }
            return list;
        }
    
        // 执行后台操作前的准备步骤(主)(显示对话框)
        @Override
        protected void onPreExecute() {
            // TODO Auto-generated method stub
            super.onPreExecute();
        }
        // 执行后台操作后的处理工作(主)(取消对话框、显示结果)
        @Override
        protected void onPostExecute(List<Person> result) {
            // 到这里才开始启动adapter
            // 因为到这里 才能真正得到数据
            MyAdapter adapter = new MyAdapter(result, context);
            listview.setAdapter(adapter); // 把数据设置到listview上
            super.onPostExecute(result);
        }
    
    }

    对象类

    public class Person {
        private int id;
        private String name; // 姓名
        private String address; // 图片地址
        private Bitmap bitmap; // 图片
        // 构造器
        public Person() {}
        public Person(int id, String name, String address, Bitmap bitmap) {
            super();
            this.id = id;
            this.name = name;
            this.address = address;
            this.bitmap = bitmap;
        }
        // getter setter
        public int getId() {
            return id;
        }
        public void setId(int id) {
            this.id = id;
        }
        public String getName() {
            return name;
        }
        public void setName(String name) {
            this.name = name;
        }
        public String getAddress() {
            return address;
        }
        public void setAddress(String address) {
            this.address = address;
        }
        public Bitmap getBitmap() {
            return bitmap;
        }
        public void setBitmap(Bitmap bitmap) {
            this.bitmap = bitmap;
        }
        // toString
        @Override
        public String toString() {
            return "Person [id=" + id + ", name=" + name + ", address=" + address + ", bitmap=" + bitmap + "]";
        }
    }

    MainActivity类

    public class MainActivity extends Activity {
        // 地址常量
        // 下载json字符串时使用:http://10.16.154.26:8080/ServerForJSON/JsonServlet
        //   URL+PATH
        // 下载图片时使用:http://10.16.154.26:8080/ServerForJSON/frjj.jpg
        //   URL+address
        public static final String URL = "http://10.16.154.26:8080/";
        public static final String PATH = "ServerForJSON/JsonServlet";
        private ListView listview;
        private ImageView imageview;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            // 找出activity_main中的listview
            listview = (ListView) findViewById(R.id.listview);
            // 设置当listview中没有数据的时候 显示空白的图片
            imageview = (ImageView) findViewById(R.id.imageview);
            listview.setEmptyView(imageview);
            // 创建异步任务类并启动执行子线程
            MyTask task = new MyTask(MainActivity.this, listview);
            task.execute(URL+PATH);
        }
    }

    3.UML流程图

    4.效果图

     

  • 相关阅读:
    VS2013 此模板尝试加载组件程序集”NuGet.VisualStudio.interop,Version=1.0.0.0 的解决办法
    备份集中的数据库备份与现有的xx数据库不同”解决方法
    Couchbase 集群小实践
    EF5+MVC4系列(1) Podwerdesigner15.1设计数据库;PD中间表和EF实体模型设计器生成中间表的区别;EF5.0 表关系插入数据(一对多,多对多)
    Vue个人笔记
    [转载] HashMap的工作原理-hashcode和equals的区别
    用VS Code写C#
    MongoDB学习笔记一:MongoDB基础
    Vue学习笔记十三:Vue+Bootstrap+vue-resource从接口获取数据库数据
    Vue学习笔记十二:vue-resource的基本使用
  • 原文地址:https://www.cnblogs.com/anni-qianqian/p/5319343.html
Copyright © 2011-2022 走看看