How do I fix this "Unknown Key Exception" error in Xcode? - ios

I'm very new to coding so I really have no idea what's going on.
I've tried pasting the error into this website and looked around for people's responses but they either slightly altered from my error code or their explanation was too convoluted for me.
Code:
import UIKit
class BasicsListScreen: UIViewController {
#IBOutlet weak var tableView: UITableView!
override func viewDidLoad() {
super.viewDidLoad()
}
}
extension BasicsListScreen: UITableViewDelegate, UITableViewDataSource {
func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
return 70
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return basics.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath) as? TableViewCell
cell?.verbLabel.text = basics[indexPath.row]
return cell!
}
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
let vc = storyboard?.instantiateViewController(withIdentifier: "ConjViewController") as? ConjViewController
vc?.pastMe = mePast[indexPath.row]
vc?.pastYou = youPast[indexPath.row]
vc?.pastHe = hePast[indexPath.row]
vc?.pastShe = shePast[indexPath.row]
vc?.pastWe = wePast[indexPath.row]
vc?.pastYall = yallPast[indexPath.row]
vc?.pastThey = theyPast[indexPath.row]
vc?.pastPassive = passivePast[indexPath.row]
vc?.presentMe = mePresent[indexPath.row]
vc?.presentYou = youPresent[indexPath.row]
vc?.presentHe = hePresent[indexPath.row]
vc?.presentShe = shePresent[indexPath.row]
vc?.presentWe = wePresent[indexPath.row]
vc?.presentYall = yallPresent[indexPath.row]
vc?.presentThey = theyPresent[indexPath.row]
vc?.presentPassive = passivePresent[indexPath.row]
self.navigationController?.pushViewController(vc!, animated: true)
}
}
28784:1039713] Unknown class BasicsListScreen in Interface Builder
file. 2019-07-10 13:30:01.795516+0100 App[28784:1039713] *
Terminating app due to uncaught exception 'NSUnknownKeyException',
reason: '[< UIViewController 0x7fcc87619000>
setValue:forUndefinedKey:]: this class is not key value
coding-compliant for the key tableView.'
* First throw call stack: (

Attach your tableView IBOutlet in code to your UITableView in Interface Builder.
Start Developing iOS Apps (Swift): Connect the UI to Code

Take a look at this page Terminating app due to uncaught exception 'NSUnknownKeyException' : iOS app crash. There may be a broken connection to a referenced outlet. The page above shows you what that looks like.
Another thing to look at is to make sure your table view is connected to the right class as Daniel Storm said. Open your storyboard and click on the view that you think is connected BasicsListScreen. Open the "Inspector" by clicking the button in the far upper right of Xcode. Then click "Identity Inspector" which is the middle button. It should show BasicsListScreen in the "Custom Class". Make sure that is right.

The error message sounds like a broken connection in BasicMathLevelOne.xib. It is the result from KVC trying to set a value on your InheritController for the key "you" but the class has no KVC compliant accessor (any more?).
To find the exact spot where the error occurs set an exception breakpoint in Xcode (press Command-6, click the "+" in lower left corner, chose "Add Exception Breakpoint"). Running the app in the debugger should make it stop at the place where the error occurs.

Related

Cannot load XIB into reusable TableViewCell

I created an XIB file and its controller to handle my reusable custom cells:
And set my XIB's class owner:
class WallTableCell: UITableViewCell {
//Outlets
func setupCell() {
setupLabels()
}
func setupLabels() {
self.title.text = "Sample Title"
self.postDescriptionLabel.text = "Sample Description"
}
}
I, currently have 2 storyboards, where the first one leads to the second one, using a NavigationView, the second one contains a TabBarView where the first of the items has a TableView.
Here, I added a UITableViewCell in the storyboard
The cell's class is set to:
And the controller's class is set to:
Where I register my Nib and try to use it on the cellForRowAt method:
class WallViewController: UIViewController {
#IBOutlet weak var messagesTable: UITableView!
override func viewDidLoad() {
loadNibForCells()
}
func loadNibForCells() {
let nib = UINib(nibName: "WallTableCell", bundle: nil)
messagesTable.register(nib, forCellReuseIdentifier: "wallCell")
}
}
extension WallViewController: UITableViewDataSource {
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 1
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
guard let wallCell = messagesTable.dequeueReusableCell(withIdentifier: "wallCell") as? WallTableCell else {
return UITableViewCell()
}
wallCell.setupCell()
return wallCell
}
}
But still, when I run the app in the simulator, I keep getting an empty cell.
What should I do in order to display my custom XIB view inside my tableViewCell?
After following #Sh_Khan's answer and adding:
messagesTable.delegate = self
messagesTable.dataSource = self
The app crashes with an error:
Thread 1: Exception: "[<NSObject 0x600001628e70> setValue:forUndefinedKey:]: this class is not key value coding-compliant for the key postDescriptionLabel"
I believe it has to do with the fact that the TableViewCell inside the storyboard is empty rather than containing the components of the WallTableCell
Make sure to set dataSource and delegate if needed
messagesTable.register(nib, forCellReuseIdentifier: "wallCell")
messagesTable.delegate = self
messagesTable.dataSource = self
There is an error: Thread 1: Exception: "[<NSObject 0x600001628e70> setValue:forUndefinedKey:]: this class is not key value coding-compliant for the key postDescriptionLabel", so maybe you need to unbind the postDescriptionLabel and bind it from xib file to swift file again.
While I was missing to add my messagesTable's dataSource which was what Sh_Khan recommended, the solution for my error afterwards was that my reference outlets were pointing to "File's owner" rather than my File's outlets.
So, when selecting the custom TableViewCell (not the prototype) should be:
For some reason, instead of being "Title Label" on the right side, it was "File's owner"
And the prototype cell shouldn't contain any class attached to it.

UITableView.reloadData() is not refreshing tableView. No error message

I've already looked at the post UITableView.reloadData() is not working. I'm not sure that it applies to my situation, but let me know if I'm wrong.
My app has a tableView. From the main viewController I am opening another viewController, creating a new object, and then passing that object back to the original viewController, where it is added to an array called timers. All of that is working fine. However, when I call tableView.reloadData() in didUnwindFromNewTimerVC() to display the updated contents of the timers array, nothing happens.
NOTE: I have verified that the timers array is updated with the new object. Its count increments, and I can access its members. Everything else in didUnwindFromNewTimerVC() executes normally. The tableView just isn't updating to reflect it.
Here is my code:
import UIKit
class TimerListScreen: UIViewController, UITableViewDelegate, UITableViewDataSource {
#IBOutlet weak var tabelView: UITableView!
var timers = [Timer]()
let tableView = UITableView()
override func viewDidLoad() {
super.viewDidLoad()
tabelView.delegate = self
tabelView.dataSource = self
let tempTimer = Timer(timerLabel: "temp timer")
timers.append(tempTimer)
}
#IBAction func didUnwindFromNewTimerVC(_sender:UIStoryboardSegue){
guard let newTimerVC = _sender.source as? newTimerVC else{return}
newTimerVC.timer.setTimerLabel(timerLabel: newTimerVC.timerLabel.text!)
timers.append(newTimerVC.timer)
tableView.reloadData()
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
if let cell = tabelView.dequeueReusableCell(withIdentifier: "TimerCell", for: indexPath) as? TimerCell{
let timer = timers[indexPath.row]
cell.updateUI(Timer: timer)
return cell
}else{
return UITableViewCell()
}
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return timers.count
}
func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
return 78
}
}
Thank you
Please note the spelling. There are two table view instances: the outlet tabelView and a (pointless) instance tableView.
Reload the data of the outlet
tabelView.reloadData()
and delete the declaration line of the second instance let tableView ....
However I'd recommend to rename the outlet to correctly spelled tableView (you might need to reconnect the outlet in Interface Builder).
And force unwrap the cell
let cell = tabelView.dequeueReusableCell(withIdentifier: "TimerCell", for: indexPath) as! TimerCell
and remove the if - else part. The code must not crash if everything is hooked up correctly in IB.

TableView crash when adding new item when reach the last element of the tableview Swift 4

I have a tableView which will display 20 item when the app start,then when scroll to the bottom,will pull another 20 item from server and display to TableView as well
At first I call this to get the 1st 20 item to display in my tableview,and this is working fine
var posts = [Item]()
//here is the latest 20 posts
func fetchPost(itemId : Int){
Alamofire.request(MY_URL!, method: .get).responseJSON{
response in
switch response.result{
case .success(let result):
//here parse the JSON.
let json = JSON(result)
guard let feedArr = json["item"].array else{
return
}
for item in feedArr {
if let item = item.dictionary,let feed = Item.init(dict: item){
self.posts.append(feed)
}
}
self.myTableView.reloadData()
break
case .failure(let error):
print(error)
}
}
}
Here is the TableView function,which is standard
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return self.posts.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "MyTableCell", for: indexPath) as! MyTableCellClass
cell.posts = self.posts[indexPath.row]
cell.delegate = self
return cell
}
Here I get Id for the last item in TableView and fetch the next 20 item by using fetchPost() method at the top
func tableView(_ tableView: UITableView, willDisplay cell: UITableViewCell, forRowAt indexPath: IndexPath) {
if indexPath.row + 1 == posts.count {
//here is the last item of the feed
let lastPostId = self.posts[indexPath.row].postId
self.fetchPost(postId: lastPostId)
}
}
But now when I reach the bottom of the TableView,let lastPostId is valid,and get the response from server,but the app crashed and keep giving this error :
Thread 1: signal SIGABRT <--this one in AppDelagate class
libc++abi.dylib: terminating with uncaught exception of type
NSException (lldb) <<-- in console
Besides that,when I keep scrolling down,then I scrolling up again,the same error also appear,and all the element inside the TableViewCell all move disorganized(means that not same with what I organized in storyboard)
What I done so far
Check the connection of IBOutlet and IBAction is connected with MyTableCell class .. This is checked,all connected
So my question is
1) What cause this error in TableView,I know this is a very general error,but how can I solved this with this little information from xcode? I dont know which line of code is causing the problem.
2) What is the correct way to display the next 20 item with same structure like the previous in a same TableView?
Please help.Thank you

Keep getting an error/crash due to uncaught exception 'NSUnknownKeyException' [duplicate]

This question already has answers here:
Xcode - How to fix 'NSUnknownKeyException', reason: … this class is not key value coding-compliant for the key X" error?
(79 answers)
Closed 5 years ago.
I've checked my connections and class names as all the other threads with this same issue suggest.
Error message
*** Terminating app due to uncaught exception 'NSUnknownKeyException', reason: '[ setValue:forUndefinedKey:]: this class is not key value coding-compliant for the key parksTableView.'
View controller where I get the crash
import UIKit
class ParksViewController: UITableView, UITableViewDataSource, UITableViewDelegate {
var parkNames = ["Sunnyside", "South Oak", "Tower", "Arno", "Arbor", "Holmes", "Brookside", "Brookside Tennis Courts", "Loose", "Gilham", "Brush Creek", "Westwood"]
#IBOutlet weak var textLabel: UILabel!
#IBOutlet weak var parksTableView: UITableView!
func viewDidLoad(){
self.parksTableView.delegate = self
self.parksTableView.dataSource = self
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return parkNames.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = UITableViewCell()
print(indexPath.row)
cell.textLabel?.text = parkNames[indexPath.row]
return cell
}
Maybe I'm just not connecting the right things to the right places? I've tried a combination of different connections and have deleted and reconnected connections many times in order to try to fix this issue, but it I still can't understand what is wrong.
Storyboard
Connection Inspector of ParksViewController
If you look at the error, it says <UIViewController 0x7fc416a04f80>. You think you have a ParksViewController but you really just have a plain UIViewController.

performSegueWithIdentifier doesn't work - Swift

Im trying to use performSegueWithIdentifier when user taps in a row of a table view. How ever, it doesn't work and i have the next error:
Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'Could not perform segue with identifier 'categoriesS'. A segue must either have a performHandler or it must override -perform.'
I googled the error, but i don't find anything. I've already create the push segues in the storyboard and set them the identifiers that I use in my code.
This is my code(PD: Im using this tableview, as a side bar menu):
import Foundation
class menuVC: UIViewController,UITableViewDelegate, UITableViewDataSource {
#IBOutlet weak var ProfileImage: UIImageView!
#IBOutlet weak var myTable: UITableView!
var opciones = [String]()
var segues = [String]()
override func viewDidLoad() {
super.viewDidLoad()
myTable.delegate = self
opciones = ["Categories","My Coins","Get Coins","Share","LogOff","Exit"]
segues = ["categoriesS","myCoinsS","getCoinsS"]
}
func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 6
}
func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
print(opciones[indexPath.row])
self.performSegueWithIdentifier(segues[indexPath.row], sender: self)
}
func numberOfSectionsInTableView(tableView: UITableView) -> Int {
return 1
}
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
var cell = tableView.dequeueReusableCellWithIdentifier("cell", forIndexPath: indexPath) as UITableViewCell
cell.textLabel?.text = opciones[indexPath.row]
return cell
}
}
Thanks!
You have given a wrong segue as console clearly stated that. You are looking for 'categoriesS' which is in 'segue' array, but you are passing from 'opciones' array. Look closely.
Edit
I saw your edit, looks like u have populate your table using different array, but u have used other array in didselectrow.please check it

Resources