ViewPager+FragmentPagerAdapter实现简单新闻客户端

2016-03-19 22:29 阅读 13,055 次 评论 10 条

一、摘要

今天工作那么久第一次加班,加班的目的修改已完成大部分的新闻列表的接口,早上一个上午在思考如何在Activity和Fragment之间传递值,Google搜索了一下发现,使用setArguments()和getArguments()方法可以实现,但是集合到现有的掌声平桂APP开发中,一直报错,调试一次次都没法解决,干脆不做了,心烦。。。
004-ViewPager+FragmentPagerAdapter demo

二、查看官方Demo

Google的官方Demo介绍如何使用FragmentPagerAdapter在一个Activity中添加多个Fragment,这些Fragment之间除了传递的参数不一样外,展示的样式和布局都是一样的,有一种恍然一醒的感觉,以前自己的做法是每个Fragment创建一个类,如果有四个Fragment就创建四个,这样做显得有点多余,在官网的Demo里面只有一个Fragment,同时可以在一个ViewPager中创建了无数个Fragment,处理的思路:1、首先创建一个Fragment模板,2、在Fragment构造方法中传递不同的参数,3、重复创建多个Fragment

于是改变一下以往的思路,根据官网提供的做法,自己先创建了一个Demo,项目的结构如下:
001-construction

三、项目结构分析

PagerSlidingTabStrip:

这是一个网上别人封装好的一个自定义View,该类的作用——实现新闻头部拖动或手势滑动切换Fragment的效果,在布局文件activity_main中添加,如下图:
002-navigation

MainActivity:

主要的界面,初始化ViewPager、PagerSlidingTabStrip视图,同时设置ViewPager的FragmentPagerAdapter适配器,这一步设置创建多个Fragment,然后在Fragment设置UI界面。

WebViewFragment:

该类用于获取从MainActivity类传递过来的实参,然后展示,这里直接使用一个WebView控件加载网页,还可以像很多新闻一样获取后台新闻数据,然后排版成新闻列表的样式,如果之前你看过《Android开发之ListView添加多种布局效果演示》这篇文章,你会发现新闻列表之间其实就是多个Fragment,然后添加不同的新闻数据,所以WebViewFragment最终的样式效果,可以根据需要更改。

NewsBean:

这是一个新闻实体,添加了title和url两个属性,一个显示Fragment头部滚动的栏目,一个在WebViewFragment中加载TeachCourse博客栏目页面。

基本思路就是这样子,然后开始完善每个类的代码。再一次验证以前说过的一句话:编程的思路决定出路,有很多时候问题并不是真的很难解决,换个思路考虑,理清楚逻辑比你绞尽脑汁思考要重要得多,总结了那么多,发现还是一塌糊涂
003-layout

四、代码实现

添加webview_fragment.xml布局代码:

  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  3.     android:layout_width="match_parent"  
  4.     android:layout_height="match_parent" >  
  5.     <WebView   
  6.         android:id="@+id/webview_id"  
  7.         android:layout_width="match_parent"  
  8.         android:layout_height="match_parent"/>  
  9.   
  10. </RelativeLayout>  

WebViewFragment重写onCreate()、onCreateView()两个方法,在构造方法中设置传入的参数,并在onCreateView()方法中获取

  1. public class WebViewFragment extends Fragment {  
  2.     String mUrlString;// Activity传递过来的url地址  
  3.   
  4.     /** 
  5.      * 创建多个Fragment,根据传递的值 
  6.      *  
  7.      * @param url 
  8.      * @return 
  9.      */  
  10.     public static WebViewFragment newInstance(String url) {  
  11.         WebViewFragment fragment = new WebViewFragment();  
  12.         Bundle args = new Bundle();  
  13.         args.putString("url", url);  
  14.   
  15.         fragment.setArguments(args);  
  16.         return fragment;  
  17.     }  
  18.       
  19.     /** 
  20.      * 获取传递过来的URL地址 
  21.      *  
  22.      *  
  23.      *  
  24.      */  
  25.     @Override  
  26.     public void onCreate(@Nullable Bundle savedInstanceState) {  
  27.         // TODO Auto-generated method stub  
  28.         super.onCreate(savedInstanceState);  
  29.         mUrlString = getArguments() != null ? getArguments().getString("url")  
  30.                 : "";  
  31.     }  
  32.       
  33.     /* 
  34.      * 初始化布局,并显示URL地址对应的网页 
  35.      *  
  36.      */  
  37.     @Override  
  38.     @Nullable  
  39.     public View onCreateView(LayoutInflater inflater,  
  40.             @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {  
  41.         super.onCreateView(inflater, container, savedInstanceState);  
  42.           
  43.         View view=inflater.inflate(R.layout.webview_fragment, container,false);  
  44.         //获取WebView控件  
  45.         WebView mWebView=(WebView)view.findViewById(R.id.webview_id);  
  46.         WebSettings setting=mWebView.getSettings();  
  47.         setting.setJavaScriptEnabled(true);//设置支持JavaScript  
  48.         mWebView.setWebViewClient(new WebViewClient());  
  49.         mWebView.loadUrl(mUrlString);  
  50.         return view;  
  51.           
  52.     }  
  53.   
  54. }  

添加activity_main.xml布局代码:

  1. <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  2.     xmlns:tools="http://schemas.android.com/tools"  
  3.     android:layout_width="match_parent"  
  4.     android:layout_height="match_parent"  
  5.     tools:context="cn.teachcourse.main.MainActivity" >  
  6.   
  7.     <RelativeLayout  
  8.         android:id="@+id/main_news_rr"  
  9.         android:layout_width="match_parent"  
  10.         android:layout_height="match_parent"  
  11.         android:visibility="visible" >  
  12.   
  13.         <cn.teachcourse.main.view.PagerSlidingTabStrip  
  14.             android:id="@+id/tabs"  
  15.             android:layout_width="match_parent"  
  16.             android:layout_height="40dp" />  
  17.   
  18.         <android.support.v4.view.ViewPager  
  19.             android:id="@+id/pager"  
  20.             android:layout_width="match_parent"  
  21.             android:layout_height="wrap_content"  
  22.             android:layout_below="@+id/tabs" />  
  23.     </RelativeLayout>  
  24.   
  25. </RelativeLayout>  

MainActivity类实现:

  • 在该类中添加了MyPagerAdapter内部类继承FragmentPagerAdapter,必须重写getCount()和getItem()方法两个方法,在getItem()中调用WebViewFragment中newInstance()返回一个Fragment,这一步是是关键,当前getCount()返回的个数决定创建Fragment的个数
  • 初始布局文件,获取控件ViewPager、PagerSlidingTabStrip,并添加ViewPager的适配器MyPagerAdapter
    1. pager.setAdapter(new MyPagerAdapter(getSupportFragmentManager()));  
  • 设置PagerSlidingTabStrip的一些基本属性(通用的代码,不理解也没关系)
    1. tabs.setViewPager(pager);  
    2. // 设置Tab是自动填充满屏幕的  
    3. tabs.setShouldExpand(true);  
    4. // 设置Tab的分割线是透明的  
    5. tabs.setDividerColor(Color.TRANSPARENT);  
    6. // 设置Tab底部线的高度  
    7. tabs.setUnderlineHeight((int) TypedValue.applyDimension(  
    8. TypedValue.COMPLEX_UNIT_DIP, 1, dm));  
    9. // 设置Tab Indicator的高度  
    10. tabs.setIndicatorHeight((int) TypedValue.applyDimension(  
    11.                         TypedValue.COMPLEX_UNIT_DIP, 4, dm));  
    12. // 设置Tab标题文字的大小  
    13. tabs.setTextSize((int) TypedValue.applyDimension(  
    14.                         TypedValue.COMPLEX_UNIT_SP, 16, dm));  
    15. // 设置Tab Indicator的颜色  
    16. tabs.setIndicatorColor(Color.parseColor("#9c231b"));  
    17. // 设置选中Tab文字的颜色 (这是我自定义的一个方法)  
    18. tabs.setSelectedTextColor(Color.parseColor("#9c231b"));  
    19. // 取消点击Tab时的背景色  
    20. tabs.setTabBackground(0);  
  • Demo使用一个工作线程获取NewsBean实体数据,如果你需要获取服务器数据,子线程是必须的,防止阻塞主线程,具体代码:
    1. private void setValues() {  
    2.   
    3.         Runnable run = new Runnable() {  
    4.   
    5.             @Override  
    6.             public void run() {  
    7.                 mList.add(new NewsBean("Android移动开发",  
    8.                         "https://www.teachcourse.cn/cat/android"));  
    9.                 mList.add(new NewsBean("Android Studio",  
    10.                         "https://www.teachcourse.cn/cat/android-studio"));  
    11.                 mList.add(new NewsBean("Genymotion",  
    12.                         "https://www.teachcourse.cn/cat/android/android-genymotion"));  
    13.                 mList.add(new NewsBean("Eclipse",  
    14.                         "https://www.teachcourse.cn/cat/android/android-eclipse"));  
    15.                 mList.add(new NewsBean("忘不掉的旅行""http://go.teachcourse.cn/"));  
    16.   
    17.                 mHandler.sendEmptyMessage(MESSAGE_REFRESH);  
    18.             }  
    19.         };  
    20.         mHandler.post(run);  
    21.     }  

NewsBean实体类:

  1. public class NewsBean implements Serializable {  
  2.   
  3.     /** 
  4.      *  
  5.      */  
  6.     private static final long serialVersionUID = 1L;  
  7.       
  8.     private String title;  
  9.     private String url;  
  10.   
  11.     public NewsBean(String title, String url) {  
  12.         super();  
  13.         this.title = title;  
  14.         this.url = url;  
  15.     }  
  16.     public String getTitle() {  
  17.         return title;  
  18.     }  
  19.     public void setTitle(String title) {  
  20.         this.title = title;  
  21.     }  
  22.     public String getUrl() {  
  23.         return url;  
  24.     }  
  25.     public void setUrl(String url) {  
  26.         this.url = url;  
  27.     }  
  28.       
  29.   
  30. }  

五、manifest添加权限

访问网络需要添加如下权限:

  1. <uses-permission android:name="android.permission.INTERNET"/>  

六、推荐阅读:

AsyncTask==Handler+Thread对比使用说明

ProgressBar+WebView实现自定义浏览器

你可能感兴趣的文章

来源:TeachCourse每周一次,深入学习Android教程,关注(QQ158#9359$239或公众号TeachCourse)
转载请注明出处: https://www.teachcourse.cn/1590.html ,谢谢支持!

资源分享

Android开发之深入理解Android 7.0系统权限更改相关文档 Android开发之深入理解Android
快速更换完整项目所有引用package属性值(包名) 快速更换完整项目所有引用packag
浅谈Java继承 浅谈Java继承
关于接口的理解:源头,接口,终点 关于接口的理解:源头,接口,终