CardView를 사용한 간단한 RecyclerView가 목록 항목으로 있습니다. Firebase Realtime 데이터베이스에서 검색된 목록의 각 항목은 noteList
에 저장됩니다. Firebase SDK는 onChildAdded, onChildChanged 및 기타 몇몇 콜백을 제공합니다. 이제 ArrayList를 사용할 리무버보기 용 어댑터를 설계했습니다. 실시간 데이터베이스의 데이터가 변경 될 때마다 콜백을 사용하여 noteList
에 항목을 추가하거나 제거합니다. onChildChanged
메서드는 특정 항목의 값이 변경 될 때마다 호출됩니다. 이 변경 내용을 noteList
에 반영하고 해당 어댑터에 알리고 싶습니다. 물론, 변경된 요소의 키와 일치하는 List의 각 요소를 순식간에 검색하고 업데이트 할 수 있습니다. 그러나 이것이 더 효율적이고 효과적인 방법으로 행해질 수 있습니까?Firebase Realtime Database로 안드로이드의 색인을 몰라도 ArrayList의 요소를 업데이트하는 방법은 무엇입니까?
class NoteListAdapter(var data: MutableList<Note>, val onItemClick: (Note) -> Unit) : RecyclerView.Adapter<NoteListAdapter.ViewHolder>() {
override fun onBindViewHolder(holder: ViewHolder?, position: Int) {
holder!!.bindNoteItem(data[position])
}
override fun getItemCount(): Int = data.size
override fun onCreateViewHolder(parent: ViewGroup?, viewType: Int): ViewHolder {
val v = LayoutInflater.from(parent?.context)
.inflate(R.layout.card_note, parent, false)
return ViewHolder(v, onItemClick)
}
class ViewHolder(v: View, val onItemClick: (Note) -> Unit): RecyclerView.ViewHolder(v) {
fun bindNoteItem(note: Note) {
...
}
}
}
HomeActivity.kt
class HomeActivity : AppCompatActivity() {
lateinit var mDb: DatabaseReference
val noteList: MutableList<Note> = ArrayList()
lateinit var adapter: NoteListAdapter
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_home)
addNoteFAB.setOnClickListener { addNote() }
mDb = FirebaseDatabase.getInstance().reference
adapter = NoteListAdapter(noteList, this::editNote)
noteListRecycler.layoutManager = LinearLayoutManager(this)
noteListRecycler.adapter = adapter
loadNotes()
}
fun addNote() {
val intent = Intent(this, EditNoteActivity::class.java)
intent.putExtra(EditNoteActivity.EXTRA_NOTE, Note())
startActivity(intent)
}
fun loadNotes() {
val path = "users/" + FirebaseAuth.getInstance().currentUser?.uid + "/notes"
mDb.child(path).addChildListener({
// onChildAdded
dataSnapshot, prevChildName ->
val note = dataSnapshot?.getValue(Note::class.java)!!
note.id = dataSnapshot.key
noteList += note
adapter.notifyDataSetChanged()
}, {
// onChildRemoved
dataSnapshot ->
noteList.remove(dataSnapshot?.getValue(Note::class.java))
adapter.notifyDataSetChanged()
}, {
// onChildChanged, TODO: update the change in elements value in noteList
dataSnapshot, s ->
})
}
fun editNote(note: Note) {
val i = Intent(this, EditNoteActivity::class.java)
i.putExtra(EditNoteActivity.EXTRA_NOTE, note)
startActivity(i)
}
}
PS : addChildListener은 확장 기능이다. 어떻게이의 인덱스를 모른 채 noteList
업데이트됩니다, (필자는 문서에서 아는까지) dataSnapshot
이후
은 우리에게 변경된 키와 값을 알 수 있습니다 (콜백의 이름을 코드에 주석을 확인) 변경된 요소? 아니면 실제로 색인을 얻는 방법이 있습니까?
감사합니다. 나는 Firebase와 함께 갈 것이다. Btw, 나는 목록의 항목을 (타임 스탬프에 따라) 끝에 추가 했으므로 onChildAdded의 코드를 추가했다고 생각했습니다. 수정 해줘서 고마워. –
글쎄, push() 메소드는 타임 스탬프를 기반으로 키를 생성하고 기본 쿼리 순서는 알파벳 순서이지만 가장 많이지지 된 게시물이나 뭔가를 얻고 싶다고 가정 해 봅시다. 'query.orderByChild ("votes")'라고 쓰면 아이들은 키에 관계없이 어디에서나 추가 될 수 있습니다. 미래의 고통에서 너를 구해줄 뿐이야. – SUPERCILEX