Cell from Xib with Swift 3

Cell from Xib with Swift 3

You need to register your nib object.

In viewDidLoad():

let nib = UINib(nibName: "nameOfYourNibFile", bundle: nil)

tableView.register(nib, forCellReuseIdentifier: "yourIdentifier")

You also need to return the number of sections:

func numberOfSections(in tableView: UITableView) -> Int {
return 1
}

Using custom XIB in table view cell

You can use 2 ways:

Create UITableViewCell (better)

1) Change UIView to UITableViewCell

class CustomTableViewCell: UITableViewCell { 

...

class var identifier: String {
return String(describing: self)
}
}

2) Register your cell

override func viewDidLoad() {
super.viewDidLoad()

self.tableView.registerNib(UINib(nibName: CustomTableViewCell.identifier, bundle: nil), forCellReuseIdentifier: CustomTableViewCell.identifier)
...
}

3) Use cellForRow(at:)

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

let cell = tableView.dequeueReusableCell(withIdentifier: CustomTableViewCell.identifier) as! CustomTableViewCell
cell.username.text = user.username

return cell
}

OR Add view as subview to cell (only in rare cases)

1) Add this to UserView

class UserView: UIView {

...

class func fromNib() -> UserView {
return UINib(nibName: String(describing: self), bundle: nil).instantiate(withOwner: nil, options: nil)[0] as! UserView
}

}

2) Use cellForRow(at:)

override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

let cellIdentifier = "UserTableViewCell"

guard let cell = tableView.dequeueReusableCell(withIdentifier: cellIdentifier, for: indexPath) as? UserTableViewCell else {
fatalError("The dequeued cell is not an instance of UserTableViewCell.")
}

let userView = UserView.fromNib()
let user = users[indexPath.row]
userView.username.text = user.username

//Use frame size, but for me better to add 4 constraints
userView.frame = CGRect(x: 0, y: 0, width: cellWidth, height: cellHeight)

cell.contentView.addSubview(UserView)

return cell
}

Custom UITableViewCell from nib in Swift

With Swift 5 and iOS 12.2, you should try the following code in order to solve your problem:

CustomCell.swift

import UIKit

class CustomCell: UITableViewCell {

// Link those IBOutlets with the UILabels in your .XIB file
@IBOutlet weak var middleLabel: UILabel!
@IBOutlet weak var leftLabel: UILabel!
@IBOutlet weak var rightLabel: UILabel!

}

TableViewController.swift

import UIKit

class TableViewController: UITableViewController {

let items = ["Item 1", "Item2", "Item3", "Item4"]

override func viewDidLoad() {
super.viewDidLoad()
tableView.register(UINib(nibName: "CustomCell", bundle: nil), forCellReuseIdentifier: "CustomCell")
}

// MARK: - UITableViewDataSource

override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return items.count
}

override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "CustomCell", for: indexPath) as! CustomCell

cell.middleLabel.text = items[indexPath.row]
cell.leftLabel.text = items[indexPath.row]
cell.rightLabel.text = items[indexPath.row]

return cell
}

}

The image below shows a set of constraints that work with the provided code without any constraints ambiguity message from Xcode:

Sample Image

Swift 3 - button in .xib custom tableviewcell is not performing action

You need to use addTarget(_:action:for:) method to add the action for your button not the actions(forTarget:forControlEvent:).

The function actions(forTarget:forControlEvent:) returns the actions that have been added to a control. It doesn't add a target/action.

cell.myButton.addTarget(self,action: #selector(myAction(sender:)), for: .touchUpInside)

Passing data from xib cell to viewcontroller

The typical pattern for this sort of thing would be to define a delegate protocol that would receive events from your UITableViewCells, such as the tap of a button. The delegate can send along which cell and which button in which cell was tapped, so your TableView or ViewController can update its view model on which of the buttons have been tapped view-wide.

class AnswerCellView: UITableViewCell {
// ...

weak var delegate: AnswerCellViewDelegate?

// The methods here linked to your outlets should call the answerCellClicked on the delegate

// ...
}

protocol AnswerCellViewDelegate {
func answerCellClicked(answerCell: AnswerCellView, answerButton: UIButton)
}

// ...

class AnswerCellTableView: UITableViewDataSource, AnswerCellViewDelegate {
// ...

func answerCellClicked(answerCell: AnswerCellView, answer: UIButton) {
// do the work to keep track of which buttons have been clicked
}

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
var answerCell: AnswerCellView
// construct your AnswerCellView, setting the delegate property on your cell to self
// ...
answerCell.delegate = self
// ...
}

// ...
}

Showing tableView in Xib with data in Swift 3.0

here anyview is a uiview which u want to show or hide

extension ViewController : UITableViewDelegate {

    func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
return any view
}
func instanceFromNib() -> UIView {
return UINib(nibName: "Header", bundle: nil).instantiate(withOwner: nil, options: nil)[0] as! UIView
}
func tableView(_ tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {
return 200;
}

have a button action like below

    @IBAction func HideShowView(_ sender: UIButton) {

if(!isSelected) {
isSelected = true

self.mytable.delegate = nil
mytable.reloadData()
}
else {
isSelected = false
self.mytable.estimatedRowHeight = 40
self.mytable.delegate = self
mytable.reloadData()

}

}


Related Topics



Leave a reply



Submit