17

Why is it important to clear the binding in onDestroyView when implementing Android View Binding in a Fragment?

As the documentation shows, Use view binding in fragments, and the Android Architecture Components sample, the binding is initiated in onCreateView, and cleared in onDestroyView.

What is the benefit of implementing this compared to initiating the binding without clearing it in onDestroyView? Without explicitly clearing the instance variable binding, it should be cleared when the Fragment is destroyed.

private var _binding: ResultProfileBinding? = null
// This property is only valid between onCreateView and
// onDestroyView.
private val binding get() = _binding!!

override fun onCreateView(
    inflater: LayoutInflater,
    container: ViewGroup?,
    savedInstanceState: Bundle?
): View? {
    _binding = ResultProfileBinding.inflate(inflater, container, false)
    val view = binding.root
    return view
}

override fun onDestroyView() {
    super.onDestroyView()
    _binding = null
}
AdamHurwitz
  • 9,758
  • 10
  • 72
  • 134

2 Answers2

11

A Fragment can potentially have its view created and destroyed multiple times while the Fragment instance itself is still in memory. If you don't null out the view references, you are "leaking" these views during the span of time between onDestroyView() and onCreateView(). They aren't permanently leaked though, so perhaps that is the wrong term.

There are some who say it doesn't matter if these views are temporarily leaked. I don't know the lifecycle details enough to know if it strictly matters. I would expect that sometimes the reason views are torn down is that Android is trying to save memory while they are off screen, so if you hang onto them, you are subverting that.

Tenfour04
  • 83,111
  • 11
  • 94
  • 154
  • Good answer, Now let suppose we have used viewbinding in adapters , what is good practice to destroy the references in adapters ? – Ali Akram Feb 01 '22 at 07:49
  • 3
    @AliAkram You don't have to do anything special inside the adapter because it is not reused across multiple lifecycles. If you reference the adapter in a Fragment property, you should follow the same pattern as you do with the view binding, because the property reference would prevent the garbage collector from taking the adapter and all its views. – Tenfour04 Feb 01 '22 at 13:51
  • java have garbage collector, is usefull to assing object to null when destroy? – Abah Adilah Feb 21 '22 at 01:54
  • A fragment instance might be reused by the framework after it is destroyed, so if you don’t set view references to null in `onDestroy` they will needlessly stay in memory until they are replaced with other references when your fragment gets reattached. – Tenfour04 Feb 21 '22 at 03:11
  • You can read the article I linked about it. It’s likely not something you really need to worry about. – Tenfour04 Feb 21 '22 at 03:18
  • Is it a good practice to do the same for binding instances in activities? – Muhammad Babar Jan 18 '23 at 07:44
  • 1
    @MuhammadBabar There is no benefit to null out views in an Activity. Unlike a Fragment, an Activity instance is completely freed to the garbage collector right after `onDestroy()` is called because the Activity instance is never reused for another lifecycle. – Tenfour04 Jan 18 '23 at 14:10
2
  • As stated in the documentation: once the fragment then invokes its onDestroyView() callback all references to the fragment's view should be removed, allowing the fragment's view to be garbage collected.

  • Basically its to avoid memory leaks and the give our app an updated view

Deeper understanding

  • so to really understand what is going on you should read up on the Fragment's lifecycle documentation, specifically the section on destroying view's and fragments.

  • It is also important to point out that a fragment's view has a separate lifecycle that is managed independently from the fragment's lifecycle

  • However, we can still get a solid understanding of what is going on under the hood. When the Fragment is no longer in view(visible to the user) and all the exit animations and transition have been completed. The fragment's view will transition into it's DESTROYED state and emits a ON_DESTROY event to it's observer's(the fragment). This then triggers the fragment to invoke its onDestroyView() method. It's documentation states, The next time the fragment needs to be displayed, a new view will be created. So we set _binding = null to allow for a new View to be created and referenced.

Tristan Elliott
  • 594
  • 10
  • 8