You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Swift 如何计算UITableViewCell中选中按钮的数值总和

现有实现的核心问题

  • 代理归属错误:两类Cell都是列表的子视图,没有直接绑定关系,无法将所有ToggleNumberCell的代理都指向同一个CalculateCell实例,导致回调无法正确收集所有选中值。
  • 数值存储逻辑错误:当前CalculateCell的increment变量是直接赋值,每次新的选中值会覆盖旧值,无法累加多个Cell的选择结果。
  • 缺少同Cell内按钮互斥逻辑:点击同个Cell的多个按钮会同时处于选中状态,导致数值回调错误。

正确实现方案

整体逻辑调整为:由持有TableView的ViewController统一管理所有选中值,接收ToggleNumberCell的选择回调,再响应CalculateCell的计算请求汇总结果。


1. 调整ToggleNumberCell逻辑

新增cell索引属性,补充同Cell内按钮互斥逻辑:

protocol ToggleNumberCellDelegate: AnyObject {
    func toggleNumberCell(_ toggleNumberCell: ToggleNumberCell, selectedValue: Int)
}

class ToggleNumberCell: UITableViewCell {
    static let reuseIdentifier = String(describing: ToggleNumberCell.self)
    // 新增属性,标记当前cell对应列表的行号
    var cellIndex: Int = 0

    @IBOutlet private weak var titleLabel: UILabel!
    @IBOutlet private weak var zeroButton: UIButton!
    @IBOutlet private weak var oneButton: UIButton!
    @IBOutlet private weak var twoButton: UIButton!
    @IBOutlet private weak var threeButton: UIButton!
    @IBOutlet private weak var fourButton: UIButton!
    @IBOutlet private weak var fiveButton: UIButton!
    @IBOutlet private weak var sixButton: UIButton!

    private weak var delegate: ToggleNumberCellDelegate?
    private var value: Int?

    @IBAction func buttonTapped(_ sender: UIButton) {
        // 先重置所有按钮为未选中样式
        [zeroButton, oneButton, twoButton, threeButton, fourButton, fiveButton, sixButton].forEach { btn in
            btn?.backgroundColor = .white // 替换为你的未选中背景色
            btn?.tintColor = .black // 替换为你的未选中文字色
        }
        // 再设置当前点击按钮的选中样式
        switch sender {
        case zeroButton:
            zeroButton.backgroundColor = UIColor.NBABlue
            zeroButton.tintColor = .white
            value = 0
        case oneButton:
            oneButton.backgroundColor = UIColor.NBABlue
            oneButton.tintColor = .white
            value = 1
        case twoButton:
            twoButton.backgroundColor = UIColor.NBABlue
            twoButton.tintColor = .white
            value = 2
        // 剩余其他按钮的case同理补充
        default: break
        }
        delegate?.toggleNumberCell(self, selectedValue: value!)
        print("选中的数值为\(value!)")
    }
}

2. 调整CalculateCell逻辑

移除不必要的代理实现,新增计算按钮点击闭包回调:

class CalculateCell: UITableViewCell {
    static let reuseIdentifier = String(describing: CalculateCell.self)
    // 新增计算按钮点击回调闭包
    var calculateButtonTapped: (() -> Void)?

    @IBOutlet private weak var calculateButton: UIButton!
    @IBOutlet private weak var totalLabel: UILabel!

    func configure(answer: AnswerModel) {
        self.backgroundColor = UIColor.secondarySystemGroupedBackground
        self.totalLabel.text = answer.text
        self.totalLabel.font = .preferredFont(forTextStyle: .headline)
        calculateButton.layer.cornerRadius = 10.0
    }

    override func prepareForReuse() {
        super.prepareForReuse()
        self.totalLabel.text = nil
    }

    @IBAction func calculateTapped(_ sender: UIButton) {
        calculateButtonTapped?()
    }
}

3. ViewController层统一管理数据

持有TableView的ViewController遵循ToggleNumberCellDelegate,维护所有选中值,处理计算请求:

class YourViewController: UIViewController, UITableViewDataSource, UITableViewDelegate, ToggleNumberCellDelegate {
    // 按实际需求修改NumberCell的数量
    private let numberCellTotalCount = 3
    // 存储每个NumberCell的选中值,默认未选中为nil
    private var selectedValues: [Int?] = Array(repeating: nil, count: numberCellTotalCount)

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        if indexPath.row < numberCellTotalCount {
            let cell = tableView.dequeueReusableCell(withIdentifier: ToggleNumberCell.reuseIdentifier, for: indexPath) as! ToggleNumberCell
            cell.delegate = self
            cell.cellIndex = indexPath.row
            // 其他cell配置逻辑
            return cell
        } else {
            let cell = tableView.dequeueReusableCell(withIdentifier: CalculateCell.reuseIdentifier, for: indexPath) as! CalculateCell
            // 监听计算按钮点击
            cell.calculateButtonTapped = { [weak self] in
                guard let self = self else { return }
                // 汇总所有非空的选中值
                let total = self.selectedValues.compactMap { $0 }.reduce(0, +)
                cell.totalLabel.text = "\(total)"
            }
            // 其他cell配置逻辑
            return cell
        }
    }

    // 接收NumberCell的选中回调,更新存储的选中值
    func toggleNumberCell(_ toggleNumberCell: ToggleNumberCell, selectedValue: Int) {
        selectedValues[toggleNumberCell.cellIndex] = selectedValue
    }
}

内容的提问来源于stack exchange,提问作者isaacthedev

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.03 20:09:01