How to disable a UIButton and send a UIAlertView message - ios

I am trying to disable a menu button is the array is shows is empty.
This is my code.
#IBAction func likedmenubuttontouched(sender: AnyObject) {
if Globals.likedArray.isEmpty {
likedMenuButton.userInteractionEnabled = false
let ac = UIAlertController(title: "No liked quotes yet", message: "No liked quotes have been chosen, go explore!", preferredStyle: .Alert)
ac.addAction(UIAlertAction(title: "OK", style: .Default, handler: nil))
presentViewController(ac, animated: true, completion: nil)
return
} else {
likedMenuButton.userInteractionEnabled = true
}
}
And in ViewDidLoad()
likedMenuButton.userInteractionEnabled = false
I have managed to disable the button, but I want to send a message alerting the user why the button is disabled, otherwise, its a little confusing.
How would I go about doing this?
Thanks.

As by default the the user Interaction is true you need not to make it true
#IBAction func likedmenubuttontouched(sender: AnyObject) {
if Globals.likedArray.isEmpty {
let ac = UIAlertController(title: "No liked quotes yet", message: "No liked quotes have been chosen, go explore!", preferredStyle: .Alert)
ac.addAction(UIAlertAction(title: "OK", style: .Default, handler: nil))
presentViewController(ac, animated: true, completion: nil)
} else {
//segue to the other view
}
}
Also check your array count, that is why your wrong condition is executing

Related

Trouble implementing UIAlertController. Cant get alert to show up

I have set an alert to be shown as any error occurs when some user tries to request a new password through firebase, but it is not working.
The print("problems with email field") is being printed so I believe I have made something wrong when writing the alert part.
#IBAction func recuperarSenha(_ sender: Any) {
Auth.auth().sendPasswordReset(withEmail: self.loginTextView.text!) { error in
if error != nil {
print("problems with email field")
let alert = UIAlertController(title: "Couldn't send recover message", message: "Check if e-mail field is properly filled.", preferredStyle: .alert)
alert.addAction(UIAlertAction(title: "OK!", style: .default, handler: nil))
}
}
}
You need to present your alert after creating it. Add the following code after adding action:
self.present(alert, animated: true, completion: nil)
Edited version of your code:
#IBAction func recuperarSenha(_ sender: Any) {
Auth.auth().sendPasswordReset(withEmail: self.loginTextView.text!) { error in
if error != nil {
print("problems with email field")
let alert = UIAlertController(title: "Couldn't send recover message", message: "Check if e-mail field is properly filled.", preferredStyle: .alert)
alert.addAction(UIAlertAction(title: "OK!", style: .default, handler: nil))
self.present(alert, animated: true, completion: nil)
}
}
}

segue performed before the UIAlertController in swift

I have just coded a signup page in which if user does not enter text in any of the uitextfield then it should receive an error message (UIAlert) ; else (if user enter text in all uitextfield) signup page will present for Firebase Authentication.
in my code, user will direct to sign-in page only if authentication successfully complete else it should remain in signup page with alert message.
Problem - my code is able to produce alert message but same time it is taking user to sign-in page automatically even when there is an error. which means it is performing a segue that takes user to sign-in page i.e. segue unwinding irrespective of alert message.
can anyone help me why this may be happening?
#IBAction func registerPressed(_ sender: Any) {
if nameText.text!.isEmpty || genderText.text!.isEmpty || countryText.text!.isEmpty || yourSchool.text!.isEmpty || yourClass.text!.isEmpty {
print("Please fill all fields") //my code is printing this error
//alert message popup - my code is ble to produce this alert but same it is performing segue and taking user to signin page
//ideally, i want user to be in signup page unless all criteria meet
let alertController = UIAlertController(title: "Error", message: "Please fill all fields", preferredStyle: .alert)
alertController.addAction(UIAlertAction(title: "Ok", style: .default, handler: { (action:UIAlertAction) in
print("Okay")
}))
let alertWindow = UIWindow(frame: UIScreen.main.bounds)
alertWindow.rootViewController = UIViewController()
alertWindow.windowLevel = UIWindowLevelAlert
alertWindow.makeKeyAndVisible()
alertWindow.rootViewController?.present(alertController, animated: true, completion: nil)
}
else {
Auth.auth().createUser(withEmail: yourEmail.text!, password: yourPassword.text!) { (user, error) in
if error != nil {
///print errror message
let alertController = UIAlertController(title: "Error", message: error?.localizedDescription, preferredStyle: .alert)
alertController.addAction(UIAlertAction(title: "Ok", style: .default, handler: { (action:UIAlertAction) in
print("Okay")
}))
let alertWindow = UIWindow(frame: UIScreen.main.bounds)
alertWindow.rootViewController = UIViewController()
alertWindow.windowLevel = UIWindowLevelAlert + 1;
alertWindow.makeKeyAndVisible()
alertWindow.rootViewController?.present(alertController, animated: true, completion: nil)
}
else {
print("You have successfully signed up")
self.performSegue(withIdentifier: "JoinUs2SignPage", sender: self)
//updating user information
let userID = Auth.auth().currentUser!.uid
let usertype: String = "Student"
self.ref.child("users").child(userID).setValue(["usertype": usertype ,"username": self.nameText.text!, "usergender": self.genderText.text!, "usercountry": self.countryText.text!, "userschool": self.yourSchool.text!, "userclass": self.yourClass.text!,])
}
}
}
}
From this bit of code it doesn't really look like anything is wrong. However, you should block the UI while Auth.auth().createUser(...) is running. Otherwise there's a chance that you call registerPressed with everything correct, but then delete the text from a label and call it again before the callback. That way you have an alert and then the segue is called.
You're also doing something quite crazy with the way that you're presenting your alerts. Instead of creating a new window, adding to it a view controller and all that jazz, just call self.present(alertController, animated: true). E.g.
let alertController = UIAlertController(title: "Error", message: "Please fill all fields", preferredStyle: .alert)
alertController.addAction(UIAlertAction(title: "Ok", style: .default, handler: { (action:UIAlertAction) in
print("Okay")
}))
self.present(alertController, animated: true)
Remove the segue and push to destination view controller programmatically.
self.navigationController?.pushViewController(destinationVC, animated: true)
I was doing a silly mistake where I created the segue directly on IBAction and hence whenever I was pressing the button it was performing the segue irrespective UIAlerts. my updated code is below :
#IBAction func registerPressed(_ sender: Any) {
if nameText.text!.isEmpty || genderText.text!.isEmpty || countryText.text!.isEmpty || yourSchool.text!.isEmpty || yourClass.text!.isEmpty {
//alert message popup
let alertController = UIAlertController(title: "Error", message: "Please fill all fields", preferredStyle: .alert)
alertController.addAction(UIAlertAction(title: "Ok", style: .default, handler: { (action:UIAlertAction) in
print("Okay")
}))
self.present(alertController, animated: true, completion: nil)
}
else {
Auth.auth().createUser(withEmail: yourEmail.text!, password: yourPassword.text!) { (user, error) in
if error != nil {
///print errror message
let alertController = UIAlertController(title: "Error", message: error?.localizedDescription, preferredStyle: .alert)
alertController.addAction(UIAlertAction(title: "Ok", style: .default, handler: { (action:UIAlertAction) in
print("Okay")
}))
self.present(alertController, animated: true, completion: nil)
}
else {
let alertController = UIAlertController(title: "Congratulation", message: "You have successfully signed up", preferredStyle: .alert)
alertController.addAction(UIAlertAction(title: "Get Started", style: .default, handler: { (action:UIAlertAction) in
self.performSegue(withIdentifier: "back2SignPage", sender: self)
}))
self.present(alertController, animated: true, completion: nil)
//updating user information
let userID = Auth.auth().currentUser!.uid
let usertype: String = "Student"
self.ref.child("users").child(userID).setValue(["usertype": usertype ,"username": self.nameText.text!, "usergender": self.genderText.text!, "usercountry": self.countryText.text!, "userschool": self.yourSchool.text!, "userclass": self.yourClass.text!,])
}
}
}
}

Swift: How to make an action occur if UIAlertAction is pressed?

I'm trying to make an app where if the score is 3 the app displays a message that says "you lose" but keeps '3' as the number in the score label until the End Game option in the popup is pressed, at which point the score goes back to 0 for a new game. I am new to swift and am having difficulty and would really appreciate any and all help! I am not sure if making an IBAction for the alert action is the right thing to do or not.
else if rightscorecount == 3 {
let alert = UIAlertController(title: "Game", message: "You Lose!", preferredStyle: UIAlertControllerStyle.alert)
alert.addAction(UIAlertAction(title: "End Game", style: UIAlertActionStyle.default) { UIAlertAction in})
self.present(alert, animated: true, completion: nil)
}
}
#IBAction func test(sender: UIAlertAction) {
rightscorecount = 0
rightscorelabel.text = String(rightscorecount)
}
Try this:
let alertController = UIAlertController.init(title: "Game", message: "You Lose!", preferredStyle: .alert)
alertController.addAction(UIAlertAction.init(title: "End Game", style: .default, handler: { (action) in
// Your handler goes here
self.someFunction()
}))
self.present(alertController, animated: true) {
// Completion block
}
And your function
func someFunction() {
// Function body goes here
}

Firebase login system

So here is the deal. Right now I have a viewcontroller where the user can signup, and it is working (checked in Firebase console). The next step is that I have another view with two fields and a Log in button. That login button now has a segue to the third view, home. But it is possible to click it even though nothing has been entered in the two textfields. The button should only work if the user enters his or he details he made in the signup view, thus logging in.
How can I do this?
already have the login code:
#IBAction func loginAction(sender: AnyObject)
{
if self.emailField.text == "" || self.passwordField.text == ""
{
let alertController = UIAlertController(title: "Oops!", message: "Please enter an email and password.", preferredStyle: .Alert)
let defaultAction = UIAlertAction(title: "OK", style: .Cancel, handler: nil)
alertController.addAction(defaultAction)
self.presentViewController(alertController, animated: true, completion: nil)
}
else
{
FIRAuth.auth()?.signInWithEmail(self.emailField.text!, password: self.passwordField.text!) { (user, error) in
if error == nil
{
self.emailField.text = ""
self.passwordField.text = ""
}
else
{
let alertController = UIAlertController(title: "Oops!", message: error?.localizedDescription, preferredStyle: .Alert)
let defaultAction = UIAlertAction(title: "OK", style: .Cancel, handler: nil)
alertController.addAction(defaultAction)
self.presentViewController(alertController, animated: true, completion: nil)
}
In the second if statement you see that it clears the fields to show the login worked.
What i need is that users can only login if the correct details are filled in, that are in the Firebase database.
Instead of checking if there isnt any errors, check that there is data is the user object like this.
FIRAuth.auth()?.signInWithEmail(self.emailField.text!, password: self.passwordField.text!) { (user, error) in
if user != nil
{
let VC = storyboard?.instantiateViewControllerWithIdentifier("Identifier") as! AccountViewController //The file that controls the view
self.presentViewController(VC, animated: true, completion: nil)
}
else
{
let alertController = UIAlertController(title: "Oops!", message: error?.localizedDescription, preferredStyle: .Alert)
let defaultAction = UIAlertAction(title: "OK", style: .Cancel, handler: nil)
alertController.addAction(defaultAction)
self.presentViewController(alertController, animated: true, completion: nil)
}
I managed to fix it by adding self. infront of
storyboard?.instantiate.
Thus creating:
self.storyboard?instantiate.

UIAlertController Keeps Re-Appearing After Closing It

I have written code for an alert to appear when the input in one of my UITextFields is less than 1050. It successfully appears when the inputs satisfies that, but after I press "OK" it instantly re-appears.
Below is the code in the viewDidLoad function:
override func viewDidLoad(){
super.viewDidLoad()
alert = UIAlertController(title: "Error", message: "Please enter an exit width value greater than 1050", preferredStyle: UIAlertControllerStyle.Alert)
let okay = UIAlertAction(title: "OK", style: UIAlertActionStyle.Destructive, handler: valueCalc)
alert.addAction(okay)
}
Then I have in my valueCalc function (which is called when a button is tapped):
#IBAction func valueCalc(sender: AnyObject){
if(Int(mmText.text!)! < 1050){ //mmText is an UITextField
self.presentViewController(alert, animated: true, completion: nil)
}
}
According to your line of code
let okay = UIAlertAction(title: "OK", style: UIAlertActionStyle.Destructive, handler: valueCalc)
Your handler name valueCalc is called when you press OK.
Again the value is calculated which when come out be less then the specified characters shows back you the alert.
Instead of that, replace this line in your code -
let okay = UIAlertAction(title: "OK", style: UIAlertActionStyle.Destructive, handler: handlerMethod)
and add this method to your code
func handlerMethod() {
//handle your action here after ok is pressed for e.g if you wanna just dismiss the alert then write
dismissViewControllerAnimated(true, completion: nil)
}
You have the handler argument for your UIAlertAction set to valueCalc. Therefore, whenever the user taps "OK", the method valueCalc gets run again, and since the value is (presumably) still the same, the alert is presented right back again.
Try this
override func viewDidLoad(){
super.viewDidLoad()
alert = UIAlertController(title: "Error", message: "Please enter an exit width value greater than 1050", preferredStyle: UIAlertControllerStyle.Alert)
let okay = UIAlertAction(
title: "OK",
style: UIAlertActionStyle.Destructive) { (action) in }
}
#IBAction func valueCalc(sender: AnyObject){
if(Int(mmText.text!)! < 1050){ //mmText is an UITextField
self.presentViewController(alert, animated: true, completion: nil)
}

Resources