簡體   English   中英

StoryBoard / Interface Builder中NSObject的功能是什么?

[英]what is the function of NSObject in StoryBoard / Interface Builder?

我目前正在觀看有關在Swift中進行iOS測試驅動開發的視頻教程課程,但是在View Controller中測試Table View時,我陷入了困境,因為我不明白為什么在Interface builder中我們需要NSObject如下圖所示:

電影庫數據服務繼承了NSObject類:

在此處輸入圖片說明

MovieLibraryDataService的類如下:

import UIKit

class MovieLibraryDataService: NSObject, UITableViewDataSource, UITableViewDelegate {

    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return 0
    }

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


}

MovieLibraryDataService將使用MovieLibraryDataService類,如下所示:

@testable import FilmFest
class LibraryViewControllerTests: XCTestCase {

    var sut: LibraryViewController!

    override func setUp() {
        super.setUp()
        // Put setup code here. This method is called before the invocation of each test method in the class.
        sut = UIStoryboard(name: "Main", bundle: nil).instantiateViewController(withIdentifier: "LibraryViewControllerID") as! LibraryViewController
        _ = sut.view
    }

    override func tearDown() {
        // Put teardown code here. This method is called after the invocation of each test method in the class.
        super.tearDown()
    }

    // MARK: Nil Checks
    func testLibraryVC_TableViewShouldNotBeNil() {
        XCTAssertNotNil(sut.libraryTableView)
    }

    // MARK: Data Source
    func testDataSource_ViewDidLoad_SetsTableViewDataSource() {
        XCTAssertNotNil(sut.libraryTableView.dataSource)
        XCTAssertTrue(sut.libraryTableView.dataSource is MovieLibraryDataService)
    }

    // MARK: Delegate
    func testDelegate_ViewDidLoad_SetsTableViewDelegate() {
        XCTAssertNotNil(sut.libraryTableView.delegate)
        XCTAssertTrue(sut.libraryTableView.delegate is MovieLibraryDataService)
    }

    // MARK: Data Service Assumptions
    func testDataService_ViewDidLoad_SingleDataServiceObject() {
        XCTAssertEqual(sut.libraryTableView.dataSource as! MovieLibraryDataService, sut.libraryTableView.delegate as! MovieLibraryDataService)
    }



}

以及LibraryViewController的定義:

import UIKit

class LibraryViewController: UIViewController {

    @IBOutlet weak var libraryTableView: UITableView!
    @IBOutlet var dataService: MovieLibraryDataService!

    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.
        self.libraryTableView.dataSource = dataService
        self.libraryTableView.delegate = dataService
    }


}

我真的不明白為什么我需要制作那個MovieLibraryDataService

我通常使用:

self.libraryTableView.dataSource = self
self.libraryTableView.delegate = self

但是為什么我需要寫:

self.libraryTableView.dataSource = dataService
self.libraryTableView.delegate = dataService

編輯

您可以將Storyboard上的NSObject用於不同的目的,其中之一也可以是委托。 而不是像下面這樣以編程方式設置它:

self.libraryTableView.dataSource = self
self.libraryTableView.delegate = self

您可以保持控制 ,然后按如下所示設置相應的代表:

在此處輸入圖片說明

原始答案

因為MovieLibraryDataService符合UITableViewDataSourceUITableViewDelegate而不是您的LibraryViewController

如果要像往常一樣更改它,請將代碼更改為:

class LibraryViewController: UIViewController, UITableViewDataSource, UITableViewDelegate {

    @IBOutlet weak var libraryTableView: UITableView!
    var dataService = MovieLibraryDataService()

    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.
        self.libraryTableView.dataSource = self
        self.libraryTableView.delegate = self
    }

    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return 0
    }

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

我個人建議保持現有狀態,因為View Controller會不斷增長並變得像我們稱之為Massive View Controller

MovieLibraryDataService只是另一個實現UITableViewDataSourceUITableViewDelegate類,區別在於情節@IBOutlet var dataService: MovieLibraryDataService!實例化它,並且由IBOutlet @IBOutlet var dataService: MovieLibraryDataService!綁定了@IBOutlet var dataService: MovieLibraryDataService! storyboard-created實例@IBOutlet var dataService: MovieLibraryDataService! 情節提要中的所有對象都是storyboard-created ,這就是為什么如果對象未綁定到您已經使用的其他變量,則必須將它們綁定到要使用的變量。

給變量dataService命名只是一種幻想的說法,因為它實現了那些委托協議,因此在本例中它應該serve tableView的dataSource and delegate

由於dataService是由情節dataService實例化的,因此可以嘗試是否將情節dataService綁定到tableView 這是可能的,因為在情節dataService中有dataService引用。 這將替換viewController中的設置dataSource and delegate

另一個例子

AppDelegate也是情節提要板中的NSObject ,因此情節提要板中的UIApplication/NSApplication能夠引用要使用的內容,從而避免了必須在情節提要板外部設置AppDelegate自己。 (否則會很丑,也許只是macOS,因為Mac應用程序必須顯示一個Menu即使它是空的。)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM