web-dev-qa-db-ja.com

ViewControllerのプロトコルに準拠、Swift

Swift UIViewControllerサブクラス内でUITableViewDataSourceおよびUITableViewDelegateに準拠しようとしています。

class GameList: UIViewController {

    var aTableView:UITableView = UITableView()

    override func viewDidLoad() {
        super.viewDidLoad()
        aTableView.delegate = self
        aTableView.dataSource = self
        self.view.addSubview(aTableView)
        //errors on both lines for not conforming
    }

}

ドキュメントでは、:の後のclass行に準拠する必要があると書かれていますが、通常はスーパークラスがそこに行きます。別の:は機能しません。スーパークラスの後にコンマ区切りリストを使用しても機能しません

編集:

答えは以下にあります。 class GameList: UIViewController, UITableViewDataSource, UITableViewDelegate {

また、各プロトコルに必要なすべてのメソッドを採用する必要がありますが、最初は実行していませんでした。

23
Justin

コンマを使用します:

class GameList: UIViewController, UITableViewDelegate, UITableViewDataSource {
    // ...
}

ただし、スーパークラスはコンマ区切りリストの最初の項目でなければならないことに注意してください。

プロトコルに必要なすべてのメソッドを採用しないと、コンパイラエラーが発生します。必要なすべてのメソッドを取得する必要があります!

32
Firo

XCode6-Beta7がリリースされると、

UITableViewDataSourceのプロトコルメソッドが少し変更され、ベータ6で正常に機能したプロトコルエラーに適合していることに気付きました。

これらは、 ITableViewDataSourceプロトコル に従って実装される必要なメソッドです。

func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell { // insert code}

func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int { // insert code
}

違いを再確認するか、実装したと思われるデリゲートメソッドを再実装することができます。

13
Berby Huang

ここで2つのrequireメソッドを実装する必要があります。

func tableView(tableView:UITableView!, numberOfRowsInSection section:Int) -> Int {
    return 10
}

func tableView(tableView:UITableView!, cellForRowAtIndexPath indexPath:NSIndexPath!) -> UITableViewCell! {
    let cell: UITableViewCell = UITableViewCell(style: UITableViewCellStyle.Subtitle, reuseIdentifier: "MyTestCell")

    cell.text = "Row #\(indexPath.row)"
    cell.detailTextLabel.text = "Subtitle #\(indexPath.row)"

    return cell
}
7
Kiet Nguyen

また、Delegateクラスからすべての非オプション関数をコピーすることも重要です。 Cmd + UITableViewDatasourceをクリックして、これら2つの定義をそのままコピーします。

Beta7の私にとって、UITableViewDatasourceには

func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int

func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell

私の実装:

var items = ["Apple", "Pear", "Banana"]

func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return items.count
}

func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
    let cell:UITableViewCell = UITableViewCell(style: UITableViewCellStyle.Subtitle, reuseIdentifier: "Default")
    cell.textLabel?.text = items[indexPath.row]
    cell.detailTextLabel?.text = "Test"
    return cell

}
3
skipy

次のメソッドを使用します。データソースメソッドに変更があります。

func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int

func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell


protocol UITableViewDataSource : NSObjectProtocol {

    ****func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int

    // Row display. Implementers should *always* try to reuse cells by setting each cell's reuseIdentifier and querying for available reusable cells with dequeueReusableCellWithIdentifier:
    // Cell gets various attributes set automatically based on table (separators) and data source (accessory views, editing controls)

    func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell****

    optional func numberOfSectionsInTableView(tableView: UITableView) -> Int // Default is 1 if not implemented

    optional func tableView(tableView: UITableView, titleForHeaderInSection section: Int) -> String? // fixed font style. use custom view (UILabel) if you want something different
    optional func tableView(tableView: UITableView, titleForFooterInSection section: Int) -> String?

    // Editing

    // Individual rows can opt out of having the -editing property set for them. If not implemented, all rows are assumed to be editable.
    optional func tableView(tableView: UITableView, canEditRowAtIndexPath indexPath: NSIndexPath) -> Bool

    // Moving/reordering

    // Allows the reorder accessory view to optionally be shown for a particular row. By default, the reorder control will be shown only if the datasource implements -tableView:moveRowAtIndexPath:toIndexPath:
    optional func tableView(tableView: UITableView, canMoveRowAtIndexPath indexPath: NSIndexPath) -> Bool

    // Index

    optional func sectionIndexTitlesForTableView(tableView: UITableView) -> [AnyObject]! // return list of section titles to display in section index view (e.g. "ABCD...Z#")
    optional func tableView(tableView: UITableView, sectionForSectionIndexTitle title: String, atIndex index: Int) -> Int // tell table which section corresponds to section title/index (e.g. "B",1))

    // Data manipulation - insert and delete support

    // After a row has the minus or plus button invoked (based on the UITableViewCellEditingStyle for the cell), the dataSource must commit the change
    // Not called for edit actions using UITableViewRowAction - the action's handler will be invoked instead
    optional func tableView(tableView: UITableView, commitEditingStyle editingStyle: UITableViewCellEditingStyle, forRowAtIndexPath indexPath: NSIndexPath)

    // Data manipulation - reorder / moving support

    optional func tableView(tableView: UITableView, moveRowAtIndexPath sourceIndexPath: NSIndexPath, toIndexPath destinationIndexPath: NSIndexPath)
}

あなたのコードは動作します!!

1
Rohit Ragmahale

この質問は既に回答されていますが、もう少しSwiftyにしたいだけです。

UITableViewDelegate, UITableViewDataSourceでプロトコルを記述する代わりに、extensionsを使用してそれらを分割できます。これはコードの編成に役立ちます。プロトコルの適合性の追加については、こちらで説明します page

上記の質問の場合、これは拡張機能を使用してプロトコルに対して確認できます。

class GameList: UIViewController {
  var aTableView:UITableView = UITableView()
    override func viewDidLoad() {
        super.viewDidLoad()
        aTableView.delegate = self
        aTableView.dataSource = self
        self.view.addSubview(aTableView)
    }
}
extension GameList: UITableViewDataSource{
    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return list.count
    }
    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCell(withIdentifier: "cellId", for: indexPath)
        return cell
    }
}
extension GameList: UITableViewDelegate{
    func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
        print("Row Clicked at \(indexPath.row)")
    }
}
1
Sahil Manchanda