1.回顾
在写文章来记录自己的学习的时候,没有录制 gif 效果图,感觉整个人都不好了,还好 通过摸索可以在ubuntu 下 制作gif 动态图 ,从而可以分享给大家了;
2.重点
(1)ViewPage 实现 底部菜单 tab
(2)Fragment 实现 底部菜单 tab
(3)Fragment+ViewPage 实现底部菜单
(4)TabHost 实现 底部菜单 (不推荐)
3.底部菜单实现
实现可以点击切换页面 , 滑动切换页面 ;
3.1 效果图
(1)ViewPage 实现 (2)Fragment实现 (3)ViewPage+Fragment实现
3.2 基本思路
(1)ViewPage实现
- Viewpage实现的是可以点击切换页面和滑动页面切换Tab 的效果,类似与微信(没有过度效果) ;
- ViewPage中的每个页面为布局文件(layout), 不是 Activity 或Fragment ;
- 每个页面的业务处理 交给 business 类实现 ,后在 Viewpage实现类中初始化;
- business类实现,将传入的当前View对象,进行业务交互控制;
(2)Fragment 实现
- 实现了点击切换的效果,没有滑动切换效果 ,类似与手机 QQ ;
- 通过 FragmentManager实现 控制 Fragment ,四个 页面对应四个 Fragment ;
- 通过 FragmentTransaction 来添加和移除Fragment 进行控制 ,不要忘记了 commit ;
- 每个页面的业务交互 都在 Fragment里进行处理;
(3)Fragment+viewpage实现
- 实现里点击切换页面和 滑动页面切换tab , 和viewpage实现一样
- 这种实现方式和viewpage+layout布局实现基本一样 ,不过是将加载布局文件和业务操作 交给了 Fragment 来处理;
- 需要实现 FragmentPagerAdapter
(4)Tabhost实现
3.3 布局和ViewPage业务实现
(1) 实现页面布局
顶部显示 实现:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="50dp"
android:orientation="vertical">
<TextView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:text="无线"
android:textColor="@android:color/white"
android:textSize="20dp"
android:gravity="center"
android:background="@android:color/holo_blue_dark"/>
</LinearLayout>
底部菜单实现:
底部 为 四个 LinearLayout 实现 布局;
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="60dp"
android:background="@android:color/background_light"
android:orientation="horizontal" >
<LinearLayout
android:id="@+id/linear_shouye"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="1"
android:gravity="center"
android:orientation="vertical" >
<!-- 通过设置 ImageButton android:clickable="false" 属性 ; 使其 没有点击的属性,不和 LinearLayout抢占点击事件 -->
<ImageButton
android:id="@+id/img_shouye"
android:layout_width="30dp"
android:layout_height="30dp"
android:background="@android:color/transparent"
android:clickable="false"
android:scaleType="centerCrop"
android:src="@drawable/ic_menu_deal_on" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="首页"
android:textColor="@android:color/black"
android:textSize="16sp" />
</LinearLayout>
<LinearLayout
android:id="@+id/linear_xinxi"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="1"
android:gravity="center"
android:orientation="vertical" >
<ImageButton
android:id="@+id/img_xinxi"
android:layout_width="30dp"
android:layout_height="30dp"
android:background="@android:color/transparent"
android:clickable="false"
android:scaleType="centerCrop"
android:src="@drawable/ic_menu_more_off" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="信息"
android:textColor="@android:color/black"
android:textSize="16sp" />
</LinearLayout>
<LinearLayout
android:id="@+id/linear_gongju"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="1"
android:gravity="center"
android:orientation="vertical" >
<ImageButton
android:id="@+id/img_gongju"
android:layout_width="30dp"
android:layout_height="30dp"
android:background="@android:color/transparent"
android:clickable="false"
android:scaleType="centerCrop"
android:src="@drawable/ic_menu_user_off" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="工具"
android:textColor="@android:color/black"
android:textSize="16sp" />
</LinearLayout>
<LinearLayout
android:id="@+id/linner_wo"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="1"
android:gravity="center"
android:orientation="vertical" >
<ImageButton
android:id="@+id/img_wo"
android:layout_width="30dp"
android:layout_height="30dp"
android:background="@android:color/transparent"
android:clickable="false"
android:scaleType="centerCrop"
android:src="@drawable/ic_menu_poi_off" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="我"
android:textColor="@android:color/black"
android:textSize="16sp" />
</LinearLayout>
</LinearLayout>
主页面实现:
使用 include 实现;
<LinearLayout 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:orientation="vertical"
tools:context="${relativePackage}.${activityClass}" >
<include layout="@layout/top"/>
<!--
这里 使用 weight , 设置为 1 ,高度设置为 0dp后 就填充了 页面的剩余部分
-->
<android.support.v4.view.ViewPager
android:id="@+id/vp_tabs"
android:layout_width="fill_parent"
android:layout_height="0dp"
android:background="#e9e9e9"
android:layout_weight="1"
>
</android.support.v4.view.ViewPager>
<include layout="@layout/buttom"/>
</LinearLayout>
(2)实现 业务
1)给Viewpage设置 OnpageChangeListener 的时候 ,也可以使用 SimpleOnPageChangeListener 实现;
2)这里的ViewPage 加载的是 4个布局文件 ,故 在 对 四个布局文件 实现业务交互的时候 需要 在 business 里处理 ,business 是 自己定义的类, 将当前布局的view对象 传入 实现;
package com.example.tabsdemo;
import java.util.ArrayList;
import java.util.List;
import com.example.Business.PageFourBusiness;
import com.example.Business.PageOneBusiness;
import com.example.Business.PageThreeBusiness;
import com.example.Business.PageTwoBusiness;
import com.example.adapter.TabsPageAdapter;
import android.app.Activity;
import android.os.Bundle;
import android.support.v4.view.ViewPager;
import android.support.v4.view.ViewPager.OnPageChangeListener;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.ImageButton;
import android.widget.LinearLayout;
/**
* 使用说明:
* (1) 实现 top.xml
* (2) 实现 buttom.xml
* (3) 实现 Acitvity.xml 页面
* (4) tab 和 ViewPage 业务 在此类 实现
* (5) 子页面 业务实现 在 com.example.Business
* (7) 基本思路
* 通过 ViewPage 实现页面可滑动 和 tab 可以点击切换页面;
* 子页面业务实现 在Business 里 实现 ,通过 子页面的View来操作 该页面业务;
* 当然 也可以在ViewPage 的监听事件里实现 (单独的将 ViewPage的切换页面的监听事件写成一个类实现) ;
*
* @author yuan
*
*/
public class PagerViewTagsActivity extends Activity implements OnClickListener {
private ViewPager vp_tabs;
private LinearLayout linear_shouye, linear_xinxi, linear_wo, linear_gongju;
private ImageButton img_shouye, img_xinxi, img_wo, img_gongju;
private View one_page, two_page, three_page, four_page;
private List<View> views;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_pagerview_tabs);
views = new ArrayList<View>();
// 初始化
InitView();
}
private void InitView() {
// 初始化工作
vp_tabs = (ViewPager) findViewById(R.id.vp_tabs);
linear_shouye = (LinearLayout) findViewById(R.id.linear_shouye);
linear_gongju = (LinearLayout) findViewById(R.id.linear_gongju);
linear_wo = (LinearLayout) findViewById(R.id.linner_wo);
linear_xinxi = (LinearLayout) findViewById(R.id.linear_xinxi);
img_gongju = (ImageButton) findViewById(R.id.img_gongju);
img_shouye = (ImageButton) findViewById(R.id.img_shouye);
img_wo = (ImageButton) findViewById(R.id.img_wo);
img_xinxi = (ImageButton) findViewById(R.id.img_xinxi);
// 初始化 view 数据
one_page = View.inflate(this, R.layout.vp_onepage, null);
two_page = View.inflate(this, R.layout.vp_twopage, null);
three_page = View.inflate(this, R.layout.vp_threepage, null);
four_page = View.inflate(this, R.layout.vp_fourpage, null);
views.add(one_page);
views.add(two_page);
views.add(three_page);
views.add(four_page);
// 设置 adapter
TabsPageAdapter pageAdapter = new TabsPageAdapter(views);
vp_tabs.setAdapter(pageAdapter);
// 设置tab 点击事件
linear_gongju.setOnClickListener(this);
linear_shouye.setOnClickListener(this);
linear_wo.setOnClickListener(this);
linear_xinxi.setOnClickListener(this);
//设置ViewPage 切换效果
vp_tabs.setOnPageChangeListener(new vp_tabsOnChangeListener());
//子页面 初始化 工作
InitItemPage();
}
/**
* 初始化
* Item 事件处理
*/
private void InitItemPage() {
//初始化 view Item 中的事件
//第一个页面事件
PageOneBusiness onePageBusiness=new PageOneBusiness(this,one_page);
onePageBusiness.OpBusinessInit();
//第二个页面事件
PageTwoBusiness pageTwoBusiness=new PageTwoBusiness(this,two_page);
pageTwoBusiness.OpBusinessInit();
//第三个页面事件
PageThreeBusiness pageThreeBusiness=new PageThreeBusiness(this,three_page);
pageThreeBusiness.OpBusinessInit();
//第四个页面事件
PageFourBusiness pageFourBusiness=new PageFourBusiness(this,four_page);
pageFourBusiness.OpBusinessInit();
}
/**
* Tags 的 点击事件
*/
@Override
public void onClick(View v) {
// tabs 点击事件
ResetTabsImg();
switch (v.getId()) {
case R.id.linear_shouye:
SetTabsSelectedImg(0);
break;
case R.id.linear_gongju:
SetTabsSelectedImg(2);
break;
case R.id.linner_wo:
SetTabsSelectedImg(3);
break;
case R.id.linear_xinxi:
SetTabsSelectedImg(1);
break;
}
}
/**
* (1)实现选中后的 tabs的img
* (2)切换 viewpager item
* @param i
*/
private void SetTabsSelectedImg(int i) {
switch (i) {
case 0:
img_shouye.setImageResource(R.drawable.ic_menu_deal_on);
break;
case 1:
img_xinxi.setImageResource(R.drawable.ic_menu_more_on);
break;
case 2:
img_gongju.setImageResource(R.drawable.ic_menu_user_on);
break;
case 3:
img_wo.setImageResource(R.drawable.ic_menu_poi_on);
break;
}
//切换 viewpage item
vp_tabs.setCurrentItem(i);
}
/**
* 将 tabs 的 图片设置 默认颜色
*/
private void ResetTabsImg() {
// 重置tab 图片
img_gongju.setImageResource(R.drawable.ic_menu_user_off);
img_shouye.setImageResource(R.drawable.ic_menu_deal_off);
img_wo.setImageResource(R.drawable.ic_menu_poi_off);
img_xinxi.setImageResource(R.drawable.ic_menu_more_off);
}
/**
* ViewPage 切换 监听事件
* @author yuan
*
*/
class vp_tabsOnChangeListener implements OnPageChangeListener{
@Override
public void onPageScrollStateChanged(int arg0) {
//
}
@Override
public void onPageScrolled(int arg0, float arg1, int arg2) {
// TODO Auto-generated method stub
}
@Override
public void onPageSelected(int arg0) {
//设置 tab 背景
ResetTabsImg();
SetTabsSelectedImg(arg0);
}
}
}
(3)PageAdapter 实现
package com.example.adapter;
import java.util.List;
import android.support.v4.view.PagerAdapter;
import android.view.View;
import android.view.ViewGroup;
public class TabsPageAdapter extends PagerAdapter {
private List<View> views;
public TabsPageAdapter(List<View> views) {
this.views = views;
}
@Override
public Object instantiateItem(ViewGroup container, int position) {
container.addView(views.get(position));
return views.get(position);
}
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
container.removeView(views.get(position));
}
@Override
public int getCount() {
return views.size();
}
@Override
public boolean isViewFromObject(View arg0, Object arg1) {
return arg0==arg1;
}
}
4.demo 下载
http://download.youkuaiyun.com/detail/lablenet/9116507
5.总结
这四种实现方式 ,我推荐实现 Fragment+viewpager实现 ,因为 层次清晰,业务处理方便 ;在Fragment 进行业务逻辑实现 和 Activity 基本一样,同时 Fragment 还有 生命周期 ,方便控制;最后Fragment 方便和 Activity 进行传参交互;