Android : BottomNavigation底部导航_简单应用

示例图:

1.先创建底部导航需要的图片

res → New → Vector Asset 创建三个矢量图

图片1 baseline_home.xml

XML 复制代码
<vector android:height="24dp" android:tint="#000000"
    android:viewportHeight="24" android:viewportWidth="24"
    android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
    <path android:fillColor="@android:color/white" android:pathData="M10,20v-6h4v6h5v-8h3L12,3 2,12h3v8z"/>
</vector>

图片2 baseline_menu.xml

XML 复制代码
<vector android:height="24dp" android:tint="#000000"
    android:viewportHeight="24" android:viewportWidth="24"
    android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
    <path android:fillColor="@android:color/white" android:pathData="M3,18h18v-2L3,16v2zM3,13h18v-2L3,11v2zM3,6v2h18L21,6L3,6z"/>
</vector>

图片3 baseline_author.xml

XML 复制代码
<vector android:height="24dp" android:tint="#000000"
    android:viewportHeight="24" android:viewportWidth="24"
    android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
    <path android:fillColor="@android:color/white" android:pathData="M12,2C6.48,2 2,6.48 2,12s4.48,10 10,10 10,-4.48 10,-10S17.52,2 12,2zM12,5c1.66,0 3,1.34 3,3s-1.34,3 -3,3 -3,-1.34 -3,-3 1.34,-3 3,-3zM12,19.2c-2.5,0 -4.71,-1.28 -6,-3.22 0.03,-1.99 4,-3.08 6,-3.08 1.99,0 5.97,1.09 6,3.08 -1.29,1.94 -3.5,3.22 -6,3.22z"/>
</vector>

图片4 用于操作的图片 baseline_img.xml

XML 复制代码
<vector android:height="50dp" android:tint="#44800C"
    android:viewportHeight="24" android:viewportWidth="24"
    android:width="50dp" xmlns:android="http://schemas.android.com/apk/res/android">
    <path android:fillColor="@android:color/white" android:pathData="M4.5,9.5m-2.5,0a2.5,2.5 0,1 1,5 0a2.5,2.5 0,1 1,-5 0"/>
    <path android:fillColor="@android:color/white" android:pathData="M9,5.5m-2.5,0a2.5,2.5 0,1 1,5 0a2.5,2.5 0,1 1,-5 0"/>
    <path android:fillColor="@android:color/white" android:pathData="M15,5.5m-2.5,0a2.5,2.5 0,1 1,5 0a2.5,2.5 0,1 1,-5 0"/>
    <path android:fillColor="@android:color/white" android:pathData="M19.5,9.5m-2.5,0a2.5,2.5 0,1 1,5 0a2.5,2.5 0,1 1,-5 0"/>
    <path android:fillColor="@android:color/white" android:pathData="M17.34,14.86c-0.87,-1.02 -1.6,-1.89 -2.48,-2.91 -0.46,-0.54 -1.05,-1.08 -1.75,-1.32 -0.11,-0.04 -0.22,-0.07 -0.33,-0.09 -0.25,-0.04 -0.52,-0.04 -0.78,-0.04s-0.53,0 -0.79,0.05c-0.11,0.02 -0.22,0.05 -0.33,0.09 -0.7,0.24 -1.28,0.78 -1.75,1.32 -0.87,1.02 -1.6,1.89 -2.48,2.91 -1.31,1.31 -2.92,2.76 -2.62,4.79 0.29,1.02 1.02,2.03 2.33,2.32 0.73,0.15 3.06,-0.44 5.54,-0.44h0.18c2.48,0 4.81,0.58 5.54,0.44 1.31,-0.29 2.04,-1.31 2.33,-2.32 0.31,-2.04 -1.3,-3.49 -2.61,-4.8z"/>
</vector>

res → New → Android Resource File 类型选择 Menu

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">

    <item
        android:id="@+id/homeFragment"
        android:icon="@drawable/baseline_home"
        android:title="旋转" />
    <item
        android:id="@+id/menuFragment"
        android:icon="@drawable/baseline_menu"
        android:title="缩放" />
    <item
        android:id="@+id/authorFragment"
        android:icon="@drawable/baseline_author"
        android:title="移动" />
</menu>

3.创建3个Fragment 页面

res → New → Fragment → Fragment(with ViewModel)

创建了6个文件

HomeFragment.java HomeViewModel.java 布局文件: fragment_home.xml

MenuFragment.java MenuViewModel.java 布局文件 : fragment_menu.xml

AuthorFragment.java AuthorViewModel.java 布局文件:fragment_author.xml

往布局中添加操作的图片

fragment_home.xml:

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout 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"
    tools:context=".HomeFragment">

    <ImageView
        android:id="@+id/imageView"
        android:layout_width="100dp"
        android:layout_height="100dp"
        android:layout_gravity="center"
        android:src="@drawable/baseline_img" />
</FrameLayout>

fragment_menu.xml

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout 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"
    tools:context=".MenuFragment">

    <ImageView
        android:id="@+id/imageView"
        android:layout_width="100dp"
        android:layout_height="100dp"
        android:layout_gravity="center"
        android:src="@drawable/baseline_img" />
</FrameLayout>

fragment_author.xml

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout 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"
    tools:context=".AuthorFragment">

    <ImageView
        android:id="@+id/imageView"
        android:layout_width="100dp"
        android:layout_height="100dp"
        android:layout_gravity="center"
        android:src="@drawable/baseline_img" />
</FrameLayout>

4.创建Navigation 导航文件 my_Navigation.xml

res → New → Android Resource File 类型选择 Navigation

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<navigation 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:id="@+id/my_navigation"
    app:startDestination="@id/homeFragment">

    <!-- 注意 这里的id 和 Menu  my_menu.xml文件中的id  相对应 才可点击跳转到对应的页面-->
    <fragment
        android:id="@+id/homeFragment"
        android:name="com.example.mybuttomnavigation.HomeFragment"
        android:label="旋转"
        tools:layout="@layout/fragment_home" />
    <fragment
        android:id="@+id/menuFragment"
        android:name="com.example.mybuttomnavigation.MenuFragment"
        android:label="缩放"
        tools:layout="@layout/fragment_menu" />
    <fragment
        android:id="@+id/authorFragment"
        android:name="com.example.mybuttomnavigation.AuthorFragment"
        android:label="移动"
        tools:layout="@layout/fragment_author" />
</navigation>

5.在主布局添加 底部导航(BottomNavigationView) 和 跳转的页面(NavHostFragment)

activity_main.xml

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"
    tools:context=".MainActivity">

    <com.google.android.material.bottomnavigation.BottomNavigationView
        android:id="@+id/bottomNavigationView"
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:foregroundTint="#4700FF"
        android:outlineAmbientShadowColor="#FFEB3B"
        app:itemRippleColor="#ff0000ff"
        app:labelVisibilityMode="selected"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintHorizontal_bias="0.0"
        app:layout_constraintStart_toStartOf="parent"
        app:menu="@menu/my_menu">

    </com.google.android.material.bottomnavigation.BottomNavigationView>


    <!-- 注意事项 :
    默认选的是androidx.fragment.app.FragmentContainerView
    手动改成 fragment
    -->
    <fragment
        android:id="@+id/fragment"
        android:name="androidx.navigation.fragment.NavHostFragment"
        android:layout_width="match_parent"
        android:layout_height="0dp"
        app:defaultNavHost="true"
        app:layout_constraintBottom_toTopOf="@+id/bottomNavigationView"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintHorizontal_bias="0.0"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent"
        app:layout_constraintVertical_bias="0.017"
        app:navGraph="@navigation/my_navigation" />

</androidx.constraintlayout.widget.ConstraintLayout>

6. 设置主题样式 默认是没有导航栏的

values 目录下 colors.xml

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<resources>

    <color name="purple_200">#FFBB86FC</color>
    <color name="purple_500">#FF6200EE</color>
    <color name="purple_700">#FF3700B3</color>
    <color name="teal_200">#FF03DAC5</color>
    <color name="teal_700">#FF018786</color>
    <color name="black">#FF000000</color>
    <color name="white">#FFFFFFFF</color>
</resources>

themes.xml

XML 复制代码
<resources xmlns:tools="http://schemas.android.com/tools">
    <!-- Base application theme. -->
    <style name="Base.Theme.MyApplication" parent="Theme.Material3.DayNight.NoActionBar">
        <!-- Customize your light theme here. -->
        <!-- <item name="colorPrimary">@color/my_light_primary</item> -->
    </style>

    <style name="Theme.MyApplication" parent="Theme.MaterialComponents.DayNight.DarkActionBar">
        <!-- Primary brand color. -->
        <item name="colorPrimary">@color/purple_500</item>
        <item name="colorPrimaryVariant">@color/purple_700</item>
        <item name="colorOnPrimary">@color/white</item>
        <!-- Secondary brand color. -->
        <item name="colorSecondary">@color/teal_200</item>
        <item name="colorSecondaryVariant">@color/teal_700</item>
        <item name="colorOnSecondary">@color/black</item>
        <!-- Status bar color. -->
        <item name="android:statusBarColor">?attr/colorPrimaryVariant</item>
        <!-- Customize your theme here. -->
    </style>
</resources>

7. MainActivity.java

java 复制代码
package com.example.mybuttomnavigation;

import android.os.Bundle;

import androidx.appcompat.app.AppCompatActivity;
import androidx.navigation.NavController;
import androidx.navigation.Navigation;
import androidx.navigation.ui.AppBarConfiguration;
import androidx.navigation.ui.NavigationUI;

import com.google.android.material.bottomnavigation.BottomNavigationView;

public class MainActivity extends AppCompatActivity {


     // 底部导航
    private BottomNavigationView bottomNavigationView;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        bottomNavigationView = findViewById(R.id.bottomNavigationView);
        //导航
        NavController navController = Navigation.findNavController(this, R.id.fragment);
        //设置顶部导航
        AppBarConfiguration configuration = new AppBarConfiguration.Builder(
                //带返回箭头 ←
//                navController.getGraph()
                //不带箭头的 ←
                bottomNavigationView.getMenu()
                // 或者这样写 ←不带箭头
//                R.id.menuFragment,R.id.authorFragment,R.id.homeFragment
        ).build();
        //装配顶部导航
        NavigationUI.setupActionBarWithNavController(this, navController, configuration);
        NavigationUI.setupWithNavController(bottomNavigationView, navController);
    }
}

经过上面这些步骤已经可以跳转了

8.设置动画

旋转:HomeFragment.java

java 复制代码
package com.example.mybuttomnavigation;

import android.animation.ObjectAnimator;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.ViewModelProvider;

public class HomeFragment extends Fragment {

    private HomeViewModel mViewModel;
    private ImageView imageView;

    public static HomeFragment newInstance() {
        return new HomeFragment();
    }

    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container,
                             @Nullable Bundle savedInstanceState) {

        View view = inflater.inflate(R.layout.fragment_home, container, false);
        imageView = view.findViewById(R.id.imageView);

        return view;
    }

    @Override
    public void onActivityCreated(@Nullable Bundle savedInstanceState) {
        super.onActivityCreated(savedInstanceState);
        mViewModel = new ViewModelProvider(this).get(HomeViewModel.class);
        imageView.setRotation(mViewModel.startAnimation);
        // TODO: Use the ViewModel
        /**设置动画
         *
         * alpha(透明度)
         * scaleX(X轴缩放)
         * scaleY(Y轴缩放)
         * rotation(旋转)
         * translationX(X轴平移)
         * translationY(Y轴平移)
         * */
        ObjectAnimator objectAnimator = ObjectAnimator.ofFloat(imageView, "rotation", 0.0f);
        //点击事件
        imageView.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                // 判断动画是在运动 objectAnimator.isRunning() 在运动
                //!objectAnimator.isRunning()取反
                //重新设置旋转角度              当前的角度  旋转到 当前的角度+100,
                objectAnimator.setFloatValues(imageView.getRotation(), imageView.getRotation() + 100);
                mViewModel.startAnimation += 100;
                objectAnimator.start();
            }
        });
    }

}

HomeViewModel.java

java 复制代码
package com.example.mybuttomnavigation;

import androidx.lifecycle.ViewModel;

public class HomeViewModel extends ViewModel {
    // TODO: Implement the ViewModel
    float startAnimation = 0;
}

缩放:MenuFragment.java

java 复制代码
package com.example.mybuttomnavigation;

import android.animation.ObjectAnimator;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.ViewModelProvider;

public class MenuFragment extends Fragment {

    private MenuViewModel mViewModel;
    private ImageView imageView;

    public static MenuFragment newInstance() {
        return new MenuFragment();
    }

    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container,
                             @Nullable Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_menu, container, false);
        imageView = view.findViewById(R.id.imageView);


        return view;
    }

    @Override
    public void onActivityCreated(@Nullable Bundle savedInstanceState) {
        super.onActivityCreated(savedInstanceState);
        mViewModel = new ViewModelProvider(this).get(MenuViewModel.class);
        imageView.setScaleX(mViewModel.scaleFactor);
        imageView.setScaleY(mViewModel.scaleFactor);
        // TODO: Use the ViewModel
        /**设置动画
         *
         * alpha(透明度)
         * scaleX(X轴缩放)
         * scaleY(Y轴缩放)
         * rotation(旋转)
         * translationX(X轴平移)
         * translationY(Y轴平移)
         * */
        ObjectAnimator objectAnimatorX = ObjectAnimator.ofFloat(imageView, "scaleX", 0);
        ObjectAnimator objectAnimatorY = ObjectAnimator.ofFloat(imageView, "scaleY", 0);
        objectAnimatorX.setDuration(500);
        objectAnimatorY.setDuration(500);
        //点击事件
        imageView.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                // 判断动画是在运动 objectAnimator.isRunning() 在运动
                //!objectAnimator.isRunning()取反
                //重新设置缩放            
                objectAnimatorX.setFloatValues(imageView.getScaleX() + 0.1f);
                objectAnimatorY.setFloatValues(imageView.getScaleY() + 0.1f);
                mViewModel.scaleFactor += 0.1;
                objectAnimatorX.start();
                objectAnimatorY.start();
            }
        });

    }

}

MenuViewModel.java

java 复制代码
package com.example.mybuttomnavigation;

import androidx.lifecycle.ViewModel;

public class MenuViewModel extends ViewModel {
    // TODO: Implement the ViewModel
    float scaleFactor = 1 ;
}

平移:AuthorFragment.java

java 复制代码
package com.example.mybuttomnavigation;

import android.animation.ObjectAnimator;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.ViewModelProvider;

import java.util.Random;

public class AuthorFragment extends Fragment {

    private AuthorViewModel mViewModel;
    public ImageView imageView;

    public static AuthorFragment newInstance() {
        return new AuthorFragment();
    }

    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container,
                             @Nullable Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_author, container, false);
        imageView = view.findViewById(R.id.imageView);
        return view;
    }

    @Override
    public void onActivityCreated(@Nullable Bundle savedInstanceState) {
        super.onActivityCreated(savedInstanceState);
        mViewModel = new ViewModelProvider(this).get(AuthorViewModel.class);
        // TODO: Use the ViewModel
        imageView.setX(imageView.getX() + mViewModel.mark);

        // TODO: Use the ViewModel
        /**设置动画
         *
         * alpha(透明度)
         * scaleX(X轴缩放)
         * scaleY(Y轴缩放)
         * rotation(旋转)
         * translationX(X轴平移)
         * translationY(Y轴平移)
         * */
        ObjectAnimator objectAnimatorX = ObjectAnimator.ofFloat(imageView, "x", 0);
        //设置动画500毫秒
        objectAnimatorX.setDuration(500);

        //点击事件
        imageView.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                // 判断动画是在运动 objectAnimator.isRunning() 在运动
                //!objectAnimator.isRunning()取反
                float dx = new Random().nextBoolean() ? 100 : -100;
                //重新设置缩放            = 当前值 移动到 , 当前值 + dx
                objectAnimatorX.setFloatValues(imageView.getScaleX(), imageView.getScaleX() + dx);

                mViewModel.mark += dx;
                objectAnimatorX.start();

            }
        });

    }

}

AuthorViewModel.java

java 复制代码
package com.example.mybuttomnavigation;

import androidx.lifecycle.ViewModel;

public class AuthorViewModel extends ViewModel {
    // TODO: Implement the ViewModel
    float mark = 0;
}
相关推荐
荏苒追寻2 分钟前
Android OpenGL基础1——常用概念及方法解释
android
越前君5 分钟前
如何开发一个 Raycast 扩展?
前端·笔记
人生游戏牛马NPC1号13 分钟前
学习 Android (十七) 学习 OpenCV (二)
android·opencv·学习
悠哉悠哉愿意41 分钟前
【机器学习学习笔记】机器学习引言
笔记·学习·机器学习
恋猫de小郭1 小时前
谷歌开启 Android 开发者身份验证,明年可能开始禁止“未经验证”应用的侧载,要求所有开发者向谷歌表明身份
android·前端·flutter
用户091 小时前
Gradle声明式构建总结
android
用户091 小时前
Gradle插件开发实践总结
android
Go 鹏ya1 小时前
【Python学习笔记】whl包打包
笔记·python·学习
不会学习?3 小时前
计算机网络
经验分享·笔记·计算机网络
l5657588 小时前
第四十三天(JavaEE应用&ORM框架&SQL预编译&JDBC&MyBatis&Hibernate&Maven)
笔记