I have recyerlView. I loaded data from the server. When it initially loads it height is normal, but when I go to the next activity through item click. And come back it slowly increasing the height of the child. I tried to debug this and found that onResume api call causing the issue. But What I am doing wrong in layout I don't get it.
FirstLayout.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent">
<androidx.recyclerview.widget.RecyclerView
android:id="@ id/reyclerview"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
FirstActivity.kt
class FirstActivity : BaseActivity() {
lateinit var binding: FirstLayoutActivityLayoutBinding
private val viewModel: FirstViewModel by inject()
private var listAdapter: ListAdapter? = null
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setupViewModel()
binding = FirstLayoutActivityLayoutBinding.inflate(layoutInflater)
setContentView(binding.root)
}
private fun setupViewModel() {
viewModel.livedata.observe(this, { list ->
setupAdapter(list)
})
}
private fun setupAdapter(list: List<String>) {
initializeAdapter(list)
listAdapter?.updateItemsList(list)
binding.recyclerView.apply {
addItemDecoration(HeaderItemDecoration(context))
val itemDecorator = DividerItemDecoration(context, DividerItemDecoration.VERTICAL)
itemDecorator.setDrawable(ContextCompat.getDrawable(context, R.drawable.divider)!!)
addItemDecoration(itemDecorator)
adapter = listAdapter
}
}
private fun initializeAdapter(list: List<String>) {
listAdapter = ListAdapter(list.toMutableList())
}
override fun onResume() {
super.onResume()
viewModel.fetchItem() // noraml retrofit call
}
}
HeaderItemDecoration is used from this
CodePudding user response:
looks like a problem with multiple ItemDecoration
s, which are set every time new data is fetched. to be exact: multiple DividerItemDecoration
s, which adds small padding to the items (for dividing them). note methods name starts with add...
, so every time you are adding new, old stays there and every instance of this divider is adding some padding. if you would implement e.g. pull-to-refresh or auto-refresh in background every e.g. 10 secs then every refresh GUI method call (setupAdapter
) would add some space without leaving Activity
. currently you are fetching data only once, in onResume
, so every move-activity-to-foreground action will add one divider (when data will be fetched properly)
move this part of code to onCreate
for setting dividers only once, thats proper place for some additional styling by code
binding.recyclerView.apply {
addItemDecoration(HeaderItemDecoration(context))
val itemDecorator = DividerItemDecoration(context, DividerItemDecoration.VERTICAL)
itemDecorator.setDrawable(ContextCompat.getDrawable(context, R.drawable.divider)!!)
addItemDecoration(itemDecorator)
}
and inside your setupAdapter
method set only adapter to RecyclerView
, don't style it (multiple times)
private fun setupAdapter(list: List<String>) {
initializeAdapter(list)
listAdapter?.updateItemsList(list)
binding.recyclerView.adapter = listAdapter
}