- 浏览: 473613 次
- 性别:
- 来自: 北京
文章分类
最新评论
-
bewithme:
我把一个透明背景的PNG画到了另外一张图片上,为啥透明背景就变 ...
Java绘制PNG图片时的黑色背景问题 -
davidwkj:
Y坐标的公式不对。算出来的值是错的!!!!!!!!!!!!!! ...
两条线段是否相交,计算交点公式。 -
zhang9181156:
茅塞顿开哈,感谢
android--相机开发 -
leecinwell:
哈
Android条用照相机,实现可剪切功能 -
life_菜鸟飞:
非常感谢作者这么详细的讲解,自己也动手实践了一下,发现前面几个 ...
android--相机开发
系出名门Android(10) - HTTP 通信, XML 解析, 通过 Hander 实现异步消息处理
作者:webabcd
介绍
在 Android 中与服务端做 HTTP 通信,解析 XML,通过 Handler 实现异步消息处理
HTTP 通信 - 与服务端做 HTTP 通信,分别以 GET 方式和 POST 方式做演示
XML 解析 - 可以用两种方式解析 XML,分别是 DOM 方式和 SAX 方式
异步消息处理 - 通过 Handler 实现异步消息处理,以一个自定义的异步下载类来说明 Handler 的用法
1、HTTP 通信和 XML 解析的 Demo
MySAXHandler.java
代码
package com.webabcd.communication;
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;
// 继承 DefaultHandler 以实现指定 XML 的 SAX 解析器
// DOM - W3C 标准,需要把 xml 数据全部加载完成后才能对其做解析,可对树做任意遍历
// SAX - 流式解析,通过事件模型解析 xml,只能顺序解析
public class MySAXHandler extends DefaultHandler {
private boolean mIsTitleTag = false;
private boolean mIsSalaryTag = false;
private boolean mIsBirthTag = false;
private String mResult = "";
// 打开 xml 文档的回调函数
@Override
public void startDocument() throws SAXException {
// TODO Auto-generated method stub
super.startDocument();
}
// 关闭 xml 文档的回调函数
@Override
public void endDocument() throws SAXException {
// TODO Auto-generated method stub
super.endDocument();
}
// 一发现元素开始标记就回调此函数
@Override
public void startElement(String uri, String localName, String qName,
Attributes attributes) throws SAXException {
if (localName == "title")
mIsTitleTag = true;
else if (localName == "salary")
mIsSalaryTag = true;
else if (localName == "dateOfBirth")
mIsBirthTag = true;
else if (localName == "employee")
mResult += "\nname:" + attributes.getValue("name");
}
// 一发现元素结束标记就回调此函数
@Override
public void endElement(String uri, String localName, String qName)
throws SAXException {
if (localName == "title")
mIsTitleTag = false;
else if (localName == "salary")
mIsSalaryTag = false;
else if (localName == "dateOfBirth")
mIsBirthTag = false;
}
// 一发现元素值或属性值就回调此函数
@Override
public void characters(char[] ch, int start, int length)
throws SAXException {
if (mIsTitleTag)
mResult += new String(ch, start, length);
else if (mIsSalaryTag)
mResult += " salary:" + new String(ch, start, length);
else if (mIsBirthTag)
mResult += " dateOfBirth:" + new String(ch, start, length);
}
public String getResult(){
return mResult;
}
}
Main.java
代码
package com.webabcd.communication;
import java.io.BufferedInputStream;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.protocol.HTTP;
import org.apache.http.util.ByteArrayBuffer;
import org.apache.http.util.EncodingUtils;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;
import org.xml.sax.InputSource;
import org.xml.sax.XMLReader;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
public class Main extends Activity {
private TextView textView;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
textView = (TextView) this.findViewById(R.id.textView);
Button btn1 = (Button) this.findViewById(R.id.btn1);
btn1.setText("http get demo");
btn1.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
httpGetDemo();
}
});
Button btn2 = (Button) this.findViewById(R.id.btn2);
btn2.setText("http post demo");
btn2.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
httpPostDemo();
}
});
Button btn3 = (Button) this.findViewById(R.id.btn3);
// DOM - Document Object Model
btn3.setText("DOM 解析 XML");
btn3.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
DOMDemo();
}
});
Button btn4 = (Button) this.findViewById(R.id.btn4);
// SAX - Simple API for XML
btn4.setText("SAX 解析 XML");
btn4.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
SAXDemo();
}
});
}
// Android 调用 http 协议的 get 方法
// 本例:以 http 协议的 get 方法获取远程页面响应的内容
private void httpGetDemo(){
try {
// 模拟器测试时,请使用外网地址
URL url = new URL("http://xxx.xxx.xxx");
URLConnection con = url.openConnection();
String result = "http status code: " + ((HttpURLConnection)con).getResponseCode() + "\n";
// HttpURLConnection.HTTP_OK
InputStream is = con.getInputStream();
BufferedInputStream bis = new BufferedInputStream(is);
ByteArrayBuffer bab = new ByteArrayBuffer(32);
int current = 0;
while ( (current = bis.read()) != -1 ){
bab.append((byte)current);
}
result += EncodingUtils.getString(bab.toByteArray(), HTTP.UTF_8);
bis.close();
is.close();
textView.setText(result);
} catch (Exception e) {
textView.setText(e.toString());
}
}
// Android 调用 http 协议的 post 方法
// 本例:以 http 协议的 post 方法向远程页面传递参数,并获取其响应的内容
private void httpPostDemo(){
try {
// 模拟器测试时,请使用外网地址
String url = "http://5billion.com.cn/post.php";
Map<String, String> data = new HashMap<String, String>();
data.put("name", "webabcd");
data.put("salary", "100");
DefaultHttpClient httpClient = new DefaultHttpClient();
HttpPost httpPost = new HttpPost(url);
ArrayList<BasicNameValuePair> postData = new ArrayList<BasicNameValuePair>();
for (Map.Entry<String, String> m : data.entrySet()) {
postData.add(new BasicNameValuePair(m.getKey(), m.getValue()));
}
UrlEncodedFormEntity entity = new UrlEncodedFormEntity(postData, HTTP.UTF_8);
httpPost.setEntity(entity);
HttpResponse response = httpClient.execute(httpPost);
String result = "http status code: " + response.getStatusLine().getStatusCode() + "\n";
// HttpURLConnection.HTTP_OK
HttpEntity httpEntity = response.getEntity();
InputStream is = httpEntity.getContent();
result += convertStreamToString(is);
textView.setText(result);
} catch (Exception e) {
textView.setText(e.toString());
}
}
// 以 DOM 方式解析 XML(xml 数据详见 res/raw/employee.xml)
private void DOMDemo(){
try {
DocumentBuilderFactory docFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder docBuilder = docFactory.newDocumentBuilder();
Document doc = docBuilder.parse(this.getResources().openRawResource(R.raw.employee));
Element rootElement = doc.getDocumentElement();
NodeList employeeNodeList = rootElement.getElementsByTagName("employee");
textView.setText("DOMDemo" + "\n");
String title = rootElement.getElementsByTagName("title").item(0).getFirstChild().getNodeValue();
textView.append(title);
for (int i=0; i<employeeNodeList.getLength(); i++){
Element employeeElement = ((Element)employeeNodeList.item(i));
String name = employeeElement.getAttribute("name");
String salary = employeeElement.getElementsByTagName("salary").item(0).getFirstChild().getNodeValue();
String dateOfBirth = employeeElement.getElementsByTagName("dateOfBirth").item(0).getFirstChild().getNodeValue();
textView.append("\nname: "+name+" salary: "+salary+" dateOfBirth: " + dateOfBirth);
}
} catch (Exception e) {
textView.setText(e.toString());
}
}
// 以 SAX 方式解析 XML(xml 数据详见 res/raw/employee.xml)
// SAX 解析器的实现详见 MySAXHandler.java
private void SAXDemo(){
try {
SAXParserFactory saxFactory = SAXParserFactory.newInstance();
SAXParser parser = saxFactory.newSAXParser();
XMLReader reader = parser.getXMLReader();
MySAXHandler handler = new MySAXHandler();
reader.setContentHandler(handler);
reader.parse(new InputSource(this.getResources().openRawResource(R.raw.employee)));
String result = handler.getResult();
textView.setText("SAXDemo" + "\n");
textView.append(result);
} catch (Exception e) {
textView.setText(e.toString());
}
}
// 辅助方法,用于把流转换为字符串
private String convertStreamToString(InputStream is) {
BufferedReader reader = new BufferedReader(new InputStreamReader(is));
StringBuilder sb = new StringBuilder();
String line = null;
try {
while ((line = reader.readLine()) != null) {
sb.append(line + "\n");
}
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return sb.toString();
}
}
2、用 Handler 来实现异步消息处理,以一个可以实时汇报下载进度的异步下载类为例
开发一个 Android 类库,本例中此类库名为 webabcd_util
New -> Java Project
项目上点右键 -> Build Path -> Add Libraries -> User Library -> User Libraries -> New -> 为类库起个名字 -> 选中这个类库 -> Add JARs 导入 Android 的 jar 包
项目上点右键 -> Build Path -> Add Libraries -> User Library -> 选择 Android 库
DownloadManagerAsync.java
代码
package webabcd.util;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;
import org.apache.http.protocol.HTTP;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
// 以一个实例,即异步下载,来演示 Android 的异步消息处理(用 Handler 的方式)
public class DownloadManagerAsync {
public DownloadManagerAsync() {
}
// 实例化自定义的 Handler
EventHandler mHandler = new EventHandler(this);
// 按指定 url 地址下载文件到指定路径
public void download(final String url, final String savePath) {
new Thread(new Runnable() {
public void run() {
try {
sendMessage(FILE_DOWNLOAD_CONNECT);
URL sourceUrl = new URL(url);
URLConnection conn = sourceUrl.openConnection();
InputStream inputStream = conn.getInputStream();
int fileSize = conn.getContentLength();
File savefile = new File(savePath);
if (savefile.exists()) {
savefile.delete();
}
savefile.createNewFile();
FileOutputStream outputStream = new FileOutputStream(
savePath, true);
byte[] buffer = new byte[1024];
int readCount = 0;
int readNum = 0;
int prevPercent = 0;
while (readCount < fileSize && readNum != -1) {
readNum = inputStream.read(buffer);
if (readNum > -1) {
outputStream.write(buffer);
readCount = readCount + readNum;
int percent = (int) (readCount * 100 / fileSize);
if (percent > prevPercent) {
// 发送下载进度信息
sendMessage(FILE_DOWNLOAD_UPDATE, percent,
readCount);
prevPercent = percent;
}
}
}
outputStream.close();
sendMessage(FILE_DOWNLOAD_COMPLETE, savePath);
} catch (Exception e) {
sendMessage(FILE_DOWNLOAD_ERROR, e);
Log.e("MyError", e.toString());
}
}
}).start();
}
// 读取指定 url 地址的响应内容
public void download(final String url) {
new Thread(new Runnable() {
public void run() {
try {
sendMessage(FILE_DOWNLOAD_CONNECT);
URL sourceUrl = new URL(url);
URLConnection conn = sourceUrl.openConnection();
conn.setConnectTimeout(3000);
BufferedReader reader = new BufferedReader(
new InputStreamReader(conn.getInputStream(),
HTTP.UTF_8));
String line = null;
StringBuffer content = new StringBuffer();
while ((line = reader.readLine()) != null) {
content.append(line);
}
reader.close();
sendMessage(FILE_DOWNLOAD_COMPLETE, content.toString());
} catch (Exception e) {
sendMessage(FILE_DOWNLOAD_ERROR, e);
Log.e("MyError", e.toString());
}
}
}).start();
}
// 向 Handler 发送消息
private void sendMessage(int what, Object obj) {
// 构造需要向 Handler 发送的消息
Message msg = mHandler.obtainMessage(what, obj);
// 发送消息
mHandler.sendMessage(msg);
}
private void sendMessage(int what) {
Message msg = mHandler.obtainMessage(what);
mHandler.sendMessage(msg);
}
private void sendMessage(int what, int arg1, int arg2) {
Message msg = mHandler.obtainMessage(what, arg1, arg2);
mHandler.sendMessage(msg);
}
private static final int FILE_DOWNLOAD_CONNECT = 0;
private static final int FILE_DOWNLOAD_UPDATE = 1;
private static final int FILE_DOWNLOAD_COMPLETE = 2;
private static final int FILE_DOWNLOAD_ERROR = -1;
// 自定义的 Handler
private class EventHandler extends Handler {
private DownloadManagerAsync mManager;
public EventHandler(DownloadManagerAsync manager) {
mManager = manager;
}
// 处理接收到的消息
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case FILE_DOWNLOAD_CONNECT:
if (mOnDownloadConnectListener != null)
mOnDownloadConnectListener.onDownloadConnect(mManager);
break;
case FILE_DOWNLOAD_UPDATE:
if (mOnDownloadUpdateListener != null)
mOnDownloadUpdateListener.onDownloadUpdate(mManager,
msg.arg1);
break;
case FILE_DOWNLOAD_COMPLETE:
if (mOnDownloadCompleteListener != null)
mOnDownloadCompleteListener.onDownloadComplete(mManager,
msg.obj);
break;
case FILE_DOWNLOAD_ERROR:
if (mOnDownloadErrorListener != null)
mOnDownloadErrorListener.onDownloadError(mManager,
(Exception) msg.obj);
break;
default:
break;
}
}
}
// 定义连接事件
private OnDownloadConnectListener mOnDownloadConnectListener;
public interface OnDownloadConnectListener {
void onDownloadConnect(DownloadManagerAsync manager);
}
public void setOnDownloadConnectListener(OnDownloadConnectListener listener) {
mOnDownloadConnectListener = listener;
}
// 定义下载进度更新事件
private OnDownloadUpdateListener mOnDownloadUpdateListener;
public interface OnDownloadUpdateListener {
void onDownloadUpdate(DownloadManagerAsync manager, int percent);
}
public void setOnDownloadUpdateListener(OnDownloadUpdateListener listener) {
mOnDownloadUpdateListener = listener;
}
// 定义下载完成事件
private OnDownloadCompleteListener mOnDownloadCompleteListener;
public interface OnDownloadCompleteListener {
void onDownloadComplete(DownloadManagerAsync manager, Object result);
}
public void setOnDownloadCompleteListener(
OnDownloadCompleteListener listener) {
mOnDownloadCompleteListener = listener;
}
// 定义下载异常事件
private OnDownloadErrorListener mOnDownloadErrorListener;
public interface OnDownloadErrorListener {
void onDownloadError(DownloadManagerAsync manager, Exception e);
}
public void setOnDownloadErrorListener(OnDownloadErrorListener listener) {
mOnDownloadErrorListener = listener;
}
}
调用上面的自定义的 Android 类库
项目上点右键 -> Properties -> Java Build Path -> Projects -> Add 引用上面的类库
Main.java
代码
package com.webabcd.handler;
import android.app.Activity;
import android.os.Bundle;
import android.widget.TextView;
import webabcd.util.DownloadManagerAsync;
public class Main extends Activity implements
DownloadManagerAsync.OnDownloadCompleteListener,
DownloadManagerAsync.OnDownloadUpdateListener,
DownloadManagerAsync.OnDownloadErrorListener {
TextView txt;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
DownloadManagerAsync manager = new DownloadManagerAsync();
manager.setOnDownloadCompleteListener(this);
manager.setOnDownloadUpdateListener(this);
manager.download("http://files.cnblogs.com/webabcd/Android.rar", "/sdcard/Android.rar");
txt = (TextView) this.findViewById(R.id.txt);
txt.setText("开始下载");
}
public void onDownloadComplete(DownloadManagerAsync manager, Object result) {
txt.setText("下载完成");
}
public void onDownloadUpdate(DownloadManagerAsync manager, int percent) {
txt.setText("下载进度:" + String.valueOf(percent) + "%");
}
public void onDownloadError(DownloadManagerAsync manager, Exception e) {
txt.setText("下载出错");
}
}
作者:webabcd
介绍
在 Android 中与服务端做 HTTP 通信,解析 XML,通过 Handler 实现异步消息处理
HTTP 通信 - 与服务端做 HTTP 通信,分别以 GET 方式和 POST 方式做演示
XML 解析 - 可以用两种方式解析 XML,分别是 DOM 方式和 SAX 方式
异步消息处理 - 通过 Handler 实现异步消息处理,以一个自定义的异步下载类来说明 Handler 的用法
1、HTTP 通信和 XML 解析的 Demo
MySAXHandler.java
代码
package com.webabcd.communication;
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;
// 继承 DefaultHandler 以实现指定 XML 的 SAX 解析器
// DOM - W3C 标准,需要把 xml 数据全部加载完成后才能对其做解析,可对树做任意遍历
// SAX - 流式解析,通过事件模型解析 xml,只能顺序解析
public class MySAXHandler extends DefaultHandler {
private boolean mIsTitleTag = false;
private boolean mIsSalaryTag = false;
private boolean mIsBirthTag = false;
private String mResult = "";
// 打开 xml 文档的回调函数
@Override
public void startDocument() throws SAXException {
// TODO Auto-generated method stub
super.startDocument();
}
// 关闭 xml 文档的回调函数
@Override
public void endDocument() throws SAXException {
// TODO Auto-generated method stub
super.endDocument();
}
// 一发现元素开始标记就回调此函数
@Override
public void startElement(String uri, String localName, String qName,
Attributes attributes) throws SAXException {
if (localName == "title")
mIsTitleTag = true;
else if (localName == "salary")
mIsSalaryTag = true;
else if (localName == "dateOfBirth")
mIsBirthTag = true;
else if (localName == "employee")
mResult += "\nname:" + attributes.getValue("name");
}
// 一发现元素结束标记就回调此函数
@Override
public void endElement(String uri, String localName, String qName)
throws SAXException {
if (localName == "title")
mIsTitleTag = false;
else if (localName == "salary")
mIsSalaryTag = false;
else if (localName == "dateOfBirth")
mIsBirthTag = false;
}
// 一发现元素值或属性值就回调此函数
@Override
public void characters(char[] ch, int start, int length)
throws SAXException {
if (mIsTitleTag)
mResult += new String(ch, start, length);
else if (mIsSalaryTag)
mResult += " salary:" + new String(ch, start, length);
else if (mIsBirthTag)
mResult += " dateOfBirth:" + new String(ch, start, length);
}
public String getResult(){
return mResult;
}
}
Main.java
代码
package com.webabcd.communication;
import java.io.BufferedInputStream;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.protocol.HTTP;
import org.apache.http.util.ByteArrayBuffer;
import org.apache.http.util.EncodingUtils;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;
import org.xml.sax.InputSource;
import org.xml.sax.XMLReader;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
public class Main extends Activity {
private TextView textView;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
textView = (TextView) this.findViewById(R.id.textView);
Button btn1 = (Button) this.findViewById(R.id.btn1);
btn1.setText("http get demo");
btn1.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
httpGetDemo();
}
});
Button btn2 = (Button) this.findViewById(R.id.btn2);
btn2.setText("http post demo");
btn2.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
httpPostDemo();
}
});
Button btn3 = (Button) this.findViewById(R.id.btn3);
// DOM - Document Object Model
btn3.setText("DOM 解析 XML");
btn3.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
DOMDemo();
}
});
Button btn4 = (Button) this.findViewById(R.id.btn4);
// SAX - Simple API for XML
btn4.setText("SAX 解析 XML");
btn4.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
SAXDemo();
}
});
}
// Android 调用 http 协议的 get 方法
// 本例:以 http 协议的 get 方法获取远程页面响应的内容
private void httpGetDemo(){
try {
// 模拟器测试时,请使用外网地址
URL url = new URL("http://xxx.xxx.xxx");
URLConnection con = url.openConnection();
String result = "http status code: " + ((HttpURLConnection)con).getResponseCode() + "\n";
// HttpURLConnection.HTTP_OK
InputStream is = con.getInputStream();
BufferedInputStream bis = new BufferedInputStream(is);
ByteArrayBuffer bab = new ByteArrayBuffer(32);
int current = 0;
while ( (current = bis.read()) != -1 ){
bab.append((byte)current);
}
result += EncodingUtils.getString(bab.toByteArray(), HTTP.UTF_8);
bis.close();
is.close();
textView.setText(result);
} catch (Exception e) {
textView.setText(e.toString());
}
}
// Android 调用 http 协议的 post 方法
// 本例:以 http 协议的 post 方法向远程页面传递参数,并获取其响应的内容
private void httpPostDemo(){
try {
// 模拟器测试时,请使用外网地址
String url = "http://5billion.com.cn/post.php";
Map<String, String> data = new HashMap<String, String>();
data.put("name", "webabcd");
data.put("salary", "100");
DefaultHttpClient httpClient = new DefaultHttpClient();
HttpPost httpPost = new HttpPost(url);
ArrayList<BasicNameValuePair> postData = new ArrayList<BasicNameValuePair>();
for (Map.Entry<String, String> m : data.entrySet()) {
postData.add(new BasicNameValuePair(m.getKey(), m.getValue()));
}
UrlEncodedFormEntity entity = new UrlEncodedFormEntity(postData, HTTP.UTF_8);
httpPost.setEntity(entity);
HttpResponse response = httpClient.execute(httpPost);
String result = "http status code: " + response.getStatusLine().getStatusCode() + "\n";
// HttpURLConnection.HTTP_OK
HttpEntity httpEntity = response.getEntity();
InputStream is = httpEntity.getContent();
result += convertStreamToString(is);
textView.setText(result);
} catch (Exception e) {
textView.setText(e.toString());
}
}
// 以 DOM 方式解析 XML(xml 数据详见 res/raw/employee.xml)
private void DOMDemo(){
try {
DocumentBuilderFactory docFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder docBuilder = docFactory.newDocumentBuilder();
Document doc = docBuilder.parse(this.getResources().openRawResource(R.raw.employee));
Element rootElement = doc.getDocumentElement();
NodeList employeeNodeList = rootElement.getElementsByTagName("employee");
textView.setText("DOMDemo" + "\n");
String title = rootElement.getElementsByTagName("title").item(0).getFirstChild().getNodeValue();
textView.append(title);
for (int i=0; i<employeeNodeList.getLength(); i++){
Element employeeElement = ((Element)employeeNodeList.item(i));
String name = employeeElement.getAttribute("name");
String salary = employeeElement.getElementsByTagName("salary").item(0).getFirstChild().getNodeValue();
String dateOfBirth = employeeElement.getElementsByTagName("dateOfBirth").item(0).getFirstChild().getNodeValue();
textView.append("\nname: "+name+" salary: "+salary+" dateOfBirth: " + dateOfBirth);
}
} catch (Exception e) {
textView.setText(e.toString());
}
}
// 以 SAX 方式解析 XML(xml 数据详见 res/raw/employee.xml)
// SAX 解析器的实现详见 MySAXHandler.java
private void SAXDemo(){
try {
SAXParserFactory saxFactory = SAXParserFactory.newInstance();
SAXParser parser = saxFactory.newSAXParser();
XMLReader reader = parser.getXMLReader();
MySAXHandler handler = new MySAXHandler();
reader.setContentHandler(handler);
reader.parse(new InputSource(this.getResources().openRawResource(R.raw.employee)));
String result = handler.getResult();
textView.setText("SAXDemo" + "\n");
textView.append(result);
} catch (Exception e) {
textView.setText(e.toString());
}
}
// 辅助方法,用于把流转换为字符串
private String convertStreamToString(InputStream is) {
BufferedReader reader = new BufferedReader(new InputStreamReader(is));
StringBuilder sb = new StringBuilder();
String line = null;
try {
while ((line = reader.readLine()) != null) {
sb.append(line + "\n");
}
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return sb.toString();
}
}
2、用 Handler 来实现异步消息处理,以一个可以实时汇报下载进度的异步下载类为例
开发一个 Android 类库,本例中此类库名为 webabcd_util
New -> Java Project
项目上点右键 -> Build Path -> Add Libraries -> User Library -> User Libraries -> New -> 为类库起个名字 -> 选中这个类库 -> Add JARs 导入 Android 的 jar 包
项目上点右键 -> Build Path -> Add Libraries -> User Library -> 选择 Android 库
DownloadManagerAsync.java
代码
package webabcd.util;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;
import org.apache.http.protocol.HTTP;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
// 以一个实例,即异步下载,来演示 Android 的异步消息处理(用 Handler 的方式)
public class DownloadManagerAsync {
public DownloadManagerAsync() {
}
// 实例化自定义的 Handler
EventHandler mHandler = new EventHandler(this);
// 按指定 url 地址下载文件到指定路径
public void download(final String url, final String savePath) {
new Thread(new Runnable() {
public void run() {
try {
sendMessage(FILE_DOWNLOAD_CONNECT);
URL sourceUrl = new URL(url);
URLConnection conn = sourceUrl.openConnection();
InputStream inputStream = conn.getInputStream();
int fileSize = conn.getContentLength();
File savefile = new File(savePath);
if (savefile.exists()) {
savefile.delete();
}
savefile.createNewFile();
FileOutputStream outputStream = new FileOutputStream(
savePath, true);
byte[] buffer = new byte[1024];
int readCount = 0;
int readNum = 0;
int prevPercent = 0;
while (readCount < fileSize && readNum != -1) {
readNum = inputStream.read(buffer);
if (readNum > -1) {
outputStream.write(buffer);
readCount = readCount + readNum;
int percent = (int) (readCount * 100 / fileSize);
if (percent > prevPercent) {
// 发送下载进度信息
sendMessage(FILE_DOWNLOAD_UPDATE, percent,
readCount);
prevPercent = percent;
}
}
}
outputStream.close();
sendMessage(FILE_DOWNLOAD_COMPLETE, savePath);
} catch (Exception e) {
sendMessage(FILE_DOWNLOAD_ERROR, e);
Log.e("MyError", e.toString());
}
}
}).start();
}
// 读取指定 url 地址的响应内容
public void download(final String url) {
new Thread(new Runnable() {
public void run() {
try {
sendMessage(FILE_DOWNLOAD_CONNECT);
URL sourceUrl = new URL(url);
URLConnection conn = sourceUrl.openConnection();
conn.setConnectTimeout(3000);
BufferedReader reader = new BufferedReader(
new InputStreamReader(conn.getInputStream(),
HTTP.UTF_8));
String line = null;
StringBuffer content = new StringBuffer();
while ((line = reader.readLine()) != null) {
content.append(line);
}
reader.close();
sendMessage(FILE_DOWNLOAD_COMPLETE, content.toString());
} catch (Exception e) {
sendMessage(FILE_DOWNLOAD_ERROR, e);
Log.e("MyError", e.toString());
}
}
}).start();
}
// 向 Handler 发送消息
private void sendMessage(int what, Object obj) {
// 构造需要向 Handler 发送的消息
Message msg = mHandler.obtainMessage(what, obj);
// 发送消息
mHandler.sendMessage(msg);
}
private void sendMessage(int what) {
Message msg = mHandler.obtainMessage(what);
mHandler.sendMessage(msg);
}
private void sendMessage(int what, int arg1, int arg2) {
Message msg = mHandler.obtainMessage(what, arg1, arg2);
mHandler.sendMessage(msg);
}
private static final int FILE_DOWNLOAD_CONNECT = 0;
private static final int FILE_DOWNLOAD_UPDATE = 1;
private static final int FILE_DOWNLOAD_COMPLETE = 2;
private static final int FILE_DOWNLOAD_ERROR = -1;
// 自定义的 Handler
private class EventHandler extends Handler {
private DownloadManagerAsync mManager;
public EventHandler(DownloadManagerAsync manager) {
mManager = manager;
}
// 处理接收到的消息
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case FILE_DOWNLOAD_CONNECT:
if (mOnDownloadConnectListener != null)
mOnDownloadConnectListener.onDownloadConnect(mManager);
break;
case FILE_DOWNLOAD_UPDATE:
if (mOnDownloadUpdateListener != null)
mOnDownloadUpdateListener.onDownloadUpdate(mManager,
msg.arg1);
break;
case FILE_DOWNLOAD_COMPLETE:
if (mOnDownloadCompleteListener != null)
mOnDownloadCompleteListener.onDownloadComplete(mManager,
msg.obj);
break;
case FILE_DOWNLOAD_ERROR:
if (mOnDownloadErrorListener != null)
mOnDownloadErrorListener.onDownloadError(mManager,
(Exception) msg.obj);
break;
default:
break;
}
}
}
// 定义连接事件
private OnDownloadConnectListener mOnDownloadConnectListener;
public interface OnDownloadConnectListener {
void onDownloadConnect(DownloadManagerAsync manager);
}
public void setOnDownloadConnectListener(OnDownloadConnectListener listener) {
mOnDownloadConnectListener = listener;
}
// 定义下载进度更新事件
private OnDownloadUpdateListener mOnDownloadUpdateListener;
public interface OnDownloadUpdateListener {
void onDownloadUpdate(DownloadManagerAsync manager, int percent);
}
public void setOnDownloadUpdateListener(OnDownloadUpdateListener listener) {
mOnDownloadUpdateListener = listener;
}
// 定义下载完成事件
private OnDownloadCompleteListener mOnDownloadCompleteListener;
public interface OnDownloadCompleteListener {
void onDownloadComplete(DownloadManagerAsync manager, Object result);
}
public void setOnDownloadCompleteListener(
OnDownloadCompleteListener listener) {
mOnDownloadCompleteListener = listener;
}
// 定义下载异常事件
private OnDownloadErrorListener mOnDownloadErrorListener;
public interface OnDownloadErrorListener {
void onDownloadError(DownloadManagerAsync manager, Exception e);
}
public void setOnDownloadErrorListener(OnDownloadErrorListener listener) {
mOnDownloadErrorListener = listener;
}
}
调用上面的自定义的 Android 类库
项目上点右键 -> Properties -> Java Build Path -> Projects -> Add 引用上面的类库
Main.java
代码
package com.webabcd.handler;
import android.app.Activity;
import android.os.Bundle;
import android.widget.TextView;
import webabcd.util.DownloadManagerAsync;
public class Main extends Activity implements
DownloadManagerAsync.OnDownloadCompleteListener,
DownloadManagerAsync.OnDownloadUpdateListener,
DownloadManagerAsync.OnDownloadErrorListener {
TextView txt;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
DownloadManagerAsync manager = new DownloadManagerAsync();
manager.setOnDownloadCompleteListener(this);
manager.setOnDownloadUpdateListener(this);
manager.download("http://files.cnblogs.com/webabcd/Android.rar", "/sdcard/Android.rar");
txt = (TextView) this.findViewById(R.id.txt);
txt.setText("开始下载");
}
public void onDownloadComplete(DownloadManagerAsync manager, Object result) {
txt.setText("下载完成");
}
public void onDownloadUpdate(DownloadManagerAsync manager, int percent) {
txt.setText("下载进度:" + String.valueOf(percent) + "%");
}
public void onDownloadError(DownloadManagerAsync manager, Exception e) {
txt.setText("下载出错");
}
}
发表评论
-
浅析android应用增量升级
2013-05-29 13:31 2741背景 随着android应用体积的不断增大 ... -
Activity是如何生成一个 view 的
2013-05-16 11:09 1380Activity是一个工人,它来控制Window;Windo ... -
Android 获取新浪天气预报数据
2012-12-07 13:07 3102新浪天气预报地址: http://php.weathe ... -
Android连接网络问题
2012-11-23 11:14 2070一、检查网络是否连接 方法一、 publ ... -
Android异步下载图片并且缓存图片到本地
2012-09-06 16:21 1953转来的,以备不时之需!! 在Android开发中 ... -
Android条用照相机,实现可剪切功能
2012-08-12 12:35 4634public class CameraActivity ... -
android--相机开发
2012-08-10 08:17 11641在android中应用相机功能,一般有两种:一种是直接调 ... -
15个令人震惊的HTML5效果
2012-07-04 10:09 137015个令人震惊的HTML5效果 除非你一直 ... -
Android 读写文件的N种写法
2012-07-04 09:54 1123Android 读写文件的N种写法(待续。。。) ... -
如何干掉360(付代码)
2012-06-29 16:09 1375最近360很凶,有推送的,有桌面图标的,全部会被提示有风 ... -
Cocos2d-x跨Android&iOS平台开发入门
2012-06-26 10:22 1587好吧,确实存在这 ... -
解决Android加载图片时内存溢出的问题
2012-06-18 13:52 46396尽量不要使用setImageBitmap或setImag ... -
android 代码 混淆
2012-06-04 10:22 20831、得到 classes.dex文件;直接用你机器上的 ... -
android代码混淆是出现Conversion to Dalvik format failed with error 1的解决方法
2012-06-04 10:18 4504最近做android项目,给代码混淆时遇到问题,在项目加入混淆 ... -
Surface、SurfaceView、SurfaceHolder及SurfaceHolder.Callback之间的关系
2012-03-20 16:44 1929一、Surface Surface就是“表面”的意思。 ... -
Re-installation failed解决方法
2011-12-27 22:49 4871我的方法:去模拟器卸载上次安装的*.apk ... -
Failed to install *.apk on device 'emulator-5554': timeout
2011-12-20 00:31 9328错误提示: Failed to inst ... -
android 中的 Bitmap
2011-12-20 00:32 3971在Android SDK中说明可以支持的图片格式如下:p ... -
Android 小球重力感应实现
2011-12-16 20:49 1686重力感应主要是依靠手机的加速度传感器(acceleromete ... -
Android中资源文件夹res/raw和assets的使用
2011-12-16 20:37 9573*res/raw和assets的相同点: 1.两者目录 ...
相关推荐
自定义异常类可以通过`throw new CustomException()`抛出,并在`ApiExceptionHandler`中进行处理。 在Lumen中,我们还可以使用中间件来处理特定类型的异常。例如,一个全局的`ErrorMiddleware`可以在所有路由之前...
- 学习案例可能包含使用`Runnable`配合`postDelayed()`来实现异步操作和延时处理。 6. **理解Android生命周期**: - 在Activity或Service中使用Handler时,需要注意生命周期管理。当组件销毁时,必须确保移除所有...
在Android开发领域,Handler是实现线程间通信的重要机制,特别是在UI更新和异步任务处理中扮演着核心角色。标题“hander_sy1.rar_android”表明这是一个关于Android Handler的实例教程,适合初学者进行学习。下面...
在Android开发中,Handler是一种非常重要的机制,它用于在主线程和子线程之间进行通信,处理异步消息。本文将深入探讨Handler的使用,并结合给出的标签"源码"和"工具"来分析其核心原理。 首先,我们了解Handler的...
在Android应用开发中,HandlerMessage1_HandlerMessage是一个关键的主题,涉及到Android系统中的消息处理机制,尤其是Handler、Message和Looper的使用。这些组件是Android异步编程的重要组成部分,用于解决UI线程与...
在Android开发中,异步处理是一项至关重要的技术,主要用于解决主线程执行耗时操作导致的UI卡顿问题。本示例“android 异步刷新demo”着重演示了两种常见的异步处理方式:AsyncTask和Handler,帮助开发者理解它们的...
在Android开发中,Handler是一种非常重要的组件,它与线程通信密切相关,特别是在更新UI和处理异步任务时。本文将深入探讨如何利用Handler构建一个图片浏览器,并结合计时器(Timer)来实现特定功能。 首先,理解...
在Android开发中,`Handler`、`Looper`和`Message`是实现线程间通信的重要组件,它们共同构建了一个消息处理机制。这个机制允许开发者在不同的线程之间传递消息,通常用于更新UI或者执行异步任务。下面我们将深入...
处理程序是接口`javax.xml.rpc.handler.Handler`的实现,它们在消息发送前和接收后被调用,可以用来执行额外的逻辑,如添加安全头部信息。 对于"jax_rpc webservices hander头增加用户密码",这通常指的是在SOAP...
总结起来,通过Handler和TimerTask实现的简易定时器利用了Java的定时任务机制和Android的消息处理机制,可以在指定的间隔内周期性地执行任务。这种实现方式简单易懂,适用于许多基本的定时需求。但在复杂的应用场景...
那么异步消息处理可以用哪呢? 1、用于UI线程当Bitmap加载完成后更新ImageView 2、在图片加载类初始化时,我们会在一个子线程中维护一个Loop实例,当然子线程中也就有了MessageQueue,Looper会一直在那loop停着等待...
这个插件的主要功能是帮助用户更方便地处理和格式化JSON数据。在Web开发过程中,JSON(JavaScript Object Notation)已经成为数据交换的常用格式,因为它简洁、易于阅读和编写。然而,原始的JSON数据往往以一长串不...
Handler是Android中处理异步消息的关键组件,它与Looper和Message紧密配合工作。Looper是消息循环,它持续检查Message Queue(消息队列),并将消息分发给相应的Handler进行处理。Message是实际携带数据的实体,而...
3. **消息循环**:`Looper`类负责管理消息队列,它通过一个无限循环不断地从消息队列中取出消息并交给`Handler`处理。 4. **消息处理**:`Handler`接收到消息后会调用`handleMessage`方法进行处理。在这个方法中,...
(1)理解HTTP协议、URL请示的类别 (2)理解并掌握Android的线程与Hander消息机制 (3)学会使用HttpURLConnection访问网络 (4)学会使用HttpClient访问网络
`Handler`是Android消息处理机制的核心部分,它与`Looper`和`Message`共同协作,实现了线程间的消息传递。`Handler`通常在主线程(UI线程)中创建,用于接收并处理来自其他线程的消息。 ### 2. Handler工作原理 - ...
Android Handler机制是Android异步消息处理的核心,它用于在主线程和子线程之间进行通信,确保UI更新在主线程中执行。以下是对Handler机制实现原理的详细解析: 1. **Handler**: Handler类是消息处理的中心,它有两...
Android之Web Service实现天气预报查询 利用Ksoap实现Web Service功能,大家自己练习的时候需要用到Ksoap2包,下载地址为 http://download.csdn.net/detail/hander_wei/5713765
4. **处理消息**:Looper不断从MessageQueue中获取消息,并通过Handler对象中的handleMessage()方法来处理消息。这样,就可以在主线程中更新UI或执行其他操作。 ```java @Override public void handleMessage...