安卓开发之抓取新闻案例
来源:互联网 发布:乒乓球 吃方便面 知乎 编辑:程序博客网 时间:2024/06/06 05:22
一、概述
这是一个通过HttpClient抓取网页新闻的demo。涉及知识点:通过HttpClient从网络获取新闻(组织成XML格式的),pull解析XML,Android下ListView的使用及优化,将XML资源文件转成视图view显示,安卓下的简单布局,Android消息处理机制。这里使用到的网页新闻是用tomcat下的一个WEB应用中的new.xml来模拟的,虚拟机访问本机可通过如下链接:http://10.0.2.2:8080/应用名称/new.xml 。
二、步骤
下面说一下思路:将新闻内容封装到JavaBean中(新闻内容包括图片、标题、详细信息、跟帖数量),当Activity被创建时,开启一个子线程去访问网络资源(因为Android4.0以后不支持主线程访问网络资源,会抛出异常:
)。解析得到的XML文件,遍历节点得到新闻信息并封装成bean添加到集合中,将此集合通过Message发送给主线程的Handler对象去处理(只有主线程可以修改用户界面),然后自定义一个适配器,将新闻bean的内容添加到指定的控件上,为ListVIew指定当前适配器来显示新闻。
主要代码分成如下几个部分:
1.从网络获取XML文件的输入流
/** * 从网络上获取新闻输入流 * @return 新闻bean组成的list集合 */protected List<NewsInfo> getNewsFromIntenet() {HttpClient client = null;try {// 定义一个客户端client = new DefaultHttpClient();HttpGet get = new HttpGet("http://10.0.2.2:8080/Example/new.xml");// 访问网络资源HttpResponse response = client.execute(get);// 执行get请求得到响应int code = response.getStatusLine().getStatusCode();// 获得状态码if(code == 200){// 请求成功,得到数据并返回InputStream in = response.getEntity().getContent();// 获得内容输入流newsList = getNewsListFromInputStream(in);// 根据流解析指定XMLreturn newsList;// 返回新闻bean组成的list集合}else{// 请求失败,打印日志Log.i(TAG, "请求失败,请检查代码" + code);}} catch (Exception e) {e.printStackTrace();}finally{if(client != null){client.getConnectionManager().shutdown();// 关闭客户端资源}}return null;}
2.通过解析XML文件获得新闻bean组成的list
/** * 从XML中解析newsList * @return News组成的集合 * @throws Exception */private List<NewsInfo> getNewsListFromInputStream(InputStream in) throws Exception {XmlPullParser parser = Xml.newPullParser();// 创建一个解析XML的pull解析器parser.setInput(in, "utf-8");int eventType = parser.getEventType();// 获取事件类型List<NewsInfo> list = null;NewsInfo newsInfo = null;while(eventType != XmlPullParser.END_DOCUMENT){String tagName = parser.getName();// 获取标签名switch(eventType){case XmlPullParser.START_TAG:// 设置指定的内容if("news".equals(tagName)){list = new ArrayList<NewsInfo>();}else if("new".equals(tagName)){newsInfo = new NewsInfo();}else if("title".equals(tagName)){newsInfo.setTitle(parser.nextText());}else if("detail".equals(tagName)){newsInfo.setDetail(parser.nextText());}else if("comment".equals(tagName)){newsInfo.setComment(Integer.valueOf(parser.nextText()));}else if("image".equals(tagName)){newsInfo.setImage(parser.nextText());}break;case XmlPullParser.END_TAG:if("new".equals(tagName)){// 一个new结束,将封装好的新闻bean添加到集合中list.add(newsInfo);}break;default:break;}eventType = parser.next();// 取下一个事件类型}return list;}
3.将获取到的信息通过Message发送给Handler
/** * 初始化操作,开启新的线程去网络获取资源 */public void init() {lvNews = (ListView) findViewById(R.id.lv_news);// 找到用来显示新闻的ListViewnew Thread(new Runnable(){// 开启一个线程去访问网络资源@Overridepublic void run() {List<NewsInfo> newsList = getNewsFromIntenet();Message msg = new Message();if(newsList != null){msg.what = SUCCESS;// 指定消息类型msg.obj = newsList;}else{msg.what = FAILED;}handler.sendMessage(msg);// 发送消息}}).start();// 开启线程}
4.Handler根据Message类型进行相应处理:list为空提示错误,不为空通过适配器将信息展示在ListView上
适配器核心代码:
<span style="font-size:14px;">public View getView(int position, View convertView, ViewGroup parent) {View view = null;ViewHolder holder = null;if(convertView == null){holder = new ViewHolder();view = View.inflate(MainActivity.this, R.layout.layout_news_list, null);holder.sivIcon = (SmartImageView) view.findViewById(R.id.image);holder.tv_title = (TextView) view.findViewById(R.id.tv_title);holder.tv_comment = (TextView) view.findViewById(R.id.tv_comment);holder.tv_detail = (TextView) view.findViewById(R.id.tv_detail);holder.sivIcon.setImageUrl(newsList.get(position).getImage());// 设置图片holder.tv_title.setText(newsList.get(position).getTitle());holder.tv_comment.setText(newsList.get(position).getComment() + "跟帖");holder.tv_detail.setText(newsList.get(position).getDetail());view.setTag(holder);// 将holder对象中的成员变量添加到view中}else{System.out.println("复用以前的view,位置:"+position);view = convertView;holder = (ViewHolder) view.getTag();holder.sivIcon.setImageUrl(newsList.get(position).getImage());// 设置图片holder.tv_title.setText(newsList.get(position).getTitle());holder.tv_comment.setText(newsList.get(position).getComment() + "跟帖");holder.tv_detail.setText(newsList.get(position).getDetail());}return view;}</span>
要注意的:
将XML资源文件转成view有三种方法,底层实现是一样的,这里使用如下方式:view = View.inflate(MainActivity.this, R.layout.layout_news_list, null);
在优化ListView时,可以通过重用convertView减少创建view的次数,再进一步,可通过定义一个类将view中控件声明成成员,如上面的ViewHolder类。
最后,上一个效果图吧:
- 安卓开发之抓取新闻案例
- 安卓开发之简易新闻客户端
- 新闻客户端案例开发
- 如何开发安卓新闻客户端?
- 安卓APP测试之日志抓取
- 安卓新闻客户端编写(一) JSOUP抓取网页信息
- 安卓新闻客户端(二) JSOUP解析HTML 抓取网页内容
- 网络编程之新闻案例
- 安卓新闻客户端
- 安卓开发日记1——虫虫新闻
- 安卓仿手机网易新闻app项目开发系列之(三)数据抓取和解析 上
- 安卓仿手机网易新闻app项目开发系列之(三)数据抓取和解析 下
- 安卓线性布局案例之计算器
- 网络爬虫之抓取网站新闻
- 网页数据抓取之新浪新闻数据
- 抓取新闻
- 【安卓随笔】轻度自虐之使用CMake开发NDK(案例:YUV转RGB)
- 【安卓随笔】引入OpenCV进行NDK开发之图片传递(案例:文字水印)
- thinkphp部署注意事项
- Jenkins使用新经验
- 1089 我很11
- Android应用程序签名
- java.lang.NullPointerException: No FileItemFactory has been set.
- 安卓开发之抓取新闻案例
- 用 WEKA 进行数据挖掘,第 1 部分: 简介和回归
- java之sleep和wait的区别
- kafka server部署配置优化
- 淘宝地址快速提取插件 for 琴朗淘宝助手
- mac系统开机启动项
- Java基础——正则表达式
- Unity3D学习之(C#概念知识复习)
- 为什么说枚举类型类型安全