Android05
网络图片查看器
// 1.得到图片的url路径
URL url = new URL(path);
// 2.通过路径打开一个http的连接
HttpURLConnection conn = (HttpURLConnection) url.openConnection();// http
// 3.得到服务器的返回信息(***)
int code = conn.getResponseCode(); // 200 OK 404 资源没找到 503服务器内部错误
if (code == 200) {
InputStream is = conn.getInputStream();//(***)
Bitmap bitmap = BitmapFactory.decodeStream(is);//(*)
iv.setImageBitmap(bitmap);
is.close();
}
4.权限
<uses-permission android:name="android.permission.INTERNET"/>
http请求的小细节
<EditText
android:id="@+id/et_path"
android:text="http://www.itheima.com/images_new/logo.jpg"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="请输入网络图片的路径" />
conn.setRequestMethod("GET");//设置请求参数为get, 默认的请求方式就是get
conn.setConnectTimeout(5000);//设置请求服务器的超时时间.
String type = conn.getContentType();
int length = conn.getContentLength();
System.out.println("服务器资源的长度:"+length);
System.out.println("服务器返回的数据类型:" + type);
ANR产生的原因
application not response :应用程序无响应
public void click(View view){
try {
System.out.println("线程名:"+Thread.currentThread().getName());
Thread.sleep(10000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
理解(主线程不能阻塞,如果主线程睡了,后面有请求,就响应不了)
主线程就相当于人,人死了就什么都干不了,其他的子线程就没有什么用了.所以主线程是不能停掉的.
主线程模型
放在子线程中(网络连接会有延迟,主线程就阻塞了,会有问题)
public void viewImage(View view) {
new Thread(){ public void run() { //开启新的子线程 去请求网络 获取数据 // 显示这个互联网上的图片 try { // 1.得到图片的url路径 URL url = new URL(path); // 2.通过路径打开一个http的连接 HttpURLConnection conn = (HttpURLConnection) url.openConnection();// http conn.setRequestMethod("GET");//设置请求参数为get, 默认的请求方式就是get conn.setConnectTimeout(5000);//设置请求服务器的超时时间. // 3.得到服务器的返回信息 String type = conn.getContentType(); int length = conn.getContentLength(); System.out.println("服务器资源的长度:"+length); System.out.println("服务器返回的数据类型:" + type); int code = conn.getResponseCode(); // 200 OK 404 资源没找到 503服务器内部错误 if (code == 200) { InputStream is = conn.getInputStream(); //这里有问题 Bitmap bitmap = BitmapFactory.decodeStream(is); iv.setImageBitmap(bitmap); is.close(); } } catch (Exception e) { e.printStackTrace(); } }; }.start();
}
放进子线中又有问题,是显示数据的时候,又要到主线程中显示,只有主线程才能修改ui.
android下的消息机制
//1.定义一个消息处理器(秘书)
private Handler handler = new Handler(){
//2.利用秘书给老板发消息,让主线程更新ui
Message msg = new Message();
msg.obj ="嘎嘎,哈哈哈,呱呱呱----"+i;
handler.sendMessage(msg);
private Handler handler = new Handler(){
//3.秘书处理消息的方法
@Override
public void handleMessage(Message msg) {
String text = (String) msg.obj;
tv.setText(text);
super.handleMessage(msg);
}
};
- 子线程不可以修改ui
- 只有主线程才可以修改ui
- 如果子线程想更新ui就必须利用消息机制处理
- Handler:消息处理器,可以发送消息给主线程的消息队列
- Message Queue :消息队列,主线程里面的一个消息队列
- looper:轮询器,检查消息队列里面是否有消息
理解(子线程要在主线程中显示数据)
- 子线程去找主线程中的Handler,将消息放进Message Queue中
- 主线程有个looper,系统自动调用,看Message Queue中的数据
- 有数据就取出来显示
网络图片查看器的完成
//1.得到消息处理器
private Handler handler = new Handler(){
public void handleMessage(android.os.Message msg) {
switch (msg.what) {
case SUCCESS:
Bitmap bitmap = (Bitmap) msg.obj;
iv.setImageBitmap(bitmap);
break;
case ERROR:
Toast.makeText(MainActivity.this, "获取图片失败", 0).show();
break;
}
};
};
new Thread(){
public void run() {
Message msg = Message.obtain();//节约了内存
msg.what = SUCCESS;
msg.obj = bitmap;
handler.sendMessage(msg);
is.close();
}
} catch (Exception e) {
e.printStackTrace();
Message msg = Message.obtain();
msg.what = ERROR;
handler.sendMessage(msg);
}
};
}.start();
网页源码查看器
- 工具类将流转换成字符串
添加一个弹窗进度框
public class StreamTools {
/**
* 工具方法
* @param is 输入流
* @return 文本字符串
* @throws Exception
*/
public static String readStream(InputStream is) throws Exception{
ByteArrayOutputStream baos = new ByteArrayOutputStream();
byte[] buffer = new byte[1024];
int len = -1;
while((len = is.read(buffer))!=-1){
baos.write(buffer, 0, len);
}
is.close();
String temp = baos.toString();
if(temp.contains("charset=utf-8")){
return temp;
}else if(temp.contains("gb2312")){
return baos.toString("gb2312");
}return null;
}
useragent的使用
conn.setRequestProperty("User-Agent", "Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; .NET4.0C; InfoPath.2");
中文乱码问题的处理
String temp = baos.toString();
if(temp.contains("charset=utf-8")){
return temp;
}else if(temp.contains("gb2312")){
return baos.toString("gb2312");
}return null;
访问网络获取手机归属地
- 网络请求数据+显示
- xml解析
天气预报案例-json数据的解析
String path = "http://wthrcdn.etouch.cn/weather_mini?city="+URLEncoder.encode(cityname,"utf-8");
String json = StreamTools.readStream(is);
JSONObject jsonObj = new JSONObject(json);
String result = jsonObj.getString("desc");
System.out.println(result);
if("OK".equals(result)){
//请求成功
JSONObject dataJSON = jsonObj.getJSONObject("data");
JSONArray array = dataJSON.getJSONArray("forecast");
Message msg = Message.obtain();
msg.obj = array;
msg.what = SUCCESS;
handler.sendMessage(msg);
}else{
//城市信息不正确.
Message msg = Message.obtain();
msg.what = ERROR_CITY;
handler.sendMessage(msg);
}
}
JSONArray array = (JSONArray) msg.obj;
tv_result_day1.setText(array.getJSONObject(0).toString());
新闻客户端的需求和服务器搭建
- apache-tomcat-7.0.53
- G:\apache-tomcat-7.0.53\webapps\ROOT\new.xml / img
连接服务器解析数据
public class NewsInfoService {
/**
* 获取服务器最新的所有的新闻信息
*
* @param path 服务器的路径
* @return null 请求失败
*/
public static List<NewsItem> getAllNews(String path) throws Exception {
List<NewsItem> newsItems = new ArrayList<NewsItem>();//所有新闻的集合
URL url = new URL(path);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("GET");
conn.setConnectTimeout(5000);
Thread.sleep(3000);
int code = conn.getResponseCode();
if (code == 200) {
InputStream is = conn.getInputStream();
XmlPullParser parser = Xml.newPullParser();
parser.setInput(is, "utf-8");
int eventType = parser.getEventType();
NewsItem newsItem = null;
while (eventType != XmlPullParser.END_DOCUMENT) {
switch (eventType) {
case XmlPullParser.START_TAG:
if("item".equals(parser.getName())){
newsItem = new NewsItem();//新闻数据要开始了创建出来对象
}else if("title".equals(parser.getName())){
newsItem.setTitle(parser.nextText());
}else if("description".equals(parser.getName())){
newsItem.setDescription(parser.nextText());
}else if("image".equals(parser.getName())){
newsItem.setImage(parser.nextText());
}else if("type".equals(parser.getName())){
newsItem.setType(parser.nextText());
}else if("comment".equals(parser.getName())){
newsItem.setComment(Integer.parseInt(parser.nextText()));
}
break;
case XmlPullParser.END_TAG:
if("item".equals(parser.getName())){
newsItems.add(newsItem);
}
break;
}
eventType = parser.next();
}
return newsItems;
} else {
return null;
}}}
------------------------------------------------
items = NewsInfoService.getAllNews(getResources()
.getString(R.string.serverpath));
数据的界面展现&正在加载的进度
<ListView
android:id="@+id/lv"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<LinearLayout
android:id="@+id/ll_loading"
android:visibility="invisible"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center"
android:orientation="vertical" >
<ProgressBar
android:layout_width="wrap_content"
android:layout_height="wrap_content"
/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="正在拼命加载中..."
/>
----------------------------------------------------
Handler
ll_loading.setVisibility(View.INVISIBLE);
---------------------------------------------------
// 设置新闻数据到界面. mainActivtyx显示
ll_loading.setVisibility(View.VISIBLE);
作者:u011480946 发表于2016/12/5 21:27:50 原文链接
阅读:59 评论:0 查看评论