How to make DetailView change data by indexPath - ios

I'm currently working on a Master-DetailView application and I'm stuck on how to make the data change....
I saw a great tutorial on how to do this :
Tutorial
But the guy is using a blank ViewController & I'm using a TableViewController With static Cells,So it doesn't work.
I want to put the data manually like
var Label1Data = ["You Tapped Cell 1,You Tapped Cell 2,You Tapped Cell 3"]
and it will show in the DetailView by the index path if i pressed the first cell the first data will show up in that Label...i know its not ideal to use static cells here but i do wanna use them design wise.
It will be great if any one could show me finally how can i put the data successfully like i said above and how the Tutorial does it.
MasterViewController Code:
import UIKit
import AVFoundation
class BarsViewController: UITableViewController,UISearchResultsUpdating,UISearchBarDelegate,UISearchDisplayDelegate,UITabBarControllerDelegate{
#IBOutlet var tableViewController: UITableView!
var audioPlayer = AVAudioPlayer()
var sel_val : String?
// TableView Data :
struct User {
var name: String
var streetName: String
var image: UIImage?
}
var allUsers: [User]!
var filteredUsers: [User]!
func createUsers(names: [String], streets: [String], images: [UIImage?]) -> [User] {
var users = [User]()
guard names.count == streets.count && names.count == images.count else { return users }
for (index, name) in names.enumerated() {
let user = User(name: name, streetName: streets[index], image: images[index])
users.append(user)
}
return users
}
override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
if tableView == self.tableView {
return self.names.count
} else {
return self.filteredUsers.count
}
}
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell{
let cell = self.tableView.dequeueReusableCell(withIdentifier: "CustomCell", for: indexPath) as! CustomCell
let user:User!
if tableView == self.tableView {
user = allUsers[indexPath.row]
} else {
user = filteredUsers[indexPath.row]
}
cell.photo.image = user.image
cell.name.text = user.name
cell.streetName.text = user.streetName
return cell
}
override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath){
let object = self.storyboard?.instantiateViewController(withIdentifier: "BarProfileTableViewController") as! BarsProfile
let user:User!
if tableView == self.tableView {
user = allUsers[indexPath.row]
} else {
user = filteredUsers[indexPath.row]
}
print("username : \(user.name)")
print("streetName : \(user.streetName)")
MyIndex = indexPath.row
object.barImage = user.image!
object.barName = user.name
object.streetName = user.streetName
self.navigationController?.pushViewController(object, animated: true)
}
DetailView's Code:
import UIKit
import AVFoundation
import MapKit
class BarsProfile: UITableViewController,MKMapViewDelegate {
#IBOutlet var Distance: UILabel!
#IBOutlet var headerImage: UIImageView!
#IBOutlet var OnlineMenu: UIButton!
#IBOutlet var Address: UILabel!
#IBOutlet var ProfileMapView: MKMapView!
#IBOutlet var BarNameLBL: UILabel!
#IBOutlet var streetNameLBL: UILabel!
#IBOutlet var MusicLabel: UILabel!
#IBOutlet var KindOfBarCell: UITableViewCell!
var barName = String()
var barImage = UIImage()
var streetName = String()
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(true)
BarNameLBL.text = barName
streetNameLBL.text = streetName
navigationItem.title = barName
}
How it looks like : ( Red line is a label i would like to put data manually in)

you cant use a TableViewController for your purpose. Instead you can use a normal ViewController with labels and textfields.
In the above picture of yours, you can use a simple label of width = 1 and color = lightGrey so that you can get the same separator line as in the tableview.

Related

Table View Cell has no Initialiser

I am trying to display table view cell property into different table view cell when button I clicked . I am using story board . I added the Horizontal and vertical stack to contains the image and label properties . I want to display this property into another table view cell when user clicked the show button . In cellFor row function i defined the button action property . I am getting following error .Class 'DetailsViewCell' has no initializers. Cannot use instance member 'mc' within property initializer; property initializers run before 'self' is available
Here is the screenshot of the both view controller .
Here is the code .
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
// guard let cell = tableView.dequeueReusableCell(withIdentifier: MovieCell.identifier, for: indexPath) as? MovieCell
// else { return UITableViewCell() }
let cell = tableView.dequeueReusableCell(withIdentifier: MovieViewCell.identifier, for: indexPath) as! MovieViewCell
cell.showButton.tag = indexPath.row
cell.showButton.addTarget(self, action: Selector("movieDetails"), for: .touchUpInside)
let row = indexPath.row
let title = presenter.getTitle(by: row)
let overview = presenter.getOverview(by: row)
let data = presenter.getImageData(by: row)
cell.configureCell(title: title, overview: overview, data: data)
return cell
}
}
Here is the code in identifier class with table view cell.
class MovieViewCell: UITableViewCell {
static let identifier = "MovieViewCell"
#IBOutlet weak var mainStackView: UIStackView!
#IBOutlet weak var movieImage: UIImageView!
#IBOutlet weak var movieTtile: UILabel!
#IBOutlet weak var movieOverview: UILabel!
#IBOutlet weak var showButton: UIButton!
#IBAction func movieDetails(_ sender: UIButton) {
var dc : DetailsViewCell
movieTtile = dc.movieTitle
movieOverview = dc.movieOverview
movieImage = dc.movieImage
}
func configureCell(title: String?, overview: String?, data: Data?) {
movieTtile.text = title
movieOverview.text = overview
if let imageData = data{
movieImage.image = UIImage(data: imageData)
}
}
}
Here is the code for Details view cell.
class DetailsViewCell: UITableViewCell {
#IBOutlet weak var movieTitle: UILabel!
#IBOutlet weak var movieOverview: UILabel!
#IBOutlet weak var movieImage: UIImageView!
var mc : MovieViewCell
movieTitle = mc.movieTtile
movieOverview = mc.movieOverview
movieImage = mc.movieImage
}
import UIKit
var loginData = ["", "", ""]
class LoginDataCell: UITableViewCell, UITextFieldDelegate {
#IBOutlet weak var txtLoginData: 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
}
func textFieldDidEndEditing(_ textField: UITextField) {
if textField.tag == 0 {
loginData[0] = textField.text
} else if textField.tag == 1 {
loginData[1] = textField.text
} else if textField.tag == 2 {
loginData[2] = textField.text
}
}
}

Having multiple buttons in cell that pass selected buttons set data to cell

I have three buttons in my cell that have a price and weight label, what im trying to do is have the selected optionBtn pass the weight and price data to the CartVC
the code that I currently have in the in the CartCell does not yet post the data for the selected optionBtn's weight and price labels
the function func configure that I have set in the CartCell works in presenting data in the cells for the CartVC
Where the cart does show the name, category, & image when the atcBtn is pressed to pass the data to the CartVC
What I want is to show the selected optionBtn price and weight (when selected) in the the CartVC cells how would I be able to modify the code I have set for the optionBtns in the func
import UIKit
import SDWebImage
import Firebase
class Cell: UITableViewCell {
weak var items: Items!
#IBOutlet weak var name: UILabel!
#IBOutlet weak var category: UILabel!
#IBOutlet weak var productImage: UIImageView!
#IBOutlet weak var weightOne: UILabel!
#IBOutlet weak var weightTwo: UILabel!
#IBOutlet weak var weightThree: UILabel!
#IBOutlet weak var priceOne: UILabel!
#IBOutlet weak var priceTwo: UILabel!
#IBOutlet weak var priceThree: UILabel!
#IBOutlet weak var addToCart: RoundButton!
#IBOutlet weak var optionBtn1: RoundButton!
#IBOutlet weak var optionBtn2: RoundButton!
#IBOutlet weak var optionBtn3: RoundButton!
var addActionHandler: (() -> Void)?
func configure(withItems items: Items) {
name.text = items.name
category.text = items.category
image.sd_setImage(with: URL(string: items.image))
priceOne.text = items.price1
priceTwo.text = items.price2
priceThree.text = items.price3
weightOne.text = items.weight1
weightTwo.text = items.weight2
weightThree.text = items.weight3
}
#IBAction func atcBtn(_ sender: UIButton) {
self.addActionHandler?()
}
}
import UIKit
import Firebase
import FirebaseFirestore
class ViewController: UITableViewController {
#IBOutlet weak var cartButton: BarButtonItem!!
#IBOutlet weak var tableView: UITableView!
var itemSetup: [Items] = []
override func viewDidLoad() {
super.viewDidLoad()
}
func numberOfSections(in tableView: UITableView) -> Int {
return 1
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return itemSetup.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
guard let cell = tableView.dequeueReusableCell(withIdentifier: "Cell") as? Cell else { return UITableViewCell() }
let item = itemSetup[indexPath.row]
cell.configure(withItem: item)
cell.addActionHandler = {
Cart.currentCart.items.append(item)
}
return cell
}
}
class CartViewController: UIViewController {
var items: Items!
#IBOutlet weak var cartTableView: UITableView!
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
cartTableView.dataSource = self
cartTableView.delegate = self
}
}
extension CartViewController: UITableViewDataSource, UITableViewDelegate {
func numberOfSections(in tableView: UITableView) -> Int {
return 1
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return Cart.currentCart.cartItems.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "CartCell", for: indexPath) as! CartCell
let cart = Tray.currentCart.cartItems[indexPath.row]
cell.configure(withItems: cart)
return cell
}
}
class CartCell: UITableViewCell {
var selctedBtn: Cell?
#IBOutlet weak var lblMealName: UILabel!
#IBOutlet weak var imageUrl: UIImageView!
#IBOutlet weak var lblSubTotal: UILabel!
#IBOutlet weak var lblWeight: UILabel!
override func awakeFromNib() {
super.awakeFromNib()
// Initialization code
}
var lastSelectedButton = UIButton()
func configure(withItems items: Items) {
// lblWeight.text = "\(items.weight1)"
// lblSubTotal.text = "$\(formatter.string(for: items.price1)!)"
lblMealName.text = "\(items.category): \(items.name)"
let formatter = NumberFormatter()
formatter.maximumFractionDigits = 2
formatter.numberStyle = .decimal
imageUrl.sd_setImage(with: URL(string: items.imageUrl))
// optionBtns I dont know how to set the code to where I can individual
// select a btn to pass the data to the cell
if selctedBtn?.optionBtn1.isSelected == true {
lblSubTotal.text = "$\(formatter.string(for: items.price1)!)"
lblWeight.text = "\(items.weight1)"
} else if selctedBtn?.optionBtn2.isSelected == true {
lblSubTotal.text = "$\(formatter.string(for: items.price2)!)"
lblWeight.text = "\(items.weight2)"
} else if selctedBtn?.optionBtn3.isSelected == true {
lblSubTotal.text = "$\(formatter.string(for: items.price3)!)"
lblWeight.text = "\(items.weight3)"
}
// or this
switch lastSelectedButton {
case selctedBtn!.optionBtn1:
isSelected = true
lblSubTotal.text = "$\(formatter.string(for: items.price1)!)"
lblWeight.text = "\(items.weight1)"
case selctedBtn!.optionBtn2:
isSelected = true
lblSubTotal.text = "$\(formatter.string(for: items.price2)!)"
lblWeight.text = "\(items.weight2)"
case selctedBtn!.optionBtn3:
isSelected = true
lblSubTotal.text = "$\(formatter.string(for: items.price3)!)"
lblWeight.text = "\(items.weight3)"
default:
break
}
}
// still running tests to make this work just can't seem to have the selected buttons data pass to the Cart Cells
}
Update:
just added some code that I have been testing still no luck in how to pass the label to the cart after the option button is selected
You can pass back values in closures.
So, in your Cell class (naming is confusing to discuss - make it something like SelectItemCell), you could change your closure var to:
var addActionHandler: ((Int) -> Void)?
Then, in your addToCart button action, something along these lines:
#IBAction func atcBtn(_ sender: UIButton) {
// pass back the user selected values
var i = 0
switch lastSelectedButton {
case optionBtn1:
i = 1
case optionBtn2:
i = 2
default:
i = 3
}
self.addActionHandler?(i)
}
That's rather awkward, and presumably you will be tracking actual values, but for example purposes this will work.
Now, in your VC that holds that table, in cellForRowAt, instead of your current:
cell.addActionHandler = {
Cart.currentCart.items.append(item)
}
assign the closure like this:
cell.addActionHandler = { (option: Int) in
print("Option selected = \(option)")
// do something based on the option that was selected
// maybe item.selectedOption = option
Cart.currentCart.items.append(item)
}
If you want to pass back more than one value, add parameters:
var addActionHandler: ((Int, Int) -> Void)?
and in your button action:
self.addActionHandler?(priceVal, weightVal)
and your closure becomes:
cell.addActionHandler = { (price: Int, weight: Int) in
// use price and weight vars
// ...
}
Edit
If you don't already have a .selectedOption property of your Items class, you should add one (of type Int). You can use that to track the user's selection.
Change your cellForRowAt func along these lines:
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
guard let cell = tableView.dequeueReusableCell(withIdentifier: "Cell") as? Cell else { return UITableViewCell() }
// use var to make item mutable
var item = itemSetup[indexPath.row]
// pass item to cell to configure labels / buttons / etc
cell.configure(withItem: item)
// when the "add to cart" button in the cell is tapped
cell.addActionHandler = { (option: Int) in
// option will be 1, 2 or 3, indicating which button the user tapped
print("Option selected = \(option)")
// update the .selected property of your data
item.selectedOption = option
Cart.currentCart.items.append(item)
}
return cell
}
Now, in your CartCell in your CartViewController, you can fill in the labels like this:
if items.selectedOption == 1 {
lblSubTotal.text = "$\(formatter.string(for: items.price1)!)"
lblWeight.text = "\(items.weight1)"
} else if items.selectedOption == 2 {
lblSubTotal.text = "$\(formatter.string(for: items.price2)!)"
lblWeight.text = "\(items.weight2)"
} else if items.selectedOption == 3 {
lblSubTotal.text = "$\(formatter.string(for: items.price3)!)"
lblWeight.text = "\(items.weight3)"
}

how to pass data from one Tableview to another Tableview when button is pressed in cell?

Im trying to pass data from the ViewController to my CartViewController. The cells in the ViewController have 3 buttons(optionBtns) that have a price and weight label above each of them.
What Im trying to do is have the optionBtn selected pass the label data above it once the ATC button is pressed
the ATC button in the cell passes the data of image, name, category, and optionBtn data to the CartViewController cells(CartCell)
how would I be able to pass selected data to the CartVC when the ATC is pressed to present selected item Name, Image, and Category in cell with selected optionBtn data(Price & Weight)
I am also using Cloud Firestore to post data to populate my VC cells
class Cell: UITableViewCell {
weak var items: Items!
#IBOutlet weak var name: UILabel!
#IBOutlet weak var category: UILabel!
#IBOutlet weak var productImage: UIImageView!
#IBOutlet weak var weightOne: UILabel!
#IBOutlet weak var weightTwo: UILabel!
#IBOutlet weak var weightThree: UILabel!
#IBOutlet weak var priceOne: UILabel!
#IBOutlet weak var priceTwo: UILabel!
#IBOutlet weak var priceThree: UILabel!
#IBOutlet weak var addToCart: RoundButton!
#IBOutlet weak var optionBtn1: RoundButton!
#IBOutlet weak var optionBtn2: RoundButton!
#IBOutlet weak var optionBtn3: RoundButton!
var addActionHandler: (() -> Void)?
func configure(withItems items: Items) {
name.text = items.name
category.text = items.category
image.sd_setImage(with: URL(string: items.image))
priceOne.text = items.price1
priceTwo.text = items.price2
priceThree.text = items.price3
weightOne.text = items.weight1
weightTwo.text = items.weight2
weightThree.text = items.weight3
self.items = items
}
var lastSelectedButton = UIButton()
#IBAction func cartTypeSelected(_ sender: RoundButton) {
lastSelectedButton.isSelected = false; do {
self.lastSelectedButton.backgroundColor = UIColor.blue
lastSelectedButton = sender
sender.isSelected = true; do {
self.lastSelectedButton.backgroundColor = UIColor.lightGreen
}
}
#IBAction func atcBtn(_ sender: UIButton) {
self.addActionHandler?()
}
}
class CartViewController: UIViewController {
var items: Items!
#IBOutlet weak var cartTableView: UITableView!
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
cartTableView.dataSource = self
cartTableView.delegate = self
}
}
extension CartViewController: UITableViewDataSource, UITableViewDelegate {
func numberOfSections(in tableView: UITableView) -> Int {
return 1
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return Cart.currentCart.cartItems.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "CartCell", for: indexPath) as! CartCell
let cart = Tray.currentCart.cartItems[indexPath.row]
cell.configure(withItems: cart)
return cell
}
}
class CartCell: UITableViewCell {
var selctedBtn: Cell?
#IBOutlet weak var lblMealName: UILabel!
#IBOutlet weak var imageUrl: UIImageView!
#IBOutlet weak var lblSubTotal: UILabel!
#IBOutlet weak var lblWeight: UILabel!
override func awakeFromNib() {
super.awakeFromNib()
// Initialization code
}
func configure(withItems items: Items) {
// lblWeight.text = "\(items.weight1)"
lblMealName.text = "\(items.category): \(items.name)"
let formatter = NumberFormatter()
formatter.maximumFractionDigits = 2
formatter.numberStyle = .decimal
// lblSubTotal.text = "$\(formatter.string(for: items.price1)!)"
imageUrl.sd_setImage(with: URL(string: items.imageUrl))
if selctedBtn?.optionBtn1.isSelected == true {
lblSubTotal.text = "$\(formatter.string(for: items.price1)!)"
lblWeight.text = "\(items.weight1)"
} else if selctedBtn?.optionBtn2.isSelected == true {
lblSubTotal.text = "$\(formatter.string(for: items.price2)!)"
lblWeight.text = "\(items.weight2)"
} else if selctedBtn?.optionBtn3.isSelected == true {
lblSubTotal.text = "$\(formatter.string(for: items.price3)!)"
lblWeight.text = "\(items.weight3)"
}
}
}
class Cart {
static let currentCart = Cart()
var cartItems = [Items]()
}
If the idea is for firebase to handle all of your data then the data should go through firebase and not through the viewController. ie your Firebase db should have an items collection (or perhaps one per store) and your user should have a cart collection. When the use taps the add to cart button you add the item in question to that users cart collection in firebase then show the cartViewController. The cartViewController should subscribe to the cart collection on the current user and then populate its tableview from that firebase collection.
TLDR the typical design of a firebase app is that the firebase DB is the source of truth for the app, so you should write all changes to firebase and then simply observe these collections elsewhere in the app. This also insures that if the user edits the cart on another device that it will update itself on the iOS device with the new cart items.
You can pass the values in closures.
So, in your Cell class you could change your closure var to:
var addActionHandler: ((Int) -> Void)?
Then, in your addToCart button action, something along these lines:
#IBAction func atcBtn(_ sender: UIButton) {
// pass back the user selected values
var i = 0
switch lastSelectedButton {
case optionBtn1:
i = 1
case optionBtn2:
i = 2
default:
i = 3
}
self.addActionHandler?(i)
}
Create a .selectedOption property of your Items class, you should add one (of type Int). You can use that to track the user's selection.
Modify cellForAt in Cell:
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
guard let cell = tableView.dequeueReusableCell(withIdentifier: "Cell") as? Cell else { return UITableViewCell() }
// use var to make item mutable
var item = itemSetup[indexPath.row]
cell.configure(withItem: item)
cell.addActionHandler = { (option: Int) in
print("Option selected = \(option)")
item.selectedOption = option
Cart.currentCart.items.append(item)
}
return cell
}
In your CartCell you can make the labels like this:
if items.selectedOption == 1 {
lblSubTotal.text = "$\(formatter.string(for: items.price1)!)"
lblWeight.text = "\(items.weight1)"
} else if items.selectedOption == 2 {
lblSubTotal.text = "$\(formatter.string(for: items.price2)!)"
lblWeight.text = "\(items.weight2)"
} else if items.selectedOption == 3 {
lblSubTotal.text = "$\(formatter.string(for: items.price3)!)"
lblWeight.text = "\(items.weight3)"
}

How to access values in UIViewController class from TableCell class in Swift?

So, I have a UIViewController(PledgeViewController) with a TableView. When the user clicks on a UIButton(plusBtn) in the UITableViewCell(PledgeTableViewCell) of the TableView, I want to perform a write to my firebase database. But to get the exact path, I need a String(getID) from the PledgeViewController class which is received with a segue from the previous ViewController. With the MVC format that I'm using, how do I access values in the PledgeViewController to write to the database from the PledgeTableViewCell?
My PledgeViewController.swift:
import UIKit
import Foundation
import FirebaseDatabase
import Firebase
class PledgeViewController: UIViewController, UITableViewDataSource, UITableViewDelegate{
var getID: String!
#IBOutlet weak var pledgeAmtLabel: UILabel!
#IBOutlet weak var RewardChooseTable: UITableView!
#IBAction func pledgeBtn(_ sender: Any) {
//get the text from the label and run all the checks to see if the tickets are available
}
let RewardRef = Database.database().reference().child("Rewards")
var rewards = [Rewards]()
func numberOfSections(in tableView: UITableView) -> Int {
return 1
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return rewards.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "TakePledgeCell", for: indexPath) as! PledgeTableViewCell
let reward = rewards[indexPath.row]
cell.reward = reward
return cell
}
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
RewardRef.child(getID).observe(.value, with: { (snapshot) in
self.rewards.removeAll()
for child in snapshot.children {
let childSnapshot = child as! DataSnapshot
let reward = Rewards(snapshot: childSnapshot)
self.rewards.insert(reward, at: 0)
}
self.RewardChooseTable.reloadData()
})
}
override func viewDidLoad() {
super.viewDidLoad()
print("The id received from the SingleViewControl is:" + getID)
}
}
My PledgeTableViewCell.swift:
import UIKit
import Firebase
import FirebaseDatabase
class PledgeTableViewCell: UITableViewCell {
#IBOutlet weak var rewardAmtLabel: UILabel!
#IBOutlet weak var ticketClasslabel: UILabel!
#IBOutlet weak var ticketDescLabel: UILabel!
#IBOutlet weak var ticketCountLabel: UILabel!
#IBOutlet weak var plusBtn: UIButton!
#IBOutlet weak var minusBtn: UIButton!
var ref: DatabaseReference!
var artcallid: Int!
#IBAction func minusBtn(_ sender: Any) {
}
var reward: Rewards! {
didSet {
rewardAmtLabel.text = "Rs. " + String(reward.rewardAmt)
ticketClasslabel.text = reward.reward_class_name
ticketDescLabel.text = reward.reward_desc
print(reward.reward_class_name + " is one of the rewards")
}
}
#IBAction func plusBtn(_ sender: AnyObject) {
}
}
Rewards.swift:
import Foundation
import Firebase
import FirebaseDatabase
class Rewards {
let ref: DatabaseReference!
// let countRef: DatabaseReference!
var rewardAmt: Int!
var rewardsLeft: Int!
var reward_class_name: String = ""
var reward_amt: String = ""
var reward_desc: String = ""
var rewardID: String = ""
var tickUpCount = 0
var tickDownCount = 0
init(text: String) {
ref = Database.database().reference().child("Fund").childByAutoId()
// countRef = Database.database().reference().child("Testing").childByAutoId()
}
init(snapshot: DataSnapshot)
{
ref = snapshot.ref
if let value = snapshot.value as? [String : Any] {
rewardAmt = value["reward_ticket_amount"] as! Int
reward_class_name = value["reward_ticket_amount_class_name"] as! String
reward_amt = value["reward_ticket_amount_txt"] as! String
reward_desc = value["reward_ticket_class_desc"] as! String
rewardsLeft = value["rewards_left"] as! Int
rewardID = snapshot.key
}
}
}
extension Rewards{
func countUp(){
tickUpCount += 1
ref.child("uppingTicket").setValue(tickUpCount)
}
}
You can try with closure
class PledgeTableViewCell: UITableViewCell {
//Define a closure
var closure:(() -> Void)? = nil
#IBAction func plusBtn(_ sender: AnyObject) {
// Do you stuff
closure?()
}
}
class PledgeViewController: UIViewController, UITableViewDataSource, UITableViewDelegate{
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "TakePledgeCell", for: indexPath) as! PledgeTableViewCell
let reward = rewards[indexPath.row]
cell.reward = reward
cell.closure = {
// You will get the callback in this block
// You can define the parameterized closure to return the value
}
return cell
}
You can try to add a new var
class PledgeTableViewCell: UITableViewCell {
var currentID = ""
}
and set it in cellForRowAt
cell.currentID = getID

TableViewCell Multiple Editext value repeated during scrolling

I have tableview with three edittext in each section of cell lies side by side.I want to give input from user interface and after giving all values while i click on Button some mathematical calculation will be done to give result.
But edittext value is getting repeated while scrolling table view.Here is my code snippet.
import UIKit
class Density_Price_Calculation_TableView: UIViewController , UITableViewDelegate , UITableViewDataSource {
#IBOutlet weak var Density_Price_Calculation_TableView: UITableView!
#IBOutlet weak var Gravity: UILabel!
#IBOutlet weak var Price: UILabel!
var phreditText = [String]()
var densityeditText = [String]()
var priceeditText = [String]()
var ArrayOfCell = [Density_Price_Calculation_TableViewCell]()
override func viewDidLoad() {
super.viewDidLoad()
Density_Price_Calculation_TableView.delegate = self
Density_Price_Calculation_TableView.dataSource = self
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return Density_Price_Chemicals_MasterData.instance.getChemical_Names().count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell : Density_Price_Calculation_TableViewCell = tableView.dequeueReusableCell(withIdentifier: "density_price_calculation_cell", for: indexPath) as! Density_Price_Calculation_TableViewCell
let chemical_names = Density_Price_Chemicals_MasterData.instance.getChemical_Names()[indexPath.row]
cell.updateViews(chemical_names: chemical_names)
ArrayOfCell.append(cell)
return cell
}
#IBAction func btn_pressed(_ sender: UIButton) {
var totalSize=0.00, gravity=0.0,price=0.0
for cell in ArrayOfCell
{
totalSize=totalSize + (Double(cell.phreditText.text ?? "") ?? 0)
let tempPhr=Double(cell.phreditText.text ?? "") ?? 0
let tempDen=Double(cell.densityeditText.text ?? "") ?? 0
let tempPrice=Double(cell.priceeditText.text ?? "") ?? 0
if(tempPhr != 0 && tempDen != 0)
{
gravity=gravity + tempPhr/tempDen
}
price = price + (tempPhr*tempPrice)
}
Gravity.text = String (format : "%.3f",(Double(totalSize/gravity)))
Price.text = String (format : "%.3f",(Double(price/totalSize)))
}
}
My TableviewCell Content
import UIKit
class Density_Price_Calculation_TableViewCell: UITableViewCell {
#IBOutlet weak var chemical_name: UILabel!
#IBOutlet weak var phreditText: UITextField!
#IBOutlet weak var densityeditText: UITextField!
#IBOutlet weak var priceeditText: UITextField!
func updateViews(chemical_names:Density_Price_Calculation) {
chemical_name.text = chemical_names.chemical_name
}
override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
// Dismiss the keyboard when the view is tapped on
phreditText.resignFirstResponder()
densityeditText.resignFirstResponder()
priceeditText.resignFirstResponder()
}
}
TableView Each Cell Content Image for referrence
Thanks in Advance.
This could be because you are dequeuing the table view cell in cellForRowAt and maintaining the same in the ArrayOfCell and due to dequeue reference this issue could have occurred.
So try the following changes,
Instead of
let cell : Density_Price_Calculation_TableViewCell = tableView.dequeueReusableCell(withIdentifier: "density_price_calculation_cell", for: indexPath) as! Density_Price_Calculation_TableViewCell
Try using,
let cell = Density_Price_Calculation_TableViewCell(style: .default, reuseIdentifier: "density_price_calculation_cell")
Note*
- This process could be little performance intensive since we are not dequeuing the cell.

Resources