Fragment碎片的切换

    在上一篇[“Android常见的高级组件搭建移动应用界面”](https://editor.csdn.net/md/?articleId=127545452)中,是通过导航来实现信息栏的显示。这样的操作过于简单。在实际上,通过侧滑菜单的导航菜单和底部视图导航BottomNavigationView的导航往往可以用于不同Fragment切换来完成。
    通过Fragment定义不同的UI界面,结合导航实现不同界面的切换,让交互更好友好和方便。

一、定义三个不同界面的Fragment
第一个碎片类定义代码如下:

 object FirstFragment : Fragment() {
    
    

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

    }

    override fun onCreateView(
        inflater: LayoutInflater, container: ViewGroup?,
        savedInstanceState: Bundle?
    ): View? {
    
    
        // Inflate the layout for this fragment
        return inflater.inflate(R.layout.fragment_first, container, false)
    }

}

第二个碎片类定义代码如下:

object SecondFragment : Fragment() {
    
    

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

    }

    override fun onCreateView(
        inflater: LayoutInflater, container: ViewGroup?,
        savedInstanceState: Bundle?
    ): View? {
    
    
        // Inflate the layout for this fragment
        return inflater.inflate(R.layout.fragment_second, container, false)
    }

}

第三个碎片类定义代码如下:

object ThirdFragment : Fragment() {
    
    

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

    }

    override fun onCreateView(
        inflater: LayoutInflater, container: ViewGroup?,
        savedInstanceState: Bundle?
    ): View? {
    
    
        // Inflate the layout for this fragment
        return inflater.inflate(R.layout.fragment_third, container, false)
    }

}

上述代码中均将三个碎片类定义成对象类,对象类通过类来维护唯一的对象即自己本身。
二、修改上一篇"Android常见的高级组件搭建移动应用界面"的MainActivity对应的布局文件activity_main.xml,使用FragmentContainerView来承载碎片。代码如下:

<?xml version="1.0" encoding="utf-8"?>
<androidx.drawerlayout.widget.DrawerLayout
    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/drawerLayout"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">

    <androidx.constraintlayout.widget.ConstraintLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <androidx.appcompat.widget.Toolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="?attr/actionBarSize"
            android:background="@android:color/holo_orange_dark"
            app:layout_constraintBottom_toBottomOf="parent"
            app:layout_constraintStart_toStartOf="parent"
            app:layout_constraintTop_toTopOf="parent"
            app:layout_constraintVertical_bias="0.0" />

        **<androidx.fragment.app.FragmentContainerView
            android:id="@+id/fragmentLayout"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            app:layout_constraintBottom_toBottomOf="parent"
            app:layout_constraintEnd_toEndOf="parent"
            app:layout_constraintHorizontal_bias="1.0"
            app:layout_constraintStart_toStartOf="parent"
            app:layout_constraintTop_toBottomOf="@+id/toolbar"
            app:layout_constraintVertical_bias="0.0"
            />**

     <com.google.android.material.bottomnavigation.BottomNavigationView
            android:id="@+id/bottomNavigationView"
            android:layout_width="match_parent"
            android:layout_height="?attr/actionBarSize"
            android:background="@color/purple_200"
            app:layout_constraintBottom_toBottomOf="parent"
            app:layout_constraintEnd_toEndOf="parent"
            app:layout_constraintHorizontal_bias="0.5"
            app:layout_constraintStart_toStartOf="parent"
            app:layout_constraintTop_toBottomOf="@+id/toolbar"
            app:layout_constraintVertical_bias="1.0"
            app:menu="@menu/menu_navigation"
            />
    </androidx.constraintlayout.widget.ConstraintLayout>

    <com.google.android.material.navigation.NavigationView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:id="@+id/navigationView"
        android:layout_gravity="start"
        app:menu="@menu/menu_navigation"
        app:headerLayout="@layout/layout_header"/>
</androidx.drawerlayout.widget.DrawerLayout>

三、在主活动MainActivity中增加碎片处理的方式
碎片处理有两种方案:
(1)碎片替换
在界面中不同的碎片进行替换,如果需要切换一个新的碎片界面,就用一个新的碎片对象替换原来的碎片。这时代码可以调整为:

class MainActivity : AppCompatActivity() {
    
    
    lateinit var binding:ActivityMainBinding
   
    override fun onCreate(savedInstanceState: Bundle?) {
    
    
        super.onCreate(savedInstanceState)
        binding = ActivityMainBinding.inflate(layoutInflater)
        replaceFragment(FirstFragment)

        configToolbar()
        configDrawerLayout()
        configBottomNavigationView()
       
        setContentView(binding.root)
    }
......
    /**
     * Config toolbar
     * 设置头部
     */
    fun configToolbar(){
    
    
        setSupportActionBar(binding.toolbar)
    }

    fun configDrawerLayout(){
    
    
        supportActionBar?.let{
    
    
            it.setDisplayHomeAsUpEnabled(true)
            it.setHomeAsUpIndicator(R.mipmap.ic_launcher)
        }
        binding.navigationView.setCheckedItem(R.id.aboutItem)
        binding.navigationView.itemIconTintList = null
        binding.navigationView.setNavigationItemSelectedListener {
    
    
            when(it.itemId){
    
    
                R.id.appItem->replaceFragment(FirstFragment)
                R.id.favorityItem->replaceFragment(SecondFragment)
                R.id.configItem->repalceFragment(ThirdFragment)
            }
            binding.drawerLayout.closeDrawer(GravityCompat.START)
            true
        }
    }

    fun configBottomNavigationView(){
    
    
        binding.bottomNavigationView.itemIconTintList = null
        binding.bottomNavigationView.setOnItemSelectedListener{
    
    
            when(it.itemId){
    
    
                R.id.appItem->replaceFragment(FirstFragment)
                R.id.favorityItem->replaceFragment(SecondFragment)
                R.id.configItem->repalceFragment(ThirdFragment)
            }
            true
        }
    }


    /**
     * 实现碎片的替换
     * @param fragment Fragment
     */
    fun replaceFragment(fragment:Fragment){
    
    
        val transaction = supportFragmentManager.beginTransaction()
        transaction.replace(R.id.fragmentLayout,fragment)
        transaction.addToBackStack(null)
        transaction.commit()
    }
}

(2)碎片的隐藏和显示
将所有碎片加入到事务Transaction中,通过事务的显示或隐藏碎片来达到切换碎片对应界面的目的。这时代码可以调整成:

class MainActivity : AppCompatActivity() {
    
    
    lateinit var binding:ActivityMainBinding
    lateinit var currentFragment:Fragment

    override fun onCreate(savedInstanceState: Bundle?) {
    
    
        super.onCreate(savedInstanceState)
        binding = ActivityMainBinding.inflate(layoutInflater)
        currentFragment = FirstFragment
        
        configToolbar()
        configDrawerLayout()
        configBottomNavigationView()
        switchFragment(currentFragment)
        setContentView(binding.root)
    }
......
    /**
     * Config toolbar
     * 设置头部
     */
    fun configToolbar(){
    
    
        setSupportActionBar(binding.toolbar)
    }

    fun configDrawerLayout(){
    
    
        supportActionBar?.let{
    
    
            it.setDisplayHomeAsUpEnabled(true)
            it.setHomeAsUpIndicator(R.mipmap.ic_launcher)
        }
        binding.navigationView.setCheckedItem(R.id.aboutItem)
        binding.navigationView.itemIconTintList = null
        binding.navigationView.setNavigationItemSelectedListener {
    
    
            **when(it.itemId){
    
    
                R.id.appItem->switchFragment(FirstFragment)
                R.id.favorityItem->switchFragment(SecondFragment)
                R.id.configItem->switchFragment(ThirdFragment)
            }**
            binding.drawerLayout.closeDrawer(GravityCompat.START)
            true
        }
    }

    fun configBottomNavigationView(){
    
    
        binding.bottomNavigationView.itemIconTintList = null
        binding.bottomNavigationView.setOnItemSelectedListener{
    
    
            **when(it.itemId){
    
    
                R.id.appItem->switchFragment(FirstFragment)
                R.id.favorityItem->switchFragment(SecondFragment)
                R.id.configItem->switchFragment(ThirdFragment)
            }**
            true
        }
    }

    ......
    /**
     * 实现碎片的切换
     * @param fragment Fragment
     */
    **fun switchFragment(fragment: Fragment){
    
    
        val transaction = supportFragmentManager.beginTransaction()
        if(!fragment.isAdded){
    
    
            transaction.hide(currentFragment)
            transaction.add(R.id.fragmentLayout,fragment)
        }else{
    
    
            transaction.hide(currentFragment)
            transaction.show(fragment)
        }
        currentFragment = fragment
        transaction.commit()
    }**
}

参考文献:
《Android移动应用开发(微课版)》 陈轶 清华大学出版社 
 ISBN:978-7-302-59734-6

猜你喜欢

转载自blog.csdn.net/userhu2012/article/details/127549993