I have a checkbox (UIButton) and a label in a UITableViewCell. I want to change the label's text (color + strikethrough) when I click on the checkbox.
This is for a Recipe Application. After a cooking step is done, the user can "check" it as done.
This is my current cellForRowAt Function for the tableView:
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 3
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
if tableView == groceryTableView {
let cell = tableView.dequeueReusableCell(withIdentifier: groceryTableViewCell, for: indexPath) as! GroceryItemTableViewCell
cell.amoutLabel.text = indexPath.item % 2 == 0 ? "50 g" : "500 ml"
cell.itemLabel.text = indexPath.item % 2 == 0 ? "Cheese" : "Milk"
cell.selectionStyle = .none
return cell
}
else {
let cell = tableView.dequeueReusableCell(withIdentifier: cookingStepTableViewCell, for: indexPath) as! CookingStepTableViewCell
cell.cookingStepDescription.text = indexPath.item % 2 == 0 ? "Test 123..." : "Test 321..."
cell.selectionStyle = .none
cell.delegate = self
return cell
}
}
And this is my Button addTarget Function, which is delegated from the TableViewCell Class to the actual ViewController Class:
func cookingStepDone(description: String, isDone: Bool) {
// if isDone == true
// label textcolor is gray + strikethrough
// if isDone == false
// no change...
}
I want that cell.cookingStepDescription label is changed if "isDone" is true (= click on the checkbox)
Assuming that the button outlet is taken in cell class. so declare a action method in the cellForRowAtIndexpath i.e like this.
cell.yourDoneBtn?.addTarget(self, action: #selector(self.cookingStepDone), for: .touchUpInside)
Now in your action function:
#objc func cookingStepDone(sender: UIButton)
{
let location = self.yourTableViewName?.convert(sender.bounds.origin, from:sender)
let indexPath = self.yourTableViewName?.indexPathForRow(at: location!)
if let cell = self.yourTableViewName.cellForRow(at: indexPath!) as? yourTableViewCell // i.e groceryTableViewCell or CookingStepTableViewCell
{
if isDone == true
{
// Set your cell label textcolor to gray + strikethrough
}
else
{
// no change
}
}
DispatchQueue.main.async
{
self.yourTableView.reloadData() // reload your table view
}
}
Set your bool value where ever needed.
You can do this using below approach
define an Array, in you cookingStepDone method add indexPath to the array and if indexPath already in Array remove it and reload the tableView. and in cellForRowAtIndexpathmethod, check if the Array contains the indexPath. if contains make text strikeThrough else make normal.
What if you create a new class whose superclass would be UITableViewCell and inside that class you add in your #IBOutlets (UIButton and UILabel) and an #IBAction (buttonWasTapped)?
Something Like:
class RecipeTableViewCell: UITableViewCell {
#IBOutlet var myButton : UIButton!
#IBOutlet var myLabel : UILabel!
#IBAction func didTouchButton(sender : UIButton)
{
myLabel.textColor = UIColor.green;
}
}
Checkout this code : RecipeTableViewCell
class RecipeTableViewCell: UITableViewCell {
#IBOutlet var myButton : UIButton!
#IBOutlet var myLabel : UILabel!
var buttonClick : (() -> Void)? = nil
override func awakeFromNib() {
myButton.addTarget(self, action: #selector(didTouchButton(sender:)), for: .touchUpInside)
}
#IBAction func didTouchButton(sender : UIButton)
{
if let action = buttonClick {
action()
}
}
}
In cellForRowAt
let cell = tableView.dequeueReusableCell...
// Your code ...
cell.buttonClick = {
//access your label and data from here
cell.yourLbl.text = yourModel[indexPath.row].text
}
Related
Lets say I have 10 buttons in a custom UITableViewCell. How do I identify which button is tapped and perform the respective action back in ViewController which holds the cell? I am looking for a optimistic solution in swift. Thank you
//Put this code in your UITableViewDataSource: cellForRowAt
//Cell must contains these buttons on which you need add do addTarget
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "currentTableViewCell", for: indexPath)
as! CurrentTableViewCell
cell.btn1.tag = 1
cell.btn1.addTarget(self, action: #selector(buttonPressed(sender:)), for: .touchUpInside)
cell.btn2.tag = 2
cell.btn2.addTarget(self, action: #selector(buttonPressed(sender:)), for: .touchUpInside)
cell.btn3.tag = 3
cell.btn3.addTarget(self, action: #selector(buttonPressed(sender:)), for: .touchUpInside)
return cell
}
#objc func buttonPressed(sender: UIButton) {
let convertedPointInTable = sender.convert(CGPoint.zero, to:self.currentTableView)
let retriveIndexPath = self.currentTableView.indexPathForRow(at: convertedPointInTable)
print("In which cell \(retriveIndexPath!.row), which button pressed \(sender.tag)")
}
Cell code
final class MyCell: UITableViewCell {
struct ConfiguringData {
let action1: () -> Void
let action2: () -> Void
}
#IBOutlet private weak var button1: UIButton!
#IBOutlet private weak var button2: UIButton!
private var didTapButton1Action: (() -> Void)?
private var didTapButton2Action: (() -> Void)?
#IBAction private func didTapButton1() {
didTapButton1Action?()
}
#IBAction private func didTapButton2() {
didTapButton2Action?()
}
func configure(with configuringData: ConfiguringData) {
didTapButton1Action = configuringData.action1
didTapButton2Action = configuringData.action2
}
}
ViewController code
class MyViewController: UIViewController {
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let myCell = tableView.dequeueReusableCell(withIdentifier: "MyCell") as! MyCell
let action1 = { print("didTapButton1") }
let action2 = { print("didTapButton2") }
myCell.configure(
with: MyCell.ConfiguringData(action1: action1, action2: action2)
)
return myCell
}
}
**There two ways to do that =:
First you can make collection of IB button outlets and define tag.
Second One is same but instead of making collection of outlets, go to your storyboard and on click button, you will see tag option there, for each button give different tag(suppose if you have 10 button give tag 1 to 10)
Since you are doing it under custom cell, you can either do above things inside UITableViewCell class or you can preform target under cellForRowAt also, both will work fine
// Now inside your button action do this -:
if sender.tag == 1{
print("one")
}
if sender.tag == 2{
print("two")
}
//OR (if inside cellForRowAt)
cell.button.addTarget(self, action:#selector(handleRegister), for: .touchUpInside)
*so on...
//Make sure sender type in IBAction must be UIButton
// you can also put this under switch cases, just basic programming*
I am trying to manage two buttons in same custom tableview cell.
Added two buttons named Yes and No. If yes button is selected the No button will be inactive and Yes button became active.
Here is the image what I need
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "tableCell") as! TableViewCell
cell.yesButton.tag = 101
cell.noButton.tag = 102
cell.yesButton.addTarget(self, action: #selector(buttonClicked(sender:)), for: UIControl.Event.touchUpInside)
cell.noButton.addTarget(self, action: #selector(buttonClicked(sender:)), for: UIControl.Event.touchUpInside)
return cell
}
#objc func buttonClicked(sender: AnyObject) {
let buttonPosition = (sender as AnyObject).convert(CGPoint.zero, to: tableList)
let indexPath = tableList.indexPathForRow(at: buttonPosition)
if sender.tag == 101 {
if indexPath != nil {
print("Cell indexpath = \(String(describing: indexPath?.row))")
}
}
if sender.tag == 102 {
if indexPath != nil {
print("Cell indexpath = \(String(describing: indexPath?.row))")
}
}
}
Create a model to main the state of yesButton and noButton for each tableViewCell, i.e.
class Model {
var isYesSelected = false
var isNoSelected = false
}
Create a custom UITableViewCell with Outlets of yesButton and noButton.
Create a single #IBAction for both the buttons and handle their UI based on which button is tapped.
Also, use a buttonTapHandler to identify the row in which the button is tapped. It will be called everytime a button is tapped. We'll be setting this when creating the instance of TableViewCell in tableView(_:cellForRowAt:).
class TableViewCell: UITableViewCell {
#IBOutlet weak var yesButton: UIButton!
#IBOutlet weak var noButton: UIButton!
var buttonTapHandler: (()->())?
var model: Model?
override func prepareForReuse() {
super.prepareForReuse()
yesButton.backgroundColor = .gray
noButton.backgroundColor = .gray
}
func configure(with model: Model) {
self.model = model
self.updateUI()
}
#IBAction func onTapButton(_ sender: UIButton) {
model?.isYesSelected = (sender == yesButton)
model?.isNoSelected = !(sender == yesButton)
self.updateUI()
}
func updateUI() {
yesButton.backgroundColor = (model?.isYesSelected ?? false) ? .green : .gray
noButton.backgroundColor = (model?.isNoSelected ?? false) ? .green : .gray
}
}
UITableViewDataSource's tableView(_:cellForRowAt:) method goes like,
let numberOfCells = 10
var models = [Model]()
override func viewDidLoad() {
super.viewDidLoad()
(0..<numberOfCells).forEach { _ in
self.models.append(Model())
}
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return numberOfCells
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "tableCell", for: indexPath) as! TableViewCell
cell.configure(with: models[indexPath.row])
cell.buttonTapHandler = {
print(indexPath.row)
}
return cell
}
To get the totalPoints, count the models with isYesSelected = true, i.e.
let totalPoints = models.reduce(0) { (result, model) -> Int in
if model.isYesSelected {
return result + 1
}
return 0
}
print(totalPoints)
Get that Button using your Tag like below and after that, you can change the value as per you want.
var tmpButton = self.view.viewWithTag(tmpTag) as? UIButton
Simple 3 step process...!!
Define Model Class
Prepare tableView Cell & handle actions
Set up tableView in view controller
Let's start implementation:
1) Define Model Class
In UI, we have a information like question & it's answer (Yes/No). So design model respectively.
//MARK:- Class Declaration -
class Question {
let questionText: String
var answerState: Bool?
init(question: String) {
self.questionText = question
}
}
2. Prepare tableView Cell & handle actions
Create a custom tableView cell with Question Label, Yes Button & No Button. Link that view with respected #IBOutlets & #IBActions.
import UIKit
class TableViewCell: UITableViewCell {
#IBOutlet weak var questionLabel: UILabel!
#IBOutlet weak var yesButton: UIButton!
#IBOutlet weak var noButton: UIButton!
var question: Question?
var toggle: Bool? {
didSet {
question?.answerState = toggle
//Do buttons operations like...
if let isToggle = toggle {
yesButton.backgroundColor = isToggle ? .green : .gray
noButton.backgroundColor = isToggle ? .gray : .green
} else {
yesButton.backgroundColor = .gray
noButton.backgroundColor = .gray
}
}
}
func prepareView(forQuestion question: Question) {
self.question = question
questionLabel.text = question.questionText
toggle = question.answerState
}
//Yes Button - IBAction Method
#IBAction func yesButtonTapped(_ sender: UIButton) {
toggle = true
}
//No Button - IBAction Method
#IBAction func noButtonTapped(_ sender: UIButton) {
toggle = false
}
}
3. Set up tableView in view controller
class ViewController: UIViewController {
//Prepare questions model array to design our tableView data source
let arrQuestions: [Question] = [Question(question: "Do you speak English?"), Question(question: "Do you live in Chicago?")]
}
//MARK:- UITableView Data Source & Delegate Methods -
extension ViewController: UITableViewDataSource, UITableViewDelegate {
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return arrQuestions.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
guard let tableViewCell = tableView.dequeueReusableCell(withIdentifier: "TableViewCell") as? TableViewCell else {
return UITableViewCell()
}
tableViewCell.prepareView(forQuestion: arrQuestions[indexPath.row])
return tableViewCell
}
func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
return 80.0
}
}
Create basic tableView and configure dataSource functions
Create tableView cell with two buttons
Create cell class with buttons outlets and actions
Result of this code
Enjoy!
I have a tableview with one textfield in each cell. I added a target like this:
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "customLevelCell") as! LevelTableViewCell
cell.cellTextField.addTarget(self, action: #selector(ViewController.TextfieldEditAction), for: .editingDidEnd)
return cell
}
But found out that I'm not able to use the indexpath.row / sender.tag to get the specific textfield text
#objc func TextfieldEditAction(sender: UIButton) {
}
So my question is how can I get the text after the user has edited one of the textfields.
Also how can i get the indexpath.row or sender.tag which will be used to collect the text they added to that specific textfield.
The easiest way to handle this is probably to use a delegate protocol…
In your cell
protocol LevelTableViewCellDelegate: class {
func levelTableViewCell(_ levelTableViewCell: LevelTableViewCell, didEndEditingWithText: String?)
}
class LevelTableViewCell: UITableViewCell {
#IBOutlet private weak var cellTextField: UITextField!
var delegate: LevelTableViewCellDelegate?
override func awakeFromNib() {
cellTextField.addTarget(self, action: #selector(didEndEditing(_:)), for: .editingDidEnd)
}
#objc func didEndEditing(_ sender: UITextField) {
delegate?.levelTableViewCell(self, didEndEditingWithText: sender.text)
}
}
In your view controller
class TableViewController: UITableViewController {
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "LevelTableViewCell") as! LevelTableViewCell
cell.delegate = self
return cell
}
}
extension TableViewController: LevelTableViewCellDelegate {
func levelTableViewCell(_ levelTableViewCell: LevelTableViewCell, didEndEditingWithText: String?) {
let indexPath = tableView.indexPath(for: levelTableViewCell)
// Now you have the cell, indexPath AND the string
}
Also, note that the view outlet is be private. You'll find that you write cleaner code if you follow this rule
Following is the extension of UIView that can be used to get the cell or indexPath of the cell enclosing textField
extension UIView {
var tableViewCell : UITableViewCell? {
var subviewClass = self
while !(subviewClass is UITableViewCell){
guard let view = subviewClass.superview else { return nil }
subviewClass = view
}
return subviewClass as? UITableViewCell
}
func tableViewIndexPath(_ tableView: UITableView) -> IndexPath? {
if let cell = self.tableViewCell {
return tableView.indexPath(for: cell)
}
return nil
}
}
Example :-
#objc func TextfieldEditAction(sender: UITextField) {
//replace tableView with the name of your tableView
guard let indexPath = sender.tableViewIndexPath(tableView) else {return}
}
I have a function inside a protocol that takes a TableViewcell as an argument.
protocol GoingButtonDelegate {
func goingButtonPressed(cell: TableViewCell)
}
class TableViewCell: UITableViewCell {
// Outlets
#IBOutlet weak var goingButton: UIButton!
var delegate: GoingButtonDelegate?
#IBAction func goingButtonTapped(_ sender: Any) {
delegate?.goingButtonPressed(cell: self)
}
I then go over to my ViewController and implement the delegate and it's function, which is to change the image of a button when tapped. The "goingSelected" is a green image and the "goingDeselected" is a red image.
This all works out fine, when tapped the button of a cell goes from red to green and vice versa. However, when the cell gets reused, the button state of the cell persists and gets reused for the new row that enters view. Is there any way to stop this from happening?
extension ViewController: GoingButtonDelegate {
func goingButtonPressed(cell: TableViewCell) {
cell.goingButton.isSelected = !cell.goingButton.isSelected
if cell.goingButton.isSelected == true {
cell.goingButton.setImage(UIImage(named: "goingSelected"), for: UIControlState.selected)
} else if cell.goingButton.isSelected == false {
cell.goingButton.setImage(UIImage(named: "goingDeselected"), for: UIControlState.normal)
}
}
}
It's possible
just replace
let cell = tableView.dequeueReusableCell(withIdentifier: identifier,
for: indexPath)
with:
let cell= Bundle.main.loadNibNamed(identifier, owner: self, options: nil)?[0]
but I think you need to change your app logic.
Set Images inside of your cell class
class TableViewCell: UITableViewCell {
override func awakeFromNib() {
super.awakeFromNib()
self.goingButton.setImage(UIImage(named: "goingDeselected"), for:.normal)
self.goingButton.setImage(UIImage(named: "goingSelected"), for:.selected)
}
}
and in method goingButtonPressed(cell: TableViewCell) change cell to your object
and just set Bool type true or false
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
...
cell.goingButton.isSelected = object.isSelected
...
}
You need to store the selected rows in an array of index paths, before that I think you should make few enhancements ... or a lot!!
the cell itself should handle it's button, the controller should just keep track of all cells status.
Add these two properties to your cell
class TableViewCell: UITableViewCell {
var indexPath:IndexPath?
var isSelected : Bool = false {
didSet{
if isSelected {
cell.goingButton.setImage(UIImage(named: "goingSelected"), for: UIControlState.normal)
} else {
cell.goingButton.setImage(UIImage(named: "goingDeselected"), for: UIControlState.normal)
}
}
}
// Outlets
#IBOutlet weak var goingButton: UIButton!
var delegate: GoingButtonDelegate?
#IBAction func goingButtonTapped(_ sender: Any) {
self.isSelected = !self.isSelected
delegate?.goingButtonPressed(cell: self)
}
..
...
}
And store the selected cells in your view controller to keep track of each cell status.
extension ViewController: GoingButtonDelegate {
var selectedCells = NSMutableArray()
func goingButtonPressed(cell: TableViewCell) {
if cell.isSelected {
selectedCells.add(cell.indexPath)
} else {
selectedCells.remove(cell.indexPath)
}
}
}
and in your "cell for row" method just add a small change
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "yourCellIdentifier") as! TableViewCell
cell.indexPath = indexPath
cell.isSelected = selectedCells.contains(indexPath)
..
...
return cell
}
I put stepper both outlets and action into tableview cell and using protocol delegate to connect it to tableview. When i tapped stepper in first row, stepper value appear normaly in first row but its also appear in some random row. how to fix this?
TableViewCell
protocol ReviewCellDelegate{
func stepperButton(sender: ReviewTableViewCell)
}
class ReviewTableViewCell: UITableViewCell {
#IBOutlet weak var countStepper: UIStepper!
#IBOutlet weak var stepperLabel: 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
}
#IBAction func stepperButtonTapped(sender: UIStepper) {
if delegate != nil {
delegate?.stepperButton(self)
stepperLabel.text = "x \(Int(countStepper.value))"
}
}
ViewController
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
let cellIdentifier = "reviewCell"
let cell = tableView.dequeueReusableCellWithIdentifier(cellIdentifier, forIndexPath: indexPath) as! ReviewTableViewCell
var imageView: UIImageView?
let photoG = self.photos[indexPath.row]
imageView = cell.contentView.viewWithTag(1) as? UIImageView
//let layout = cell.goodiesImage
let tag = indexPath.row // +1
cell.tag = tag
photoG.fetchImageWithSize(CGSize(width: 1000, height: 1000), completeBlock: { image, info in
if cell.tag == tag {
imageView?.image = image
cell.goodiesImage.image = image
}
})
func stepperButton(sender: ReviewTableViewCell) {
if let indexPath = tableView.indexPathForCell(sender){
print(indexPath)
}
}
Reset the value of stepper while loading your cell. you can reset the cell property values in cell's prepareForReuse method. add the following method in your ReviewTableViewCell class.
override func prepareForReuse()
{
super.prepareForReuse()
countStepper.value = 0.0
}
In tableViewCell VC:
1 - add these field
var cellDelegate: cellProtocol?
var index: IndexPath?
2 - then add this in the delegate:
func onStepperClick(index: Int, sender: UIStepper)
3 - when you have dragged your stepper over as an action use this:
#IBAction func cellStepper(_ sender: UIStepper) {
cellDelegate?.onStepperClick(index: (index?.row)!, sender: sender)
sender.maximumValue = 1 //for incrementing
sender.minimumValue = -1 //for decrementing
//this will make sense later
}
In ViewController
1 - add these to the tableView function that has the cellAtRow variable.
cell.cellDelegate = self
cell.index = indexPath
2 - Use this instead of your stepperButton function
func onStepperClick(index: Int, sender: UIStepper) {
print(index)
if sender.value == 1.0{
//positive side of stepper was pressed
}else if sender.value == -1.0{
//negative side of stepper was pressed
}
sender.value = 0 //resetting to zero so sender.value produce different values on plus and minus
}
Hope this works for you
As mentioned by #A-Live, your component is being reused and so need to be updated.
So in your view controller:
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
let cellIdentifier = "reviewCell"
let cell = tableView.dequeueReusableCellWithIdentifier(cellIdentifier, forIndexPath: indexPath) as! ReviewTableViewCell
var imageView: UIImageView?
let photoG = self.photos[indexPath.row]
imageView = cell.contentView.viewWithTag(1) as? UIImageView
//let layout = cell.goodiesImage
let tag = indexPath.row // +1
cell.tag = tag
photoG.fetchImageWithSize(CGSize(width: 1000, height: 1000), completeBlock: { image, info in
if cell.tag == tag {
imageView?.image = image
cell.goodiesImage.image = image
}
})
cell.countStepper.value = XXX[indexPath.row].value; //Here you update your view
cell.stepperLabel.text = "x \(Int(cell.countStepper.value))" //And here
And
func stepperButton(sender: ReviewTableViewCell) {
if let indexPath = tableView.indexPathForCell(sender){
print(indexPath)
XXX[sender.tag].value = sender.counterStepper.value //Here you save your updated value
}
NOTE:
1.MY Cell class is just normal..All changes are in viewcontroller class
2.I have taken stepper and over it added ibAddButton with same constraint as ibStepper
class cell: UITableViewCell {
#IBOutlet weak var ibAddButton: UIButton!
#IBOutlet weak var ibStepper: UIStepper!
#IBOutlet weak var ibCount: UILabel!
#IBOutlet weak var ibLbl: UILabel!
}
1.define empty int array [Int]()
var countArray = [Int]()
2.append countArray with all zeros with the number of data u want to populate in tableview
for arr in self.responseArray{
self.countArray.append(0)
}
3.in cell for row at
func tableView(_ tableView: UITableView, cellForRowAt indexPath:
IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "Cell", for: indexPath) as! cell
let dict = responseArray[indexPath.row] as? NSDictionary ?? NSDictionary()
cell.ibLbl.text = dict["name"] as? String ?? String()
if countArray[indexPath.row] == 0{
cell.ibAddButton.tag = indexPath.row
cell.ibStepper.isHidden = true
cell.ibAddButton.isHidden = false
cell.ibCount.isHidden = true
cell.ibAddButton.addTarget(self, action: #selector(addPressed(sender:)), for: .touchUpInside)
}else{
cell.ibAddButton.isHidden = true
cell.ibStepper.isHidden = false
cell.ibStepper.tag = indexPath.row
cell.ibCount.isHidden = false
cell.ibCount.text = "\(countArray[indexPath.row])"
cell.ibStepper.addTarget(self, action: #selector(stepperValueChanged(sender:)), for: .valueChanged)}
return cell
}
4.objc functions
#objc func stepperValueChanged(sender : UIStepper){
if sender.stepValue != 0{
countArray[sender.tag] = Int(sender.value)
}
ibTableView.reloadData()
}
#objc func addPressed(sender : UIButton){
countArray[sender.tag] = 1//countArray[sender.tag] + 1
ibTableView.reloadData()
}