当前位置: 代码网 > it编程>App开发>Android > Android在kts中使用navigation及Args的方法

Android在kts中使用navigation及Args的方法

2024年10月25日 Android 我要评论
android在kts中使用navigation及args前言:​ 之前在项目中使用过navigation,但都是以groory的方式,最近一年多使用kts后忍不住把项目都改成kts的方式,不过其中也

android在kts中使用navigation及args

前言:

​ 之前在项目中使用过navigation,但都是以groory的方式,最近一年多使用kts后忍不住把项目都改成kts的方式,不过其中也遇到不少坑,今天就讲解一下如何在kts中使用navigation和安全地传递参数args。

1.项目依赖导入:

在libs.versions.toml文件下添加以下依赖:

navigationfragmentktx = "2.6.0"
navigationuiktx = "2.6.0"
navigation-fragment = {group = "androidx.navigation",name = "navigation-fragment-ktx",version.ref = "navigationfragmentktx"}
navigation-ui = {group = "androidx.navigation",name = "navigation-ui-ktx",version.ref = "navigationuiktx"}
navigation-safe-args = { id = "androidx.navigation.safeargs.kotlin", version = "2.8.0" }

在这里插入图片描述

2.app目录的build.gradle配置:

plugins {
    alias(libs.plugins.androidapplication)
    alias(libs.plugins.jetbrainskotlinandroid)
    alias(libs.plugins.navigation.safe.args)
}
    implementation(libs.navigation.fragment)
    implementation(libs.navigation.ui)

在这里插入图片描述

在这里插入图片描述

3.项目的build.gradle配置:

plugins {
    alias(libs.plugins.androidapplication) apply false
    alias(libs.plugins.jetbrainskotlinandroid) apply false
    alias(libs.plugins.navigation.safe.args) apply false
}

在这里插入图片描述

4.在布局添加导航组件:

在res目录添加navigation——nav_graph文件

<?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/nav_graph"
    app:startdestination="@id/mainfragment">
    <fragment
        android:id="@+id/mainfragment"
        android:label="fragment_main"
        android:name="com.cloud.flowbusdemo.fragment.mainfragment"
        tools:layout="@layout/fragment_main">
        <action
            android:id="@+id/action_mainfragment_to_secondfragment"
            app:destination="@id/secondfragment"
            app:popenteranim="@anim/slide_in_left"
            app:popexitanim="@anim/slide_out_right"
            app:enteranim="@anim/slide_in_right"
            app:exitanim="@anim/slide_out_left"/>
        <action
            android:id="@+id/action_mainfragment_to_minefragment"
            app:destination="@id/minefragment"
            app:enteranim="@anim/slide_in_left"
            app:exitanim="@anim/slide_in_right"
            app:popenteranim="@anim/slide_out_left"
            app:popexitanim="@anim/slide_out_right" />
        <argument
            android:name="name"
            app:argtype="string"
            android:defaultvalue="xiaozhang"/>
        <argument
            android:name="age"
            app:argtype="integer"
            android:defaultvalue="1"/>
    </fragment>
    <fragment
        android:id="@+id/secondfragment"
        android:label="fragment_second"
        android:name="com.cloud.flowbusdemo.fragment.secondfragment"
        tools:layout="@layout/fragment_second"/>
    <fragment
        android:id="@+id/minefragment"
        android:name="com.cloud.flowbusdemo.fragment.minefragment"
        android:label="fragment_mine"
        tools:layout="@layout/fragment_mine" />
</navigation>

在这里插入图片描述

5.fragment_main布局:

fragment_mine.xml

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.constraintlayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:app="http://schemas.android.com/apk/res-auto">
    <androidx.appcompat.widget.appcompattextview
        android:id="@+id/tvtitle"
        android:layout_width="0dp"
        android:layout_height="40dp"
        app:layout_constraintstart_tostartof="parent"
        app:layout_constraintend_toendof="parent"
        app:layout_constrainttop_totopof="parent"
        android:textsize="18sp"
        android:textcolor="@color/white"
        android:gravity="center"
        android:text="mainfragment"
        android:layout_margin="20dp"
        android:background="@color/design_default_color_primary"
        tools:ignore="missingconstraints" />
    <androidx.appcompat.widget.appcompattextview
        android:id="@+id/btntosecondfragment"
        android:layout_width="0dp"
        android:layout_height="40dp"
        app:layout_constrainttop_tobottomof="@id/tvtitle"
        app:layout_constraintstart_tostartof="parent"
        app:layout_constraintend_toendof="parent"
        android:textallcaps="false"
        android:textcolor="@color/white"
        android:gravity="center"
        android:layout_margin="20dp"
        android:background="@color/design_default_color_primary"
        android:text="打开secondfragment"/>
    <androidx.appcompat.widget.appcompattextview
        android:id="@+id/btntominefragment"
        android:layout_width="0dp"
        android:layout_height="40dp"
        app:layout_constrainttop_tobottomof="@+id/btntosecondfragment"
        app:layout_constraintstart_tostartof="parent"
        app:layout_constraintend_toendof="parent"
        android:textallcaps="false"
        android:layout_margintop="10dp"
        android:textcolor="@color/white"
        android:gravity="center"
        android:layout_margin="20dp"
        android:background="@color/design_default_color_primary"
        android:text="打开minefragment"/>
</androidx.constraintlayout.widget.constraintlayout>

6.fragment_mine布局:

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.constraintlayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:tools="http://schemas.android.com/tools"
    xmlns:app="http://schemas.android.com/apk/res-auto">
    <textview
        android:id="@+id/tvtitle"
        android:layout_width="200dp"
        android:layout_height="50dp"
        android:textsize="20sp"
        tools:text="姓名"
        android:gravity="center"
        android:background="@color/design_default_color_primary"
        app:layout_constrainttop_totopof="parent"
        app:layout_constraintstart_tostartof="parent"
        app:layout_constraintend_toendof="parent"
        android:textcolor="@color/white"
        android:layout_margintop="20dp"/>
    <textview
        android:id="@+id/tvage"
        android:layout_width="200dp"
        android:layout_height="50dp"
        android:textsize="18sp"
        tools:text="年龄"
        android:gravity="center"
        android:background="@color/design_default_color_primary"
        app:layout_constraintstart_tostartof="parent"
        app:layout_constraintend_toendof="parent"
        app:layout_constrainttop_tobottomof="@id/tvtitle"
        android:textcolor="@color/white"
        android:layout_margintop="20dp"/>
</androidx.constraintlayout.widget.constraintlayout>

7.fragment_second布局:

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.constraintlayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:tools="http://schemas.android.com/tools"
    xmlns:app="http://schemas.android.com/apk/res-auto">
    <textview
        android:id="@+id/tvtitle"
        android:layout_width="200dp"
        android:layout_height="50dp"
        android:textsize="20sp"
        tools:text="姓名"
        android:gravity="center"
        android:background="@color/design_default_color_primary"
        app:layout_constrainttop_totopof="parent"
        app:layout_constraintstart_tostartof="parent"
        app:layout_constraintend_toendof="parent"
        android:textcolor="@color/white"
        android:layout_margintop="20dp"/>
    <textview
        android:id="@+id/tvage"
        android:layout_width="200dp"
        android:layout_height="50dp"
        android:textsize="18sp"
        tools:text="年龄"
        android:gravity="center"
        android:background="@color/design_default_color_primary"
        app:layout_constraintstart_tostartof="parent"
        app:layout_constraintend_toendof="parent"
        app:layout_constrainttop_tobottomof="@id/tvtitle"
        android:textcolor="@color/white"
        android:layout_margintop="20dp"/>
</androidx.constraintlayout.widget.constraintlayout>

8.activity_main主界面:

<?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">
    <androidx.recyclerview.widget.recyclerview
        android:id="@+id/rv_wallpaper"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:paddingstart="2dp"
        android:paddingend="2dp"
        android:visibility="gone" />
    <progressbar
        android:id="@+id/pb_loading"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:visibility="gone"
        app:layout_constraintbottom_tobottomof="parent"
        app:layout_constraintend_toendof="parent"
        app:layout_constraintstart_tostartof="parent"
        app:layout_constrainttop_totopof="parent" />
    <textview
        android:id="@+id/btn_get_wallpaper"
        android:layout_width="0dp"
        android:layout_height="40dp"
        android:text="获取壁纸"
        android:textcolor="@color/white"
        android:gravity="center"
        android:background="@color/design_default_color_primary"
        app:layout_constraintend_toendof="parent"
        app:layout_constraintstart_tostartof="parent"
        app:layout_constrainttop_totopof="parent"
        android:layout_margin="20dp"/>
    <fragment
        android:id="@+id/nav_host_fragment"
        android:name="androidx.navigation.fragment.navhostfragment"
        android:layout_width="0dp"
        android:layout_height="0dp"
        app:defaultnavhost="true"
        app:layout_constraintbottom_tobottomof="parent"
        app:layout_constraintleft_toleftof="parent"
        app:layout_constraintright_torightof="parent"
        app:layout_constrainttop_tobottomof="@+id/btn_get_wallpaper"
        app:navgraph="@navigation/nav_graph"
        android:layout_margintop="20dp"/>
</androidx.constraintlayout.widget.constraintlayout>

9.mainactivity代码:

package com.cloud.flowbusdemo
import android.annotation.suppresslint
import android.content.intent
import android.os.bundle
import android.util.log
import android.view.view
import android.widget.toast
import androidx.appcompat.app.appcompatactivity
import androidx.lifecycle.viewmodelprovider
import androidx.lifecycle.lifecyclescope
import androidx.recyclerview.widget.gridlayoutmanager
import com.blankj.utilcode.util.logutils
import com.cloud.flowbusdemo.databinding.activitymainbinding
import com.cloud.flowbusdemo.flow.flowbus
import com.cloud.flowbusdemo.http.httputils
import com.cloud.flowbusdemo.intent.mainintent
import com.cloud.flowbusdemo.model.messageevent
import com.cloud.flowbusdemo.service.flowbustestservice
import com.cloud.flowbusdemo.ui.adapter.wallpaperadapter
import com.cloud.flowbusdemo.ui.viewmodel.mainviewmodel
import com.cloud.flowbusdemo.ui.viewmodel.viewmodelfactory
import com.cloud.flowbusdemo.uistate.mainuistate
import com.cloud.flowbusdemo.utils.ctoast
import com.cloud.flowbusdemo.utils.generictoast
import com.cloud.flowbusdemo.utils.singletoast
import kotlinx.coroutines.launch
class mainactivity : appcompatactivity() {
    private lateinit var binding: activitymainbinding
    private lateinit var mainviewmodel: mainviewmodel
    private var wallpaperadapter = wallpaperadapter(arraylistof())
    private val tag = "flowbusdemo"
    private var mctoast: ctoast? = null
    override fun oncreate(savedinstancestate: bundle?) {
        super.oncreate(savedinstancestate)
        binding = activitymainbinding.inflate(layoutinflater)
        setcontentview(binding.root)
        mainviewmodel = viewmodelprovider(
            this,
            viewmodelfactory(httputils.apiservice)
        )[mainviewmodel::class.java]
        initview()
        observeviewmodel()
        initservice()
    }
    private fun initservice() {
        val intent = intent(this@mainactivity, flowbustestservice::class.java)
        intent.putextra("sockurl","")
        startservice(intent)
    }
    /**
     * viewmodel
     */
    @suppresslint("notifydatasetchanged")
    private fun observeviewmodel() {
        lifecyclescope.launch {
            mainviewmodel.state.collect {
                when (it) {
                    is mainuistate.idle -> {
                    }
                    is mainuistate.loading -> {
                        binding.btngetwallpaper.visibility = view.gone
                        binding.pbloading.visibility = view.visible
                    }
                    is mainuistate.success -> {     //数据返回
                        binding.btngetwallpaper.visibility = view.gone
                        binding.pbloading.visibility = view.gone
                        binding.rvwallpaper.visibility = view.visible
                        it.wallpaper.let { paper ->
                            wallpaperadapter.adddata(paper.res.vertical)
                        }
                        wallpaperadapter.notifydatasetchanged()
                    }
                    is mainuistate.error -> {
                        binding.pbloading.visibility = view.gone
                        binding.btngetwallpaper.visibility = view.visible
                        log.d("tag", "observeviewmodel: $it.error")
                        toast.maketext(this@mainactivity, it.error, toast.length_long).show()
                    }
                }
            }
        }
    }
    /**
     * 初始化
     */
    private fun initview() {
        binding.rvwallpaper.apply {
            layoutmanager = gridlayoutmanager(this@mainactivity, 2)
            adapter = wallpaperadapter
        }
        binding.btngetwallpaper.setonclicklistener {
           lifecyclescope.launch {
                mainviewmodel.mainintentchannel.send(mainintent.getwallpaper)
            }
            val intent = intent(this@mainactivity,testactivity::class.java)
            startactivity(intent)
            val timetoast =
                singletoast.maketext(this@mainactivity, "显示时间自定的toast", 10.0)
            timetoast.show()
        }
        flowbus.with<messageevent>("test").register(this@mainactivity) {
            logutils.d(tag,it.tostring())
            if(it.message == "stop"){
                logutils.d(tag,"===接收到的消息为==="+it.message)
            }
        }
        flowbus.with<messageevent>("minefragment").register(this@mainactivity) {
            logutils.d(tag,it.tostring())
            if(it.message == "onmine"){
                logutils.d(tag,"===接收到的消息为1111==="+it.message)
            }
        }
    }
}

10.mainfragment代码:

package com.cloud.flowbusdemo.fragment
import android.os.bundle
import android.view.layoutinflater
import android.view.view
import android.view.viewgroup
import androidx.fragment.app.fragment
import androidx.navigation.navigation
import com.cloud.flowbusdemo.r
import com.cloud.flowbusdemo.databinding.fragmentmainbinding
private const val arg_param_name = "name"
private const val arg_param_age = "age"
/**
 * @auth: njb
 * @date: 2024/9/17 18:46
 * @desc: 描述
 */
class mainfragment : fragment() {
    private lateinit var binding: fragmentmainbinding
    private var name: string? = null
    private var age: int? = null
    override fun oncreate(savedinstancestate: bundle?) {
        super.oncreate(savedinstancestate)
        arguments?.let {
            name = it.getstring(arg_param_name)
            age = it.getint(arg_param_age)
        }
    }
    override fun oncreateview(
        inflater: layoutinflater,
        container: viewgroup?,
        savedinstancestate: bundle?
    ): view {
        binding = fragmentmainbinding.inflate(layoutinflater)
        initview()
        return binding.root
    }
    private fun initview() {
        binding.btntosecondfragment.setonclicklistener(view.onclicklistener { v ->
            /*      val bundle = bundle()
                  bundle.putstring("name", "michael")
                  bundle.putint("age", 30)*/
            val args: bundle = bundle().apply {
                this.putstring(arg_param_name, "哈哈")
                this.putint(arg_param_age, 25)
            }
            navigation.findnavcontroller(v)
                .navigate(r.id.action_mainfragment_to_secondfragment, args)
        })
        binding.btntominefragment.setonclicklistener{v ->
            val args: bundle = bundle().apply {
                this.putstring(arg_param_name, "tom")
                this.putint(arg_param_age, 18)
            }
            val navcontroller = navigation.findnavcontroller(v)
            //navcontroller.navigate(r.id.action_mainfragment_to_minefragment, args)
            val bundle: bundle = mainfragmentargs("haha",20).tobundle()
             navigation.findnavcontroller(v).navigate(r.id.action_mainfragment_to_minefragment,bundle)
        }
    }
}

11.minefragment代码:

package com.cloud.flowbusdemo.fragment
import android.os.bundle
import android.util.log
import android.view.layoutinflater
import android.view.view
import android.view.viewgroup
import androidx.fragment.app.fragment
import androidx.lifecycle.lifecyclescope
import androidx.navigation.fragment.navargs
import com.cloud.flowbusdemo.databinding.fragmentminebinding
import com.cloud.flowbusdemo.flow.flowbus
import com.cloud.flowbusdemo.model.messageevent
import kotlinx.coroutines.launch
private const val arg_param_name = "name"
private const val arg_param_age = "age"
/**
 * @auth: njb
 * @date: 2024/9/17 19:43
 * @desc: 描述
 */
class minefragment :fragment(){
    private lateinit var binding: fragmentminebinding
    private val tag = "minefragment"
    private var name: string? = null
    private var age: int? = 0
    private val args:mainfragmentargs by  navargs()
    override fun oncreate(savedinstancestate: bundle?) {
        super.oncreate(savedinstancestate)
        args.let {
            name = args.name
            age = args.age
        }
        log.i(tag, "传递过来的参数为 name = $name , age = $age")
        log.d(tag, "姓名:" + name + "年龄:" + age)
    }
    override fun oncreateview(
        inflater: layoutinflater,
        container: viewgroup?,
        savedinstancestate: bundle?
    ): view {
        binding = fragmentminebinding.inflate(layoutinflater)
        initview()
        return binding.root
    }
    private fun initview() {
        val messageevent = messageevent()
        messageevent.message = "onmine"
        messageevent.state = false
        binding.let {
            it.tvtitle.text = name
            it.tvage.text  = age.tostring()
            it.tvtitle.setonclicklistener {
                lifecyclescope.launch {
                    flowbus.with<messageevent>("minefragment").post(this, messageevent)
                }
            }
        }
    }
}

12.secondfragment代码:

package com.cloud.flowbusdemo.fragment
import android.os.bundle
import android.util.log
import android.view.layoutinflater
import android.view.view
import android.view.viewgroup
import androidx.fragment.app.fragment
import androidx.lifecycle.lifecyclescope
import com.cloud.flowbusdemo.constants.constants
import com.cloud.flowbusdemo.databinding.fragmentminebinding
import com.cloud.flowbusdemo.databinding.fragmentsecondbinding
import com.cloud.flowbusdemo.flow.flowbus
import com.cloud.flowbusdemo.model.messageevent
import kotlinx.coroutines.launch
/**
 * @auth: njb
 * @date: 2024/9/17 18:48
 * @desc: 描述
 */
class secondfragment : fragment(){
    private val tag = "secondfragment"
    private var name: string? = null
    private var age: int? = null
    private lateinit var binding: fragmentsecondbinding
    override fun oncreateview(
        inflater: layoutinflater,
        container: viewgroup?,
        savedinstancestate: bundle?
    ): view {
        binding = fragmentsecondbinding.inflate(layoutinflater)
        initview()
        return binding.root
    }
    override fun oncreate(savedinstancestate: bundle?) {
        super.oncreate(savedinstancestate)
        arguments?.let {
            name = it.getstring(constants.arg_param_name)
            age = it.getint(constants.arg_param_age)
        }
        log.i(tag, "mainfragment 传递到 secondfragment 的参数为 name = $name , age = $age")
        log.d(tag, "姓名:" + name + "年龄:" + age)
    }
    private fun initview() {
        binding.let {
            it.tvtitle.text = name
            it.tvage.text  = age.tostring()
        }
    }
}

13.传递参数的方式:

13.1使用bundle:

binding.btntosecondfragment.setonclicklistener(view.onclicklistener { v ->
          val bundle = bundle()
          bundle.putstring("name", "michael")
          bundle.putint("age", 30)
    navigation.findnavcontroller(v)
        .navigate(r.id.action_mainfragment_to_secondfragment, bundle)
})

13.2使用safs安全方式传递:

binding.btntominefragment.setonclicklistener{v ->
    val bundle: bundle = mainfragmentargs("haha",20).tobundle()
     navigation.findnavcontroller(v).navigate(r.id.action_mainfragment_to_minefragment,bundle)
}

14.实现效果如下:

15.项目demo地址:

https://gitee.com/jackning_admin/flowbus-demo

到此这篇关于android在kts中使用navigation及args的文章就介绍到这了,更多相关android 使用navigation args内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网!

(0)

相关文章:

版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。

发表评论

验证码:
Copyright © 2017-2025  代码网 保留所有权利. 粤ICP备2024248653号
站长QQ:2386932994 | 联系邮箱:2386932994@qq.com