赞
踩
一、实现效果
二、思路分析
三、实现方式1(ViewPager方式)
1.代码结构
2.代码文件
2.1 顶部 activity_top.xml
- <?xml version="1.0" encoding="utf-8"?>
-
- <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:tools="http://schemas.android.com/tools"
- android:layout_width="match_parent"
- android:background="#ffffff"
- android:paddingTop="10dp"
- android:paddingLeft="10dp"
- android:layout_height="45dp">
-
- <TextView
- android:id="@+id/title"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:text="微信"
- android:textColor="#1B940A"
- android:textSize="16dp" />
-
- </RelativeLayout>
2.2 底部 activity_bottom.xml
- <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="wrap_content"
- android:background="#ffffff"
- android:padding="5dp"
- >
-
- <LinearLayout
- android:id="@+id/ll_home"
- android:layout_width="0dp"
- android:layout_height="wrap_content"
- android:layout_weight="1"
- android:gravity="center"
- android:orientation="vertical">
-
- <ImageView
- android:id="@+id/img_home"
- android:layout_width="24dp"
- android:layout_height="24dp"
- android:src="@mipmap/home" />
-
- <TextView
- android:id="@+id/txt_home"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_marginTop="3dp"
- android:text="@string/txt_nav_home"
- android:textSize="12dp"
- android:textColor="#888888"
- />
- </LinearLayout>
-
- <LinearLayout
- android:id="@+id/ll_news"
- android:layout_width="0dp"
- android:layout_height="wrap_content"
- android:layout_weight="1"
- android:gravity="center"
- android:orientation="vertical">
-
- <ImageView
- android:id="@+id/img_news"
- android:layout_width="24dp"
- android:layout_height="24dp"
- android:src="@mipmap/news_index" />
-
- <TextView
- android:id="@+id/txt_news"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_marginTop="3dp"
- android:text="@string/txt_nav_news"
- android:textSize="12dp"
- android:textColor="#888888"
- />
- </LinearLayout>
-
- <LinearLayout
- android:id="@+id/ll_friend"
- android:layout_width="0dp"
- android:layout_height="wrap_content"
- android:layout_weight="1"
- android:gravity="center"
- android:orientation="vertical">
-
- <ImageView
- android:id="@+id/img_friend"
- android:layout_width="24dp"
- android:layout_height="24dp"
- android:src="@mipmap/news_add" />
-
- <TextView
- android:id="@+id/txt_friend"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_marginTop="3dp"
- android:text="@string/txt_nav_friend"
- android:textSize="12dp"
- android:textColor="#888888"
- />
- </LinearLayout>
-
- <LinearLayout
- android:id="@+id/ll_user"
- android:layout_width="0dp"
- android:layout_height="wrap_content"
- android:layout_weight="1"
- android:gravity="center"
- android:orientation="vertical">
-
- <ImageView
- android:id="@+id/img_user"
- android:layout_width="24dp"
- android:layout_height="24dp"
- android:src="@mipmap/phone" />
-
- <TextView
- android:id="@+id/txt_user"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_marginTop="3dp"
- android:text="@string/txt_nav_user"
- android:textSize="12dp"
- android:textColor="#888888"
- />
- </LinearLayout>
-
- </LinearLayout>
2.3 主视图 activity_main.xml
- <?xml version="1.0" encoding="utf-8"?>
- <LinearLayout 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"
- android:orientation="vertical"
- tools:context=".MainActivity">
-
- <!--这里有个小技巧,把底部菜单栏的每一个小的LinearLayout的宽度都设置成0dp,然后用weight权重去分配它,中间内容区域也是把高度设置成0dp,然后用weight权重去分配它。(weight默认是把界面里空闲的位置作为划分位置,所以这里的宽度或者高度要注意设置成0dp)-->
- <include layout="@layout/activity_top" />
-
- <androidx.viewpager.widget.ViewPager
- android:id="@+id/vp_content"
- android:layout_width="match_parent"
- android:layout_height="0dp"
- android:layout_weight="1"
- android:background="#ffffff"
- tools:ignore="MissingConstraints"></androidx.viewpager.widget.ViewPager>
-
- <include layout="@layout/activity_bottom" />
-
- </LinearLayout>
这里有个小技巧,把底部菜单栏的每一个小的LinearLayout的宽度都设置成0dp,然后用weight权重去分配它,中间内容区域也是把高度设置成0dp,然后用weight权重去分配它。(weight默认是把界面里空闲的位置作为划分位置,所以这里的宽度或者高度要注意设置成0dp)
2.4 分页视图 page_home.xml(以首页为例,其他子页面代码类似)
- <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"
- tools:context=".ui.HomeActivity">
-
- <TextView
- android:id="@+id/txt_home_title"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerInParent="true"
- android:text="我是01"
- android:textColor="#1B940A"
- android:textSize="30dp" />
-
- </RelativeLayout>
2.5 ContentAdapter.java:ViewPager需配合一个Adapter使用,所以需先自定义一个Adapter。
- package com.rc.bottombar;
-
- import java.util.List;
-
- import android.view.View;
- import android.view.ViewGroup;
-
- import androidx.viewpager.widget.PagerAdapter;
-
- public class ContentAdapter extends PagerAdapter {
-
- private List<View> views;
-
- public ContentAdapter(List<View> views) {
- this.views = views;
- }
-
- @Override
- public int getCount() {
- return views.size();
- }
-
- @Override
- public boolean isViewFromObject(View arg0, Object arg1) {
- return arg0 == arg1;
- }
-
- @Override
- public Object instantiateItem(ViewGroup container, int position) {
- View view = views.get(position);
- container.addView(view);
- return view;
- }
-
- @Override
- public void destroyItem(ViewGroup container, int position, Object object) {
- container.removeView(views.get(position));
- }
-
- }
2.6 MainActivity.java
- package com.rc.bottombar;
-
- import androidx.viewpager.widget.ViewPager;
-
- import android.app.Activity;
- import android.graphics.Color;
- import android.os.Bundle;
- import android.view.View;
- import android.widget.ImageView;
- import android.widget.LinearLayout;
- import android.widget.TextView;
-
- import com.rc.bottombar.ui.HomeActivity;
-
- import java.util.ArrayList;
- import java.util.List;
-
- public class MainActivity extends Activity implements View.OnClickListener, ViewPager.OnPageChangeListener {
-
- private TextView txt_title;
-
- // 底部菜单4个Linearlayout
- private LinearLayout ll_home;
- private LinearLayout ll_address;
- private LinearLayout ll_friend;
- private LinearLayout ll_setting;
-
- // 底部菜单4个ImageView
- private ImageView img_home;
- private ImageView img_news;
- private ImageView img_friend;
- private ImageView img_user;
-
- // 底部菜单4个菜单标题
- private TextView txt_home;
- private TextView txt_news;
- private TextView txt_friend;
- private TextView txt_user;
-
- // 中间内容区域
- private ViewPager viewPager;
-
- // ViewPager适配器ContentAdapter
- private ContentAdapter adapter;
- private List<View> views;
-
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setContentView(R.layout.activity_main);
- initView();// 初始化控件
- initEvent();// 设置按钮监听
-
- txt_title.setText(R.string.txt_nav_home);
- txt_home.setTextColor(0xff1B940A);
- }
-
- private void initEvent() {
- ll_home.setOnClickListener(this);
- ll_address.setOnClickListener(this);
- ll_friend.setOnClickListener(this);
- ll_setting.setOnClickListener(this);
- viewPager.setOnPageChangeListener(this);
- }
-
- private void initView() {
- txt_title = findViewById(R.id.title);
-
- // 底部菜单4个Linearlayout
- ll_home = findViewById(R.id.ll_home);
- ll_address = findViewById(R.id.ll_news);
- ll_friend = findViewById(R.id.ll_friend);
- ll_setting = findViewById(R.id.ll_user);
-
- // 底部菜单4个ImageView
- img_home = findViewById(R.id.img_home);
- img_news = findViewById(R.id.img_news);
- img_friend = findViewById(R.id.img_friend);
- img_user = findViewById(R.id.img_user);
-
- // 底部菜单4个菜单标题
- txt_home = findViewById(R.id.txt_home);
- txt_news = findViewById(R.id.txt_news);
- txt_friend = findViewById(R.id.txt_friend);
- txt_user = findViewById(R.id.txt_user);
-
- // 中间内容区域ViewPager
- viewPager = findViewById(R.id.vp_content);
-
- // 适配器
- View page_home = View.inflate(MainActivity.this, R.layout.page_home, null);
- View page_news = View.inflate(MainActivity.this, R.layout.page_news, null);
- View page_friend = View.inflate(MainActivity.this, R.layout.page_friend, null);
- View page_user = View.inflate(MainActivity.this, R.layout.page_user, null);
-
- views = new ArrayList<View>();
- views.add(page_home);
- views.add(page_news);
- views.add(page_friend);
- views.add(page_user);
- adapter = new ContentAdapter(views);
- viewPager.setAdapter(adapter);
- }
-
-
- @Override
- public void onClick(View v) {
- switch (v.getId()) {
- case R.id.ll_home:
- restartBotton();
- txt_title.setText(R.string.txt_nav_home);
- txt_home.setTextColor(0xff1B940A);
- viewPager.setCurrentItem(0);
- break;
- case R.id.ll_news:
- restartBotton();
- txt_title.setText(R.string.txt_nav_news);
- txt_news.setTextColor(0xff1B940A);
- viewPager.setCurrentItem(1);
- break;
- case R.id.ll_friend:
- restartBotton();
- txt_title.setText(R.string.txt_nav_friend);
- txt_friend.setTextColor(0xff1B940A);
- viewPager.setCurrentItem(2);
- break;
- case R.id.ll_user:
- restartBotton();
- txt_title.setText(R.string.txt_nav_user);
- txt_user.setTextColor(0xff1B940A);
- viewPager.setCurrentItem(3);
- break;
-
- default:
- break;
- }
- }
-
- @Override
- public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
-
- }
-
- @Override
- public void onPageSelected(int position) {
- restartBotton();
- switch (position) {
- case 0:
- txt_title.setText(R.string.txt_nav_home);
- txt_home.setTextColor(0xff1B940A);
- break;
- case 1:
- txt_title.setText(R.string.txt_nav_news);
- txt_news.setTextColor(0xff1B940A);
- break;
- case 2:
- txt_title.setText(R.string.txt_nav_friend);
- txt_friend.setTextColor(0xff1B940A);
- break;
- case 3:
- txt_title.setText(R.string.txt_nav_user);
- txt_user.setTextColor(0xff1B940A);
- break;
-
- default:
- break;
- }
- }
-
- @Override
- public void onPageScrollStateChanged(int state) {
-
- }
-
- //重置链接样式
- private void restartBotton() {
- txt_home.setTextColor(Color.parseColor("#888888"));
- txt_news.setTextColor(Color.parseColor("#888888"));
- txt_friend.setTextColor(Color.parseColor("#888888"));
- txt_user.setTextColor(Color.parseColor("#888888"));
- }
- }
注意事项:
1.需实现视图点击事件和ViewPager切换事件,implements View.OnClickListener, ViewPager.OnPageChangeListener。
2.initEvent()方法中给控件绑定事件后,下面的Listener才捕捉得到。
3.上面代码只切换选中菜单文字的效果,选中图片也是可以切换的,暂忽略。
四、实现方式2(Fragment方式)
1.布局文件基本没变化,只是把主界面的ViewPager改成了FramLayout,其他文件保持一致,就不贴出来了。
- <?xml version="1.0" encoding="utf-8"?>
- <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=".MainActivity">
- <!--这里有个小技巧,把底部菜单栏的每一个小的LinearLayout的宽度都设置成0dp,然后用weight权重去分配它,
- 中间内容区域也是把高度设置成0dp,然后用weight权重去分配它。
- (weight默认是把界面里空闲的位置作为划分位置,所以这里的宽度或者高度要注意设置成0dp)-->
- <include layout="@layout/activity_top" />
- <FrameLayout
- android:id="@+id/fl_content"
- android:layout_width="match_parent"
- android:background="#ffffff"
- android:layout_height="0dp"
- android:layout_weight="1" >
- </FrameLayout>
- <include layout="@layout/activity_bottom" />
- </LinearLayout>
2.新增4个Fragment类,结构如下图:
以HomeFragment.java 为例,其他类似。
- package com.rc.bottombar.ui;
-
- import android.app.Fragment;
- import android.os.Bundle;
- import android.view.LayoutInflater;
- import android.view.View;
- import android.view.ViewGroup;
- import android.widget.TextView;
-
- import androidx.annotation.Nullable;
-
- import com.rc.bottombar.R;
-
- import java.text.SimpleDateFormat;
- import java.util.Date;
-
- public class HomeFragment extends Fragment {
- View view;
- TextView title;
-
- @Override
- public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
- view = inflater.inflate(R.layout.page_home, container, false);
- title = view.findViewById(R.id.txt_home_title);
- title.setText("我是" + getResources().getString(R.string.txt_nav_home));
- return view;
- }
-
- public void Load() {
- //title.setText("当前时间:\n" + new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
-
- }
-
- }
3.MainActivity.java
- package com.rc.bottombar;
-
- import android.app.Activity;
- import android.app.Fragment;
- import android.app.FragmentManager;
- import android.app.FragmentTransaction;
- import android.graphics.Color;
- import android.os.Bundle;
- import android.view.View;
- import android.widget.ImageView;
- import android.widget.LinearLayout;
- import android.widget.TextView;
-
- import com.rc.bottombar.ui.FriendFragment;
- import com.rc.bottombar.ui.HomeFragment;
- import com.rc.bottombar.ui.NewsFragment;
- import com.rc.bottombar.ui.UserFragment;
-
- public class MainActivity extends Activity implements View.OnClickListener {
-
- private TextView txt_title;
-
- // 底部菜单4个Linearlayout
- private LinearLayout ll_home;
- private LinearLayout ll_address;
- private LinearLayout ll_friend;
- private LinearLayout ll_setting;
-
- // 底部菜单4个ImageView
- private ImageView img_home;
- private ImageView img_news;
- private ImageView img_friend;
- private ImageView img_user;
-
- // 底部菜单4个菜单标题
- private TextView txt_home;
- private TextView txt_news;
- private TextView txt_friend;
- private TextView txt_user;
-
- // 4个Fragment
- private HomeFragment homeFragment;
- private Fragment newsFragment;
- private Fragment friendFragment;
- private Fragment userFragment;
-
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setContentView(R.layout.activity_main);
- initView();// 初始化控件
- initEvent();// 设置按钮监听
-
- // 初始化并设置当前Fragment
- initFragment(0);
-
- }
-
- private void initEvent() {
- ll_home.setOnClickListener(this);
- ll_address.setOnClickListener(this);
- ll_friend.setOnClickListener(this);
- ll_setting.setOnClickListener(this);
- }
-
- private void initView() {
- txt_title = findViewById(R.id.title);
-
- // 底部菜单4个Linearlayout
- ll_home = findViewById(R.id.ll_home);
- ll_address = findViewById(R.id.ll_news);
- ll_friend = findViewById(R.id.ll_friend);
- ll_setting = findViewById(R.id.ll_user);
-
- // 底部菜单4个ImageView
- img_home = findViewById(R.id.img_home);
- img_news = findViewById(R.id.img_news);
- img_friend = findViewById(R.id.img_friend);
- img_user = findViewById(R.id.img_user);
-
- // 底部菜单4个菜单标题
- txt_home = findViewById(R.id.txt_home);
- txt_news = findViewById(R.id.txt_news);
- txt_friend = findViewById(R.id.txt_friend);
- txt_user = findViewById(R.id.txt_user);
- }
-
-
- @Override
- public void onClick(View v) {
- switch (v.getId()) {
- case R.id.ll_home:
- restartBotton();
- txt_title.setText(R.string.txt_nav_home);
- txt_home.setTextColor(0xff1B940A);
- initFragment(0);
- break;
- case R.id.ll_news:
- restartBotton();
- txt_title.setText(R.string.txt_nav_news);
- txt_news.setTextColor(0xff1B940A);
- initFragment(1);
- break;
- case R.id.ll_friend:
- restartBotton();
- txt_title.setText(R.string.txt_nav_friend);
- txt_friend.setTextColor(0xff1B940A);
- initFragment(2);
- break;
- case R.id.ll_user:
- restartBotton();
- txt_title.setText(R.string.txt_nav_user);
- txt_user.setTextColor(0xff1B940A);
- initFragment(3);
- break;
-
- default:
- break;
- }
- }
-
- private void initFragment(int index) {
- FragmentManager fragmentManager = getFragmentManager();
- FragmentTransaction transaction = fragmentManager.beginTransaction();
- hideFragment(transaction);
- switch (index) {
- case 0:
- if (homeFragment == null) {
- homeFragment = new HomeFragment();
- transaction.add(R.id.fl_content, homeFragment);
- } else {
-
- homeFragment.Load();//加载数据
- transaction.show(homeFragment);
- }
- break;
- case 1:
- if (newsFragment == null) {
- newsFragment = new NewsFragment();
- transaction.add(R.id.fl_content, newsFragment);
- } else {
- transaction.show(newsFragment);
- }
-
- break;
- case 2:
- if (friendFragment == null) {
- friendFragment = new FriendFragment();
- transaction.add(R.id.fl_content, friendFragment);
- } else {
- transaction.show(friendFragment);
- }
-
- break;
- case 3:
- if (userFragment == null) {
- userFragment = new UserFragment();
- transaction.add(R.id.fl_content, userFragment);
- } else {
- transaction.show(userFragment);
- }
-
- break;
- default:
- break;
- }
- transaction.commit();
-
- }
-
- //隐藏Fragment
- private void hideFragment(android.app.FragmentTransaction transaction) {
- if (homeFragment != null) {
- transaction.hide(homeFragment);
- }
- if (newsFragment != null) {
- transaction.hide(newsFragment);
- }
- if (friendFragment != null) {
- transaction.hide(friendFragment);
- }
- if (userFragment != null) {
- transaction.hide(userFragment);
- }
- }
-
- //重置链接样式
- private void restartBotton() {
- txt_home.setTextColor(Color.parseColor("#888888"));
- txt_news.setTextColor(Color.parseColor("#888888"));
- txt_friend.setTextColor(Color.parseColor("#888888"));
- txt_user.setTextColor(Color.parseColor("#888888"));
- }
- }
五、小结
方式1:基于ViewPager实现的内容:
优点:
1、界面可以滑动,美观,流畅。
缺点:
1、当界面里有一些需要用手势来实现的内容会起冲突,比如我们ListView里的侧滑删除。
2、由于采用的是ViewPager,所以页面内容实现代码会严重依赖于MainActivity,代码太过冗余,不便于后期维护。
方式2:基于Fragment实现的内容:
优点:
1、Fragment文件单独存在,各自页面的内容各自去实现完成,有自己的生命周期,便于后期维护。
2、对于需要手势操作的一些内容不会起冲突。
缺点:
1、界面不可滑动,比较死板。
参考内容:
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。