传送门 ☞ 轮子的专栏 ☞ 转载请注明 ☞ http://blog.csdn.net/leverage_1229
雁翎刀
《鹿鼎记》神龙教无根道人:许雪亭一对判官笔向洪教主背心连递两招,同时无根道人的雁翎刀也已砍向他腰间。今天我们学习如何利用Android平台“雁翎刀”ImageView来异步显示从网络下载的图片。像我们在浏览网页中的图片时,经常会遇到图片刷新的情景,尤其是在网络状况不给力的情况下。实质上对于这些图片的加载通常都是以异步方式实现的。下面给出该情景的案例:
1案例技术要点
(1)编写HTTP协议工具类HttpUtils,并提供如下两个方法:getInputStream():获取网络中图片的输入流。getBytes():获取网络中图片的字节数组。(2)开启一个工作线程从网络上读取图片的字节数组,然后将其推送到Handler的消息队列当中。
(3)使用Handler类的handleMessage()方法接收此字节数组,并显示在对应的ImageView控件中。
2案例代码陈列
工程包目录
AndroidManifest.xml
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.android.imageview"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="8"
android:targetSdkVersion="15" />
<uses-permission android:name="android.permission.INTERNET"/>
<application
android:icon="@drawable/ic_launcher"
android:label="@string/app_name" >
<activity
android:name=".ImageViewMainActivity"
android:label="@string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
strings.xml
<resources>
<string name="app_name">ImageView从网络下载图片</string>
<string name="download">下载图片</string>
</resources>
main.xml
<?xml version="1.0" encoding="utf-8" ?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<ImageView
android:id="@+id/imageView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@android:drawable/star_big_on"
android:layout_gravity="center_horizontal" />
<Button
android:id="@+id/download_btn"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/download" />
</LinearLayout>
HTTP请求服务工具类:HttpUtils.java
package com.android.imageview;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import javax.net.ssl.HttpsURLConnection;
/**
* HTTP请求工具类
* @author lynnli1229
*/
public class HttpUtils {
// 网络上待下载图片的路径
private static final String URL_PATH = "http://www.linuxidc.com/upload/2012_12/121218101020341.png";
public static InputStream getInputStream() throws IOException {
InputStream in = null;
URL url = new URL(URL_PATH);
if (url != null) {
HttpsURLConnection conn = (HttpsURLConnection) url.openConnection();
conn.setConnectTimeout(3000);
conn.setRequestMethod("GET");
conn.setDoInput(true);
if (conn.getResponseCode() == 200) {
in = conn.getInputStream();
}
}
return in;
}
public static byte[] getBytes() throws IOException {
byte[] data = null;
InputStream in = null;
int len = 0;
byte[] buffer = new byte[1024];
// 此输出流不需要关闭,直接写入内存中
ByteArrayOutputStream out = new ByteArrayOutputStream();
try {
URL url = new URL(URL_PATH);
if (url != null) {
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
// 设置HTTP连接超时为3s,防止页面出现“假死”现象
conn.setConnectTimeout(3000);
// 设置采用GET方式请求数据
conn.setRequestMethod("GET");
// 允许从服务端读取数据
conn.setDoInput(true);
if (conn.getResponseCode() == 200) { // 服务端响应成功返回码为200
in = conn.getInputStream();
while ((len = in.read(buffer)) != -1) {
out.write(buffer, 0, len);
}
data = out.toByteArray();
}
}
} catch (IOException e) {
throw new IOException();
} finally {
if (in != null) {
try {
in.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
return data;
}
}
ImageViewMainActivity.java
package com.android.imageview;
import java.io.IOException;
import android.app.Activity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.Bundle;
import android.os.Handler;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.ImageView;
/**
* ImageView案例四:从网络上获取图像显示到本地
* ImageView是用于显示图片的控件,支持对图片进行放大、缩小和旋转等
* @author lynnli1229
*/
public class ImageViewMainActivity extends Activity implements OnClickListener {
private Button downloadButton;
private ImageView imageView;
// 设置下载图片的消息标示(当只有一个消息任务时,此标示可以不设置)
private static final int DOWNLOAD_IMAGE = 0x12;
private byte[] data;
private Handler handler = new Handler() {
public void handleMessage(android.os.Message msg) {
// 取出包含下载图片字节数据的消息并处理
byte[] data = (byte[]) msg.obj;
Bitmap bitmap = BitmapFactory.decodeByteArray(data, 0, data.length);
imageView.setImageBitmap(bitmap);
}
};
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
downloadButton = (Button) findViewById(R.id.download_btn);
imageView = (ImageView) findViewById(R.id.imageView);
downloadButton.setOnClickListener(this);
}
@Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.download_btn:
// 点击下载按钮开启一个工作线程来下载图片
new Thread(new Runnable() {
@Override
public void run() {
try {
data = HttpUtils.getBytes();
} catch (IOException e) {
}
// 将封装下载图像的字节数据的消息发送到消息队列中等候处理
handler.sendMessage(handler.obtainMessage(DOWNLOAD_IMAGE, data));
}
}).start();
break;
}
}
}