Android Jetpack组件库(第四部分)---Navigation

Android Jetpack 是 Google 推出的一整套帮助 Android 应用程序开发的库、工具包和架构指南,旨在为 Android 应用程序提供更快,更轻松,更稳定的开发体验。自推出以来已经发展成了一个庞大的技术生态系统,包括了许多使用方便、功能强大的库,以下是其中一些新特性、新组件:

  1. Paging: 分页库增加了对后端和前端数据的分页处理;

  2. Room: 数据库库 Room 的升级增加了对数据库的全面支持和更好的一致性;

  3. WorkManager: 工作管理库 WorkManager 更加智能和可靠,支持更复杂的后台任务,并可与后台服务和 Job 统一管理器进行交互;

  4. Navigation: 导航库 Navigation 可以更轻松地设置和管理应用程序中的导航功能;

  5. CameraX: 相机库 CameraX 简化了相机应用程序的开发;

  6. Hilt: 依赖注入库 Hilt 简化了依赖注入和管理;

  7. Compose: UI工具包 Compose 提供了更加现代化、灵活和响应式的UI构建方式,可以大大简化UI构建的工作量;

  8. AppStartup: App Startup 库提供了对应用程序启动操作的检视和日志记录工具,可以更有效地优化启动时间;

  9. Security: 安全库 Security 提供了应用程序安全管理和保护数据的方案。

第四章 Navigation库

  1. Navigation 的原理:Navigation 是一个与屏幕动画流畅度无缝整合的处理导航和屏幕分层显示的组件。Navigation 组件可以帮助你实现 UI 导航和屏幕间的转换动画,处理屏幕旋转和其它重要的状态变化,以及处理屏幕、手势和导航请求等等。实现 Navigation 的核心是借助于 Fragment、FragmentManager 和导航图(Navigation Graph)。

  2. Navigation 的使用场景:在实际开发中,可以通过 Navigation 组件来管理和优化 Android 应用程序。常见的使用场景有:

  • 应用程序拥有多个 Activity 和 Fragment,需要使用导航组件将这些屏幕进行连接
  • 应用程序需要在不同的区域显示并处理不同的内容,需要使用导航以及动画效果进行列表、详细内容和表单等界面间的无缝切换
  • 应用程序需要对用户进行不断地引导、引导、提示和反馈,尤其是针对新手用户
  1. Navigation 的代码示例:

先在 gradle 文件中添加依赖引用:

implementation 'androidx.navigation:navigation-fragment-ktx:2.3.5'
implementation 'androidx.navigation:navigation-ui-ktx:2.3.5'

在 navigation 文件夹中创建导航图,并定义 Fragment 之间的关系,如下所示:

<navigation xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/app_nav_graph"
    app:startDestination="@id/fragment_home">

    <fragment
        android:id="@+id/fragment_home"
        android:name="com.example.navigation.HomeFragment"
        android:label="Home"
        tools:layout="@layout/fragment_home" />

    <fragment
        android:id="@+id/fragment_detail"
        android:name="com.example.navigation.DetailFragment"
        android:label="Detail"
        tools:layout="@layout/fragment_detail" >
        <argument
            android:name="itemId"
            app:argType="integer"
            android:defaultValue="0" />
    </fragment>

    <action
        android:id="@+id/action_home_to_detail"
        app:destination="@id/fragment_detail"/>
        
</navigation>

如上所述,我们定义了两个 Fragment,分别是 HomeFragment 和 DetailFragment,并且为 DetailFragment 添加一个 itemId(详细信息 ID)的参数。除此之外,还定义了一个从 HomeFragment 到 DetailFragment 的 action。

接下来,在你的 Activity 或 Fragment 中通过 Navigation.findNavController(view),来获取 NavControlller 对象:

val navController = Navigation.findNavController(
    findViewById(R.id.nav_host_fragment)
)

建议在 Activity 中使用 findNavController(),在 Fragment 中使用 view.findNavController() 来获取 NavController 对象。之后,可以通过 NavController 对象来进行相应的操作,如:添加并控制Fragment:

val detailFragment = DetailFragment(items[position].id)
navController.navigate(R.id.action_home_to_detail)

如上所述,我们创建了 DetailFragment 的实例对象,并将 itemId 的参数传递给了它。之后,我们通过 action_home_to_detail 的 action,控制导航到 DetailFragment。

  1. 场景一:应用程序需要通过 Bottom Navigation 来实现关键性的流程操作,如实现应用主要业务的导航。

在布局文件底部加入 BottomNavigationView 组件,之后在 Activity 中关联 Navigation,并为他们添加关联,并根据用户交互跳转到相应的 Fragment 窗口:

XML 文件:

<com.google.android.material.bottomnavigation.BottomNavigationView
    android:id="@+id/navigation"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_gravity="bottom"
    android:background="?android:attr/windowBackground"
    app:itemIconTint="@drawable/bottom_navigation_selector"
    app:itemTextColor="@drawable/bottom_navigation_selector"
    app:labelVisibilityMode="unlabeled"
    app:menu="@menu/navigation_menu" />

Activity 代码:

class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        val binding = ActivityMainBinding.inflate(layoutInflater)
        setContentView(binding.root)

        setSupportActionBar(binding.toolbar)

        val navController = findNavController(R.id.navHostFragment)

        binding.navigation.setupWithNavController(navController)
        setupActionBarWithNavController(navController)
    }

    override fun onSupportNavigateUp(): Boolean {
        val navController = findNavController(R.id.navHostFragment)
        return navController.navigateUp() || super.onSupportNavigateUp()
    }

}

如上所述,我们在 Activity 中添加了 BottomNavigationView,并通过 setupWithNavController() 方法,将其与 NavController 关联起来。接着,通过 setupActionBarWithNavController() 方法,将 ActionBar 与 NavController 关联起来。

  1. 场景二:应用程序需要为 Fragment 指定转场动画,从而优化用户体验。

在导航图中使用 Fragment 的 enterAnim 和 exitAnim 两个属性进行动画设置。如下所示:

<fragment
    android:id="@+id/my_fragment"
    android:name="com.example.MyFragment"
    android:label="My Fragment"
    tools:layout="@layout/fragment_my">

    <action
        android:id="@+id/my_action"
        app:destination="@id/other_fragment"
        app:enterAnim="@anim/slide_up"
        app:exitAnim="@anim/fade_out" />

</fragment>

如上所述,我们在 action 标签中为目标 Fragment 指定 enterAnim 和 exitAnim 属性。在具体的动画实现上,可以使用 Android 自带的 Transition、Animator 等组件或第三方框架等。例如,可以定义一个 Slide_Up.xml 文件,从而实现从底部向上滑入的效果:

<set xmlns:android="http://schemas.android.com/apk/res/android">
    <translate
        android:duration="200"
        android:fromYDelta="100%"
        android:toYDelta="0" />
</set>
  1. 场景三:应用程序需要通过使用 Fragment 从启动应用程序到关闭应用程序的整个生命周期,来管理所有应用程序状态。

使用 Navigation 可以让所有生命周期管理逻辑更加明了,更加易于维护。以下示例,展示了应用程序鉴权处理、以及组织主要 UI 和流程的简单实例:

<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/app_nav_graph"
    app:startDestination="@id/authentication_fragment">

    <fragment
        android:id="@+id/authentication_fragment"
        android:name="com.example.AuthenticationFragment"
        android:label="Authentication"
        tools:layout="@layout/authentication_fragment">

        <action
            android:id="@+id/sign_up_action"
            app:destination="@id/sign_up_fragment" />

        <action
            android:id="@+id/sign_in_action"
            app:destination="@id/sign_in_fragment" />

    </fragment>

    <fragment
        android:id="@+id/sign_up_fragment"
        android:name="com.example.SignUpFragment"
        android:label="Sign Up"
        tools:layout="@layout/sign_up_fragment" />

    <fragment
        android:id="@+id/sign_in_fragment"
        android:name="com.example.SignInFragment"
        android:label="Sign In"
        tools:layout="@layout/sign_in_fragment" />

    <fragment
        android:id="@+id/home_fragment"
        android:name="com.example.HomeFragment"
        android:label="Home"
        tools:layout="@layout/home_fragment">

        <action
            android:id="@+id/sign_out_action"
            app:destination="@id/authentication_fragment"
            app:popUpTo="@id/authentication_fragment"
            app:popUpToInclusive="true" />

    </fragment>

</navigation>

如上所述,我们定义了一个 Navigation 导航图,并包含了三个 Fragment:AuthenticationFragment、SignUpFragment 和 SignInFragment。AuthenticationFragment 作为启动应用程序的入口,通过设置相应的 action,来连接所有 Fragment,并在用户登陆和退出时,执行相应的逻辑和动画。在具体实现中,我们可以通过 ViewModel 等组件获取数据,通过 LiveData 等组件进行状态更新以及 UI 显示等操作。

以上是 Navigation 的应用场景和示例介绍。作为 Android 应用程序开发的关键组件之一,Navigation 提供了非常便捷的屏幕导航和界面控制方式,同时显著提高了应用程序的用户体验,也符合当前应用程序架构和用户界面设计的趋势。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

凉亭下

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值