This is what my story board shows
However, the right arrow is not there when I run on simulator
I don't know why and I don't know what code I should show you because I actually didn't make that arrow myself, I just selected the cell's accessory as Discolosure Indicator
update 1
there is no overlap, this is from the debugger:
The problem is that you implemented layoutSubviews, but never called super.layoutSubviews(). Thus the disclosure indicator was never laid out.
Try adding this inside your tableview method
cell.accessoryType = UITableViewCellAccessoryType.DisclosureIndicator
//Complete Code
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell{
let cell = UITableViewCell(style: UITableViewCellStyle.Default, reuseIdentifier: "Cell")
cell.accessoryType = UITableViewCellAccessoryType.DisclosureIndicator
return cell
}
try adding disclosure indicator programmatically in cellForRowAtIndexPath:
override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
...
cell.accessoryType = UITableViewCellAccessoryType.DisclosureIndicator
...
}
Try using preview in the assistant editor. Most likely one of the images is overlapping the indicator and you need to adjust your constraints.
Related
UITableView allows you to assign an accessory -- like a button -- that shows on the right side of the cell (documentation).
In my audio app, I will want to allow a user to download by clicking the accessory and then show it succeeded with a checkmark. To test this now, I just want the accessory detail to turn into a checkmark after it's tapped.
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath)
cell.textLabel?.text = TableData[indexPath.row]
// this works, adds a button to right cell
cell.accessoryType = .detailDisclosureButton
return cell
}
override func tableView(_ tableView: UITableView, accessoryButtonTappedForRowWith indexPath: IndexPath) {
// doSomethingWithItem(indexPath.row)
// my logic: this function applies when button is tapped. I try to reset the accessory type to checkmark when clicked
let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath)
cell.accessoryType = .checkmark
}
This will build, but it results in a failure starting with *** Assertion failure in -[UITableView _dequeueReusableCellWithIdentifier:forIndexPath:usingPresentationValues:],
I'm new to Swift, but this seemed logical: set a function to take an action when the accessory is clicked and then set the accessory to a checkmark (one of the accessory types).
Is there a better way to do this?
A note: I do not want to use a segue or move to a different VC; I'd like this to update the UI within the table view.
Instead of using dequeReusableCell you should be using cellForRow in your accessoryButtonTappedForRow function.
Read the documentation to see the difference between those two functions and look a little further into how cell reuse works. cellForRow(at:) returns the specific UITableViewCell, which is what you are looking for in this situation.
override func tableView(_ tableView: UITableView, accessoryButtonTappedForRowWith indexPath: IndexPath) {
// doSomethingWithItem(indexPath.row)
// cellForRow instead of dequeue
let cell = tableView.cellForRow(at: indexPath)
cell.accessoryType = .checkmark
}
In addition, make sure you are registering your cell with that same reuse identifier of "cell" with either registerClass or registerNib
public func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = UITableViewCell(style: UITableViewCellStyle.default, reuseIdentifier: "approve_cell");
let event = self.events[indexPath.row];
cell.textLabel?.text = event.name;
return cell;
}
I placed 2 images and a label in tableviewcell. When i run the app, images are not visible. What could be the reason?
Check that you are not using the basic style of the UITableViewCell because if you are then that style only includes labels.. no image views. Change it to subtitle or one of the details.
For reference, see: https://developer.apple.com/library/content/documentation/UserExperience/Conceptual/TableView_iPhone/TableViewCells/TableViewCells.html
You probably forgot to set AutoLayoutConstraints of your image view. You could either add constraints to that image view through storyboard or through code. The other method is setting the frame of your image view in -(void)viewDidLayoutSubviews, because when you're using auto-layout, the layout of those views will be undefined if its constraints doesn't fulfill system's computing need. So you should either set right constraints or give a specific frame to those undefined views after all of the others has-constraints-views are arranged.
You creat cell in storyboard but you never use this cell created from storyboard. instead you manually creat it by UITableViewCell's designated initializer without override layout method of it.
public func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "approve_cell", for: indexPath)
let event = self.events[indexPath.row];
cell.textLabel?.text = event.name;
return cell;
}
You need to set either Autolayout or used Autoresizing. For autolayout just pinned the proper leading, trailing, top and bottom constraint.
I'm trying to add check marks to my UItableview cells. I want to checkmarks to display like circle buttons on the left margin like this image:
I am unable to get the checkmarks in the left margin with my code and instead I keep getting checkmarks on the right that display only when tapped. Here is my current code:
override func tableView(tableView: UITableView, didDeselectRowAtIndexPath indexPath: NSIndexPath) {
if let cell = tableView.cellForRowAtIndexPath(indexPath) {
cell.accessoryType = .None
}
}
override func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
if let cell = tableView.cellForRowAtIndexPath(indexPath) {
cell.accessoryType = .Checkmark
}
}
Any idea on how i can get the checkmarks to display on the left like the image?
I've made for you whole sample application for this.
just try this.
And this is what it looks like.
I have created a simple table view and embed in navigation controller. I have selected a accessory type for cell and use a segue to the other view controller to show details of that cell. But accessory not showing. If i use this code
cell.accessoryType = UITableViewCellAccessoryType.DisclosureIndicator
Then accessory shows but segue not working.
This is my code
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell{
let cell = UITableViewCell(style: UITableViewCellStyle.Subtitle, reuseIdentifier: "Cell")
cell.textLabel?.text = "test"
// cell.accessoryType = UITableViewCellAccessoryType.DisclosureIndicator
return cell
}
Please tell me where is the problem.
You should be using something like this to perform the segue:
func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell{
self.performSegueWithIdentifier("SEGUENAME", sender: self)
}
If so, adding
cell.accessoryType = .DisclosureIndicator
should work fine.
It sounds like you've hooked the segue in the storyboard to the accessory (the disclosure indicator). But a disclosure indicator is not a button, so that can never work (it is not tappable); and it is not what your users expect. Either:
Hook the segue to the cell itself; or
Use a tappable button accessory, such as an info button.
You should create your segues between viewcontrollers.
Do not create segue from cell to viewcontrollers.
Then after you select a cell you should decide which segue you would like to invoke.
I tried to add many details (fields) to display in TableView. by concat each fields and put in for detailTextLabel e.g.:
From:
func tableView(tableView: UITableView!, cellForRowAtIndexPath indexPath: NSIndexPath!) -> UITableViewCell!{
let cell: UITableViewCell = UITableViewCell(style: UITableViewCellStyle.Subtitle, reuseIdentifier:"test")
cell.textLabel.text = taskMgr.tasks[indexPath.row].name
cell.detailTextLabel.text = taskMgr.tasks[indexPath.row].desc
return cell
}
To
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell{
let cell:UITableViewCell = UITableViewCell(style: UITableViewCellStyle.Subtitle, reuseIdentifier: "Test")
cell.textLabel?.text=tasksList[indexPath.row].name
var yString = tasksList[indexPath.row].desc
var xString = tasksList[indexPath.row].amnt
var zString = xString+" "+yString
cell.detailTextLabel?.text=zString
return cell
}
Could anyone point out any other ways for better code for many fields to display in the view.
I think your first method is great. In storyboard inside a prototype cell you can place several UILabels. Then just update each label as you did. You can place labels in a xib or create them in code. But there is nothing wrong with having several labels and then updating them individually. This gives more flexibility that concatenation because you can justify the text in each label as required to make the tableview pretty. So each cell row has good alignment with the one above it.