Waks hs
Waks hs

Reputation: 11

RecyclerView duplicate list on notifyItemInserted()

i tried making a RecyclerView that displays a list of items, I used another activity to add the items, but when i tried to update the RecyclerView, it keeps duplicating the items and add the new item to the bottom of it. i tried notifyDataSetChanged() and still the same result.

IMAGE

this is the adapter code :

import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.recyclerview.widget.RecyclerView
import androidx.recyclerview.widget.StaggeredGridLayoutManager
import com.example.notap.databinding.NotesLayoutBinding

class NotesAdapter(private val notes : ArrayList<Notes>) : RecyclerView.Adapter<NotesAdapter.ViewHolder>() {
    class ViewHolder(binding : NotesLayoutBinding) : RecyclerView.ViewHolder(binding.root){
        val noteTitle = binding.tvNoteTitle
        val noteBody = binding.tvNoteBody
        val rvTagsInNotePreview = binding.rvTagsInNotePreview
        val llTagsDisplay = binding.llTAgsDisplay
    }

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
        return ViewHolder(NotesLayoutBinding.inflate(LayoutInflater.from(parent.context),parent,false))
    }

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        val item = notes[position]
        holder.noteTitle.text = item.title
        holder.noteBody.text = item.noteBody
        if (setTagsInNotePreview(holder,item.tags))
            holder.llTagsDisplay.visibility = View.VISIBLE
    }

    override fun getItemCount(): Int {
        return notes.size
    }

    private fun setTagsInNotePreview(holder : ViewHolder, tags : String) : Boolean{
        if (tags.isNotEmpty()){
            val tagsObjects = arrayListOf<TagsObject>()
            val tagsListString = tags.split(" || ")
            tagsListString.forEach {
                if (it.isNotEmpty())
                    tagsObjects.add(TagsObject(it))
            }
            val tagsAdapter = TagsAdapter(tagsObjects)
            holder.rvTagsInNotePreview.apply {
                adapter = tagsAdapter
                layoutManager = StaggeredGridLayoutManager(1, StaggeredGridLayoutManager.HORIZONTAL)
            }
            return true
        }
        return false
    }

}

class MainActivity : AppCompatActivity() {

private var IS_NOTES_RADIO_BUTTON_SELECTED = true
private var isNoteAdded = false
private lateinit var notesListFromDatabase : ArrayList<Notes>
private lateinit var notesAdapter : NotesAdapter
private lateinit var noteDao : NoteDao
companion object{
    private const val ADD_NEW_NOTE_REQUEST_CODE = 1
    private const val ADD_NEW_FILE_REQUEST_CODE = 2
}

private lateinit var binding: ActivityMainBinding

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    binding = ActivityMainBinding.inflate(layoutInflater)
   

    noteDao = (application as NoteApp).db.noteDao()
    notesListFromDatabase = getNotesFromDatabase(noteDao)

    notesAdapter = NotesAdapter(notesListFromDatabase)
    setNotesInRecyclerView(notesAdapter)

    
    binding.btnAddNote.setOnClickListener {
        val intent = Intent(this,AddNewNoteActivity::class.java)
        startActivityForResult(intent, ADD_NEW_NOTE_REQUEST_CODE)
    }



}



@SuppressLint("NotifyDataSetChanged")
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
    super.onActivityResult(requestCode, resultCode, data)
    if(resultCode == Activity.RESULT_OK){
        when(requestCode){
            ADD_NEW_NOTE_REQUEST_CODE -> {
                Toast.makeText(this, "Note Added To Database", Toast.LENGTH_SHORT).show()
                notesAdapter.notifyDataSetChanged()
                isNoteAdded = true

            }
            ADD_NEW_FILE_REQUEST_CODE -> {
                // to do
            }
        }
    }else if (resultCode == Activity.RESULT_CANCELED){
        when(requestCode){
            ADD_NEW_NOTE_REQUEST_CODE -> {
                // to do
            }
            ADD_NEW_FILE_REQUEST_CODE -> {
                // to do
            }
        }
    }
}






private fun setNotesInRecyclerView(notesAdapter : NotesAdapter){
    binding.rvNotesListView.apply {
        adapter = notesAdapter
        layoutManager = LinearLayoutManager(this.context)
    }
}

private fun getNotesFromDatabase(notesDao: NoteDao) : ArrayList<Notes> {
    val notesList = arrayListOf<Notes>()
    lifecycleScope.launch {
        notesDao.fetchAllNotes().collect{ListOfNotes ->
            ListOfNotes.forEach {NoteEntity ->
                notesList.add(Notes(title = NoteEntity.title, tags = NoteEntity.tags, noteBody = NoteEntity.noteBody))
            }

        }
    }
    return notesList
}

}

Upvotes: 1

Views: 198

Answers (1)

TANIMUL ISLAM
TANIMUL ISLAM

Reputation: 359

Before you notify and value add you should clear previous arraylist by list.clear().

 private fun showNotes() {
        noteViewModel.showAllNotes.observe(
            this
        ) {
            noteList.clear()
            noteList.addAll(it)
            noteAdapter.notifyDataSetChanged()
        }
    }

Upvotes: 1

Related Questions