Swift中如何在TableView里用if-else根据API状态标记Cell标签?
Hey there! Your current code gets the job done, but it’s packed with repetitive logic that’ll get messy fast if you add more order statuses later. Let’s refactor this to be cleaner, more maintainable, and fix a common pitfall with table view cell reuse.
The Problem with Your Current Code
Every status branch repeats the same elementDesign call and text formatting. Worse, if your cell gets reused (which table views do automatically), you’ll end up with leftover styles or checkmarks from previous cells—super frustrating to debug!
Refactored Solution
First, we’ll centralize the mapping between statuses and their corresponding labels, then handle resetting default styles before applying the active status. Here’s how to do it:
Step 1: Clean Up in cellForRowAt
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { guard let cell = tableView.dequeueReusableCell(withIdentifier: "YourCellIdentifier", for: indexPath) as? YourCustomCell else { return UITableViewCell() } let currentOrder = myOrderJSON[indexPath.row] let currentStatus = currentOrder.status // Map each status string to its corresponding label in the cell let statusToLabelMap: [String: UILabel] = [ "Placed": cell.placed, "Dispatched": cell.dispatched, "Delivered": cell.delivered, "Payment Received": cell.paymentReceived ] // 1. Reset ALL labels to default styles first (critical for cell reuse!) for label in statusToLabelMap.values { // Set your default unselected style here label.layer.cornerRadius = 0 label.layer.shadowRadius = 0 label.layer.shadowOpacity = 0 label.layer.shadowOffset = .zero // Remove any existing checkmark label.text = label.text?.replacingOccurrences(of: " ✔︎", with: "") } // 2. Apply styles to the active status label if let targetLabel = statusToLabelMap[currentStatus] { targetLabel.elementDesign(cornerRadius: 12, shadowRadius: 2, shadowOpacity: 0.5, offsetWidth: 2, offsetHeight: 2) targetLabel.text = "\(currentStatus) ✔︎" } return cell }
Step 2: Even Better—Encapsulate Logic in the Cell
To keep your view controller lean, move the status handling directly into your custom cell class. This follows MVC best practices (keeping cell UI logic inside the cell):
// Inside your custom TableViewCell class extension YourCustomCell { func configure(with status: String) { let statusToLabelMap: [String: UILabel] = [ "Placed": placed, "Dispatched": dispatched, "Delivered": delivered, "Payment Received": paymentReceived ] // Reset all labels to default for label in statusToLabelMap.values { label.layer.cornerRadius = 0 label.layer.shadowRadius = 0 label.layer.shadowOpacity = 0 label.layer.shadowOffset = .zero label.text = label.text?.split(separator: " ").first.map(String.init) // Keep only the status text } // Highlight active status if let targetLabel = statusToLabelMap[status] { targetLabel.elementDesign(cornerRadius: 12, shadowRadius: 2, shadowOpacity: 0.5, offsetWidth: 2, offsetHeight: 2) targetLabel.text = "\(status) ✔︎" } } }
Then your cellForRowAt becomes super simple:
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { guard let cell = tableView.dequeueReusableCell(withIdentifier: "YourCellIdentifier", for: indexPath) as? YourCustomCell else { return UITableViewCell() } let currentStatus = myOrderJSON[indexPath.row].status cell.configure(with: currentStatus) return cell }
Key Improvements
- No more repeated code: Adding a new status only requires one line in the
statusToLabelMap - Fixes cell reuse bugs: Resetting all labels ensures old styles/checkmarks don’t stick around when cells are reused
- Cleaner separation of concerns: Cell UI logic lives where it belongs—in the cell class
内容的提问来源于stack exchange,提问作者Aquib Afzal

