I've seen some answers on Stack about this question but a lot of them are from 5 years ago and using an older version of Swift. I would like to reload the data in the table every time the user hits save so that the appended event will now be added to the table. But no matter what I seem to do nothing is showing up!
I've tried adding table.reloadData() in my save function. But i get an error for:
Thread 1 error, Fatal error: unexpectedly found a nil while unwrapping an optional value.
class ViewController: UIViewController, UITableViewDataSource, UITableViewDelegate {
#IBOutlet weak var txtTitle: UITextField!
#IBOutlet weak var txtLocation: UITextField!
#IBOutlet weak var txtDate: UITextField!
#IBOutlet weak var txtTime: UITextField!
var eventsArray = [Event]()
#IBAction func btnSave() {
let event = Event(tits: txtTitle.text!, locs: txtLocation.text!)
eventsArray.append(event)
table.reloadData()
print(eventsArray)
}
#IBOutlet weak var table: UITableView!
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return eventsArray.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "cell") as! CustomeCell
cell.title.text = eventsArray[indexPath.row].title
cell.location.text = eventsArray[indexPath.row].location
return cell
}
}
Did you set tableView's delegate on viewDidLoad?
table.delegate = self
Related
2 days ago I started developing an APP as a school project with Swift and Storyboard.
Now I've started to use UITableViews and also have Cells design, but somehow they are generated and reduced in size and I don't understand exactly why.
How i designed it:
How it looks:
I wrote these costum subclass for the Cell:
import UIKit
class ContentView: UITableViewCell {
#IBOutlet weak var CellPriority: UILabel!
#IBOutlet weak var FromCell: UILabel!
#IBOutlet weak var CellTime: UILabel!
#IBOutlet weak var CellDesc: UILabel!
#IBOutlet weak var CellTitle: UILabel!
#IBOutlet weak var CellImage: UIImageView!
}
and this is my ViewController.swift
import UIKit
class ViewController: UIViewController, UITableViewDataSource, UITableViewDelegate{
#IBOutlet weak var ContentTable: UITableView!
var ContentArray = [ContentView]()
override func viewDidLoad() {
super.viewDidLoad()
ContentTable.dataSource = self
ContentTable.delegate = self
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 6
}
var titleArray = ["asd", "bsd", "csd", "dsd", "esd", "fsd", "gsd", "hsd", "isd", "jsd", "ksd", "lsd", "msd", "nsd", "osd", "psd", "qsd", "rsd", "ssd", "tsd", "usd", "vsd", "wsd", "xsd", "ysd", "zsd"]
var descArray = ["asd", "bsd", "csd", "dsd", "esd", "fsd", "gsd", "hsd", "isd", "jsd", "ksd", "lsd", "msd", "nsd", "osd", "psd", "qsd", "rsd", "ssd", "tsd", "usd", "vsd", "wsd", "xsd", "ysd", "zsd"]
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = ContentTable.dequeueReusableCell(withIdentifier: "cell", for: indexPath) as! ContentView
let image = UIImage(named:"")
cell.CellImage.image = image
cell.CellTitle.text = titleArray[indexPath.row]
cell.CellDesc.text = descArray[indexPath.row]
cell.CellTime.text = "resultE"
cell.CellPriority.text = "!!!"
cell.FromCell.text = "lol"
return cell
}
}
(I have everything else which is unnecessary, regarding the problem, has been deleted)
(These were things like the "erstellen" button and so on.)
Thank you very much
I have a tableView as a part of Stack View, but it doesn't appears on the screen
Here is the view:
Here I define the cells
class MealViewController: UIViewController, UITextFieldDelegate, UIImagePickerControllerDelegate, UINavigationControllerDelegate,
UITableViewDelegate, UITableViewDataSource{
let imagePickerController = UIImagePickerController()
#IBOutlet weak var nameTextField: UITextField!
#IBOutlet weak var photoImageView: UIImageView!
#IBOutlet weak var ratingControl: RatingControl!
#IBOutlet weak var saveButton: UIBarButtonItem!
#IBOutlet var tableView: UITableView!
let list = ["Milk", "Honey", "Bread", "Tacos", "Tomatoes"]
public func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int
{
return(list.count)
}
public func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell
{
let cell = UITableViewCell(style: UITableViewCell.CellStyle.default, reuseIdentifier: "cell")
cell.textLabel?.text = list[indexPath.row]
return(cell)
}
And also I override the viewDidLoad() method with this:
override func viewDidLoad() {
super.viewDidLoad()
tableView.delegate = self
tableView.dataSource = self
}
The structure of view looks like this:
where Table View itself has the following setting:
I don't get any errors and build is successful, but still I can't see the table on the screen (all other elements are presented), what could be the problem?
I read the other topics, but not solves my problem, I create a tableview and your cells with same value to make tests, but when I execute my project nothing data is showed. I put 5 size of rows to only to test. I don't know why my code not works.
My storyboard:
TableViewCellVenda.swift
class TableViewCellVenda: UITableViewCell {
#IBOutlet weak var cellView: UIView!
#IBOutlet weak var imageCloud: UIImageView!
#IBOutlet weak var labelValorTotal: UILabel!
#IBOutlet weak var labelQtdItens: UILabel!
#IBOutlet weak var labelCliente: UILabel!
#IBOutlet weak var labelDataVenda: UILabel!
override func awakeFromNib() {
super.awakeFromNib()
}
override func setSelected(_ selected: Bool, animated: Bool) {
super.setSelected(selected, animated: animated)
// Configure the view for the selected state
}
}
ViewControllerVendas.swift
class ViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
// UI View
#IBOutlet weak var tableViewVendas: UITableView!
#IBOutlet weak var waitView: UIActivityIndicatorView!
// DB
var db: OpaquePointer?
var count : Int = 0
// Data
var saleOrders : [SaleOrder] = []
override func viewDidLoad() {
super.viewDidLoad()
self.waitView.startAnimating()
self.waitView.hidesWhenStopped = true
tableViewVendas.delegate = self
tableViewVendas.dataSource = self
}
// TableView
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 5
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "cellVenda") as! TableViewCellVenda
print("Cell for row")
cell.labelCliente.text = "Nome do Cliente"
cell.labelDataVenda.text = "14/02/1991"
cell.labelQtdItens.text = "20"
cell.labelValorTotal.text = "R$ 542,22"
return cell
}
func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
return 75
}
}
Emulator:
Try adding a new swift UIKit file with a class of type UITableView and do all the tableview setup in there. And of coarse set the tables’s class as this UITableView class.
I have a Stack in my ViewController and I want to load a nib file(which contain a tableview) and add it to the stack. when I add it in viewDidLoad, there is no problem but when I put it in viewDidAppear app crash and got this error:
fatal error: unexpectedly found nil while unwrapping an Optional value
There are some UITableViewCell which I return them in cellForRowAt function based on row. It seems nib files are nil when they load and added in viewDidAppear!
Here is my code:
class MyOrdersViewController: UIViewController {
#IBOutlet weak var stack: UIStackView!
override func viewDidLoad() {
super.viewDidLoad()
//setCards()
}
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
setCards()
}
func setCards(){
let orderCard = NibLoader.loadViewFromNib(name: "MyOrdersView", selfInstance: self, nibType: MyOrdersView.self) as! MyOrdersView
stack.addArrangedSubview(orderCard)
}
}
class MyOrdersView: UIView,UITableViewDelegate,UITableViewDataSource {
#IBOutlet weak var tableView: UITableView!
#IBOutlet weak var seprator: UITableViewCell!
#IBOutlet weak var date: UILabel!
#IBOutlet weak var firstCell: UITableViewCell!
#IBOutlet weak var code: UILabel!
#IBOutlet weak var secondCell: UITableViewCell!
#IBOutlet weak var price: UILabel!
#IBOutlet weak var thirdCell: UITableViewCell!
#IBOutlet weak var orderStep: UILabel!
#IBOutlet weak var payModel: UILabel!
#IBOutlet weak var cancelBtn: UIButton!
#IBOutlet weak var fourthCell: UITableViewCell!
override func awakeFromNib() {
tableView.delegate = self
tableView.dataSource = self
UIFunctions.setBordersStyle(view: cancelBtn, radius: 5, width: 1, color: UIColor.red)
}
func setValue(order:Order){
self.date.text = order.order_date
self.code.text = String(describing: order.order_code ?? 0)
}
// MARK: - Table view data source
func numberOfSections(in tableView: UITableView) -> Int {
return 1
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 5
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
var cell=UITableViewCell()
switch indexPath.row {
case 0:
cell = seprator
case 1:
cell = firstCell
cell.separatorInset = UIEdgeInsetsMake(0, 0, 0, 0)
case 2:
cell = secondCell
cell.separatorInset = UIEdgeInsetsMake(0, 0, 0, 0)
case 3:
cell = thirdCell
cell.separatorInset = UIEdgeInsetsMake(0, 0, 0, 0)
case 4:
cell = fourthCell
default:
break
}
return cell
}
func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
var height = 0
switch indexPath.row {
case 0:
height = 25
case 4:
height = 70
default:
height = 50
}
return CGFloat(height)
}
}
The reason seems that since viewDidLoad is the first method to be
called in the view life cycle, adding nib reference there makes sure
that when the views are drawn(your tables), they are available to
locate in cellForRow.
But if you put the same code in viewDidAppear, the views are already
loaded by that time, and your table view is not referenced yet
referenced from Nib. Hence the nil error.
This link discusses the various view lifecycle methods and their calling order in detail.
My storyboard looks like this
and my code is the following
UIViewController
class DownLoadSoundsViewController: UIViewController, UITableViewDataSource, UITableViewDelegate {
// MARK: View Controller Properties
let viewName = "DownLoadSoundsViewController"
#IBOutlet weak var visualEffectView: UIVisualEffectView!
#IBOutlet weak var dismissButton: UIButton!
#IBOutlet weak var downloadTableView: UITableView!
// MARK: Properties
var soundPacks = [SoundPack?]() // structure for downloadable sounds
override func viewDidLoad() {
super.viewDidLoad()
downloadTableView.dataSource = self
downloadTableView.delegate = self
downloadTableView.register(DownLoadTableViewCell.self, forCellReuseIdentifier: "cell")
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return numberOfSoundPacks
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let method = "tableView.cellForRowAt"
//if (indexPath as NSIndexPath).section == 0 {
let cell = tableView.dequeueReusableCell(withIdentifier: "downloadTableViewCell", for: indexPath) as! DownLoadTableViewCell
cell.backgroundColor = UIColor.green
if soundPacks[(indexPath as NSIndexPath).row]?.price == 0 {
cell.soundPackPriceUILabel.text = "FREE"
} else {
cell.soundPackPriceUILabel.text = String(format: "%.2", (soundPacks[(indexPath as NSIndexPath).row]?.price)!)
}
//cell.textLabel?.text = soundPacks[(indexPath as NSIndexPath).row]?.soundPackTitle
cell.soundPackTitleUILabel.text = soundPacks[(indexPath as NSIndexPath).row]?.soundPackTitle
cell.soundPackAuthorUILabel.text = soundPacks[(indexPath as NSIndexPath).row]?.author
cell.soundPackShortDescription.text = soundPacks[(indexPath as NSIndexPath).row]?.shortDescription
cell.soundPackImage.image = UIImage(named: "Placeholder Icon")
DDLogDebug("\(viewName).\(method): table section \((indexPath as NSIndexPath).section) row \((indexPath as NSIndexPath).row))")
return cell
//}
}
UItableViewCell
class DownLoadTableViewCell: UITableViewCell {
#IBOutlet weak var soundPackImage: UIImageView!
#IBOutlet weak var soundPackTitleUILabel: UILabel!
#IBOutlet weak var soundPackAuthorUILabel: UILabel!
#IBOutlet weak var soundPackShortDescription: UILabel!
#IBOutlet weak var soundPackPriceUILabel: UILabel!
let gradientLayer = CAGradientLayer()
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
}
}
But I get the following;
I am sure I am doing something small incorrectly, but as of yet can't figure it out. Looked through many examples included my own code where I have gotten this working before.
Not a single one of my settings for the tableview are getting invoked except the number of cells. But everything in;
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell{...}
is not working.
Help is appreciated.
I think you need to reload the tableView after getting data from Firebase
self.saveMixesTableView.reloadData()