Search code examples
androidandroid-fragmentskotlinandroid-fragmentactivitykotlin-android-extensions

Passing Value from Activity to Fragment


I have bottom navigation activity in my project and contain two fragments. I am trying to pass value from Activity--->FragmentOne and then From FragmentOne--->FragmentTwo. Any help is appreciated.

Language Used

Kotlin

Expectation

1)Pass value from Activity to Fragment
2)Send value from Fragment to Fragment

Error

Null Pointer Exception

Code

Activity

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_test)
        var testName:String=intent.getStringExtra("name")
        println("TestCLLicked: $testName")
navigation.setOnNavigationItemSelectedListener(mOnNavigationItemSelectedListener)
        replaceFragment(TestFragmentOne.newInstance(),TestFragmentOne.TAG)
    }

TestFragmentOne

override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
            super.onViewCreated(view, savedInstanceState)
            var st:String=arguments!!.getString("name")
             println("TestCLLicked: $testName")

Solution

  • You can go many ways but given your current implementation (using a newInstance), I'd go with using your parent activity as a mediator, going like this:

    1) Create a BaseFragment class which your TestFragmentOne and TestFragmentTwo will extend and in there hold a reference to your parent Activity (here named "MainActivity"):

    abstract class BaseFragment : Fragment() {
    
         lateinit var ACTIVITY: MainActivity
    
         override fun onAttach(context: Context) {
             super.onAttach(context)
             ACTIVITY = context as MainActivity
         }
    }
    

    2) Then, in your Activity make sure you declare your variable as a field:

    class MainActivity : AppCompatActivity() {
    
         var textVariable = "This to be read from the fragments"
         ...
         override fun onCreate(savedInstanceState: Bundle?) {
             super.onCreate(savedInstanceState)
             textVariable = "I can also change this text"
             ...
         }
    }
    

    3) Then, from each fragment you can access your variable using the instance inherited from your BaseFragment:

     class TestFragmentOne : BaseFragment() {
    
          override fun onActivityCreated(savedInstanceState: Bundle?) {
              super.onActivityCreated(savedInstanceState)
              val incomingText = ACTIVITY.textVariable
              println("Incoming text: "+incomingText)
    
              // You can also set the value of this variable to be read from 
              // another fragment later
              ACTIVITY.textVariable = "Text set from TestFragmentOne"
          }
     }