Reputation: 67
I am trying to dequeue multiple tableviews with custom cells in the same view controller I keep getting the error (Value of type 'UITableViewCell?' has no member 'serviceChoiceAmount','serviceChoicePrice','serviceChoiceTitle','serviceChoiceImage') below I have the code for the view controller and one custom cell (same error will appear for others). (I have not input all the code for the other cells, if I have a solution to this error I will do so), should I create an initializer for the cell inside the custom cell class and dequeue using that inside the view controller?
View Controller
import UIKit
class CartViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
let defaults = UserDefaults.standard
var TOTAL = [Double]()
@IBOutlet weak var cartTableView: UITableView!
@IBOutlet weak var totalTableView: UITableView!
@IBOutlet weak var optionsTableView: UITableView!
@IBOutlet weak var choosePayment: UITableViewCell!
@IBOutlet var address: [UITableViewCell]!
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
let Cartcell = defaults.array(forKey: "Cart")
print(Cartcell as Any)
print(TOTAL)
print("ViewDidLoad")
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
@IBAction func clearCart(_ sender: Any) {
//add function to clear total cell
CartSingleton1.sharedInstance.orderDict.removeAll()
cartTableView.reloadData()
}
func numberOfSections(in tableView: UITableView) -> Int {
var section: Int?
if tableView == self.cartTableView{
section = 1
}
if tableView == self.totalTableView{
section = 1
}
if tableView == self.optionsTableView{
section = 3
}
return section!
}
func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
var title: String?
if tableView == self.cartTableView{
title = ("Order Details")
}
if tableView == self.totalTableView{
title = ("Total")
}
if tableView == self.optionsTableView{
title = ("Payment Option")
//dropoff address
//pickup address
}
return title!
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
var count: Int?
if tableView == self.cartTableView{
count = CartSingleton1.sharedInstance.orderDict.count
}
if tableView == self.totalTableView{
count = 1
}
if tableView == self.optionsTableView{
count = 3
}
return count!
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
var cell: UITableViewCell?
if tableView == self.cartTableView{
let cart = CartSingleton1.sharedInstance.orderDict[indexPath.row] as NSDictionary
cell = tableView.dequeueReusableCell(withIdentifier: "ServiceCart") as! CartTableViewCell
cell.serviceChoiceImage.image = cart.value(forKey: "image") as? UIImage
cell.serviceChoicePrice.text = cart.value(forKey: "pricing") as? String
cell.serviceChoiceTitle.text = cart.value(forKey: "titled") as? String
let quantityInt = cart.value(forKey: "quantity") as? Int
cell.serviceChoiceAmount.text = quantityInt?.description
}
if tableView == self.totalTableView{
}
if tableView == self.optionsTableView{
}
return cell!
}
func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) {
if tableView == self.cartTableView{
if editingStyle == .delete{
print("deleted")
CartSingleton1.sharedInstance.orderDict.remove(at: indexPath.row)
self.cartTableView.deleteRows(at: [indexPath], with: .automatic)
print("cart dictionary delete", CartSingleton1.sharedInstance.orderDict)
}
}
}
/*
// MARK: - Navigation
// In a storyboard-based application, you will often want to do a little preparation before navigation
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
// Get the new view controller using segue.destinationViewController.
// Pass the selected object to the new view controller.
}
*/
}
custom cell: CartTableViewCell
import UIKit
class CartTableViewCell: UITableViewCell {
@IBOutlet weak var serviceChoiceImage: UIImageView!
@IBOutlet weak var serviceChoiceTitle: UILabel!
@IBOutlet weak var serviceChoiceAmount:UILabel!
@IBOutlet weak var serviceChoicePrice: UILabel!
override func awakeFromNib() {
super.awakeFromNib()
// Initialization code
}
override func setSelected(_ selected: Bool, animated: Bool) {
super.setSelected(selected, animated: animated)
// Configure the view for the selected state
}
}
Upvotes: 0
Views: 659
Reputation: 154583
Your problem is that you have declared cell
to be of type UITableViewCell?
with this line:
var cell: UITableViewCell?
So, when you dequeue the cell and assign it to this variable, it assumes that type. So even though it is really a CartTableViewCell
, Swift will only let you call methods and access properties that are available to UITableViewCell
.
Get rid of that declaration and change your dequeue
line to:
let cell = tableView.dequeueReusableCell(withIdentifier: "ServiceCart") as! CartTableViewCell
cell
will then be of type CartTableViewCell
and you'll be able to access its properties. Since cell
is no longer optional, change your:
return cell!
to:
return cell
You will need to move this return
into your if
block, or assign the cell
to another variable to return at the end of the function.
Alternatively, change cell
to tableCell
and use it only to return the cell value:
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
var tableCell: UITableViewCell?
if tableView == self.cartTableView {
let cart = CartSingleton1.sharedInstance.orderDict[indexPath.row] as NSDictionary
let cell = tableView.dequeueReusableCell(withIdentifier: "ServiceCart") as! CartTableViewCell
cell.serviceChoiceImage.image = cart.value(forKey: "image") as? UIImage
cell.serviceChoicePrice.text = cart.value(forKey: "pricing") as? String
cell.serviceChoiceTitle.text = cart.value(forKey: "titled") as? String
let quantityInt = cart.value(forKey: "quantity") as? Int
cell.serviceChoiceAmount.text = quantityInt?.description
tableCell = cell
}
if tableView == self.totalTableView {
}
if tableView == self.optionsTableView {
}
// safely unwrap tableCell and return UITableViewCell() if nothing was assigned
return tableCell ?? UITableViewCell()
}
Upvotes: 1