Android 开源框架ActionBarSherlock 和 ViewPager 仿网易新闻客户端

转载请注明出处:http://blog.csdn.net/xiaanming/article/details/9971721

大家都知道Android的ActionBar是在3.0以上才有的,那么在3.0以下呢,google并没有给我提供在3.0以下支持ActionBar的包,但是外国的大牛JakeWharton实现了在3.0以下使用ActionBar, JakeWharton这位大牛是ActionBarSherlock,Android-ViewPagerIndicator ,NineOldAndroids的作者,非常厉害的一个人,Github的关注量超过2.6K,我左侧的友情链接里面有他的Github的主页链接,有兴趣的朋友可以去follow下他,今天我们使用的是他的开源框架ActionBarSherlock,ActionBarSherlock是让Action Bar功能支持2.X后的所有平台,而且他会自动的判断是调用原生Action Bar还是使用扩展ActionBar,很多知名的应用也使用这个库,我之前对ActionBar也不了解,所以就去下了ActionBarSherlock来好好的了解了解ActionBar的使用


把红色框框标记的文件导入Eclipse里面,我们可以先看下例子,来了解下ActionBar的一些使用情况

  • 我们新建一个Android工程,叫ViewPagerAndTab,然后指定ActionBarSherlock为ViewPagerAndTab的库工程,右键工程--->Properties


通过上面的几步我们就指定ActionBarSherlock为ViewPagerAndTab的库工程,接下来我们就能在3.0以下使用ActionBar,我这里使用的是ActionBar  Tab和ViewPager仿网易新闻,我们看看主要代码的编写

1.先看布局文件,里面一个ViewPager,非常简单

  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.     android:background="@android:color/white"> 
  6.      
  7.     <android.support.v4.view.ViewPager     
  8.         android:id="@+id/viewPager"     
  9.         android:layout_width="fill_parent"     
  10.         android:layout_height="wrap_content" />    
  11.  
  12. </RelativeLayout> 
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="@android:color/white">
    
    <android.support.v4.view.ViewPager    
        android:id="@+id/viewPager"    
        android:layout_width="fill_parent"    
        android:layout_height="wrap_content" />   

</RelativeLayout>

2.MainActivity代码,点击ActionBar的Tab,ViewPager切换不同的Fragment,滑动ViewPager,选中相对应的ActiionBar Tab

  1. package com.example.viewpagerandtabdemo; 
  2.  
  3. import java.util.ArrayList; 
  4. import java.util.List; 
  5.  
  6. import android.os.Bundle; 
  7. import android.support.v4.app.Fragment; 
  8. import android.support.v4.app.FragmentTransaction; 
  9. import android.support.v4.view.ViewPager; 
  10. import android.support.v4.view.ViewPager.OnPageChangeListener; 
  11.  
  12. import com.actionbarsherlock.app.ActionBar; 
  13. import com.actionbarsherlock.app.ActionBar.Tab; 
  14. import com.actionbarsherlock.app.SherlockFragmentActivity; 
  15.  
  16. public class MainActivity extends SherlockFragmentActivity implements ActionBar.TabListener, OnPageChangeListener{ 
  17.     /**
  18.      * 顶部Tab的title
  19.      */ 
  20.     private String [] mTabTitles; 
  21.      
  22.     /**
  23.      * ViewPager对象的引用
  24.      */ 
  25.     private ViewPager mViewPager; 
  26.      
  27.     /**
  28.      * 装载Fragment的容器,我们的每一个界面都是一个Fragment
  29.      */ 
  30.     private List<Fragment> mFragmentList; 
  31.      
  32.     /**
  33.      * ActionBar对象的引用
  34.      */ 
  35.     private ActionBar mActionBar; 
  36.  
  37.     @Override 
  38.     protected void onCreate(Bundle savedInstanceState) { 
  39.         super.onCreate(savedInstanceState); 
  40.         setContentView(R.layout.activity_main); 
  41.          
  42.         //从资源文件在获取Tab的title 
  43.         mTabTitles = getResources().getStringArray(R.array.tab_title); 
  44.         mFragmentList =  new ArrayList<Fragment>(); 
  45.          
  46.         mViewPager = (ViewPager) findViewById(R.id.viewPager); 
  47.         //设置Adapter 
  48.         mViewPager.setAdapter(new TabPagerAdapter(getSupportFragmentManager(), mFragmentList)); 
  49.         //设置监听 
  50.         mViewPager.setOnPageChangeListener(this); 
  51.          
  52.          
  53.         //获取Action实例我们使用getSupportActionBar()方法 
  54.         mActionBar = getSupportActionBar(); 
  55.          
  56.         //隐藏Title 
  57.         mActionBar.setDisplayShowTitleEnabled(false); 
  58.         //隐藏Home logo 
  59.         mActionBar.setDisplayShowHomeEnabled(false); 
  60.         //设置ActionBar的导航模式为Tab 
  61.         mActionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS); 
  62.          
  63.          
  64.         //为ActionBar添加Tab并设置TabListener 
  65.         for(int i=0; i<mTabTitles.length; i++){ 
  66.              ActionBar.Tab tab = mActionBar.newTab(); 
  67.              tab.setText(mTabTitles[i]); 
  68.              tab.setTabListener(this); 
  69.              mActionBar.addTab(tab, i); 
  70.         } 
  71.          
  72.          
  73.         //将Fragment加入到List中,并将Tab的title传递给Fragment 
  74.         for(int i=0; i<mTabTitles.length; i++){ 
  75.             Fragment fragment = new ItemFragment(); 
  76.             Bundle args = new Bundle(); 
  77.             args.putString("arg", mTabTitles[i]); 
  78.             fragment.setArguments(args); 
  79.              
  80.             mFragmentList.add(fragment); 
  81.         } 
  82.          
  83.     } 
  84.      
  85.      
  86.  
  87.     @Override 
  88.     public void onTabSelected(Tab tab, FragmentTransaction ft) { 
  89.         //点击ActionBar Tab的时候切换不同的Fragment界面 
  90.         mViewPager.setCurrentItem(tab.getPosition()); 
  91.     } 
  92.  
  93.     @Override 
  94.     public void onTabUnselected(Tab tab, FragmentTransaction ft) { 
  95.  
  96.     } 
  97.  
  98.     @Override 
  99.     public void onTabReselected(Tab tab, FragmentTransaction ft) { 
  100.          
  101.     } 
  102.      
  103.      
  104.     @Override 
  105.     public void onPageScrollStateChanged(int arg0) { 
  106.          
  107.     } 
  108.  
  109.     @Override 
  110.     public void onPageScrolled(int arg0, float arg1, int arg2) { 
  111.          
  112.     } 
  113.  
  114.     @Override 
  115.     public void onPageSelected(int arg0) { 
  116.         //滑动ViewPager的时候设置相对应的ActionBar Tab被选中 
  117.         mActionBar.setSelectedNavigationItem(arg0); 
  118.     } 
  119.  
  120.  
package com.example.viewpagerandtabdemo;

import java.util.ArrayList;
import java.util.List;

import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentTransaction;
import android.support.v4.view.ViewPager;
import android.support.v4.view.ViewPager.OnPageChangeListener;

import com.actionbarsherlock.app.ActionBar;
import com.actionbarsherlock.app.ActionBar.Tab;
import com.actionbarsherlock.app.SherlockFragmentActivity;

public class MainActivity extends SherlockFragmentActivity implements ActionBar.TabListener, OnPageChangeListener{
	/**
	 * 顶部Tab的title
	 */
	private String [] mTabTitles;
	
	/**
	 * ViewPager对象的引用
	 */
	private ViewPager mViewPager;
	
	/**
	 * 装载Fragment的容器,我们的每一个界面都是一个Fragment
	 */
	private List<Fragment> mFragmentList;
	
	/**
	 * ActionBar对象的引用
	 */
	private ActionBar mActionBar;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		
		//从资源文件在获取Tab的title
		mTabTitles = getResources().getStringArray(R.array.tab_title);
		mFragmentList =  new ArrayList<Fragment>();
		
		mViewPager = (ViewPager) findViewById(R.id.viewPager);
		//设置Adapter
		mViewPager.setAdapter(new TabPagerAdapter(getSupportFragmentManager(), mFragmentList));
		//设置监听
		mViewPager.setOnPageChangeListener(this);
		
		
		//获取Action实例我们使用getSupportActionBar()方法
		mActionBar = getSupportActionBar();
		
		//隐藏Title
		mActionBar.setDisplayShowTitleEnabled(false);
		//隐藏Home logo
		mActionBar.setDisplayShowHomeEnabled(false);
		//设置ActionBar的导航模式为Tab
		mActionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
		
		
		//为ActionBar添加Tab并设置TabListener
		for(int i=0; i<mTabTitles.length; i++){
			 ActionBar.Tab tab = mActionBar.newTab();
			 tab.setText(mTabTitles[i]);
			 tab.setTabListener(this);
			 mActionBar.addTab(tab, i);
		}
		
		
		//将Fragment加入到List中,并将Tab的title传递给Fragment
		for(int i=0; i<mTabTitles.length; i++){
			Fragment fragment = new ItemFragment();
			Bundle args = new Bundle();
			args.putString("arg", mTabTitles[i]);
			fragment.setArguments(args);
			
			mFragmentList.add(fragment);
		}
		
	}
	
	

	@Override
	public void onTabSelected(Tab tab, FragmentTransaction ft) {
		//点击ActionBar Tab的时候切换不同的Fragment界面
		mViewPager.setCurrentItem(tab.getPosition());
	}

	@Override
	public void onTabUnselected(Tab tab, FragmentTransaction ft) {

	}

	@Override
	public void onTabReselected(Tab tab, FragmentTransaction ft) {
		
	}
	
	
	@Override
	public void onPageScrollStateChanged(int arg0) {
		
	}

	@Override
	public void onPageScrolled(int arg0, float arg1, int arg2) {
		
	}

	@Override
	public void onPageSelected(int arg0) {
		//滑动ViewPager的时候设置相对应的ActionBar Tab被选中
		mActionBar.setSelectedNavigationItem(arg0);
	}


}
我们使用ActionBarSherlock的时候不再是继承Activity,而是继承SherlockActivity,SherlockDialogFragment,SherlockFragmentActivity等等,我这里用到Fragment,所以继承SherlockFragmentActivity,我们不能随便设置Activity的theme,以后我们要全屏显示的时候直接设置android:theme="@android:style/Theme.Black.NoTitleBar"

,我们使用ActionBar就不能这样设置了,并且不能随便设置他的Theme,必须是Theme.Sherlock, Theme.Sherlock.Light, Theme.Sherlock.Light.DarkActionBar,或者是他们的子样式,不然就会出java.lang.IllegalStateException异常,所以为了自定义ActionBar的Tab,我们必须修改其style

注意:我们还必须删除ViewPagerAndTab工程libs下面的android-support-v4.jar包,因为在ActionBarSherlock已经包含android-support-v4.jar


3.ViewPager的适配器TabPagerAdapter,因为我们用到Fragment,所以我们继承FragmentStatePagerAdapter而不是PagerAdapter

  1. package com.example.viewpagerandtabdemo; 
  2.  
  3. import java.util.List; 
  4.  
  5. import android.support.v4.app.Fragment; 
  6. import android.support.v4.app.FragmentManager; 
  7. import android.support.v4.app.FragmentStatePagerAdapter; 
  8.  
  9. public class TabPagerAdapter extends FragmentStatePagerAdapter { 
  10.     private List<Fragment> list; 
  11.      
  12.     //构造函数 
  13.     public TabPagerAdapter(FragmentManager fm, List<Fragment> list) { 
  14.         super(fm); 
  15.         this.list = list; 
  16.     } 
  17.  
  18.     @Override 
  19.     public Fragment getItem(int arg0) { 
  20.         return list.get(arg0); 
  21.     } 
  22.  
  23.     @Override 
  24.     public int getCount() { 
  25.         return list.size(); 
  26.     } 
  27.  
package com.example.viewpagerandtabdemo;

import java.util.List;

import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentStatePagerAdapter;

public class TabPagerAdapter extends FragmentStatePagerAdapter {
	private List<Fragment> list;
	
	//构造函数
	public TabPagerAdapter(FragmentManager fm, List<Fragment> list) {
		super(fm);
		this.list = list;
	}

	@Override
	public Fragment getItem(int arg0) {
		return list.get(arg0);
	}

	@Override
	public int getCount() {
		return list.size();
	}

}

4.ItemFragment 继承SherlockFragment,也可以直接继承Fragment,里面的的布局比较简单,一个TextView用来显示从Activity传递过来的ActionBar Tab的title

  1. package com.example.viewpagerandtabdemo; 
  2.  
  3. import android.os.Bundle; 
  4. import android.view.LayoutInflater; 
  5. import android.view.View; 
  6. import android.view.ViewGroup; 
  7. import android.widget.TextView; 
  8.  
  9. import com.actionbarsherlock.app.SherlockFragment; 
  10.  
  11.  
  12. public class ItemFragment extends SherlockFragment { 
  13.  
  14.     @Override 
  15.     public View onCreateView(LayoutInflater inflater, ViewGroup container, 
  16.             Bundle savedInstanceState) { 
  17.          
  18.         View contextView = inflater.inflate(R.layout.fragment_item, container, false); 
  19.         TextView mTextView = (TextView) contextView.findViewById(R.id.textview); 
  20.          
  21.         //获取Activity传递过来的参数 
  22.         Bundle mBundle = getArguments(); 
  23.         String title = mBundle.getString("arg"); 
  24.          
  25.         mTextView.setText(title); 
  26.          
  27.         return contextView; 
  28.     } 
  29.  
  30.     @Override 
  31.     public void onActivityCreated(Bundle savedInstanceState) { 
  32.         super.onActivityCreated(savedInstanceState); 
  33.     } 
  34.  
package com.example.viewpagerandtabdemo;

import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;

import com.actionbarsherlock.app.SherlockFragment;


public class ItemFragment extends SherlockFragment {

	@Override
	public View onCreateView(LayoutInflater inflater, ViewGroup container,
			Bundle savedInstanceState) {
		
		View contextView = inflater.inflate(R.layout.fragment_item, container, false);
		TextView mTextView = (TextView) contextView.findViewById(R.id.textview);
		
		//获取Activity传递过来的参数
		Bundle mBundle = getArguments();
		String title = mBundle.getString("arg");
		
		mTextView.setText(title);
		
		return contextView;
	}

	@Override
	public void onActivityCreated(Bundle savedInstanceState) {
		super.onActivityCreated(savedInstanceState);
	}

}
然后我们将上面的Activity的theme设置成android:theme="@style/Theme.Sherlock.Light.DarkActionBar" 运行项目看看效果,下图一是项目的效果,图二是网易的效果


是不是相差很大呢?人家下面的指示条是红色的,我们做出来的是蓝色的,人家选中Tab的字体颜色是红色,我们的不变色等等,那么我们要怎么才能做出网易新闻的那样子的效果,我们需要改变其style,改变如下

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值