Swift hide just one button on tabbar - swift

I have seen lots of code to hide the whole tabbar. I am using tab bar controller in storyboard.
If I had third and fourth buttons how could I hide just the second but still have 1, 3 and 4 buttons shown?

Well just hide the button itself.
button2.hidden = true
You will need to create an outlet.
#IBOutlet var button2 : UIButton!
And link it to the button in Interface Builder

Ok to hide the button the following can be done. I used this code in a table view to add the editing function and change the title of the button based on the the click. But I modified it for this post just to show that when I clicked on the button again it would make it disappear.
var condition: Bool = true
#IBAction func buttonEdit(sender: UIBarButtonItem) {
if(condition == true) {
tableView.editing = true
sender.title = "Done"
condition = false
} else {
tableView.editing = false
sender.title = "" // This clears the title
sender.enabled = false // This disables the button
sender.image = UIImage() // This would clear the image
condition = true
}
}

Related

How to let search bar disappear immediately when moving to another VC

Below Gif is from my app, the 1st VC includes a search bar to filter the songs, and when press a row to transition to 2nd VC to show selected playing song.
The question here is that when 2nd VC is opened, the search bar is not disappeared immediately, it has like 1 or 2 seconds delay, could see that behavior from below GIF.
/ / / Here is my code, how could I solve this issue? Any hint is appreciate.
The search bar
var resultSearchController = UISearchController()
override func viewDidLoad() {
...
// add search bar
resultSearchController = ({
let controller = UISearchController(searchResultsController: nil)
controller.searchResultsUpdater = self
controller.hidesNavigationBarDuringPresentation = false
controller.dimsBackgroundDuringPresentation = false
controller.searchBar.sizeToFit()
// set search Bar covered color, same with tableView's background color.
controller.searchBar.barTintColor = UIColor(rgb: 0x292f33)
self.tableView.tableHeaderView = controller.searchBar
return controller
})() // closure, learn it later!!
...
}
I set search bar to disabled state when leaving current VC.
override func viewWillDisappear(_ animated: Bool) {
super.viewWillDisappear(true)
resultSearchController.isActive = false
}
/ / / Update, as matt's comment, I change the code to integrate search bar into navigation bar, and now the search bar is disappear immediately after opening VC2.
remove self.tableView.tableHeaderView = controller.searchBar and integrate the search bar into the nav bar navigationItem.searchController = resultSearchController. Now the behavior is same as Apple's inbox app.
searchController.searchBar.isHidden = false
Hiding the searchController instead of making the active state to false may solve your issue.
Try adding in the above line to your code in viewWillDisappear()
hopefully this helps.

I want to Switch UIView by Clicking UISegmented Control but my Code is not working

i want to Switch UIView by clicking Segmented Control but this Code is not working.
#IBOutlet weak var flightTypeSegCont: UISegmentedControl!
#IBAction func flightType(_ sender: UISegmentedControl) {
if(flightTypeSegCont.selectedSegmentIndex == 0)
{
self.direcrCard.isHidden = false
self.ViaCardView.isHidden = true
}
else
{
self.direcrCard.isHidden = true
self.ViaCardView.isHidden = false
}
}
Did you check if the function is getting called in XCode debugger? If not, connect IBAction from storyboard / xib to your function - valuechanged callout of UISegmentedControl.
If it is being called but views are not hidden as you want, check if they are having parent/child relationship. To check this in more details, go to XCode->View Debugging->Capture View hierarchy option to see the runtime UIView layout.

How do I make a button add one view at a time?

I'm practicing creating an app that has 3 views. Each view has a button to hide itself. Now, I added a button outside the views to re-add them after I hide them, but, when i remove the views and I press it, it shows me all of the three views. I want it to add one view at a time (without removing the other views). What can I do?
This is my code, I was even thinking about adding multiple add buttons but it wouldn't be clear.
#IBAction func addViewButton(_ sender: Any) {
view1.isHidden = false
view2.isHidden = false
view3.isHidden = false
}
Declare a variable like currentVisibleViews in your ViewController, and lets say at first there is only first one is visible so we start off the number as 1, and also add your views to an array to control easier:
var currentVisibleViews = 1
var viewArray = [UIView]()
In viewDidLoad, add your views to viewArray:
view1.isHidden = false
view2.isHidden = true
view3.isHidden = true
viewArray.append(view1)
viewArray.append(view2)
viewArray.append(view3)
Then in your button:
#IBAction func addViewButton(_ sender: Any) {
if currentVisibleViews > 2 {
viewArray.forEach { (view) in
view.isHidden = true
}
currentVisibleViews = 0
} else {
viewArray[currentVisibleViews].isHidden = false
currentVisibleViews += 1
}
}
Code above works as this:
First all views are visible
First tap will hide all views
Then each tap will make a view visible
Go to step 2 (once all views are visible)
By this way, you can only have one function to control all your views, it doesnt have to be IBAction anymore, it can be just a method of your ViewController

Disable a Button

I want to disable a button (UIButton) on iOS after it is clicked. I am new to developing for iOS but I think the equivalent code on objective - C is this:
button.enabled = NO;
But I couldn't do that on swift.
The boolean value for NO in Swift is false.
button.isEnabled = false
should do it.
Here is the Swift documentation for UIControl's isEnabled property.
If you want the button to stay static without the "pressed" appearance:
// Swift 2
editButton.userInteractionEnabled = false
// Swift 3
editButton.isUserInteractionEnabled = false
Remember:
1) Your IBOutlet is --> #IBOutlet weak var editButton: UIButton!
2) Code above goes in viewWillAppear
The way I do this is as follows:
#IBAction func pressButton(sender: AnyObject) {
var disableMyButton = sender as? UIButton
disableMyButton.enabled = false
}
The IBAction is connected to your button in the storyboard.
If you have your button setup as an Outlet:
#IBOutlet weak var myButton: UIButton!
Then you can access the enabled properties by using the . notation on the button name:
myButton.enabled = false
Disable a button on Swift 3:
yourButton.isEnabled = false
For those who Googled "disable a button" but may have more nuanced use cases:
Disable with visual effect: As others have said, this will prevent the button from being pressed and the system will automatically make it look disabled:
yourButton.isEnabled = false
Disable without visual effect: Are you using a button in a case where it should look normal but not behave likes button by reacting to touches? Try this!
yourButton.userInteractionEnabled = false
Hide without disabling: This approach hides the button without disabling it (invisible but can still be tapped):
yourButton.alpha = 0.0
Remove: This will remove the view entirely:
yourButton.removeFromSuperView()
Tap something behind a button: Have two buttons stacked and you want the top button to temporarily act like it's not there? If you won't need the top button again, remove it. If you will need it again, try condensing its height or width to 0!
Swift 5 / SwiftUI
Nowadays it's done like this.
Button(action: action) {
Text(buttonLabel)
}
.disabled(!isEnabled)
You can enable/disable a button using isEnabled or isUserInteractionEnabled property.
The difference between two is :
isEnabled is a property of UIControl (super class of UIButton) and it has visual effects (i.e. grayed out) of enable/disable
isUserInteractionEnabled is a property of UIView (super class of UIControl) and has no visual effect although but achieves the purpose
Usage :
myButton.isEnabled = false // Recommended approach
myButton.isUserInteractionEnabled = false // Alternative approach
Let's say in Swift 4 you have a button set up for a segue as an IBAction like this #IBAction func nextLevel(_ sender: UIButton) {}
and you have other actions occurring within your app (i.e. a timer, gamePlay, etc.). Rather than disabling the segue button, you might want to give your user the option to use that segue while the other actions are still occurring and WITHOUT CRASHING THE APP. Here's how:
var appMode = 0
#IBAction func mySegue(_ sender: UIButton) {
if appMode == 1 { // avoid crash if button pressed during other app actions and/or conditions
let conflictingAction = sender as UIButton
conflictingAction.isEnabled = false
}
}
Please note that you will likely have other conditions within if appMode == 0 and/or if appMode == 1 that will still occur and NOT conflict with the mySegue button. Thus, AVOIDING A CRASH.
The button can be Disabled in Swift 4 by the code
#IBAction func yourButtonMethodname(sender: UIButon) {
yourButton.isEnabled = false
}
in order for this to work:
yourButton.isEnabled = false
you need to create an outlet in addition to your UI button.
Building on other answers here. I wanted to disable button for a few seconds to prevent double taps. Swift 5 version, xcode 13.4.1 likes this and has no warnings or errors.
#IBAction func saveComponent(_ sender: Any) {
let myButton = sender as? UIButton
myButton?.isEnabled = false
DispatchQueue.main.asyncAfter(deadline: .now() + .milliseconds(2000))
{
myButton?.isEnabled = true
}
}

swipe gesture and uisegmented control

In the notification center (iOS 7) it is possible to swipe between the "Today", "All", and "Missed" options of (what I presume is ) a segmented control. I would like to do this in my code but am unsure how to contiunue. I have a uisegmented control and a uitableviiew as my view.
I accomplished this by following the respective steps:
Add 2 swipe gesture recognisers(one to swipe left and the other to
swipe right)
For each of them on the connections inspector reference the outlet
collection as your main view.
Selecting actions when swiping as follows:
viewSelector is the UISegmentedControl and firstView, secondView and
thirdView are 3 views used to select which one is being shown.
Code:
#IBAction func indexChanged(sender: UISegmentedControl) {
switch sender.selectedSegmentIndex
{
case 0:
firstView.hidden = false
secondView.hidden = true
thirdView.hidden = true
case 1:
firstView.hidden = true
secondView.hidden = false
thirdView.hidden = true
case 2:
firstView.hidden = true
secondView.hidden = true
thirdView.hidden = false
default:
break;
}
}
#IBAction func swipeLeft(sender: UISwipeGestureRecognizer) {
viewSelector.selectedSegmentIndex = (viewSelector.selectedSegmentIndex + 1) % viewSelector.numberOfSegments
indexChanged(viewSelector)
}
#IBAction func swipeRight(sender: UISwipeGestureRecognizer) {
viewSelector.selectedSegmentIndex = (viewSelector.selectedSegmentIndex - 1) % viewSelector.numberOfSegments
if(viewSelector.selectedSegmentIndex == -1){
viewSelector.selectedSegmentIndex = viewSelector.numberOfSegments-1
}
println(viewSelector.selectedSegmentIndex)
indexChanged(viewSelector)
}
This could be accomplished using a UIScrollView with paging enabled, and when the user scrolls through the pages, the UISegmentedControl's selectedSegmentIndex is updated.
It looks like it isn't a scrollView with paging enabled to me. I think it could be easier with a UIGestureRecognizer. If it recognises a gesture, slide the view of the current tab and update the segmented control.