如何在Swift中设置UITableViewCellStyleSubtitle和dequeueReusableCell?

use*_*576 48 uitableview ios swift

我想要一个UITableView使用的带subtitle式单元格dequeueReusableCellWithIdentifier.

我原来的Objective-C代码是:

static NSString*    reuseIdentifier = @"Cell";
    UITableViewCell*    cell = [tableView dequeueReusableCellWithIdentifier:reuseIdentifier];
    if(!cell)
    {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:reuseIdentifier];
    }
Run Code Online (Sandbox Code Playgroud)

UITableViewSO上搜索了几个问题之后,我想在Swift中写这样的话:

    tableView.registerClass(UITableViewCell.classForCoder(), forCellReuseIdentifier: "Cell")

    let cell = tableView.dequeueReusableCellWithIdentifier("Cell", forIndexPath: indexPath) as UITableViewCell
Run Code Online (Sandbox Code Playgroud)

但这并没有让我说我想要一种subtitle风格.所以我尝试了这个:

var cell :UITableViewCell = UITableViewCell(style: UITableViewCellStyle.Subtitle, reuseIdentifier: "Cell")
Run Code Online (Sandbox Code Playgroud)

这给了我一个subtitle细胞,但它不让我dequeueReusableCellWithIdentifier.

我已经研究了一些并看了这个视频教程,但他创建了一个单独subclassUITableViewCell,我认为是不必要的,因为我之前在Obj-C中完成了相同的效果.

有任何想法吗?谢谢.

mem*_*ons 68

请记住,UITableView在函数中定义为可选,这意味着您的初始单元格声明需要检查属性中的可选项.此外,返回的排队单元格也是可选的,因此请确保对其进行可选的强制转换UITableViewCell.之后,我们可以强行打开包装,因为我们知道我们有一个单元格.

var cell:UITableViewCell? = 
tableView?.dequeueReusableCellWithIdentifier(reuseIdentifier) as? UITableViewCell
if (cell == nil)
{
   cell = UITableViewCell(style: UITableViewCellStyle.Subtitle, 
                reuseIdentifier: reuseIdentifier)
}
// At this point, we definitely have a cell -- either dequeued or newly created,
// so let's force unwrap the optional into a UITableViewCell
cell!.detailTextLabel.text = "some text"

return cell
Run Code Online (Sandbox Code Playgroud)

  • dequeueReusableCell始终返回自iOS 4以来的单元格. (3认同)
  • 不应该检查`if cell == nil {//实例化一个新的}`? (2认同)
  • @Lshi 不完全是。`dequeueReusableCell(withIdentifier:forIndexPath:)` 确实返回了一个非可选单元格,但 `dequeueReusableCell(withIdentifier:)` 仍然返回一个可选单元格。 (2认同)

Jer*_*sel 31

如果你宁愿避免选择性,你可以创建一个UITableViewCell的子类,如下所示:

class SubtitleTableViewCell: UITableViewCell {

    override init(style: UITableViewCellStyle, reuseIdentifier: String?) {
        super.init(style: .subtitle, reuseIdentifier: reuseIdentifier)
    }

    required init?(coder aDecoder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }
}
Run Code Online (Sandbox Code Playgroud)

然后注册它:

override func viewDidLoad() {
    super.viewDidLoad()
    self.tableView.register(SubtitleTableViewCell.self, forCellReuseIdentifier: reuseIdentifier)
}
Run Code Online (Sandbox Code Playgroud)

这允许您的单元格自定义代码非常好:

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

    let cell = tableView.dequeueReusableCell(withIdentifier: reuseIdentifier, for: indexPath)

    cell.textLabel?.text = "foo"
    cell.detailTextLabel?.text = "bar"

    return cell
}
Run Code Online (Sandbox Code Playgroud)

  • 这就是我要找的。 (2认同)

Nic*_*ari 20

基本上与其他答案相同,但我通过使用计算变量处理讨厌的选项(你不能nil-tableView:cellForRow:atIndexPath:Swift中返回):

斯威夫特3

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

    let cell: UITableViewCell = {
        guard let cell = tableView.dequeueReusableCell(withIdentifier: "UITableViewCell") else {
            // Never fails:
            return UITableViewCell(style: UITableViewCellStyle.value1, reuseIdentifier: "UITableViewCell")
        }
        return cell
    }()

    // (cell is non-optional; no need to use ?. or !)

    // Configure your cell:
    cell.textLabel?.text       = "Key"
    cell.detailTextLabel?.text = "Value"

    return cell
}
Run Code Online (Sandbox Code Playgroud)

编辑:

其实,这将是更好的使用出列的单元格:tableView.dequeueReusableCell(withIdentifier:for:)不是.

如果没有人可以重用(这正​​是我的代码在上面明确指出的那样),函数的后来变量会自动实例化一个新单元格,因此永远不会返回nil.

  • 您可以只使用 nil 合并运算符并说“tableView.dequeueReusableCell(...) ??”,而不是使用立即调用的闭包来做有趣的事情。UITableViewCell(...)`。 (2认同)

jon*_*ert 12

通过清理Swift 2风格来构建memmons的答案......

let cell = tableView.dequeueReusableCellWithIdentifier(reuseIdentifier) ?? UITableViewCell(style: UITableViewCellStyle.Subtitle, reuseIdentifier: reuseIdentifier)

cell.detailTextLabel?.text = "some text"

return cell
Run Code Online (Sandbox Code Playgroud)

斯威夫特3:

let cell = tableView.dequeueReusableCell(withIdentifier: cellIdentifier) ?? UITableViewCell(style: .subtitle, reuseIdentifier: cellIdentifier)

cell.detailTextLabel?.text = ""

return cell
Run Code Online (Sandbox Code Playgroud)


Mei*_*lbn 7

由于tableView.dequeueReusableCell(withIdentifier:, for:)返回非零单元格,因此if cell == nil检查始终为false。但是我找到了一个解决方案,使默认样式单元格成为您想要的样式(值1,值2或字幕),因为默认样式单元格detailTextLabel为nil,因此请检查其detailTextLabel是否为nil,然后创建新样式单元格,并将其交给出队格, 喜欢:

斯威夫特3:

var cell = tableView.dequeueReusableCell(withIdentifier: yourCellReuseIdentifier, for: indexPath)

if cell.detailTextLabel == nil {
    cell = UITableViewCell(style: .value1, reuseIdentifier: repeatCellReuseIdentifier)
}

cell.textLabel?.text = "Title"
cell.detailTextLabel?.text = "Detail"

return cell
Run Code Online (Sandbox Code Playgroud)

那对我有用。

希望对您有所帮助。


小智 5

func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
    let reuseIdentifier = "cell"
    var cell:UITableViewCell? = tableView.dequeueReusableCellWithIdentifier(reuseIdentifier) as UITableViewCell?
    if (cell == nil) {
        cell = UITableViewCell(style: UITableViewCellStyle.Subtitle, reuseIdentifier: reuseIdentifier)
    }
    cell!.textLabel?.text = self.items[indexPath.row]
    cell!.detailTextLabel?.text = self.items[indexPath.row]
    return cell!
}
Run Code Online (Sandbox Code Playgroud)

  • 尽管代码可以很好地回答这个问题,但请考虑解释它以获得更全面的答案 (3认同)
  • 如果我没有弄错的话,你应该替换"=="条件的"!=" (3认同)