android--新闻阅读器实现源码

先看布局文件

MainActivity:
android--新闻阅读器实现源码_第1张图片

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">

    <Button
        android:id="@+id/btnzg"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_marginStart="16dp"
        android:layout_marginTop="16dp"
        android:onClick="btn1"
        android:text="国内新闻	"
        app:layout_constraintEnd_toStartOf="@+id/btnwg"
        app:layout_constraintHorizontal_bias="0.5"
        app:layout_constraintHorizontal_chainStyle="packed"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

    <Button
        android:id="@+id/btnwg"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_marginStart="16dp"
        android:layout_marginTop="16dp"
        android:layout_marginEnd="16dp"
        android:onClick="btn2"
        android:text="国际新闻"
        app:layout_constraintEnd_toStartOf="@+id/btnjj"
        app:layout_constraintHorizontal_bias="0.5"
        app:layout_constraintStart_toEndOf="@+id/btnzg"
        app:layout_constraintTop_toTopOf="parent" />

    <Button
        android:id="@+id/btnjj"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_marginTop="16dp"
        android:layout_marginEnd="16dp"
        android:onClick="btn3"
        android:text="经济新闻"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintHorizontal_bias="0.5"
        app:layout_constraintStart_toEndOf="@+id/btnwg"
        app:layout_constraintTop_toTopOf="parent" />

    <ListView
        android:id="@+id/lv"
        android:layout_width="0dp"
        android:layout_height="0dp"
        android:layout_marginStart="16dp"
        android:layout_marginTop="16dp"
        android:layout_marginEnd="16dp"
        android:layout_marginBottom="16dp"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@+id/btnwg" />

</android.support.constraint.ConstraintLayout>

在创建一个layout 布局页面

android--新闻阅读器实现源码_第2张图片

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/linearLayout"
    android:layout_width="match_parent"
    android:layout_height="wrap_content">

    <TextView
        android:id="@+id/txt_count"
        android:layout_width="0dp"
        android:layout_height="64dp"
        android:layout_marginStart="16dp"
        android:layout_marginTop="16dp"
        android:layout_marginEnd="16dp"
        android:text="TextView"
        android:textSize="24sp"
        android:textStyle="bold"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

    <TextView
        android:id="@+id/txt_author"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_marginStart="32dp"
        android:layout_marginTop="16dp"
        android:layout_marginBottom="16dp"
        android:text="TextView"
        android:textSize="18sp"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintEnd_toStartOf="@+id/txt_Date"
        app:layout_constraintHorizontal_bias="0.5"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@+id/txt_count" />

    <TextView
        android:id="@+id/txt_Date"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_marginStart="16dp"
        android:layout_marginEnd="32dp"
        android:text="TextView"
        android:textAlignment="textEnd"
        android:textSize="18sp"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintHorizontal_bias="0.5"
        app:layout_constraintStart_toEndOf="@+id/txt_author"
        app:layout_constraintTop_toTopOf="@+id/txt_author" />
</android.support.constraint.ConstraintLayout>

创建news 新闻对象

用来放 读取到的每一条新闻

package com.weilaikeji.newsread;

/**
 * Created by hxp on 2019/5/10.
 */

public class news {
//建立新闻xml里面 所需要的字段 
    private String title;
    private String link;
    private String pubDate;
    private String author;
    private String description;

    public String getTitle() {
        return title;
    }

    public void setTitle(String title) {
        this.title = title;
    }

    public String getLink() {
        return link;
    }

    public void setLink(String link) {
        this.link = link;
    }

    public String getPubDate() {
        return pubDate;
    }

    public void setPubDate(String pubDate) {
        this.pubDate = pubDate;
    }

    public String getAuthor() {
        return author;
    }

    public void setAuthor(String author) {
        this.author = author;
    }

    public String getDescription() {
        return description;
    }

    public void setDescription(String description) {
        this.description = description;
    }

    @Override
    public String toString() {
        return "news{" +
                "title='" + title + '\'' +
                ", link='" + link + '\'' +
                ", pubDate='" + pubDate + '\'' +
                ", author='" + author + '\'' +
                ", description='" + description + '\'' +
                '}';
    }
}

创建 xmlPull()解析方法 用来解析下载的xml

package com.weilaikeji.newsread;
import android.util.Xml;
import org.xmlpull.v1.XmlPullParser;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;


public  class NewsPull {
    public static List<news> getNews(InputStream is)throws Throwable{ //创建一个list集合类型的getNews方法,使方法最终返回一个新闻 类型的list 集合 给一个输入流的参数
        List<news> news = null;
        news mnews = null;

        //创建XMLPullParser
        XmlPullParser parser = Xml.newPullParser();
        //解析文件输入流
        parser.setInput(is,"UTF-8");
        int eventType = parser.getEventType();
        while(eventType!=XmlPullParser.END_DOCUMENT){
            switch(eventType){
                case XmlPullParser.START_DOCUMENT:
                    //解析开始的时候初始化list
                    news = new ArrayList<>();
                    break;
                case XmlPullParser.START_TAG:
                    //获得当前指向元素的名字
                    //当指向元素的名字和title,link,author,description 这些属性重合时可以返回他们的值
                    String xpptiele = parser.getName();
                    if("item".equals(parser.getName())){//判断开始标签元素是否是item
                        mnews = new news();
                        mnews.getTitle();
                    }
                    if(mnews!=null){
                        if("title".equals(xpptiele)){
                            mnews.setTitle(parser.nextText());
                        }
                        if("link".equals(xpptiele)){
                            mnews.setLink(parser.nextText());
                        }
                        if("author".equals(xpptiele)){
                            mnews.setAuthor(parser.nextText());
                        }
                        if("description".equals(xpptiele)){
                            mnews.setDescription(parser.nextText());
                        }
                        if("pubDate".equals(xpptiele)){
                            mnews.setPubDate(parser.nextText());
                        }
                    }
                    break;
                //出发结束元素事件
                case XmlPullParser.END_TAG:
                    //判断开始标签元素是否是item
                    if("item".equals(parser.getName())){
                        news.add(mnews);
                        mnews = null;
                    }
                    break;
                default:
                    break;
            }
            eventType = parser.next();
        }
        return news;
    }
}

在MainActivity中

package com.weilaikeji.newsread;

import android.content.Context;
import android.os.Handler;
import android.os.Message;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.ListView;
import android.widget.SimpleAdapter;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class MainActivity extends AppCompatActivity {

    ListView lvs;
    Map<String,Object> map3;
    List<Map<String,Object>> itmes = new ArrayList<>();

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        btn();
    }

    //定义按钮方法 点击那个按钮 获得选中的url 赋值给download()方法
    public static String url ;
    public void btn( ){  //国内新闻(默认显示)
        itmes.clear();
        url="http://www.people.com.cn/rss/politics.xml";
        download();

    };
    public void btn1(View view){  //国内新闻
        itmes.clear();
        url="http://www.people.com.cn/rss/politics.xml";
        download();

    };
    public void btn2(View view){  //体育新闻
        itmes.clear();
        url="http://www.people.com.cn/rss/sports.xml";
        download();
        //"http://www.people.com.cn/rss/haixia.xml"
    };
    public void btn3(View view){  //台湾新闻
        itmes.clear();
        url="http://www.people.com.cn/rss/haixia.xml";
        download();

    };


    Handler handler = new Handler(){//创建一个Android消息处理机制 重写handleMessage方法
        @Override
        public void handleMessage(Message msg) {//处理消息的方法,使用handleMessage去处理消息,里面的参数Message
            //message对象可以接受任何类型的对象 并且可以通过反向强制转换 转换回来
            String title = ((news)msg.obj).getTitle();
            String pubDate = ((news)msg.obj).getPubDate();
            String author = ((news)msg.obj).getAuthor();
            String description = ((news)msg.obj).getDescription();

            map3 = new HashMap<>();//创建map 对象进行复制传递
            map3.put("title",title);
            map3.put("pubDate",pubDate);
            map3.put("author",author);
            map3.put("description",description);

            itmes.add(map3); //将map对象放进 list集合里面

            lvs = MainActivity.this.findViewById(R.id.lv); //获取ListView控件
            lvs.setAdapter(new SimpleAdapter(MainActivity.this,itmes,R.layout.lv2,new String[]{"title","pubDate","author"},new int[]{R.id.txt_count,R.id.txt_Date,R.id.txt_author}));
        }
    };




    //创建一个下载文件的方法
    public void download(){

        //创建一个工作线程,继承 Thread,重新 run 方法,处理耗时操作
        new Thread(){ //创建子线程 引文下载进程是一个缓慢的程序,主线线程不可以使用

            //重写run()方法。
            @Override
            public void run() {
                try {
                    Context context = MainActivity.this.getApplication(); //获取一个Context对象
                    String path =context.getFilesDir()+"/test.xml";        //目的为了获得安卓的file目录
                    String url1 = url;//创建下载连接
                    URL url = new URL(url1);                                //创建一个URL
                    HttpURLConnection con = (HttpURLConnection)url.openConnection();//获得一个HttpURLConnection对象 con
                    con.setConnectTimeout(3*1000);
                    //防止屏蔽程序抓取而返回403错误
                    con.setRequestProperty("User-Agent", "Mozilla/4.0 (compatible; MSIE 5.0; Windows NT; DigExt)");

                    InputStream iso = con.getInputStream(); //通过con 获得一个输入流 iso 对象
                    File file = new File(path);             //创建一个file对象 将路径写入
                    FileOutputStream fos = new FileOutputStream(file);
                    byte[] b = new byte[1024];
                    int count = 0;
                    while((count = iso.read(b,0,1024))!= -1){
                        fos.write(b,0,count);
                        System.out.print(b+"/kb");
                    }
                    fos.close();
                    iso.close();

                    List<news> pull = Pull(); //调用Pull()解析方法解析xml文件 并返回List 对象

                    for(news n : pull){ //遍历list集合
                        Message msg = new Message();   //创建一个 Message 对象 M
                        msg.obj=n;  //message对象可以接受任何类型的对象 并且可以通过反向强制转换 转换回来
                        handler.sendMessage(msg);
                    }

                }
                catch (Exception e){
                    System.out.println(e.getMessage());
                }
            }
        }.start();
    }

    public  List<news> Pull(){
        try {

            Context context = MainActivity.this.getApplication();
            String url = context.getFilesDir()+"/test.xml";
            InputStream fis = new FileInputStream(url);

            List<news> list=NewsPull.getNews(fis);
            for (news n:list){
                System.out.println(n);
            }
            return list;
        } catch (Exception e) {
            e.printStackTrace();
            return  null;
        } catch (Throwable throwable) {
            throwable.printStackTrace();
            return  null;
        }

    }

}

最后添加上权限:

	<!--读写权限-->
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
    <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
    <!--网络权限-->
    <uses-permission android:name="android.permission.INTERNET"/>

我们看一下最终的效果图

android--新闻阅读器实现源码_第3张图片

你可能感兴趣的:(android)