Firstly, I'm a beginner in Swift and iOS development. This is my first app, which I am working on after learning the basics of Swift and iOS.
Reloading the data in the tableview
after adding new data is working properly using Realm. Unfortunately, after an update or deletion, reloading the data in the tableview
does not work. Showing the previous data in table view after an update or deletion. Please help.
How the code works or app works:
didSelectRowAt
it jumps to the DisplayDataViewController, just to view the title and notes in the Data. This page contains EDIT and DELETE button.tableview
).And the thing is, CRUD is working properly with the database.
Data
import Foundation
import RealmSwift
@objcMembers class Data: Object {
dynamic var title = ""
dynamic var notes = ""
}
HomeViewController:
import UIKit
import RealmSwift
class HomeViewController: UIViewController, RefreshDelegate {
@IBOutlet var tableViewField: UITableView!
let realm = try! Realm()
var taskView: Results<Data>?
override func viewDidLoad() {
super.viewDidLoad()
tableViewField.delegate = self
tableViewField.dataSource = self
loadData()
}
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
let addVc = segue.destination as! AddNotesViewController
addVc.flagAdd = 0
addVc.delegate = self
}
func loadData() {
taskView = realm.objects(Data.self)
tableViewField.reloadData()
}
}
extension HomeViewController: UITableViewDataSource {
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return taskView?.count ?? 1
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "Cell", for: indexPath)
cell.textLabel?.text = taskView?[indexPath.row].title ?? "Empty List"
return cell
}
}
extension HomeViewController: UITableViewDelegate {
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
tableView.deselectRow(at: indexPath, animated: true)
let displayVc = storyboard?.instantiateViewController(identifier: "displayData") as! DisplayDataViewController
displayVc.index1 = indexPath.row
displayVc.viewDetails = taskView![indexPath.row]
navigationController?.pushViewController(displayVc, animated: true)
}
}
AddNotesViewController:
import UIKit
import RealmSwift
protocol RefreshDelegate {
func loadData()
}
class AddNotesViewController: UIViewController {
@IBOutlet var titleTextField: UITextField!
@IBOutlet var notesTextView: UITextView!
let realm = try! Realm()
var delegate: RefreshDelegate?
var EditView : Data?
var index2: Int?
var flagAdd: Int?
var flagEdit: Int?
override func viewDidLoad() {
super.viewDidLoad()
}
override func viewWillAppear(_ animated: Bool) {
if flagEdit == 1 {
navigationItem.title = "Edit Page"
if let myEdit = self.EditView {
titleTextField.text = myEdit.title
notesTextView.text = myEdit.notes
}
}
}
@IBAction func doneButtonPressed(_ sender: UIBarButtonItem) {
let note = notesTextView.text
if titleTextField.text == ""
{
titleTextField.placeholder = "Write Something.."
}
else if note == "" || note == "Write notes here...." || note == "Sorry! Write Something here."
{
notesTextView.text = "Sorry! Write Something here."
}
else if flagAdd == 0
{
let titleText = titleTextField.text
let notesField = notesTextView.text
let dataRealm = Data()
dataRealm.title = titleText!
dataRealm.notes = notesField!
try! realm.write{
realm.add(dataRealm)
}
delegate?.loadData()
titleTextField.endEditing(true)
notesTextView.endEditing(true)
navigationController?.popViewController(animated: true)
}
else
{
let newData = realm.objects(Data.self)[index2!]
try! realm.write {
newData.title = titleTextField.text!
newData.notes = notesTextView.text
}
delegate?.loadData()
titleTextField.endEditing(true)
notesTextView.endEditing(true)
navigationController?.popToRootViewController(animated: true)
}
}
}
The same add page is used as an edit page. That's why I used the flagAdd/flagEdit variable.
DisplayDataViewController:
import UIKit
import RealmSwift
class DisplayDataViewController: UIViewController {
@IBOutlet var DisplayTitleField: UITextField!
@IBOutlet var DisplayNotesField: UITextView!
let realm = try! Realm()
var index1 : Int?
var viewDetails : Data?
var delegate : RefreshDelegate?
override func viewDidLoad() {
super.viewDidLoad()
}
override func viewWillAppear(_ animated: Bool) {
if let myView = self.viewDetails {
DisplayTitleField.text = myView.title
DisplayNotesField.text = myView.notes
}
}
@IBAction func EditButtonPressed(_ sender: UIButton) {
let editVc = storyboard?.instantiateViewController(identifier: "goToAdd") as! AddNotesViewController
editVc.index2 = index1
editVc.EditView = viewDetails
editVc.flagEdit = 1
navigationController?.pushViewController(editVc, animated: true)
}
@IBAction func deleteButtonPressed(_ sender: UIBarButtonItem) {
try! realm.write {
realm.delete(viewDetails!)
}
delegate?.loadData()
navigationController?.popViewController(animated: true)
}
}
HomeViewController,
What I did is just add one line of code in didSelectRowAt
. Here is the updated didSelectRowAt
:
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
tableView.deselectRow(at: indexPath, animated: true)
let dv = (storyboard?.instantiateViewController(identifier: "displayData"))! as! DisplayDataViewController
dv.index1 = indexPath.row
dv.viewDetails = taskView![indexPath.row]
dv.delegate = self // Newly added code.It solves a problem for deletion.
navigationController?.pushViewController(dv, animated: true)
}
DisplayDataViewController , Here also I added ev.delegate = delegate
. Here is the updated code for EditButtonPressed
@IBAction func EditButtonPressed(_ sender: UIButton) {
let ev = storyboard?.instantiateViewController(identifier: "goToAdd") as! AddNotesViewController
ev.EditView = viewDetails
ev.index2 = index1!
ev.flagEdit = 1
ev.delegate = delegate // Newly added code.It solves a problem for updating.
navigationController?.pushViewController(ev, animated: true)
}
Finally it's working.