I have implemented RecyclerView with changing backround when clicked on an item. RecyclerView contains only TextView. Sometimes when I click on an item the recyclerview scroll little bit. Strange is, that recyclerview behave like this, sometimes is everything OK. I am not sure why the RV is acting like this.
Direct link to gif - Action on RecyclerView
This is my Adapter
private var selectedItemPosition: Int = 0
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): PolozkaViewHolder {
val binding = PolozkyItemBinding.inflate(LayoutInflater.from(parent.context), parent, false)
return PolozkaViewHolder(binding)
}
override fun onBindViewHolder(holder: PolozkaViewHolder, position: Int) {
val currentItem = getItem(position)
holder.bind(currentItem)
if (selectedItemPosition == position){
holder.itemView.setBackgroundColor(Color.parseColor("#DA745A"))
} else
{
holder.itemView.setBackgroundColor(Color.TRANSPARENT)
}
}
inner class PolozkaViewHolder(private val binding: PolozkyItemBinding): RecyclerView.ViewHolder(binding.root){
init {
binding.root.setOnClickListener{
val position = bindingAdapterPosition
if (position != RecyclerView.NO_POSITION){
val item = getItem(position)
if (item != null){
listener.onItemClick(item, position)
//listener.onItemClickListener(item, position)
}
}
notifyItemChanged(selectedItemPosition)
selectedItemPosition = absoluteAdapterPosition
notifyItemChanged(selectedItemPosition)
}
binding.root.setOnLongClickListener{
val positionLong = bindingAdapterPosition
if (positionLong != RecyclerView.NO_POSITION){
val itemLong = getItem(positionLong)
if(itemLong != null){
listener.onLongClick(itemLong)
}
}
true
}
}
fun bind(polozkaPolozka: Polozka){
binding.apply {
tvStar.text = if (polozkaPolozka.mnoz_vyd == 0.toFloat()){
""
}else (if (polozkaPolozka.mnoz_vyd != polozkaPolozka.mnoz_obj){
"-"
} else if (polozkaPolozka.mnoz_vyd == polozkaPolozka.mnoz_obj){
"*"
} else{
""
})
tvKDE.text = polozkaPolozka.znacky
tvREG.text = polozkaPolozka.reg
tvVB.text = polozkaPolozka.veb.toString()
tvMN.text = polozkaPolozka.mnoz_obj.toString()
tvMNV.text = polozkaPolozka.mnoz_vyd.toString()
tvDATSPOTR.text = polozkaPolozka.datspo
tvSARZE.text = polozkaPolozka.sarze
}
}
}
interface OnItemClickListener{
fun onItemClick(polozkaDoklad: Polozka, position: Int)
fun onLongClick(polozkaDoklad: Polozka)
}
class DiffCallback: DiffUtil.ItemCallback<Polozka>(){
override fun areItemsTheSame(oldItem: Polozka, newItem: Polozka) =
oldItem.pvp06pk == newItem.pvp06pk
override fun areContentsTheSame(oldItem: Polozka, newItem: Polozka) =
oldItem == newItem
}
}
And this is my simple Activity
class PolozkaActivity: AppCompatActivity(), PolozkaAdapter.OnItemClickListener{
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val binding = ActivityPolozkaBinding.inflate(layoutInflater)
}
override fun onItemClick(polozkaDoklad: Polozka, position: Int) {
val resultReg = polozkaViewModel.getInfoByREG(polozkaDoklad.reg.toString())
textViewStatus.text = "$resultReg"
positionItem = position
}
override fun onLongClick(polozkaDoklad: Polozka) {
val intent = Intent(this, NewActivity::class.java)
startActivity(intent)
}
}
EDIT: Change of url of gif.
ViewHolder.absoluteAdapterPosition
returns the position of the root view in pixels relative to the RecyclerView. It has nothing to do with the index of the associated item in the list.
I think the simplest way to fix what you have is to add a var currentIndex: Int
property to your ViewHolder, and set that position in onBindViewHolder
. Then change
notifyItemChanged(selectedItemPosition)
selectedItemPosition = absoluteAdapterPosition
notifyItemChanged(selectedItemPosition)
to
notifyItemChanged(selectedItemPosition)
selectedItemPosition = currentIndex
notifyItemChanged(selectedItemPosition)
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.