底部导航栏是每一个APP的核心UI组件之一,本文记录一下自己最近实现的一个沉浸式底部导航栏效果。
效果:
在这个效果当中实现了一个比较美观的底部导航栏效果,使用buttomnavigationview与ViwePager2实现了该效果。
具体实现:
buttomnavigationview部分实现
1、在build.gradle导入必要的依赖:
implementation 'com.google.android.material:material:1.1.0'
2、在主界面的xml中添加buttomnavigationview
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.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"
android:background="@color/colorBgLittleWhite"
tools:context=".MainActivity">
<com.google.android.material.bottomnavigation.BottomNavigationView
android:id="@+id/bottom_nav"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
app:itemIconTint="@color/color_selector"
app:itemTextColor="@color/color_selector"
android:background="@drawable/transparent_rect"
app:labelVisibilityMode="unlabeled"
app:layout_constraintBottom_toBottomOf="parent"
app:menu="@menu/menu_bottom_navigation_view"
/>
</androidx.constraintlayout.widget.ConstraintLayout>
其中有几个比较核心的属性:
1、app:itemIconTint
:用来设置bottomview设置的图标的点击颜色
2、app:itemTextColor
:用来设置bottomview设置的文字的点击颜色
3、app:labelVisibilityMode
:设置点击按钮缩放特效,这里我将其关闭
4、android:background
:设置背景,这里我为了将bottomview自带的边界阴影去掉选择了一个空白透明背景。
5、app:menu
:设置buttomview的内容相关属性
3、给menu添加相关的menu:
在该目录中创建menu_bottom_navigation_view文件:
<menu xmlns:android="http://schemas.android.com/apk/res/android"
>
<item
android:id="@+id/main_button_bar_home"
android:title="主页"
android:icon="@drawable/main_icon"
/>
<item
android:id="@+id/main_button_bar_function"
android:title="功能"
android:icon="@drawable/main_icon_function"
/>
<item
android:id="@+id/main_button_bar_me"
android:title="我的"
android:icon="@drawable/main_icon_me"
/>
</menu>
这里我设置了3个item。
4、设置点击选中切换颜色:
创建对应的selector文件:
在该目录下创建。
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:color="@color/colorLightBlue" android:state_checked="true"></item>
<item android:color="@color/colorLightGrey" android:state_checked="false"></item>
</selector>
ViewPager部分实现:
1、导入依赖
implementation "androidx.viewpager2:viewpager2:1.0.0"
2、在对应的xml文件中引入:
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.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"
android:background="@color/colorBgLittleWhite"
tools:context=".MainActivity">
<androidx.viewpager2.widget.ViewPager2
android:id="@+id/main_viewPager"
android:layout_width="match_parent"
android:layout_height="0dp"
app:layout_constraintBottom_toTopOf="@+id/bottom_nav"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="1.0"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintVertical_bias="0.0" />
<com.google.android.material.bottomnavigation.BottomNavigationView
android:id="@+id/bottom_nav"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
app:itemIconTint="@color/color_selector"
app:itemTextColor="@color/color_selector"
android:background="@drawable/transparent_rect"
app:labelVisibilityMode="unlabeled"
app:layout_constraintBottom_toBottomOf="parent"
app:menu="@menu/menu_bottom_navigation_view"
/>
</androidx.constraintlayout.widget.ConstraintLayout>
3、创建相关的FragmentStateAdapter(ViewPager2新的特性,简化ViewPager的Adapter):
public class MyViewPager2Adapter extends FragmentStateAdapter {
List<Fragment> list;
public MyViewPager2Adapter(@NonNull FragmentActivity fragmentActivity, List<Fragment> list) {
super(fragmentActivity);
this.list = list;
}
@NonNull
@Override
public Fragment createFragment(int position) {
return list.get(position);
}
@Override
public int getItemCount() {
return list.size();
}
}
4、创建自定义的Fragment。
代码略。
建立buttomnavigationview与ViwePager2联系
主要思路:
1、在Activity中ViewPager2的滑动监听方法中切换buttomnavigationview的选中项。
2、buttomnavigationview的选中响应事件当中切换ViewPager2绑定的Fragment。
详细见代码解析:
public class MainActivity extends BaseActivity {
Fragment fragment_function, fragment_me, fragment_main;
ViewPager2 viewPager2;
BottomNavigationView bottomNavigationView;
List<Fragment> list;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initFragment();
initViewPager2();
initBottomNavigationView();
}
// 初始化BottomNavigationView并建立与ViewPager2联系
public void initBottomNavigationView() {
bottomNavigationView = findViewById(R.id.bottom_nav);
// 设置按钮点击监听
bottomNavigationView.setOnNavigationItemSelectedListener(new BottomNavigationView.OnNavigationItemSelectedListener() {
@Override
public boolean onNavigationItemSelected(@NonNull MenuItem item) {
// 获得点击的item
String title = item.getTitle().toString();
// 根据点击的item项目切换对应的Fragment
switch (item.getItemId()) {
case R.id.main_button_bar_function:
viewPager2.setCurrentItem(1);
break;
case R.id.main_button_bar_home:
viewPager2.setCurrentItem(0);
break;
case R.id.main_button_bar_me:
viewPager2.setCurrentItem(2);
break;
}
return true;
}
});
}
// 初始化ViewPager2并建立与BottomNavigationView联系
public void initViewPager2() {
viewPager2 = findViewById(R.id.main_viewPager);
viewPager2.setAdapter(new MyViewPager2Adapter(this, list));
// 设置ViewPager的滑动监听
viewPager2.registerOnPageChangeCallback(new ViewPager2.OnPageChangeCallback() {
@Override
public void onPageSelected(int position) {
// 根据滑动监听切换对应的Fragment
super.onPageSelected(position);
bottomNavigationView.getMenu().getItem(position).setChecked(true);
}
});
}
// 初始化Fragment
public void initFragment() {
fragment_function = new Fragment_function();
fragment_main = new Fragment_main();
fragment_me = new Fragment_me();
list = new ArrayList<>();
list.add(fragment_main);
list.add(fragment_function);
list.add(fragment_me);
}
}