I'm trying to make a table view with sections.
So far so good. But when I add the override ViewDidLoad immediately under the structure, I get an error message: Type 'ViewController' does not conform to protocol 'UITableViewDataSource'.
If I delete the UITableViewDataSource, everything goes bananas...
Why?
(My next checkpoint is to edit this sections by clicking on each row)
This is my code
import UIKit
class ViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
// Creating a structure
struct Objects {
var sectionName : String!
var sectionObjects : [String]!
}
/I would insert viewDidLoad here/
var objectsArray = [Objects(sectionName: "Section 01", sectionObjects: ["11", "12", "13", "14", "15"]),
Objects(sectionName: "Section 02", sectionObjects: ["21", "22", "23"]),
Objects(sectionName: "Section03", sectionObjects: ["31"]),
Objects(sectionName: "Section04", sectionObjects: ["41", "42", "43","44"])
]
/// Determine the content of the cell: in this case the objectsArray
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = UITableViewCell(style: UITableViewCellStyle.default, reuseIdentifier: "Cell")
cell.textLabel?.text = objectsArray[indexPath.section].sectionObjects[indexPath.row]
return cell
}
/// Determine the number of rows
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return objectsArray[section].sectionObjects.count
}
/// Determine the number of sections
func numberOfSections(in tableView: UITableView) -> Int {
return objectsArray.count
}
/// Determine the Title of the sections
func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
return objectsArray[section].sectionName
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
}
Related
I'm using the latest beta of Xcode 7. I'm programming a simple UITableView, but this doesn't work well, the inspector error doesn't show anithing but when I start the simulator, the App crash. Can someone help me?
// RestaurantTableViewController.swift
import UIKit
class RestaurantTableViewController: UITableViewController {
var restaurantNames = ["Cafe Deadend", "Homei", "Teakha", "Cafe Loisl", "Petite Oyster", "For Kee Restaurant", "Po's Atelier", "Bourke Street Bakery", "Haigh's Chocolate", "Palomino Espresso","Upstate","Traif","Graham Avenue Meats","Waffle & Wolf", "Five Leaves", "Cafe Lore", "Confessional", "Barrafina", "Donostia", "Rpyal Oak", "Thai Cafe"]
var restaurantImages = ["cafedeadend.jpg", "homei.jpg", "teakha.jpg", "cafeloisl.jpg",
"petiteoyster.jpg", "forkeerestaurant.jpg", "posatelier.jpg", "bourkestreetbakery.jpg",
"haighschocolate.jpg", "palominoespresso.jpg", "upstate.jpg", "traif.jpg",
"grahamavenuemeats.jpg", "wafflewolf.jpg", "fiveleaves.jpg", "cafelore.jpg",
"confessional.jpg", "barrafina.jpg", "donostia.jpg", "royaloak.jpg", "thaicafe.jpg"]
override func viewDidLoad() {
super.viewDidLoad()
// Uncomment the following line to preserve selection between presentations
// self.clearsSelectionOnViewWillAppear = false
// Uncomment the following line to display an Edit button in the navigation bar for this view controller.
// self.navigationItem.rightBarButtonItem = self.editButtonItem()
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
// MARK: - Table view data source
override func numberOfSectionsInTableView(tableView: UITableView) -> Int {
// #warning Incomplete implementation, return the number of sections
return 1
}
override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
// #warning Incomplete implementation, return the number of rows
return self.restaurantNames.count
}
override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCellWithIdentifier("reuseIdentifier", forIndexPath: indexPath)
// Configure the cell...
cell.textLabel!.text = restaurantNames[indexPath.row]
cell.imageView?.image = UIImage(named: restaurantImages[indexPath.row])
return cell
}
}
I have data saved like this:
var mineSpillere = ["erik", "tom", "phil"]
How can i add that data to a UITableView by pressing a UIButton like this?:
#IBAction func backButtonAction(sender: AnyObject) {
// Press this button here to add the "mineSpillere" data to myTableView
}
Set the data source of the table view inside the IBAction. so like this:
#IBAction func backButtonAction(sender: AnyObject) {
myTableView.dataSource = self
// Loading from NSUserDefaults:
// Please name it something better than array I couldn't come up with any names.
if let array = NSUserDefaults.standardUserDefaults().arrayForKey("key") as? [String]
{
// The key exists in user defaults
}
else
{
// The key doesn't exist in the user defaults, do some error handling here.
}
}
And then implement the data source:
extension MyVC : UITableViewDataSource
{
func numberOfSectionsInTableView(tableView: UITableView) -> Int
{
return 1
}
func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int
{
return mineSpillere.count
}
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell
{
let cell = UITableViewCell(style: .Default, reuseIdentifier: "cell")
cell.textLabel!.text = mineSpillere[indexPath.row]
return cell
}
}
I'm try to simulate the dragging of the cell with the single tap on the cell.
Once tapped the single cell has to be the first item in the list.
I tried with ll the method but my indexpath change but I don't see the result in the table, even if i reload it.
Any Suggestion?
here's my code:
import UIKit
var array = ["1", "2", "3", "4", "5", "6"]
class Table: UITableViewController {
override func viewDidLoad() {
super.viewDidLoad()
tableView.setEditing(true, animated: true)
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
override func numberOfSectionsInTableView(tableView: UITableView) -> Int {
return 1
}
override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return array.count
}
override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCellWithIdentifier("Cell", forIndexPath: indexPath) as UITableViewCell
cell.textLabel.text = array[indexPath.row]
return cell
}
var indexPathForCell = NSIndexPath(forRow: 0, inSection: 0)
override func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPathForCell: NSIndexPath) {
tableView.reloadData()
println(indexPathForCell)
//
}
override func tableView(tableView: UITableView, moveRowAtIndexPath sourceIndexPath: NSIndexPath, toIndexPath indexPathForCell: NSIndexPath) {
println(indexPathForCell)
}
}
Thank you
To swap a cell's position animated, you'll need to update your data source and the tableView's representation at the same time. You can do that like this:
table.beginUpdates()
table.moveRowAtIndexPath(indexPath, toIndexPath: NSIndexPath(forRow: 0, inSection: 0))
array.insert(array.removeAtIndex(indexPath.row), atIndex: 0)
table.endUpdates()
In xcode 6 while deleting cell in my to do list i randomly get an error
"exc_bad_access code=exc_i386_gpflt"
i have got a two views - on second i enter items in array "toDoList"
In first i show all item from "toDoList" and have an option to delete when, code of first page in this:
import UIKit
var toDoList: [String] = []
class FirstViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
//var cell = UITableViewCell()
#IBOutlet weak var itemList: UITableView!
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int{
return toDoList.count
}
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell{
var cell = UITableViewCell(style: UITableViewCellStyle.Default, reuseIdentifier: "Cell")
cell.textLabel.text = toDoList[indexPath.row]
return cell
}
override func viewWillAppear(animated: Bool) {
if var storedItems: AnyObject = NSUserDefaults.standardUserDefaults().objectForKey("items"){
toDoList = []
for var i = 0; i < storedItems.count; ++i{
toDoList.append(storedItems[i] as NSString)
}
}
itemList.reloadData()
}
func tableView(tableView: UITableView, commitEditingStyle editingStyle: UITableViewCellEditingStyle, forRowAtIndexPath indexPath: NSIndexPath){
if editingStyle == UITableViewCellEditingStyle.Delete{
toDoList.removeAtIndex(indexPath.row)
let saveData = toDoList
NSUserDefaults.standardUserDefaults().setObject(saveData, forKey: "items")
NSUserDefaults.standardUserDefaults().synchronize()
itemList.reloadData()
}
}
}
What's causing your error is
itemList.reloadData()
in your function
func tableView(tableView: UITableView, commitEditingStyle editingStyle: UITableViewCellEditingStyle, forRowAtIndexPath indexPath: NSIndexPath)
So to fix your problem, remove that line and then add this line after toDoList.removeAtIndex(indexPath.row):
tableView.deleteRowsAtIndexPaths([indexPath], withRowAnimation: UITableViewRowAnimation.None)
What this method does is: Deletes the rows specified by an array of index paths, with an option to animate the deletion. (from Xcode Quick Help)
In swift, if I create a new cocoa touch class of type UITableViewController, I am given this file called TableViewController.swift:
import UIKit
class TableViewController: UITableViewController {
override func viewDidLoad() {
super.viewDidLoad()
// Uncomment the following line to preserve selection between presentations
// self.clearsSelectionOnViewWillAppear = false
// Uncomment the following line to display an Edit button in the navigation bar for this view controller.
// self.navigationItem.rightBarButtonItem = self.editButtonItem()
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
// MARK: - Table view data source
override func numberOfSectionsInTableView(tableView: UITableView) -> Int {
// #warning Potentially incomplete method implementation.
// Return the number of sections.
return 0
}
override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
// #warning Incomplete method implementation.
// Return the number of rows in the section.
return 0
}
/*override func tableView(tableView: UITableView!, cellForRowAtIndexPath indexPath: NSIndexPath!) -> UITableViewCell! {
let cell = tableView.dequeueReusableCellWithIdentifier("reuseIdentifier", forIndexPath: indexPath) as UITableViewCell
// Configure the cell...
return cell
}*/
/*
// Override to support conditional editing of the table view.
override func tableView(tableView: UITableView!, canEditRowAtIndexPath indexPath: NSIndexPath!) -> Bool {
// Return NO if you do not want the specified item to be editable.
return true
}
*/
/*
// Override to support editing the table view.
override func tableView(tableView: UITableView!, commitEditingStyle editingStyle: UITableViewCellEditingStyle, forRowAtIndexPath indexPath: NSIndexPath!) {
if editingStyle == .Delete {
// Delete the row from the data source
tableView.deleteRowsAtIndexPaths([indexPath], withRowAnimation: .Fade)
} else if editingStyle == .Insert {
// Create a new instance of the appropriate class, insert it into the array, and add a new row to the table view
}
}
*/
/*
// Override to support rearranging the table view.
override func tableView(tableView: UITableView!, moveRowAtIndexPath fromIndexPath: NSIndexPath!, toIndexPath: NSIndexPath!) {
}
*/
/*
// Override to support conditional rearranging of the table view.
override func tableView(tableView: UITableView!, canMoveRowAtIndexPath indexPath: NSIndexPath!) -> Bool {
// Return NO if you do not want the item to be re-orderable.
return true
}
*/
/*
// MARK: - Navigation
// In a storyboard-based application, you will often want to do a little preparation before navigation
override func prepareForSegue(segue: UIStoryboardSegue!, sender: AnyObject!) {
// Get the new view controller using [segue destinationViewController].
// Pass the selected object to the new view controller.
}
*/
}
When I uncomment this provided method:
override func tableView(tableView: UITableView!, cellForRowAtIndexPath indexPath: NSIndexPath!) -> UITableViewCell! {
let cell = tableView.dequeueReusableCellWithIdentifier("reuseIdentifier", forIndexPath: indexPath) as UITableViewCell
// Configure the cell...
return cell
}
I am greeted with this compiler error: "Overriding method with selector 'tableView: cellForRowAtIndex path has incomplete type..."
Is there something I can do to fix this or is this just a beta issue?
The tableView:didSelectRowAtIndexPath: method's declaration has changed between Xcode 6 beta 6 and Xcode 6 beta 7. This method now requires non-optional parameters and returns a non-optional UITableViewCell.
So, with Xcode 6 beta 7, you have to set the following lines in your UITableViewController subclasses in order to avoid error messages:
override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
...
}
instead of:
override func tableView(tableView: UITableView!, cellForRowAtIndexPath indexPath: NSIndexPath!) -> UITableViewCell! {
...
}
See Apple Developper Library for more details.