androidkotlindatepickerdialog

Android Date Picker dialog context parameter


I am playing around with android and I wanted to create a date picker in my app. I followed the tutorial at developer.android.com which shows the following code:

class DatePickerFragment : DialogFragment(), DatePickerDialog.OnDateSetListener {

    override fun onCreateDialog(savedInstanceState: Bundle): Dialog {
        // Use the current date as the default date in the picker
        val c = Calendar.getInstance()
        val year = c.get(Calendar.YEAR)
        val month = c.get(Calendar.MONTH)
        val day = c.get(Calendar.DAY_OF_MONTH)

        // Create a new instance of DatePickerDialog and return it
        return DatePickerDialog(activity, this, year, month, day)
    }

    override fun onDateSet(view: DatePicker, year: Int, month: Int, day: Int) {
        // Do something with the date chosen by the user
    }
}

However, when I use this code android studio complains that there is a Type mismatch on the first parameter of DatePickerDialog:

Type mismatch.
Required: Contex
Found: FragmentActivity?

I also tried to get the context as activity?.applicationContext but that does not solve it either.


Solution

  • Is because FragmentActivity? is nullable ? so you need a non-nullable Context. You can use:

    requireContext()
    

    The function requireContext() is the recommended way of getting the context for non-nullable in Kotlin, in fragments. It doesn't mean is not nullable, the Context can always end up as null. What the function does is to throw an exception if is null, that is why you can use it as if weren't null. The exception is mostly never thrown and if it happens is because it was used before or after the Context were available, so using context!! would have also crashed.

    Using activity!!.applicationContext would also work, but that is a cast to not nullable from a nullable and therefore not recommended.

    This is very similar to requireActivity()

    The last thing you could try is using this which would be the Fragment, sadly you can't

    val context: Context = this
    

    That would be not null because the fragment is not null if is doing something, but the fragment doesn't extend from Context like activities do (if you follow the inheritance of the context for the activities the 3 more upper parents are ContextThemeWrapper, ContextWrapper and Context)