swift - 将 self 分配给 TableView 数据源时出错

标签 swift xcode macos swift4 nstableview

这是 Xcode 输出的错误

解包可选值时意外发现 nil

我有一个 View Controller ,它有一个表格 View 和一些按钮;这些按钮允许我插入或删除数据。似乎当我单击“添加”(这会通过 segue 作为工作表调出一个新的 View Controller )时,应用程序崩溃并出现上述错误。单击“删除”不会产生此影响。所以这与新 View Controller 的猜测有关。控制台除了打印出 (lldb) 之外不会进一步处理错误

这是我的代码

override func viewDidLoad() {
    super.viewDidLoad()
    alarmTableView.dataSource = self //error occurs here
    alarmTableView.delegate = self //if i remove the above line if will occur here too.
}

嵌入上述 viewDidLoad 函数的我的 Viewcontroller 列出了我需要的协议(protocol)

class ViewController: NSViewController, NSTableViewDelegate, NSTableViewDataSource {


    @IBOutlet weak var addAlarm: NSButton!
    @IBOutlet weak var resetDataButton: NSButton!
    @IBOutlet var alarmArrayController: NSArrayController!
    @IBOutlet weak var alarmTableView: NSTableView!
    @IBOutlet weak var deleteAll: NSButton!

    @objc let moc: NSManagedObjectContext

    required init?(coder: NSCoder) {
        self.moc = CoreDataHandler.getContext()
        super.init(coder: coder)
    }
    override func prepare(for segue: NSStoryboardSegue, sender: Any?) {
        let destinationController = segue.destinationController as! AddAlarmViewController
        //pass data to next controller here

    }



    @IBAction func deleteAllAction(_ sender: Any) {

        if (alarmTableView.selectedRow >= 0) {
            if (CoreDataHandler.deleteAllObjectsInEntity(entityName: "Alarm")) {
                //remove from nsarray controller
                for object in alarmArrayController.arrangedObjects as! [Alarm] {
                    print(object)
                    alarmArrayController.removeObject(object)
                }

                alarmTableView.reloadData()
            }
        }
        else {
            printInfo(str: "There are no alarms to delete")
        }

    }


    /* Response to the remove alarm button  - It removes a selected alarm object from the table */
    @IBAction func resetDataAction(_ sender: Any) {
        if (alarmTableView.selectedRow >= 0) {
            let selectedAlarm = self.alarmArrayController.selectedObjects.first as! Alarm

            alarmArrayController.remove(atArrangedObjectIndex: alarmTableView.selectedRow)

            CoreDataHandler.deleteObjectInEntity(entityName: "Alarm", obj: selectedAlarm)
            alarmTableView.reloadData()
        }
        else {
            //will need a warning or play a sound.
            printInfo(str: "Please select an alarm")
        }

    }

    override func viewDidLoad() {
        super.viewDidLoad()
        printInfo(str: "viewdidload")
        print(alarmTableView)

        if (alarmTableView != nil) {
            printInfo(str: "AlarmTableView Is initialised")
            alarmTableView.dataSource = self
            alarmTableView.delegate = self
        }
        else {
            printInfo(str: "AlarmTableView is not initialised")
        }

    }

    override var representedObject: Any? {
        didSet {
        // Update the view, if already loaded.
        }
    }

    func printInfo(str: String) {
        print("ViewController: \(str)")
    }

    func tableView(_ tableView: NSTableView, heightOfRow row: Int) -> CGFloat {
        return 100.0
    }
}

class AddAlarmViewController: ViewController {

@IBOutlet weak var closeButton: NSButton!


override func viewDidLoad() {
    super.viewDidLoad()
    // Do view setup here.
    printClassInfo(str: "viewDidLoad")
    CoreDataHandler.saveTestData()


}

@IBAction func closeButtonAction(_ sender: Any) {
    self.dismissViewController(self)
}

func printClassInfo(str: String) {
    print("AddAlarmViewController \(str)")
}

}

如果我删除发生错误的行,应用程序运行正常。但我想重写委托(delegate)和数据源并使用函数来进一步自定义表。我也在使用 Cocoa Bindings。

为什么我会收到此错误?

更新

我还没有解决这个问题,但我在 viewDidLoad 函数中放置了一些打印语句。似乎当应用程序首次加载时, TableView 被初始化。但是,当我单击“添加”按钮后,由于某种奇怪的原因, TableView 被设置为 nil,就好像另一个 TableView 已被初始化一样。但是数据仍然可见

最佳答案

问题:

class AddAlarmViewController: ViewController {    
//... 

    override func viewDidLoad() {
        super.viewDidLoad()
        //...
    }
}

您的 AddAlarmViewControllerViewController 的子类,而不是 NSViewController

AddAlarmViewControllerviewDidLoad 中,您调用 super.viewDidLoad() ,它基本上调用了 ViewControllerviewDidLoad
但是...在这种情况下,ViewController是一个新实例,作为AddAlarmViewController的父类(super class),并且它的任何属性都没有初始化。
不管是什么,它可能都不是您想要的。

解决方案:

class AddAlarmViewController: NSViewController {
//... rest as it is
}

关于swift - 将 self 分配给 TableView 数据源时出错,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49103848/

相关文章:

ios - swift ios 中的 tableview 详细文本标签

xcode - 如何显示 "the"助手编辑器?

swift - PromiseKit pod 安装正确,但导入 PromiseKit 返回错误?

xcode - 自动布局约束在 iOS 8 中有效,在 iOS 9 中失效

objective-c - 如何编写 OS X Finder 插件

java - 如何使用 Homebrew 在 Mac 上安装 Java 9 和 10?

ios - URL : "message://" - error: "This app is not allowed to query for scheme message" 失败

swift - 如何将Realm中某个类的所有对象获取到一个数组中

Swift:调用applicationDidEnterBackground时确定Active View Controller

ios - Alamofire 不会在 podfile 中使用 osx 而不是 ios