Adding a hideable headerview to recyclerview - android

I want to add a headerview that hides when user scrolls to down and shows again when user scrolls to up.
Example: https://imgur.com/a/tTq70B0
As you can see in the link "You are writing as..." pharase is showing only when user scrolls to top. Is there something like that in Android sdk?
How can i achive the same thing?

Obtaining the scroll event is just the first step to achieving this. Animations is required to achieve the effect. I recreated a simple version of the gif example you posted.
Layout for the main activity, activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:animateLayoutChanges="true"> <!-- Note the last line-->
<TextView
android:id="#+id/textview_hello"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_margin="8dp"
android:text="Hello Stack Overflow!"/>
<androidx.recyclerview.widget.RecyclerView
android:id="#+id/recyclerview_main"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
</LinearLayout>
Below is the code for the main activity where we populate the RecyclerView and use the addOnScrollListener to provide animations to the TextView. Do note the commented out lines these will provide a default fade-out or fade-in animation due to the noted line in the xml layout above. The method slideAnimation() is an example of creating a custom animation. This link proved useful for creating the animations.
class MainActivity : AppCompatActivity() {
private lateinit var viewAdapter: RecyclerView.Adapter<*>
private lateinit var viewManager: LinearLayoutManager
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
// Some data for the RecyclerView
val data: List<String> = (1..100).toList().map { it.toString() }
viewManager = LinearLayoutManager(this)
viewAdapter = TextAdapter(data)
findViewById<RecyclerView>(R.id.recyclerview_main).apply {
setHasFixedSize(true)
layoutManager = viewManager
adapter = viewAdapter
addOnScrollListener(
object : RecyclerView.OnScrollListener() {
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
super.onScrolled(recyclerView, dx, dy)
val pastVisibleItems = viewManager.findFirstCompletelyVisibleItemPosition()
if (pastVisibleItems == 0) {
slideAnimation(0f, 1f, View.VISIBLE)
//textview_hello.visibility = View.VISIBLE
} else if (textview_hello.visibility != View.GONE) {
slideAnimation(-150f, 0f, View.GONE)
//textview_hello.visibility = View.GONE
}
}
}
)
}
... // SlideAnimation function
}
}
The slideAnimation function
private fun slideAnimation(translationY: Float, alpha: Float, viewVisibility: Int) {
textview_hello.visibility = View.VISIBLE
textview_hello.clearAnimation()
textview_hello
.animate()
.translationY(translationY)
.alpha(alpha)
.setListener(object : AnimatorListenerAdapter() {
override fun onAnimationEnd(animation: Animator) {
super.onAnimationEnd(animation)
textview_hello.clearAnimation()
textview_hello.visibility = viewVisibility
}
})
.duration = 500
}
The adapter for the RecycleView:
class TextAdapter(private val textList: List<String>) :
RecyclerView.Adapter<TextAdapter.TextViewHolder>() {
class TextViewHolder(val textView: TextView) : RecyclerView.ViewHolder(textView)
override fun onCreateViewHolder(
parent: ViewGroup,
viewType: Int
): TextViewHolder {
val textView = LayoutInflater.from(parent.context)
.inflate(R.layout.item_text_view, parent, false) as TextView
return TextViewHolder(textView)
}
override fun onBindViewHolder(holder: TextViewHolder, position: Int) {
holder.textView.text = textList[position]
}
override fun getItemCount() = textList.size
}
Item to display in the RecyclerView, item_text_view.xml
<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent" android:layout_height="wrap_content"
android:layout_margin="8dp"
android:padding="16dp"
android:textAlignment="center"
android:background="#android:color/darker_gray">
</TextView>

Related

Android: RelativeLayout measures child width incorrectly

What I want to do:
My idea is simple:
I have RecyclerView in RelativeLayout
When data loaded I set first item's text to TextView for pinned message
On scroll I take first visible item and set this item's text to header (TextView)
So I have:
RelativeLayout + RecyclerView + TextView for pinned message + TextView for header
I update header on scroll, it looks like sticky header for list.
It is my layout:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<TextView
android:id="#+id/pin"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#ebebeb"
android:gravity="center"
android:padding="24dp"/>
<androidx.recyclerview.widget.RecyclerView
android:id="#+id/list"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_below="#+id/pin"/>
<androidx.appcompat.widget.AppCompatTextView
android:id="#+id/header"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignTop="#id/list"
android:layout_alignEnd="#id/list"
android:background="#33ff0000"
android:gravity="center"
android:padding="24dp"/>
</RelativeLayout>
And it is my Activity:
class CustomAdapter() :
RecyclerView.Adapter<CustomAdapter.ViewHolder>() {
var data: List<UUID> = listOf()
class ViewHolder(view: View) : RecyclerView.ViewHolder(view) {
val textView: TextView
init {
textView = view.findViewById(R.id.text)
}
}
override fun onCreateViewHolder(viewGroup: ViewGroup, viewType: Int): ViewHolder {
val view = LayoutInflater.from(viewGroup.context)
.inflate(R.layout.list_item, viewGroup, false)
return ViewHolder(view)
}
override fun onBindViewHolder(viewHolder: ViewHolder, position: Int) {
viewHolder.textView.text = data[position].toString()
}
override fun getItemCount() = data.size
}
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val adapter = CustomAdapter()
val header = findViewById<TextView>(R.id.header)
findViewById<RecyclerView>(R.id.list).apply {
this.adapter = adapter
layoutManager = LinearLayoutManager(this#MainActivity, LinearLayoutManager.VERTICAL, false)
addOnScrollListener(object : RecyclerView.OnScrollListener() {
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
val position = recyclerView.topChildPosition() ?: return
if (position >= 0) {
header.text = adapter.data[position].toString().substring(0, 10)
Log.w("MainActivity", header.text.toString())
} else {
header.text = null
}
}
})
}
/**
* SIMULATE DATA LOADING
*/
Handler(Looper.getMainLooper()).postDelayed({
adapter.data = List(100) {
UUID.randomUUID()
}
findViewById<TextView>(R.id.pin).text = adapter.data[0].toString()
adapter.notifyDataSetChanged()
}, 1000L)
}
private fun RecyclerView.topChildPosition(): Int? {
layoutManager.let { layoutManager ->
if (layoutManager != null && layoutManager is LinearLayoutManager) {
return if (!layoutManager.reverseLayout) layoutManager.findFirstVisibleItemPosition()
else layoutManager.findLastVisibleItemPosition()
} else {
val topChild: View = getChildAt(0) ?: return null
return getChildAdapterPosition(topChild)
}
}
}
}
And what I have:
RelativeLayout measured views, header has text = null, so header's width = padding only
Data loaded (see "SIMULATE DATA LOADING" in the activity code), I call notifyDataSetChanged and I set text to header. Header (TextView) calls requestLayout() on set text, but RelativeLayout doesn't measured new width (actually, RelativeLayout calls header's onMeasure with widthMode == MeasureSpec.EXACTLY and pass old width)
When I scroll RecyclerView header remeasured successfully.
I can reproduce it on Android 26-33
What I can do with this.
I can change layout:
from this:
<androidx.appcompat.widget.AppCompatTextView
android:id="#+id/header"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignTop="#id/list"
android:layout_alignEnd="#id/list"
android:background="#33ff0000"
android:gravity="center"
android:padding="24dp"/>
to this:
<FrameLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_alignTop="#id/list"
android:layout_alignEnd="#id/list">
<androidx.appcompat.widget.AppCompatTextView
android:id="#+id/header"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="end"
android:background="#33ff0000"
android:gravity="center"
android:padding="24dp"/>
</FrameLayout>
But actually I can't, because really my TextView in custom view extends from TextView and it is part of library. I don't know how it will be used in layouts.
I can call requestLayout() after data loading like this:
adapter.notifyDataSetChanged()
header.doOnNextLayout { header.post { header.requestLayout() } }
But it is ugly.
So, finally my questions:
Do you know how to fix it without layout changing?
Do you know bug or some documented RelativeLayout behavior
Thanks for any help!

Data not displayed on recycler view

I have a recycler view issue where the data is not being displayed. onCreateViewHolder and onBindViewHolder are not being called. When I call notifyDataSetChanged(), notifyChanged() is called but mObservers is empty, so it won't update my list.
public void notifyChanged() {
for (int i = mObservers.size() - 1; i >= 0; i--) {
mObservers.get(i).onChanged();
}
}
here's my adapter code:
class ReleasesAdapter : RecyclerView.Adapter<ReleasesAdapter.ReleasesViewHolder>() {
private val data = mutableListOf<Album>(Album())
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ReleasesViewHolder {
return ReleasesViewHolder(
LayoutInflater.from(parent.context)
.inflate(R.layout.song_item, parent, false)
)
}
override fun onBindViewHolder(holder: ReleasesViewHolder, position: Int) {
holder.bindView(data[position])
}
override fun getItemCount(): Int {
return data.size
}
fun setItems(items: List<Album>) {
data.addAll(items)
notifyDataSetChanged()
}
inner class ReleasesViewHolder(
override val containerView: View
) : RecyclerView.ViewHolder(containerView), LayoutContainer {
fun bindView(item: Album) {
containerView.nameTv.text = item.name
}
}
}
And here's my activity code:
#AndroidEntryPoint
class MainActivity : AppCompatActivity(), Contract.View {
#Inject
lateinit var presenter: Contract.Presenter
private val releasesAdapter = ReleasesAdapter()
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
resultsRv.run {
adapter = releasesAdapter
layoutManager = LinearLayoutManager(this#MainActivity)
}
presenter.loadNewReleases()
}
override fun showReleases(data: List<Album>) {
releasesAdapter.setItems(data)
}
override fun showErrorMessage(message: String) {
}
}
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.appcompat.widget.LinearLayoutCompat xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".presentation.MainActivity">
<com.google.android.material.appbar.MaterialToolbar
android:id="#+id/toolbar"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"/>
<androidx.recyclerview.widget.RecyclerView
android:id="#+id/resultsRv"
android:layout_width="match_parent"
android:layout_height="wrap_content"
tools:listitem="#layout/song_item" />
</androidx.appcompat.widget.LinearLayoutCompat>
song_item.xml
<?xml version="1.0" encoding="utf-8"?>
<com.google.android.material.textview.MaterialTextView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/nameTv"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="#dimen/song_item_margin"
android:textColor="#color/black" />
Please send help :(
Edit: Added Xml code
I believe you are using the scope functions wrong especially run in this case. Use run() function if you need to compute some value or want to limit the scope of multiple local variables.
So while your other code seems okay, I believe your Adapter and LayoutManager is not being assigned. I would suggest you replace the run with apply and try again.
resultsRv.apply {
adapter = releasesAdapter
layoutManager = LinearLayoutManager(this#MainActivity)
}

All child recyclerView's items changed when one child recyclerview's item is changed while click the item

I am working with nested recyclerView. According to business logic, first I have to call an API that fetched the list of item that is shown in the Parent recycler view. After that, if a user clicks any of the items of the parent recycler view, another API is called which fetches a list of sub-items, and I have to show the item list in the inner recycler view of that clicked-positioned parent recycler view.
I successfully implemented showing items in the parent recycler view and sub-items in the clicked-position nested recycler view.
But the problem I am facing is when I clicked any specific item of the parent recycler view, all the other nested recycler view's item get changed with the newly populated sub-items value.
How can I solve this issue?. Here is the sample code
main_item.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.appcompat.widget.LinearLayoutCompat 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="wrap_content"
android:orientation="vertical">
<com.google.android.material.card.MaterialCardView
style="#style/CardViewStyle"
android:id="#+id/chapter_layout"
android:layout_width="match_parent">
<com.google.android.material.textview.MaterialTextView
android:id="#+id/chapter_name_text_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
<com.google.android.material.textview.MaterialTextView
android:id="#+id/header_text_view"
android:layout_width="0dp"
android:layout_height="wrap_content"/>
</com.google.android.material.card.MaterialCardView>
<androidx.recyclerview.widget.RecyclerView
android:id="#+id/chapter_topic_recycler_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:visibility="gone"
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
tools:itemCount="3"
tools:listitem="#layout/item_main" />
</androidx.appcompat.widget.LinearLayoutCompat>
MainItemViewHolder.kt
class MainItemViewHolder(val view: View) : RecyclerView.ViewHolder(view) {
fun bind(item: SpecificChapter, onClick: (SpecificChapter, Int) -> Unit) {
with(view) {
chapter_name_text_view.text = "Chapter "+ item.no
header_text_view.text = item.name
chapter_layout.setOnClickListener { onClick(item, bindingAdapterPosition) }
}
}
}
MainItemAdapter.kt
class MainItemAdapter(
val onClick: (SpecificChapter, Int) -> Unit
) : ListAdapter<SpecificChapter, MainItemViewHolder>(DIFF_CALLBACK) {
companion object {
private val DIFF_CALLBACK = object : DiffUtil.ItemCallback<SpecificChapter>() {
override fun areItemsTheSame(old: SpecificChapter, aNew: SpecificChapter) = (old.id == aNew.id)
override fun areContentsTheSame(old: SpecificChapter, aNew: SpecificChapter) = (old == aNew)
}
}
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): MainItemViewHolder {
return MainItemViewHolder(parent.inflate(R.layout.main_item))
}
override fun onBindViewHolder(holder: MainItemViewHolder, position: Int) {
holder.bind(getItem(position)!!, onClick)
}
}
sub_item.xml
<?xml version="1.0" encoding="utf-8"?>
<com.google.android.material.card.MaterialCardView
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="wrap_content">
<com.google.android.material.textview.MaterialTextView
android:id="#+id/chapter_topic_text_view"
android:layout_width="0dp"
android:layout_height="wrap_content" />
</com.google.android.material.card.MaterialCardView>
SubItemViewHolder.kt
class SubItemViewHolder(val view: View) : RecyclerView.ViewHolder(view) {
fun bind(item: SpecificTopic, onClick: (SpecificTopic) -> Unit) {
with(view) {
chapter_topic_text_view.text = item.name
chapter_topic_layout.setOnClickListener { onClick(item) }
}
}
}
SubItemAdapter.kt
class SubItemAdapter(
val onClick: (SpecificTopic) -> Unit
) : ListAdapter<SpecificTopic, SubItemViewHolder>(DIFF_CALLBACK) {
companion object {
private val DIFF_CALLBACK = object : DiffUtil.ItemCallback<SpecificTopic>() {
override fun areItemsTheSame(old: SpecificTopic, aNew: SpecificTopic) = (old.id == aNew.id)
override fun areContentsTheSame(old: SpecificTopic, aNew: SpecificTopic) = (old == aNew)
}
}
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): SubItemViewHolder {
return SubItemViewHolder(parent.inflate(R.layout.sub_item))
}
override fun onBindViewHolder(holder: SpecificTopicViewHolder, position: Int) {
holder.bind(getItem(position)!!, onClick)
}
}
activity_chapter.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.appcompat.widget.LinearLayoutCompat
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<androidx.recyclerview.widget.RecyclerView
android:id="#+id/chapter_recycler_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
tools:listitem="#layout/main_item"/>
</androidx.appcompat.widget.LinearLayoutCompat>
ChapterActivity.kt
class ChapterActivity : BaseActivity<ChapterViewModel>() {
var chapterPosition = 0
private val mainItemAdapter: MainItemAdapter by lazy {
MainItemAdapter { specificChapter, position ->
// sub item Api call when clicked specific item. response is viewmodel.allTopics
chapterPosition = position
specificChapter.id?.let { viewModel.getChapterWiseTopics(it) }
}
}
private val subItemAdapter: SubItemAdapter by lazy {
SubItemAdapter {
}
}
override fun onResume() {
super.onResume()
// Main item Api call. response is viewmodel.allChapters
viewModel.getChapters("subject_code")
}
override fun observeLiveData() {
// showing Main item in parent recyclerView
observe(viewModel.allChapters) {
val chapterList = ArrayList<SpecificChapter>()
chapterList.add(SpecificChapter(...))
chapter_recycler_view.adapter = mainItemAdapter
mainItemAdapter.submitList(chapterList)
chapter_recycler_view.setItemViewCacheSize(chapterList.size)
}
// showing sub item in nested recyclerView
observe(viewModel.allTopics) {
val topicList = ArrayList<SpecificTopic>()
topicList.add(SpecificTopic(...))
with((chapter_recycler_view.findViewHolderForAdapterPosition(chapterPosition) as MainItemViewHolder).itemView) {
this.chapter_topic_recycler_view.adapter = subItemAdapter
subItemAdapter.submitList(topicList)
}
}
}
}

how to add views in onBindViewHolder?

I'm using RecyclerView to display a list of items.
Dependent on the specific item, i want to show additional views in the cell.
I know the viewholder should be static, but how do i achieve a cell design that depends on the properties of the item?
Minified example, which gives me weird results:
class CustomAdapter internal constructor() :
RecyclerView.Adapter<CustomAdapter.ViewHolder>() {
private var dataSet = emptyList()
inner class ViewHolder(v: View) : RecyclerView.ViewHolder(v) {
val title: TextView
val linearLayout: LinearLayout
init {
title = v.findViewById(R.id.textView)
linearLayout = v.findViewById(R.id.linearLayout)
}
}
override fun onCreateViewHolder(viewGroup: ViewGroup, viewType: Int): ViewHolder {
val v = LayoutInflater.from(viewGroup.context)
.inflate(R.layout.cardview, viewGroup, false)
return ViewHolder(v)
}
override fun onBindViewHolder(viewHolder: ViewHolder, position: Int) {
viewHolder.title.text = dataSet[position].name
for (i in 0 until 5) {
viewHolder.linearLayout.addView(ImageView())
}
}
internal fun setItems(items: List<T>) {
this.dataSet = items
notifyDataSetChanged()
}
}
<androidx.cardview.widget.CardView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center_vertical">
<TextView
android:id="#+id/textView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_marginStart="22dp"
android:layout_marginEnd="12dp"
android:text="Title"
android:textSize="18sp"
android:textStyle="bold" />
<LinearLayout
android:id="#+id/linearLayout"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal">
</LinearLayout>
</androidx.cardview.widget.CardView>
You can't add an ImageView directly as shown in your example. Try this:
override fun onBindViewHolder(viewHolder: ViewHolder, position: Int) {
viewHolder.title.text = dataSet[position].name
for (i in 0 until 5) {
val holder = viewHolder
val context = holder.itemView.context
val imagebyCode = ImageView(context)
imagebyCode.setImageResource(R.drawable.exampleImage)
val params : LinearLayout.LayoutParams = LinearLayout.LayoutParams(
LinearLayout.LayoutParams.MATCH_PARENT,LinearLayout.LayoutParams.WRAP_CONTENT);
imagebyCode.layoutParams = params
val myLayout : LinearLayout = holder.itemView.findViewById(R.id.linearLayout)
myLayout.addView(imagebyCode)
}
}
You can add views to the xml for the recycler view row and keep the visibility hidden.
In onBindViewHolder you can check the condition and make the View visible.
override fun onBindViewHolder(viewHolder: ViewHolder, position: Int) {
viewHolder.title.text = dataSet[position].name
for (i in 0 until 5) {
viewHolder.linearLayout.view.visibility = View.VISIBLE //Set visibility here
}
}

Kotlin / Android Custom RecyclerView issue

I was trying to make a custom RecyclerView with Adapter which takes a HashMap as parameter, I succeeded but now only 1 item is showing in recyclerView list and I have no idea why.
Here my code snippet:
Custom RecyclerAdapter:
class ProductsRecyclerAdapter(private val dataSet: HashMap<Int, ProductEntry>) : RecyclerView.Adapter<ProductsRecyclerAdapter.ViewHolder>() {
class ViewHolder(val linearLay: LinearLayout) : RecyclerView.ViewHolder(linearLay)
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) : ProductsRecyclerAdapter.ViewHolder {
val linearLay = LayoutInflater.from(parent.context).inflate(R.layout.test_text_view, parent, false) as LinearLayout
return ViewHolder(linearLay)
}
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
holder.linearLay.textView.text = dataSet[position]?.pName
holder.linearLay.textView2.text = dataSet[position]?.pExpiry
}
override fun getItemCount(): Int {
return dataSet.size
}
}
Initialization:
// Setup RecyclerView
val prod1 = ProductEntry("Milk", "04/06/1996")
val prod2 = ProductEntry("Bread", "04/01/2012")
val testArray : HashMap<Int, ProductEntry> = hashMapOf(1 to prod1, 2 to prod2)
viewManager = LinearLayoutManager(this)
viewAdapter = ProductsRecyclerAdapter(testArray)
recyclerView = findViewById<RecyclerView>(R.id.productsRecyclerView).apply {
setHasFixedSize(true)
layoutManager = viewManager
adapter = viewAdapter
}
And finally, custom XML for row:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="#+id/linearLay"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:id="#+id/textView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="TextView" />
<TextView
android:id="#+id/textView2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="40dp"
android:layout_weight="1"
android:text="TextView" />
Despite everything seems to be OK, I get only 1 row showing "milk".
Thanks for all help!
position in override fun onBindViewHolder(holder: ViewHolder, position: Int) starts at index 0.
So in your case, it will be [0, 1] and your map keys are [1, 2]. Only key "1" will be displayed correctly.
try:
val testArray : HashMap<Int, ProductEntry> = hashMapOf(0 to prod1, 1 to prod2)
But no need to use a map here! Just use a simple list of ProductEntry.

Categories

Resources