0

here is the image i had designed here is the code for UITableviewCell and in this I had placed the stepper action method to trigger but unable to update the price label when I tap on stepper can anyone help me?

class productTableViewCell: UITableViewCell {

    @IBOutlet var stepper: UIStepper!
    @IBOutlet var imageview: UIImageView!
    @IBOutlet var nameLabel: UILabel!
    @IBOutlet var priceLabel: UILabel!
    @IBOutlet var quantityTextField: UITextField!
    var pricearr = [String]()
    var price : String = ""
    override func awakeFromNib() {
        super.awakeFromNib()
        // Initialization code
    }
    @IBAction func changeCart(_ sender: Any) {
        let value = Int(stepper.value)
        quantityTextField.text = String(value)
   }
}

Here is the code for UITableViewCell and in this I had placed the stepper action method to trigger but unable to update the price label when I tap on the stepper can anyone help me?

 @IBOutlet var tableDetails: UITableView!
    var productsArray = [String]()
    var nameArray = [String]()
    var priceArray = [String]()
    let urlstring = "http://www.json-generator.com/api/json/get/ceghMiWudK?indent=2"
    var price = [String]()
    var sum = 0

    override func viewDidLoad() {
        super.viewDidLoad()
       self.downloadJsonWithURL()
        tableDetails.delegate = self
        tableDetails.dataSource = self
        tableDetails.alwaysBounceVertical = false
        // Do any additional setup after loading the view.
    }

    func downloadJsonWithURL() {
            let url = NSURL(string: urlstring)
            URLSession.shared.dataTask(with: (url as? URL)!, completionHandler: {(data, response, error) -> Void in
                if let jsonObj = try? JSONSerialization.jsonObject(with: data!, options: .allowFragments) as? NSDictionary {
                    print(jsonObj!.value(forKey: "Detail"))
                if let detailsArray = jsonObj!.value(forKey: "Detail") as? NSArray {
                    for item in detailsArray {
                        if let detailDict = item as? NSDictionary {
                            if let name = detailDict.value(forKey: "productName"){
                                self.nameArray.append(name as! String)
                            }
                            if let price = detailDict.value(forKey: "productPrice"){
                                self.priceArray.append(price as! String)
                            }
                            if let image = detailDict.value(forKey: "img"){
                                self.productsArray.append(image as! String)
                            }
                        }
                    }
                }
                OperationQueue.main.addOperation({
                    self.tableDetails.reloadData()
                    for item in self.priceArray{
                        let endIndex = item.index(item.endIndex, offsetBy: -5)
                        let truncated = item.substring(to: endIndex)
                        self.price.append(truncated)
                    }
                    print(self.price)
                })
            }
        }).resume()
    }

    func numberOfSections(in tableView: UITableView) -> Int {
        // #warning Incomplete implementation, return the number of sections
        return 3
    }

    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int{
        if (section == 0){
            return productsArray.count
        }else{
            return 1
        }
    }

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        if indexPath.section == 0{
            let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath) as! productTableViewCell
            let arr = self.productsArray[indexPath.row]
            let urls = NSURL(string: arr)
            let data = NSData (contentsOf: urls! as URL)
            cell.imageview.image = UIImage(data: data! as Data)
            cell.nameLabel.text = nameArray[indexPath.row]
            let x = priceArray[indexPath.row]
            let array = String(x)
            cell.priceLabel.text = array
            cell.quantityTextField.text = "1"
            cell.pricearr = [price[indexPath.row]]
            return cell
        }else if indexPath.section == 1{
            let cell = tableView.dequeueReusableCell(withIdentifier: "couponcell", for: indexPath) as! CouponTableViewCell
            return cell
        }else {
            let cell = tableView.dequeueReusableCell(withIdentifier: "checkout", for: indexPath) as! checkoutTableViewCell
            return cell
        }
    }

2 Answers2

0

I think the problem is with the following line

 priceLabel.text = x * String(value)

What are you trying to accomplish here? This should not compile

kathayatnk
  • 975
  • 1
  • 7
  • 9
0

Add your stepper's outlet and action like in below image:

Add your stepper's outlet and action like in image

Replace your code with below one:

 class productTableViewCell: UITableViewCell {

            @IBOutlet var stepper: UIStepper!
            @IBOutlet var imageview: UIImageView!
            @IBOutlet var nameLabel: UILabel!
            @IBOutlet var priceLabel: UILabel!
            @IBOutlet var quantityTextField: UITextField!
            var pricearr = [String]()
            var price : String = ""
            override func awakeFromNib() {
                super.awakeFromNib()
                // Initialization code
            }
            @IBAction func changeCart(_ sender: Any) {
                let value = Int(stepper.value)
                quantityTextField.text = String(value)
                let x = Int(pricearr[0])
                priceLabel.text = String(x! * value)
            }
        }

Your code has one bug is that when you scroll tableView that time cell will be reset to its default value because of cell reuse.

EDIT:

Better way to achieve your goal (as far as I understood) can be as defined below :

  1. Remove stepper action

enter image description here

  1. Remove action from UITableview cell class

    class productTableViewCell: UITableViewCell {

        @IBOutlet var stepper: UIStepper!
        @IBOutlet var imageview: UIImageView!
        @IBOutlet var nameLabel: UILabel!
        @IBOutlet var priceLabel: UILabel!
        @IBOutlet var quantityTextField: UITextField!
        var price : String = ""
        override func awakeFromNib() {
            super.awakeFromNib()
            // Initialization code
        }
    }
    

3.Replace your core logic with below code

@IBOutlet var tableDetails: UITableView!
    var CartArray : [[String: String]] = []
    var itemsArray : [[String: AnyObject]] = []
    let urlstring = "http://www.json-generator.com/api/json/get/ceghMiWudK?indent=2"
    var sum = 0

    override func viewDidLoad() {
        super.viewDidLoad()
        self.downloadJsonWithURL()
        tableDetails.delegate = self
        tableDetails.dataSource = self
        tableDetails.alwaysBounceVertical = false
        // Do any additional setup after loading the view.
    }
    func downloadJsonWithURL() {
        let url = NSURL(string: urlstring)
        URLSession.shared.dataTask(with: (url as? URL)!, completionHandler: {(data, response, error) -> Void in
            if let jsonObj = try? JSONSerialization.jsonObject(with: data!, options: .allowFragments) as? NSDictionary {
              //  print(jsonObj!.value(forKey: "Detail"))
                self.itemsArray = (jsonObj!.value(forKey: "Detail") as? [[String: AnyObject]])!

                OperationQueue.main.addOperation({
                    self.tableDetails.reloadData()
                })
            }
        }).resume()
    }

    func numberOfSections(in tableView: UITableView) -> Int {
        // #warning Incomplete implementation, return the number of sections
        return 1
    }
    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int{
        if (section == 0){
            return itemsArray.count
        }else{
            return 1
        }
    }
    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

        //if indexPath.section == 0{
            let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath) as! productTableViewCell
            let arr = itemsArray[indexPath.row]
            let urls = NSURL(string: arr["img"] as! String)
            let data = NSData (contentsOf: urls! as URL)
            cell.imageview.image = UIImage(data: data! as Data)
            cell.nameLabel.text = arr["productName"] as? String
            var price = arr["productPrice"] as! String

        var aQuntity : Float = 1
        let itemId : Int =  arr["sku"] as! Int

        for aDic in CartArray{
            if aDic["id"] == String(itemId){

            aQuntity = Float(String(aDic["quantity"]!))!
            }
        }


        cell.stepper.value = Double(Int(aQuntity))
        cell.stepper.tag = indexPath.row

        cell.stepper.addTarget(self, action: #selector(stapperValueChange), for:.valueChanged)
        price = price.replacingOccurrences(of: "KD", with: "")

            cell.priceLabel.text = String(Float(price)! * aQuntity)
        cell.quantityTextField.text = String(aQuntity)
            cell.price = price
            return cell
       // }
//        else if indexPath.section == 1{
//            let cell = tableView.dequeueReusableCell(withIdentifier: "couponcell", for: indexPath) as! CouponTableViewCell
//            return cell
//        }else {
//            let cell = tableView.dequeueReusableCell(withIdentifier: "checkout", for: indexPath) as! checkoutTableViewCell
//            return cell
//        }


    }

    func stapperValueChange (stepper : UIStepper){
        let index : Int = stepper.tag
        let arr = itemsArray[index]

        let cell : productTableViewCell = tableDetails.cellForRow(at: IndexPath(row: index, section: 0)) as! productTableViewCell

                let value = Float(stepper.value)
                cell.quantityTextField.text = String(value)
                let x = Float(cell.price)
                cell.priceLabel.text = String(Int(x! * value))
        let itemId : Int =  arr["sku"] as! Int

        var aFoundIndex : Int?
        var counter : Int = 0

        _ = CartArray.filter { (aDic) -> Bool in

            if aDic["id"] ==  String(itemId){
            aFoundIndex = counter
            }
            counter += 1
            return false
        }


        if(aFoundIndex != nil){
        CartArray.remove(at: aFoundIndex!)
        }

        CartArray.append(["quantity" : String(value),"id" : String(itemId)])
    }
Govind Prajapati
  • 957
  • 7
  • 24
  • if possible can you tell me how to update the total cart value that means i am getting data from webservices which i will get 9 keyvalue pairs how to add and show it in the final total price cart and it should update with the stepper too ? –  Jun 07 '17 at 06:47
  • the bug also i got it how to overcome any suggestion –  Jun 07 '17 at 06:52
  • First of all, You don't have to make separate arrays for items like name, price, and product because you are getting all values in one separate dictionary and for your cart item you can make different array of dictionary (like arrCart[[String:String]] ) and store 'sku' as an item-id and Quantity in it. Now you have to just compare sku with item-id in 'cellForRow' method and if found then code should be: priceLabel.text = arrCart[FoundIndex].Quantity; – Govind Prajapati Jun 07 '17 at 09:06
  • can u explain clearly i didn't understand i was new to swift if possible any example to demonstrate –  Jun 07 '17 at 09:44
  • then how to read the price,name & product ? @Govind Prajapati –  Jun 07 '17 at 11:12
  • Please refer newly edited answer which is tested and working. – Govind Prajapati Jun 07 '17 at 12:29
  • I hope you will understand the logic behind it. – Govind Prajapati Jun 07 '17 at 12:31
  • 1
    really u r superb bro no words to say and ur dedication is also superb perfectly working –  Jun 07 '17 at 12:44
  • but in this below two sections got missed how to embed in it ? –  Jun 07 '17 at 12:46
  • i am trying now –  Jun 07 '17 at 12:50
  • i got the remaining two sections also –  Jun 07 '17 at 12:53
  • if possible can i have ur mobile number –  Jun 07 '17 at 12:59
  • i am individually having a delete button on every cell how to give action for a button to delete the particular selected row ? –  Jun 08 '17 at 04:54
  • 1. Give an action to the button as we did in stepper's case, Let's say it is 'deleteButtonAction'. 2. find button's superview in 'deleteButtonAction' and convert it into your cell's custom class. 3.use tableview's method 'indexPathForCell:' to find the index of found cell. 4. Now delete that cell from indexpath as well from associated array. – Govind Prajapati Jun 08 '17 at 05:01
  • what is super view i didn't understand ? –  Jun 08 '17 at 05:08
  • You can find any UIView's super view with the help of UIView's property superview. (Ex. let cell = aDeleteButton.superview) – Govind Prajapati Jun 08 '17 at 05:10
  • but i am unable to acess delete button in delete button action –  Jun 08 '17 at 05:36
  • aDeleteButton is what you posted in comment ? –  Jun 08 '17 at 06:15
  • It is a sender button which is inside of UITableviewCell. – Govind Prajapati Jun 08 '17 at 06:43
  • let cell = button.superview?.superview as! productTableViewCell let indexPath = tableDetails.indexPath(for: cell) func tableView(tableView: UITableView, commitEditingStyle editingStyle: UITableViewCellEditingStyle, forRowAtIndexPath indexPath: NSIndexPath) { if (editingStyle == UITableViewCellEditingStyle.delete) { cell. } } –  Jun 08 '17 at 06:51
  • in that comment what is associated array that means which array i need to be called to delete ? –  Jun 08 '17 at 07:00
  • i got an error with this code that Could not cast value of type 'UITableViewCellContentView' (0x10ed2d0d8) to 'Ecommerce.productTableViewCell' in first line –  Jun 08 '17 at 07:14
  • i am having contentView on top of the view in the custom cell is it the error caused of this ? –  Jun 08 '17 at 07:15
  • Sorry, I thought you have a custom delete button in your cell. If you are using accessory then please refer -> https://stackoverflow.com/questions/14148229/change-table-to-edit-mode-and-delete-rows-inside-a-normal-viewcontroller – Govind Prajapati Jun 08 '17 at 07:37
  • no i am having custom delete button cell only and the image link is https://i.stack.imgur.com/CGZGF.png –  Jun 08 '17 at 07:47
  • Sorry, right now I can't help you anymore because I also have my work. – Govind Prajapati Jun 08 '17 at 08:32
  • how to do just tell me so that i can try on my own ? –  Jun 08 '17 at 08:51
  • Have a look -> https://stackoverflow.com/questions/7504421/getting-row-of-uitableview-cell-on-button-press – Govind Prajapati Jun 08 '17 at 10:30
  • last and final one what is associated array please give me clarification about that ? –  Jun 08 '17 at 11:08
  • It is your data source array from which you are displaying data in your table view. – Govind Prajapati Jun 08 '17 at 11:12
  • if possible any idea how to update the total cart price ? –  Jun 08 '17 at 12:55
  • Right now we are storing item-id and quantity in our cart array which is obviously not sufficient to calculate total cart value so we have to add 'productPrice' also in cart array so later we can enumerate cart array and sum up total cart value. (**Advice:** Better you store product's all data available in cart array like img, name etc. may you need them in next page when user click on cart icon) – Govind Prajapati Jun 09 '17 at 04:41
  • i try to implement this –  Jun 09 '17 at 05:00
  • how to enumerate cart array to add total cart value ? –  Jun 09 '17 at 06:49
  • Instead of asking here better you google for such small things. – Govind Prajapati Jun 09 '17 at 06:52