Android 底部导航栏 (BottomNavigationView) 制作教程

在 Android 应用开发中,底部导航栏是非常常见的交互组件,能够让用户快速切换不同的功能模块。本文将详细介绍如何使用 Material Design 组件中的 BottomNavigationView 实现底部导航功能。

目录结构如图

一、布局文件实现

首先,我们需要在 activity_main.xml 中定义主布局结构,主要包含一个用于显示内容的 FrameLayout 和底部导航栏 BottomNavigationView。

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"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
    <!-- 用于显示Fragment内容的容器 -->
    <FrameLayout
        android:id="@+id/fragment_container"
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="1" />

    <!-- 底部导航栏 -->
    <com.google.android.material.bottomnavigation.BottomNavigationView
        android:id="@+id/bottom_nav"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:menu="@menu/bottom_nav_menu" />
</LinearLayout>

二、创建导航菜单

接下来需要创建底部导航栏的菜单文件,在 res/menu 目录下创建 bottom_nav_menu.xml:

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:id="@+id/nav_home"
        android:icon="@drawable/ic_home"
        android:title="Home" />
    <item
        android:id="@+id/nav_dashboard"
        android:icon="@drawable/ic_dashboard"
        android:title="Dashboard" />
    <item
        android:id="@+id/nav_notify"
        android:icon="@drawable/ic_notify"
        android:title="Notify" />
</menu>

三、添加导航图标

在 res/drawable 目录下添加三个导航图标文件(可以使用 Vector Asset 创建):

  1. ic_home.xml(首页图标)
XML 复制代码
<vector xmlns:android="http://schemas.android.com/apk/res/android"
    android:width="24dp"
    android:height="24dp"
    android:viewportWidth="24.0"
    android:viewportHeight="24.0">
    <path
        android:fillColor="#FF000000"
        android:pathData="M10,20v-6h4v6h5v-8h3L12,3 2,12h3v8z" />
</vector>
  1. ic_dashboard.xml(仪表盘图标)
XML 复制代码
<vector xmlns:android="http://schemas.android.com/apk/res/android"
    android:width="24dp"
    android:height="24dp"
    android:viewportWidth="24.0"
    android:viewportHeight="24.0">
    <path
        android:fillColor="#FF000000"
        android:pathData="M3,13h8L11,3L3,3v10zM3,21h8v-6L3,15v6zM13,21h8L21,11h-8v10zM13,3v6h8L21,3h-8z" />
</vector>
  1. ic_notify.xml(通知图标)
XML 复制代码
<vector xmlns:android="http://schemas.android.com/apk/res/android"
    android:width="24dp"
    android:height="24dp"
    android:viewportWidth="24.0"
    android:viewportHeight="24.0">
    <path
        android:fillColor="#FF000000"
        android:pathData="M12,22c1.1,0 2,-0.9 2,-2h-4c0,1.1 0.9,2 2,2zM18,16v-5c0,-3.07 -1.63,-5.64 -4.5,-6.32L13.5,4c0,-0.83 -0.67,-1.5 -1.5,-1.5s-1.5,0.67 -1.5,1.5v0.68C7.64,5.36 6,7.92 6,11v5l-2,2v1h16v-1l-2,-2z" />
</vector>

四、创建 Fragment 布局

我们需要为三个导航项创建对应的 Fragment 布局文件:

  1. fragment_home.xml(首页布局):
XML 复制代码
<?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="match_parent"
    android:gravity="center"
    android:orientation="vertical">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="首页"
        android:textSize="24sp" />
</LinearLayout>
  1. fragment_dashboard.xml(仪表盘布局):
复制代码
```XML
<?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="match_parent"
    android:gravity="center"
    android:orientation="vertical">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="仪表盘"
        android:textSize="24sp" />
</LinearLayout>
```
  1. fragment_notify.xml(通知布局):
复制代码
```XML
<?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="match_parent"
    android:gravity="center"
    android:orientation="vertical">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="通知"
        android:textSize="24sp" />
</LinearLayout>
```

### 五、创建 Fragment 类

为每个布局创建对应的 Fragment 类:
  1. HomeFragment.java:
复制代码
```java
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import androidx.fragment.app.Fragment;

public class HomeFragment extends Fragment {
    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        // 加载布局文件
        return inflater.inflate(R.layout.fragment_home, container, false);
    }
}
```

其他代码也一样 注意修改 类名和 布局选择

六、实现 MainActivity 逻辑

最后,在 MainActivity 中实现底部导航栏的切换逻辑:

java 复制代码
package com.example.demo01;
import android.os.Bundle;
import androidx.appcompat.app.AppCompatActivity;
import androidx.fragment.app.Fragment;
import com.google.android.material.bottomnavigation.BottomNavigationView;
public class MainActivity extends AppCompatActivity {
    private BottomNavigationView bottomNav;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        bottomNav = findViewById(R.id.bottom_nav);
        // 默认首页
        loadFragment(new HomeFragment());
        // 1.2.1 旧版监听接口
        bottomNav.setOnNavigationItemSelectedListener(
                item -> {
                    Fragment selected = null;
                    int id = item.getItemId();

                    if (id == R.id.nav_home) {
                        selected = new HomeFragment();
                    } else if (id == R.id.nav_dashboard) {
                        selected = new DashboardFragment();
                    } else if (id == R.id.nav_notify) {
                        selected = new NotifyFragment();
                    }
                    return loadFragment(selected);
                });
    }
    private boolean loadFragment(Fragment f) {
        if (f == null) return false;
        getSupportFragmentManager()
                .beginTransaction()
                .replace(R.id.fragment_container, f)
                .commit();
        return true;
    }
}

七、注意事项

  1. 底部导航栏的图标和文字颜色可以通过主题进行自定义

  2. 当导航项超过 3 个时,BottomNavigationView 会默认使用移位模式,可通过代码禁用

相关推荐
努力学习的小廉2 小时前
初识MYSQL —— 事务
android·mysql·adb
阿里云云原生2 小时前
深度解析 Android 崩溃捕获原理及从崩溃到归因的闭环实践
android
.豆鲨包2 小时前
【Android】Android内存缓存LruCache与DiskLruCache的使用及实现原理
android·java·缓存
JulyYu4 小时前
【Android】针对非SDK接口的限制解决方案
android·客户端
猪哥帅过吴彦祖4 小时前
Flutter 系列教程:应用导航 - Navigator 1.0 与命名路由
android·flutter·ios
2501_916008895 小时前
iOS 跨平台开发实战指南,从框架选择到开心上架(Appuploader)跨系统免 Mac 发布全流程解析
android·macos·ios·小程序·uni-app·iphone·webview
stevenzqzq5 小时前
Android Hilt教程_构造函数
android
鹏多多6 小时前
flutter图片选择库multi_image_picker_plus和image_picker的对比和使用解析
android·flutter·ios