Last active
May 3, 2022 18:36
-
-
Save nullptr2this/a05be2b8dd24813c35f33db77f8d4b48 to your computer and use it in GitHub Desktop.
View Binding Holder for Fragments
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import android.view.View | |
import androidx.viewbinding.ViewBinding | |
/** | |
* Creates a [ViewBindingHolder] with the given [ViewBinding] factory to | |
* act as an accessor to the [ViewBinding]. | |
* | |
* ``` | |
* class MyFragment : Fragment(R.layout.fragment_mine) { | |
* | |
* private val binding = viewBindingFrom(FragmentMineBinding::bind) | |
* private var counter: Int = 0 | |
* | |
* override fun onViewCreated(view: View, savedInstanceState: Bundle?) { | |
* super.onViewCreated(view, savedInstanceState) | |
* binding.bindTo(view) | |
* binding.views.buttonIncrement.setOnClickListener { | |
* counter += 1 | |
* updateCounterDisplay() | |
* } | |
* } | |
* | |
* override fun onDestroyView() { | |
* super.onDestroyView() | |
* binding.clear() | |
* } | |
* | |
* private fun updateCounterDisplay() { | |
* binding.doWithViews { | |
* textCounter.setText("Counter: $counter") | |
* } | |
* } | |
* ``` | |
*/ | |
fun <T : ViewBinding> viewBindingFrom(factory: (View) -> T): ViewBindingHolder<T> { | |
return ViewBindingHolder(factory) | |
} | |
/** | |
* Wrapper around a [ViewBinding] intended to slightly reduce boiler plate | |
* when [ViewBinding]s are used in Fragments. | |
*/ | |
class ViewBindingHolder<T : ViewBinding>( | |
private val factory: (View) -> T | |
) { | |
private var viewBinding: T? = null | |
/** | |
* Gets the view binding instance that has been bound to this holder instance. | |
*/ | |
val views: T | |
get() = requireNotNull(viewBinding) { "The associated view binding does not exist." } | |
/** | |
* Executes the block provided with the view binding instance if it exists. | |
*/ | |
fun doWithViews(block: T.() -> Unit) { | |
viewBinding?.let(block) | |
} | |
/** | |
* Binds a view binding instance from the View provided and returns the View | |
* as a convenience. | |
*/ | |
fun bindTo(view: View): View { | |
viewBinding = factory.invoke(view) | |
return view | |
} | |
/** | |
* Frees the view binding instance so it and its associated views | |
* are not leaked. | |
*/ | |
fun clear() { | |
viewBinding = null | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment