2016-11-23 57 views
0

我在swift 3.0的項目中工作,我有兩個UITableViews,我從一個名爲UserIncome的核心數據模塊實體設置數據。由於這些數據將填充到單個UIViewController中的兩個UItableViews中(基於ViewWillAppear委託方法中的字符串值進行過濾),一旦在一個UITableView中刪除了一行,其數組也會自動被其他tableView的對象更新。但是,一旦我點擊後退按鈕並回到相同的UIViewController似乎都很好。我的要求是更新UItableView,一旦行被刪除,作爲核心數據模塊。代碼如下。我在這裏錯過了什麼?一旦行被刪除,UITableView不會更新

import UIKit 
import CoreData 

class MyIncomesViewController: UIViewController, UITableViewDelegate, UITableViewDataSource { 
    @IBOutlet weak var recurringIncomeTableView: UITableView! 
    @IBOutlet weak var otherIncomeTableView: UITableView! 
    //var myIncomeType : String? 

    var stores = [UserIncome]() 
    var other = [UserIncome]() 
    let context = (UIApplication.shared.delegate as! AppDelegate).persistentContainer.viewContext 

    var rowTbl : Int! 
    var rowTbl2 : Int! 



    override func viewDidLoad() { 
     super.viewDidLoad() 

} 
    override func viewDidAppear(_ animated: Bool) { 

     stores.removeAll() 
     other.removeAll() 

     let request = NSFetchRequest <NSFetchRequestResult> (entityName: "UserIncome") 
     request.returnsObjectsAsFaults = false 



     do { 

      let results = try context.fetch(request) as! [UserIncome] 

      print("Results from the fetch request are : ", request) 

      // check data existance 
      if results.count>0 { 
       print("results are :", results.count) 

       for resultGot in results { 

        //lets check if the data is available and whether the loop is working by printing out the "name" 
        if let incName = resultGot.incomeName { 
         print("expence name is :", incName) 

         //set the value to the global variable as to filter the arrays 
         let myIncomeType = resultGot.incomeType 

         if myIncomeType == "Recurring Income"{ 

          stores += [resultGot] 
          print("my recurring income array is : \(stores)") 
         }else if myIncomeType == "Other Income"{ 

          other += [resultGot] 
          print("my other income array is : \(other)") 
         } 
        } 
       } 
       self.recurringIncomeTableView.reloadData() 
       self.otherIncomeTableView.reloadData() 

      } 

     }catch{ 


      print("No Data to load") 
     } 


    } 

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { 

     if tableView.tag == 1 { 
     let cell: RecuringIncomeTableViewCell = tableView.dequeueReusableCell(withIdentifier: "recurringIncomeCell") as! RecuringIncomeTableViewCell 

     let store = stores [indexPath.row] 

     cell.incomeNameLabel.text = store.incomeName 
     cell.amountLabel.text = store.amount 


     return cell 

     } 
     else { 
      let cell: OtherIncomeTableViewCell = tableView.dequeueReusableCell(withIdentifier: "otherIncomeCell") as! OtherIncomeTableViewCell 

      let otherIncomes = other [indexPath.row] 

      cell.incomeNameLabel.text = otherIncomes.incomeName 
      cell.amountLabel.text = otherIncomes.amount 


      return cell 

     } 
    } 




    func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) { 
     //performSegue(withIdentifier: "editStore", sender: nil) 
     if tableView.tag == 1 { 
      rowTbl = tableView.indexPathForSelectedRow?.row 
      print("current row in tbl 1 is : ",rowTbl) 

     }else { 

      rowTbl2 = tableView.indexPathForSelectedRow?.row 
      print("current row in tbl 2 is : ",rowTbl2) 
     } 

    } 
    override func prepare(for segue: UIStoryboardSegue, sender: Any?) { 
     if segue.identifier == "editRecurringIncome"{ 

      let v = segue.destination as! AddIncomeViewController 
      let indexPath = self.recurringIncomeTableView.indexPathForSelectedRow 
      let row = indexPath?.row 
      v.store = stores[row!] 

     }else if segue.identifier == "editOtherIncome" { 
      let t = segue.destination as! AddIncomeViewController 
      let indexPath = self.otherIncomeTableView.indexPathForSelectedRow 
      let row = indexPath?.row 
      t.store = other [row!] 

     } 
    } 

//  

    func tableView(_ tableView: UITableView, canEditRowAt indexPath: IndexPath) -> Bool { 
     print("delete delegate being activated") 
     return true 
    } 

    //For remove row from tableview & object from array. 
    func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) { 
     let context = (UIApplication.shared.delegate as! AppDelegate).persistentContainer.viewContext 
     if tableView.tag == 1 { 
      if editingStyle == .delete { 
       let task = stores [indexPath.row] 
       context.delete(task) 
       (UIApplication.shared.delegate as! AppDelegate).saveContext() 


       do { 
        stores = try context.fetch(UserIncome.fetchRequest()) 
        print("Stores deleted from indexPath",stores) 
       }catch{ 
        print("fail") 
       } 


       recurringIncomeTableView.reloadData() 

      } 

      self.recurringIncomeTableView.reloadData() 

     } else if tableView.tag == 2 { 
      if editingStyle == .delete { 
       let task = other[indexPath.row] 
       print("task on otherTblView is : ",task) 
       context.delete(task) 
       (UIApplication.shared.delegate as! AppDelegate).saveContext() 
       otherIncomeTableView.reloadData() 

       do { 
        other = try context.fetch(UserIncome.fetchRequest()) 
        print("Stores deleted from indexPath",other) 
       }catch{ 
        print("fail") 
       } 

     } 


      self.otherIncomeTableView.reloadData() 
     } 
     tableView.reloadData() 


    } 


} 
+0

後實現代碼如下代碼太,你寫在它的內容... –

+0

正是在那裏爵士 – danu

+0

嘗試調用viewDidAppear()不tableView.reloadData()FUNC的tableView內(_的tableView:UITableView的,提交editingStyle:UITableViewCellEditingStyle,forRowAt indexPath :IndexPath) – Rob

回答

1

您需要刪除任務,像這樣

let task = stores [indexPath.row] 
context.delete(task) 
stores.removeAtIndex(indexPath.row) // i think you forget this line 
(UIApplication.shared.delegate as! AppDelegate).saveContext() 

試試這個,希望它會幫助你

+0

我也這樣做了,但看起來仍然是一樣的。例如,如果我刪除我的第一個tableView中的一行,其他tableView的值會自動填充到該tableView。如果你能幫助我解決這個小問題,我將非常感激 – danu

0

核心數據對象並沒有真正包含的任何信息。它有一個指向上下文和ID的指針,所以當你詢問信息時,它會去商店詢問。如果該對象從上下文中刪除,那麼您存儲在數組中的管理對象將不再起作用並且會崩潰。這就是爲什麼你永遠不應該保留NSManagedObjects。或者

a)將核心數據中的值複製到不同的對象中。如果要刪除某個對象,則必須將其從商店和您保留的副本中刪除。如果插入新對象,或者從其他來源刪除viewController,它將不會更新(但也不會崩潰)。

b)使用NSFetchedResultsController並在值更改時更新結果。這會讓代表告訴你何時發生變化。因此,您只需從商店中刪除該對象,然後fetchedResultsController會告訴您何時將其刪除。