Show/Hide tableView Header on UIButton click inside UIViewController in Swift 3 - uitableview

I have a tableView and created tableViewHeader using Xib. I am able to show tableViewHeader on UIViewController. Outside tableView their is a UIButton so when i click that button headerView will hide,tableView will scroll up upto its position and when i again click the same button tableView header will be shown & tableView will scroll down. Any help will be appreciated.

You can use boolean for the state of the UIButton Action and based on TRUE & FALSE you can hide the UITableViewHeader.
override func tableView(tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {
if boolObj {
return 0.0
}else{
return 50.0
}
On Button Action
if boolObj {
boolObj = false
}else{
boolObj = true
}
tblOutlet.reloadData()

Related

Keyboard pushes FooterView up when its opening < TextView > Swift

I have a problem that I couldn't find any appropriate solution.
I have a tableView with custom cells which holds a textView inside.
also I have a blank grey footer for the section.
whenever I click on the textView and the keyboard pops up the footer in that section goes up and hides behind the textView field.
I don't know how to make that footer sticky so it won't move when the keyboard pops.
if anyone have a solution it will be great!
thank you!
func tableView(_ tableView: UITableView, viewForFooterInSection section: Int) -> UIView? {
if section == 0 {
let footerView = UIView()
footerView.backgroundColor = .red
return footerView
}else {
return UIView()
}
}
func tableView(_ tableView: UITableView, heightForFooterInSection section: Int) -> CGFloat {
return 8
}
Set your tableView as grouped give height to the tableview footer and tableView Header in the tableview header,footer height functions.
If you are not using tableview header the set the height of the header to .leastNormalMagnitude .
This is the way to make the tableView Footer Static.

hiding tableView.tableFooterView causes my section headerView to disappear

I have a tableViewController with one section. I have added a UIView directly to the tableView in storyboard and set outlets to my tableViewController for that view (headerView) and it's contents which are a segmented control and a searchBar.
In the tableView delegate methods I have the following for my header:
override func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
return headerView
}
override func tableView(_ tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {
return 88
}
Everything is working fine except that there is no separator for the very last row of my tableView. This is expected and the workaround for me has always been the following in viewDidLoad:
self.tableView.tableFooterView = UIView(frame: CGRect.zero)
self.tableView.tableFooterView?.isHidden = true
For some reason, these two lines of code cause my headerView to completely disappear from the table.
I could create a tableViewCell and use that as my tableView header but there is a lot of delegation required for the searchBar and segmented control and that leads to other problems. Mainly that the searchBar wants to resignFirstResponder every time I reload my tableView. Again there are workarounds for that but it all starts to get a bit messy.
Just wondering why my headerView is disappearing and what I could do about it.
Remove that header view from tableview and add it on UIViewController i.e directly drag them adjacent to first responder and exit. Then using IBOutlet you can use it as Section view. Here it is being treated as footer view as well.
It is because you assign the new UIView object to table header view
If you want to toggle table header then you have to follow below step
1) keep the reference of you view which you want to set in table header
UIView footerView = your storyboard referance
2) when you want to hide then just assign nil to table footer
self.tableView.tableFooterView = nil
3) Now when you want to show then again assign your refence view
self.tableView.tableFooterView = footerView

Detect Change in UISegmentedControl inside UITableView HeaderView

I am trying to control my UITableView based on the selectedSegmentIndex of a UISegmentedControl inside my UITableView header. Essentially, I want this UISegmentedControl to work like Twitter's 'Me' tab. I have the UISegmentedControl inside a UITableView header and it is dequeued using this method:
override func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
let cell = tableView.dequeueReusableCell(withIdentifier: "sectionDetailsHeaderView") as! SectionDetailsHeaderTableViewCell
return cell
}
I have an outlet for the UISegmentedControl hooked up to SectionDetailsHeaderTableViewCell, but I can't figure out how to detect a change in the UISegmentedControl. I want to set a variable, var segmentedControlValue = Int() to the selectedSegmentIndex every time the value changes and call a function, func chooseDataToDisplay() {} when the value changes. How do I go about doing this?
With the help of #Schomes answer and this post, I was able to figure it out!
1) Add the UISegmentedControl into its own UITableViewCell. I would recommend adding a UIView with a white background behind the UISegmentedControl that covers the entire UITableViewCell so the TableView cells flow behind the UISegmentedControl.
2) Add your custom cell class and hook it up to the UITableViewCell
3) Add an outlet, such as yourSegmentedControl to your custom UITableViewCell class. DO NOT add an action into the custom UITableViewCell class. This is done programmatically in step 4.
4) In the UIViewController or UITableViewController class, add the code below.
override func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
let header = tableView.dequeueReusableHeaderFooterView(withIdentifier: "yourCellIdentifier") as! yourCustomCellClass
header.yourSegmentedControl.selectedSegmentIndex = self.segmentedControlValue
header.yourSegmentedControl.addTarget(self, action: #selector(self.getSegmentValue(sender:)), for: .valueChanged)
return header
}
self.segmentedControlValue should be declared as var segmentedControlValue = Int() at the top of your ViewController class. self.getSegmentValue(sender:) should be declared as:
func getSegmentValue(sender: UISegmentedControl) {
self.segmentedControlValue = sender.selectedSegmentIndex
}
5) You also need to add:
override func tableView(_ tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {
return 45
}
This is the height of the header. In my case, the size is 45
6) You can now access self.segmentedControlValue anywhere in your ViewController. It will update when the user taps on a different segment.
segmentedControl.addTarget(self, action: "chooseDataToDisplay:", forControlEvents: .ValueChanged)
Where segmentedControl is your UISegmentedControl. This will call func chooseDataToDisplay(segment: UISegmentedControl) {} every time the value changes.
References:
https://developer.apple.com/reference/uikit/uisegmentedcontrol
The section Behavior of Segmented Controls
https://developer.apple.com/library/content/documentation/UserExperience/Conceptual/UIKitUICatalog/UISegmentedControl.html#//apple_ref/doc/uid/TP40012857-UISegmentedControl

Section footer of UITableView is moving when keyboard is appearing

I have a UITableView with different sections in it. Each section has its own footer (just a grey line for design reasons). When clicking on a table view cell in a section an AlertView and the keyboard appears (to enter a password). But when the keyboard appears the footer of the section is pushed up by the keyboard. U can see it behind the AlertView in the grey background. Looks very ugly.
How can i avoid that? The footer in the background should stay where it was (on the bottom of the section). Any ideas?
There is a work around for this which worked for me, set tableView.sectionFooterHeight = 0 when textFieldShouldBeginEditing.
func textFieldShouldBeginEditing(textField: UITextField) -> Bool {
tableView.beginUpdates()
tableView.sectionFooterHeight = 0
tableView.endUpdates()
return true
}
func textFieldShouldEndEditing(textField: UITextField) -> Bool {
tableView.beginUpdates()
tableView.sectionFooterHeight = 100
tableView.endUpdates()
return true
}
Make sure you're setting the footerView height using tableView.sectionFooterHeight = 100 in viewDidLoad() and not using the func tableView(tableView: UITableView, heightForFooterInSection section: Int) -> CGFloat

Designing tap-to-expand cell in storyboard

I have added a feature to my app that allows users to add notes which will appear in table view cells when they are tapped as they expand to show more content.
My question is - How do I layout the content that is to be shown when the cell is expanded? I have tried adding the textView to the prototype cell, but I just get the textView overlapping on the other cells in the table view rather than being hidden before being tapped.
Here is my code for when a cell is tapped:
var selectedRowIndex: NSIndexPath = NSIndexPath(forRow: -1, inSection: 0)
override func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
selectedRowIndex = indexPath
tableView.beginUpdates()
tableView.endUpdates()
}
override func tableView(tableView: UITableView, heightForRowAtIndexPath indexPath: NSIndexPath) -> CGFloat {
if indexPath.row == selectedRowIndex.row {
if cellTapped == false {
cellTapped = true
return 141
} else {
cellTapped = false
return 70
}
}
return 70
}
You need to set the cell's clipToBounds property to YES (or select the "Clip Subviews" check box in IB for the cell), so none of its subviews will show outside the bounds of the cell. The text view should have constraints to the sides of the contentView as well as a height constraint. It should also have a constraint to something above it, and that view should have a constraint to the top of the contentView. The constraints should look something like this,

Resources