@@ -39,7 +39,7 @@ class LoadingStateView @JvmOverloads constructor(
3939 private val parent: ViewGroup ?
4040 private var currentView: View ? = null
4141 private var viewDelegates: HashMap <Any , ViewDelegate > = HashMap ()
42- private val viewCashes : HashMap <Any , View > = HashMap ()
42+ private val viewCaches : HashMap <Any , View > = HashMap ()
4343
4444 /* *
4545 * Constructs a LoadingStateView with an activity and listener.
@@ -111,6 +111,7 @@ class LoadingStateView @JvmOverloads constructor(
111111 onCreateDecorView(contentView.context, LayoutInflater .from(contentView.context)).also { decorView ->
112112 contentView.layoutParams?.let {
113113 decorView.layoutParams = if (it is ConstraintLayout .LayoutParams ) ConstraintLayout .LayoutParams (it) else it
114+ (it as ? ViewGroup .MarginLayoutParams )?.setMargins(0 , 0 , 0 , 0 )
114115 }
115116 }
116117
@@ -122,39 +123,41 @@ class LoadingStateView @JvmOverloads constructor(
122123 fun register (vararg delegates : ViewDelegate ) = delegates.forEach { viewDelegates[it.viewType] = it }
123124
124125 @JvmOverloads
125- fun showLoadingView (animation : Animation ? = null ) = showView(ViewType .LOADING , animation )
126+ fun showLoadingView (animatable : Animatable ? = defaultAnimatable ) = showView(ViewType .LOADING , animatable )
126127
127128 @JvmOverloads
128- fun showContentView (animation : Animation ? = null ) = showView(ViewType .CONTENT , animation )
129+ fun showContentView (animatable : Animatable ? = defaultAnimatable ) = showView(ViewType .CONTENT , animatable )
129130
130131 @JvmOverloads
131- fun showErrorView (animation : Animation ? = null ) = showView(ViewType .ERROR , animation )
132+ fun showErrorView (animatable : Animatable ? = defaultAnimatable ) = showView(ViewType .ERROR , animatable )
132133
133134 @JvmOverloads
134- fun showEmptyView (animation : Animation ? = null ) = showView(ViewType .EMPTY , animation )
135+ fun showEmptyView (animatable : Animatable ? = defaultAnimatable ) = showView(ViewType .EMPTY , animatable )
135136
136137 /* *
137138 * Shows the view by view type
138139 *
139140 * @param viewType the view type of view delegate
140141 */
141142 @JvmOverloads
142- fun showView (viewType : Any , animation : Animation ? = null ) {
143+ fun showView (viewType : Any , animatable : Animatable ? = defaultAnimatable ) {
143144 val currentView = currentView
144145 if (currentView == null ) {
145146 addView(viewType)
146147 } else {
147- if (viewCashes [viewType] == null ) addView(viewType)
148+ if (viewCaches [viewType] == null ) addView(viewType)
148149 if (viewType != currentViewType) {
149- val view = getView(viewType)
150- view.visibility = View .VISIBLE
151- if (animation != null ) {
152- animation.onStartHideAnimation(currentView, currentViewType)
153- animation.onStartShowAnimation(view, getViewDelegate<ViewDelegate >(viewType)!! .viewType)
150+ val nextView = getOrCreateView(viewType)
151+ nextView.visibility = View .VISIBLE
152+ val nextViewDelegate = getViewDelegate<ViewDelegate >(viewType)
153+ nextViewDelegate?.onViewAttached(nextView)
154+ getViewDelegate<ViewDelegate >(currentViewType)?.onViewDetached(nextView)
155+ if (animatable != null && nextViewDelegate != null ) {
156+ animatable.toggleViewsAnimation(nextView, currentView, viewType, currentViewType)
154157 } else {
155158 currentView.visibility = View .GONE
156159 }
157- this .currentView = view
160+ this .currentView = nextView
158161 }
159162 }
160163 currentViewType = viewType
@@ -167,7 +170,7 @@ class LoadingStateView @JvmOverloads constructor(
167170 fun <T : ViewDelegate > getViewDelegate (viewType : Any ) = viewDelegates[viewType] as ? T
168171
169172 private fun addView (viewType : Any ) {
170- val view = getView (viewType)
173+ val view = getOrCreateView (viewType)
171174 (view.parent as ? ViewGroup )?.removeView(view)
172175 if (parent is ConstraintLayout && viewType == ViewType .CONTENT ) {
173176 val params = view.layoutParams
@@ -179,24 +182,25 @@ class LoadingStateView @JvmOverloads constructor(
179182 currentView = view
180183 }
181184
182- private fun getView (viewType : Any ): View {
183- if (viewCashes [viewType] == null ) {
185+ private fun getOrCreateView (viewType : Any ): View {
186+ if (viewCaches [viewType] == null ) {
184187 val viewDelegate = requireNotNull(getViewDelegate(viewType)) { " Please register view delegate for $viewType type." }
185188 val view = viewDelegate.onCreateView(LayoutInflater .from(contentParent.context), contentParent)
186189 viewDelegate.onReloadListener = onReloadListener
187- viewCashes [viewType] = view
190+ viewCaches [viewType] = view
188191 }
189- return viewCashes [viewType]!!
192+ return viewCaches [viewType]!!
190193 }
191194
192195 abstract class ViewDelegate (val viewType : Any ) {
196+ abstract fun onCreateView (inflater : LayoutInflater , parent : ViewGroup ): View
197+ open fun onViewAttached (view : View ) = Unit
198+ open fun onViewDetached (view : View ) = Unit
193199 var onReloadListener: OnReloadListener ? = null
194200 internal set
195-
196- abstract fun onCreateView (inflater : LayoutInflater , parent : ViewGroup ): View
197201 }
198202
199- private inner class ContentViewDelegate : LoadingStateView . ViewDelegate (ViewType .CONTENT ) {
203+ private inner class ContentViewDelegate : ViewDelegate (ViewType .CONTENT ) {
200204 override fun onCreateView (inflater : LayoutInflater , parent : ViewGroup ) = contentView
201205 }
202206
@@ -210,7 +214,7 @@ class LoadingStateView @JvmOverloads constructor(
210214
211215 constructor (delegates: Array <out ViewDelegate >) : this (delegates.map {
212216 register(it)
213- getView (it.viewType)
217+ getOrCreateView (it.viewType)
214218 })
215219
216220 override fun onCreateDecorView (context : Context , inflater : LayoutInflater ) =
@@ -233,14 +237,16 @@ class LoadingStateView @JvmOverloads constructor(
233237 fun T.invoke ()
234238 }
235239
236- interface Animation {
237- fun onStartShowAnimation (view : View , viewType : Any )
238- fun onStartHideAnimation (view : View , viewType : Any )
240+ interface Animatable {
241+ fun toggleViewsAnimation (showView : View , hideView : View , showViewType : Any , hideViewType : Any )
239242 }
240243
241244 companion object {
242245 private var poolInitializer: Callback <PoolInitializer >? = null
243246
247+ @JvmStatic
248+ var defaultAnimatable: Animatable ? = null
249+
244250 @JvmStatic
245251 fun setViewDelegatePool (poolInitializer : Callback <PoolInitializer >) {
246252 this .poolInitializer = poolInitializer
0 commit comments