Problem with UIAlertController's Text field Swift - ios

Here is my code. When I press "Download" button my "someVariable" global variable doesn't change. I tried to debug it in the debugger but couldn't find the issue.
#IBAction func addButtonPressed(_ sender: UIBarButtonItem) {
let textField = UITextField()
let alert = UIAlertController(title: "Download URL", message: "", preferredStyle: .alert)
alert.addTextField { (actionTextField) in
actionTextField.placeholder = "Paste link here"
}
let action = UIAlertAction(title: "Download", style: .default) { (action) in
self.someVariable = textField.text!
}
let secondAction = UIAlertAction(title: "Cancel", style: .cancel, handler: nil)
alert.addAction(action)
alert.addAction(secondAction)
present(alert, animated: true, completion: nil)
}

Welcome to Stackoverflow. Your textField in line 2 is what you're getting your someVariable's new value from. I'm supposing you want to get the value from your alert's textField instead.
You can get reference from your alert's textField through your alert's textFields property, like so:
let action = UIAlertAction(title: "Download", style: .default) { (action) in
guard let textField = alert.textFields?.first else { return }
self.someVariable = textField.text!
}

Related

swift iOS adding validation in alert textfield [duplicate]

This question already has answers here:
Enable UIAlertAction of UIAlertController only after input is validated
(6 answers)
Closed 1 year ago.
I would like to add validation on my hardcode data which known as itemArray
Below are my screenshot that current alert view here
These are my codes
#IBAction func adDButtonPressed(_ sender: UIBarButtonItem) {
var textField = UITextField()
let alert = UIAlertController(title: "Add Email", message: "", preferredStyle: .alert)
let cancel = UIAlertAction(title: "cancel", style: .default) { (action) -> Void in
print("Cancel button tapped")
}
let action = UIAlertAction(title: "Add", style: .default) { (action) in
self.itemArray.append(textField.text!)
self.defaults.set(self.itemArray, forKey: "EmailArray")
self.tableView.reloadData()
}
alert.addTextField { (alertTextField) in
alertTextField.placeholder = "Create New Email"
textField = alertTextField
}
alert.addAction(action)
alert.addAction(cancel)
present(alert, animated: true, completion: nil)
}
}
to all swift experts, may I know is there any way for me too add validation such as alert textfield == "0" disable the add function for the users. your help is highly appreciated!
I am not sure what you want to happen if it does say "0"?
#IBAction func adDButtonPressed(_ sender: UIBarButtonItem) {
var textField = UITextField()
let alert = UIAlertController(title: "Add Email", message: "", preferredStyle: .alert)
let cancel = UIAlertAction(title: "cancel", style: .default) { (action) -> Void in
print("Cancel button tapped")
}
let action = UIAlertAction(title: "Add", style: .default) { (action) in
if textField.text != "0" {
self.itemArray.append(textField.text!)
self.defaults.set(self.itemArray, forKey: "EmailArray")
self.tableView.reloadData()
} else {
//do something to help them like display error message
}
}
alert.addTextField { (alertTextField) in
alertTextField.placeholder = "Create New Email"
textField = alertTextField
}
alert.addAction(action)
alert.addAction(cancel)
present(alert, animated: true, completion: nil)
}
}

How can i add "essential typing" use with UIAlertController's textField in swift?

I want to add function such as, if there are no any letters in textfield and press confirm button, than textfield print "you must need to write folder name", and stop action while there print is showing. I was find something examples in google, but I don't know how adjust with my code.
func folderAddAlert() {
let alert = UIAlertController(title: "Folder name", message: nil, preferredStyle: .alert)
alert.addTextField {(folderAddTF) in folderAddTF.placeholder = "Please add folder name"
print("+ clicked." )
}
let action = UIAlertAction(title: "Confirm", style: .default){ (_) in
guard let folder = alert.textFields?.first?.text else { return }
print("folderName: \(folder)")
self.folderNames.append(folder)
self.collectionView.reloadData()
}
let cancel = UIAlertAction(title: "Cancel", style: UIAlertAction.Style.default, handler: nil)
alert.addAction(action)
alert.addAction(cancel)
present(alert, animated: true, completion: nil)
}
}
you are in the right way, but in here you need check the textfield is empty or not on your validation on user press the Confirm button like this
let action = UIAlertAction(title: "Confirm", style: .default){ (_) in
guard let folder = alert.textFields?.first?.text, !folder.isEmpty else {
self.present(alert, animated: true, completion: nil)
if let getPlaceholder = alert.textFields?.first, let placeHolderText = getPlaceholder.placeholder{
getPlaceholder.attributedPlaceholder = NSAttributedString(string: placeHolderText,
attributes: [NSAttributedString.Key.foregroundColor: UIColor.red])
}
return }
print("folderName: \(folder)")
}

Is there a way to call an alert controller from inside a current alert controller (or a textfield in an action sheet)? Xcode 8, Swift 3, IOS

Please help! Im a huge beginner. Im trying to get a picker view and a textfield into one alert controller. Apparently I can't add a picker view into an alert controller since IOS 8. Instead I need to use an action sheet with multiple actions. Why can't I use a default alert style? Because I need more than 2 actions and the default alert style apparently only permits a max of 2 actions. So, I need to use an action sheet. Only problem is I can't seem to find a way to put an editable textfield into an action sheet, to have multiple action options - instead of an editable textfield in my default alert style, with only two action options.
This is what I have so far, for my editable textfield in my default alert style, with only two options (OK and cancel):
#IBOutlet weak var TEXTTESTLabel: UILabel!
#IBAction func TEXTESTTapped(_ sender: UIButton) {
print("TEXTTEST Button Tapped")
openTEXTTESTAlert()
}
func openTEXTTESTAlert() {
//Create Alert Controller
let alert9 = UIAlertController (title: "Test Your Text:", message: nil, preferredStyle: UIAlertControllerStyle.alert)
//Create Cancel Action
let cancel9 = UIAlertAction(title: "Cancel", style: UIAlertActionStyle.cancel, handler: nil)
alert9.addAction(cancel9)
//Create OK Action
let ok9 = UIAlertAction(title: "OK", style: UIAlertActionStyle.default) { (action: UIAlertAction) in print("OK")
let textfield = alert9.textFields?[0]
print(textfield?.text!)
self.TEXTTESTLabel.text = textfield?.text!
}
alert9.addAction(ok9)
//Add Text Field
alert9.addTextField { (textfield: UITextField) in
textfield.placeholder = "TEXTTEST"
}
//Present Alert Controller
self.present(alert9, animated:true, completion: nil)
}
//////////////////////////////////////////////////////////////////////////////////
Since this, I've gotten help to create two separate alert controllers but it looks and feels messy. It's set up so if I click button 2 the default alert style with a textfield will pop and insert text into a label. But, if i click button 1, AND THEN I click button 2, it will show an action sheet with 4 actions that put a word into that same label. This is what I have for that method:
#IBOutlet weak var TextLabel: UILabel!
var userWantsToShowAlert = false
#IBAction func yourNewButtonTapped(_ sender: UIButton) {
userWantsToShowAlert = !userWantsToShowAlert
print("User wants to show alert? \(userWantsToShowAlert)")
//This is userWantsToShowAlert is false, it will change it to true. And if it is true, it will change it to false.
}
#IBAction func TextButtonTapped(_ sender: UIButton) {
print("Text Button Tapped")
if(userWantsToShowAlert){
openTextAlert()
}else{
openActionSheetAlert()
}
}
func openTextAlert() {
//Create Alert Controller
let alert9 = UIAlertController (title: "Whatever Text Your Heart Desires:", message: nil, preferredStyle: UIAlertControllerStyle.alert)
//Create Cancel Action
let cancel9 = UIAlertAction(title: "Cancel", style: UIAlertActionStyle.cancel, handler: nil)
alert9.addAction(cancel9)
//Create OK Action
let ok9 = UIAlertAction(title: "OK", style: UIAlertActionStyle.default) { (action: UIAlertAction) in print("OK")
let textfield = alert9.textFields?[0]
print(textfield?.text!)
self.TextLabel.text = textfield?.text!
}
alert9.addAction(ok9)
//Add Text Field
alert9.addTextField { (textfield: UITextField) in
textfield.placeholder = "Whatever text you want to enter"
}
//Present Alert Controller
self.present(alert9, animated:true, completion: nil)
}
func openActionSheetAlert(){
let alert9 = UIAlertController (title: "Whatever Text Your Heart Desires:", message: nil, preferredStyle: UIAlertControllerStyle.actionSheet)
//Create Cancel Action
let cancel9 = UIAlertAction(title: "Cancel", style: UIAlertActionStyle.cancel, handler: nil)
alert9.addAction(cancel9)
let bt1 = UIAlertAction(title: "1", style: UIAlertActionStyle.default){
(action) in self.TextLabel.text = "Word 1"}
alert9.addAction(bt1)
let bt2 = UIAlertAction(title: "2", style: UIAlertActionStyle.default){
(action) in self.TextLabel.text = "Word 2"}
alert9.addAction(bt2)
let bt3 = UIAlertAction(title: "3", style: UIAlertActionStyle.default){
(action) in self.TextLabel.text = "Word 3"}
alert9.addAction(bt3)
let bt4 = UIAlertAction(title: "4", style: UIAlertActionStyle.default){
(action) in self.TextLabel.text = "Word 4"}
alert9.addAction(bt4)
alert9.popoverPresentationController?.sourceView = self.view
alert9.popoverPresentationController?.sourceRect = CGRect(x: self.view.bounds.size.width / 2.0, y: self.view.bounds.size.height / 4.0, width: 1.0, height: 1.0)
self.present(alert9, animated:true, completion: nil)
}
I find that this method is confusing to the application user. If anyone has a different method to get a textfield into an action sheet (or even a separate alert controller imbedded in a current alert controller), I'd appreciate it VERY much!
Thank you :)
For Action sheet you can use as
func showActionSheet()
{
let actionSheet = UIAlertController(title: nil, message: nil, preferredStyle: UIAlertControllerStyle.actionSheet)
actionSheet.addAction(UIAlertAction(title: "1:", style: UIAlertActionStyle.default, handler: { (alert:UIAlertAction!) -> Void in
)
self.action1()
}))
actionSheet.addAction(UIAlertAction(title: "2", style: UIAlertActionStyle.default, handler: { (alert:UIAlertAction!) -> Void in
self.action2()
}))
actionSheet.addAction(UIAlertAction(title: "3", style: UIAlertActionStyle.default, handler: { (alert:UIAlertAction!) -> Void in
// self.action3()
}))
actionSheet.addAction(UIAlertAction(title: "Cancel", style: UIAlertActionStyle.cancel, handler: nil))
self.present(actionSheet, animated: true, completion: nil)
}
// showActionSheet()
I found the solution! I was wrong about having only 2 actions in the default alert style. How to scroll through actions in alert controller? Xcode 8, Swift 3, IOS

Alert controller with dropdown menu and keyboard option? Swift 3, Xcode 8, IOS

I'm a huge beginner when it comes to programming.
I currently have an alert controller set up so that when I click a button in the view controller an alert controller pops up. I can enter text into a textfield (in the alert controller) and the text will show up on a label (in my view controller), when I click okay (in the alert controller). This is the code for what i have:
//Text button
#IBOutlet weak var TextLabel: UILabel!
#IBAction func TextButtonTapped(_ sender: UIButton) {
print("Text Button Tapped")
openTextAlert()
}
func openTextAlert() {
//Create Alert Controller
let alert9 = UIAlertController (title: "Whatever Text Your Heart Desires:", message: nil, preferredStyle: UIAlertControllerStyle.alert)
//Create Cancel Action
let cancel9 = UIAlertAction(title: "Cancel", style: UIAlertActionStyle.cancel, handler: nil)
alert9.addAction(cancel9)
//Create OK Action
let ok9 = UIAlertAction(title: "OK", style: UIAlertActionStyle.default) { (action: UIAlertAction) in print("OK")
let textfield = alert9.textFields?[0]
print(textfield?.text!)
self.TextLabel.text = textfield?.text!
}
alert9.addAction(ok9)
//Add Text Field
alert9.addTextField { (textfield: UITextField) in
textfield.placeholder = "Whatever text you want to enter"
}
//Present Alert Controller
self.present(alert9, animated:true, completion: nil)
}
How can I get multiple actions in my alert controller so that it ALSO acts as a dropdown menu with certain words so that I don't need to always write out key words? I need both, the ability to type my own words and phrases and a preset of words and phrases for efficiency.
Please help! I'm a huge noob. Thank you :)
Swift 3, Xcode 8, IOS
Just write this using your code. Is this what you need?
EDIT: the yourNewButtonTapped function is simply to show you how you can set a condition to show either the simple alert or the actionSheet. In this function, when you click your new button, and then your TextButton, your alert will be shown. If you click your new button again, you will set userWantsToShowAlert as false. And when you click again your textButtonTapped, the openActionSheet will be called.
You can do this in so many ways.
#IBOutlet weak var TextLabel: UILabel!
var userWantsToShowAlert = false
#IBAction func yourNewButtonTapped(_ sender: UIButton) {
userWantsToShowAlert = !userWantsToShowAlert
print("User wants to show alert? \(userWantsToShowAlert)")
//This is userWantsToShowAlert is false, it will change it to true. And if it is true, it will change it to false.
}
#IBAction func TextButtonTapped(_ sender: UIButton) {
print("Text Button Tapped")
if(userWantsToShowAlert){
openTextAlert()
}else{
openActionSheetAlert()
}
}
func openTextAlert() {
//Create Alert Controller
let alert9 = UIAlertController (title: "Whatever Text Your Heart Desires:", message: nil, preferredStyle: UIAlertControllerStyle.alert)
//Create Cancel Action
let cancel9 = UIAlertAction(title: "Cancel", style: UIAlertActionStyle.cancel, handler: nil)
alert9.addAction(cancel9)
//Create OK Action
let ok9 = UIAlertAction(title: "OK", style: UIAlertActionStyle.default) { (action: UIAlertAction) in print("OK")
let textfield = alert9.textFields?[0]
print(textfield?.text!)
self.TextLabel.text = textfield?.text!
}
alert9.addAction(ok9)
//Add Text Field
alert9.addTextField { (textfield: UITextField) in
textfield.placeholder = "Whatever text you want to enter"
}
//Present Alert Controller
self.present(alert9, animated:true, completion: nil)
}
func openActionSheetAlert(){
let alert9 = UIAlertController (title: "Whatever Text Your Heart Desires:", message: nil, preferredStyle: UIAlertControllerStyle.actionSheet)
//Create Cancel Action
let cancel9 = UIAlertAction(title: "Cancel", style: UIAlertActionStyle.cancel, handler: nil)
alert9.addAction(cancel9)
let bt1 = UIAlertAction(title: "1", style: UIAlertActionStyle.default){
(action) in self.TextLabel.text = "Word 1"}
alert9.addAction(bt1)
let bt2 = UIAlertAction(title: "2", style: UIAlertActionStyle.default){
(action) in self.TextLabel.text = "Word 2"}
alert9.addAction(bt2)
let bt3 = UIAlertAction(title: "3", style: UIAlertActionStyle.default){
(action) in self.TextLabel.text = "Word 3"}
alert9.addAction(bt3)
let bt4 = UIAlertAction(title: "4", style: UIAlertActionStyle.default){
(action) in self.TextLabel.text = "Word 4"}
alert9.addAction(bt4)
alert9.popoverPresentationController?.sourceView = self.view
alert9.popoverPresentationController?.sourceRect = CGRect(x: self.view.bounds.size.width / 2.0, y: self.view.bounds.size.height / 2.0, width: 1.0, height: 1.0)
self.present(alert9, animated:true, completion: nil)
}

Get input value from TextField in iOS alert in Swift

I'm trying to make an alert message with input, and then get the value from the input. I've found many good tutorials how to make the input text field. but I can't get the value from the alert.
Updated for Swift 3 and above:
//1. Create the alert controller.
let alert = UIAlertController(title: "Some Title", message: "Enter a text", preferredStyle: .alert)
//2. Add the text field. You can configure it however you need.
alert.addTextField { (textField) in
textField.text = "Some default text"
}
// 3. Grab the value from the text field, and print it when the user clicks OK.
alert.addAction(UIAlertAction(title: "OK", style: .default, handler: { [weak alert] (_) in
let textField = alert.textFields![0] // Force unwrapping because we know it exists.
print("Text field: \(textField.text)")
}))
// 4. Present the alert.
self.present(alert, animated: true, completion: nil)
Swift 2.x
Assuming you want an action alert on iOS:
//1. Create the alert controller.
var alert = UIAlertController(title: "Some Title", message: "Enter a text", preferredStyle: .Alert)
//2. Add the text field. You can configure it however you need.
alert.addTextFieldWithConfigurationHandler({ (textField) -> Void in
textField.text = "Some default text."
})
//3. Grab the value from the text field, and print it when the user clicks OK.
alert.addAction(UIAlertAction(title: "OK", style: .Default, handler: { [weak alert] (action) -> Void in
let textField = alert.textFields![0] as UITextField
println("Text field: \(textField.text)")
}))
// 4. Present the alert.
self.presentViewController(alert, animated: true, completion: nil)
Swift 5
You can use the below extension for your convenience.
Usage inside a ViewController:
showInputDialog(title: "Add number",
subtitle: "Please enter the new number below.",
actionTitle: "Add",
cancelTitle: "Cancel",
inputPlaceholder: "New number",
inputKeyboardType: .numberPad, actionHandler:
{ (input:String?) in
print("The new number is \(input ?? "")")
})
The extension code:
extension UIViewController {
func showInputDialog(title:String? = nil,
subtitle:String? = nil,
actionTitle:String? = "Add",
cancelTitle:String? = "Cancel",
inputPlaceholder:String? = nil,
inputKeyboardType:UIKeyboardType = UIKeyboardType.default,
cancelHandler: ((UIAlertAction) -> Swift.Void)? = nil,
actionHandler: ((_ text: String?) -> Void)? = nil) {
let alert = UIAlertController(title: title, message: subtitle, preferredStyle: .alert)
alert.addTextField { (textField:UITextField) in
textField.placeholder = inputPlaceholder
textField.keyboardType = inputKeyboardType
}
alert.addAction(UIAlertAction(title: actionTitle, style: .default, handler: { (action:UIAlertAction) in
guard let textField = alert.textFields?.first else {
actionHandler?(nil)
return
}
actionHandler?(textField.text)
}))
alert.addAction(UIAlertAction(title: cancelTitle, style: .cancel, handler: cancelHandler))
self.present(alert, animated: true, completion: nil)
}
}
In Swift5 ans Xcode 10
Add two textfields with Save and Cancel actions and read TextFields text data
func alertWithTF() {
//Step : 1
let alert = UIAlertController(title: "Great Title", message: "Please input something", preferredStyle: UIAlertController.Style.alert )
//Step : 2
let save = UIAlertAction(title: "Save", style: .default) { (alertAction) in
let textField = alert.textFields![0] as UITextField
let textField2 = alert.textFields![1] as UITextField
if textField.text != "" {
//Read TextFields text data
print(textField.text!)
print("TF 1 : \(textField.text!)")
} else {
print("TF 1 is Empty...")
}
if textField2.text != "" {
print(textField2.text!)
print("TF 2 : \(textField2.text!)")
} else {
print("TF 2 is Empty...")
}
}
//Step : 3
//For first TF
alert.addTextField { (textField) in
textField.placeholder = "Enter your first name"
textField.textColor = .red
}
//For second TF
alert.addTextField { (textField) in
textField.placeholder = "Enter your last name"
textField.textColor = .blue
}
//Step : 4
alert.addAction(save)
//Cancel action
let cancel = UIAlertAction(title: "Cancel", style: .default) { (alertAction) in }
alert.addAction(cancel)
//OR single line action
//alert.addAction(UIAlertAction(title: "Cancel", style: .default) { (alertAction) in })
self.present(alert, animated:true, completion: nil)
}
For more explanation https://medium.com/#chan.henryk/alert-controller-with-text-field-in-swift-3-bda7ac06026c
Swift version: 5.+
Create a new TextField variable in current scope and assign it to alertTextField in alert.addTextField completion handler. Use textField's value inside UIAlertAction completion handler.
#IBAction func addButtonPressed(_ sender: UIBarButtonItem) {
//Variable to store alertTextField
var textField = UITextField()
let alert = UIAlertController(title: "Add new item", message: "", preferredStyle: .alert)
alert.addTextField { alertTextField in
alertTextField.placeholder = "Create new item"
//Copy alertTextField in local variable to use in current block of code
textField = alertTextField
}
let action = UIAlertAction(title: "Add item", style: .default) { action in
//Prints the alertTextField's value
print(textField.text!)
}
alert.addAction(action)
present(alert, animated: true, completion: nil)
}
let ac = UIAlertController(title: "title", message: "message", preferredStyle: .alert)
ac.addTextField()
let submitAction = UIAlertAction(title: "Submit", style: .default) { [weak self, weak ac] action in
guard let wordToget = ac?.textFields?[0].text else { return }
//here you can do what you need like
print(wordToget)
}
ac.addAction(submitAction)
present(ac, animated: true)

Resources