Reputation: 51
I have listView that use Realm to populate the items. The list view is a SwipeMenuListView by baoyongzhang. I have an issue that the listView is not being updated instantly. Rather when I exist the app and return back, the list will reflect the new changes.
I use AlertDialog to prompt the users to update selected parameters and those will be updated in the listView.
I use RealmHelper class to populate the listView ArrayAdapter
Below is the code from the helper class (RealmHelper):
fun readAll(): ArrayList<User> {
val finalList = ArrayList<User>()
val listOfUsers = mRealm.where(User::class.java).findAll()
finalList += listOfUsers
return finalList
}
This is the main activity class code
class Users: AppCompatActivity() {
private lateinit var realm: Realm
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.list_of_emirates)
realm = Realm.getDefaultInstance()
val helper = RealmHelper(realm)
val users = helper.readAll()
val mAdapter = MyAdapter(this, users)
listView.adapter = mAdapter
}
}
This is the main code where the actual update occurs:
listView.setOnMenuItemClickListener(SwipeMenuListView.OnMenuItemClickListener { position, menu, index ->
when (index) {
0 -> {
val alert = AlertDialog.Builder(this@Users).create()
alert.setTitle("Update Car Details")
val all = realm.where(User::class.java).findAll()
val selectedCar = all[position]!!
val name = EditText(this@Users)
name.hint = "Nickname"
val carNumber = EditText(this@Users)
carNumber.hint = "Car Number"
val duration = EditText(this@Users)
duration.hint = "Duration (hr)"
val code = EditText(this@Emirates)
code.hint = "Code"
name.setText(selectedCar.nickName)
carNumber.setText(selectedCar.plateNum)
duration.setText(selectedCar.duration)
code.setText(selectedCar.code)
val layout = LinearLayout(this)
layout.orientation = LinearLayout.VERTICAL
layout.addView(name)
layout.addView(carNumber)
layout.addView(duration)
layout.addView(code)
alert.setView(layout, 60, 0,60,0)
alert.setButton(AlertDialog.BUTTON_POSITIVE,"Update", object :DialogInterface.OnClickListener {
override fun onClick(dialog: DialogInterface?, which: Int) {
realm.beginTransaction()
selectedCar.code = code.text.toString()
selectedCar.plateNum = carNumber.text.toString()
selectedCar.duration = duration.text.toString()
selectedCar.nickName = name.text.toString()
emirates[position] = selectedCar
realm.commitTransaction()
mAdapter.notifyDataSetChanged()
Toast.makeText(this@Users, "${mAdapter.notifyDataSetChanged()} called", Toast.LENGTH_LONG).show()
}
})
alert.setButton(AlertDialog.BUTTON_NEGATIVE, "Cancel", object : DialogInterface.OnClickListener {
override fun onClick(dialog: DialogInterface?, which: Int) {
dialog?.dismiss()
}
})
alert.show()
}
1 -> {
realm.beginTransaction()
val all = realm.where(User::class.java).findAll()
val selectedUser = all[position]
selectedUser?.deleteFromRealm()
emirates.removeAt(position)
realm.commitTransaction()
mAdapter.notifyDataSetChanged()
}
else -> return@OnMenuItemClickListener false
}
true
})
I use Toast to test whether mAdapter.notifyDataSetChanged() is called and I verified that it is called, but seems that listView is not updating until the app is restarted.
Any idea why this behavior is?
Note: this is the link to the actual library of: https://github.com/baoyongzhang/SwipeMenuListView
Upvotes: 0
Views: 43
Reputation: 488
The problem with the method notifyDataSetChanged is that it detects when the source of the info changes but not when it is reasigned. I have faced a lot of problems with this method, so what i recomend is not use notifyDateSetChanged in this case but you can create a new adapter with the new source of information. try with this change.
alert.setButton(AlertDialog.BUTTON_POSITIVE,"Update", object :DialogInterface.OnClickListener {
override fun onClick(dialog: DialogInterface?, which: Int) {
realm.beginTransaction()
selectedCar.code = code.text.toString()
selectedCar.plateNum = carNumber.text.toString()
selectedCar.duration = duration.text.toString()
selectedCar.nickName = name.text.toString()
emirates[position] = selectedCar
realm.commitTransaction()
val realm = Realm.getDefaultInstance()
val helper = RealmHelper(realm)
val users = helper.readAll()
mAdapter = MyAdapter(this, users)
listView.adapter = mAdapter
Toast.makeText(this@Users, "${mAdapter.notifyDataSetChanged()} called", Toast.LENGTH_LONG).show()
}
})
Try this, i hope it works with you.
Upvotes: 1