2017-06-05 2 views
0

Ich versuche, Alarmaktionen in einem Array an eine Funktion zu übergeben, die die UIAlertController-Konfiguration in einer einzigen Zeile vereinfacht. Ich bin in der Lage, Schaltflächenüberschriften, aber keine Warnaktionen erfolgreich zu übergeben. Hier ist was ich mache.Übergabe von Sperren/Blöcken im Array als Parameter iOS

+(void)showAlertWithTitle:(NSString*)title 
        message:(NSString*)alertmessage 
      buttonTitles:(NSArray*)buttonTitles 
      buttonActions:(NSArray*)buttonActions 
     inViewController:(UIViewController*)viewController { 

    UIAlertController *alert = [UIAlertController alertControllerWithTitle:title message:alertmessage preferredStyle:UIAlertControllerStyleAlert]; 

    [buttonTitles enumerateObjectsUsingBlock:^(NSString* buttonTitle,NSUInteger idx,BOOL *stop){ 
     UIAlertAction *action = [UIAlertAction actionWithTitle:buttonTitle style:UIAlertActionStyleDefault handler: [[buttonActions objectAtIndex:idx] copy]]; //blocks should always be copied to heap from stack else they will crash 
     [alert addAction:action]; 
    }]; 

    [viewController presentViewController:alert animated:YES completion:nil]; 

} 

Die obige Codedatei wurde lange zurück geschrieben, so dass es in Ziel c. Ich habe einige neue Dateien geschrieben, die in swift sind und ich rufe die obige Methode in swift wie unten auf.

CommonManager.showAlert(withTitle: "", message: "Feedback Sent", 
     buttonTitles: ["Ok"], buttonActions: [ { (action: UIAlertAction) in 

        print("you pressed Ok alert button"); 

        // call method whatever u need 
       }], in: self) 

Wenn ich die Schließung passieren nicht, dass es funktioniert gut, wenn die Schließung vorbei, wenn Sie auf Ok stürzt. Ich fand auch, dass wir einen Block kopieren müssen, wenn er als eine Sammlung übergeben wurde, und ich tat das, aber etwas ist immer noch nicht richtig, was ich nicht herausfinden kann. Kannst du mir sagen, was ich hier machen soll?

Dank

Antwort

-1

Anstatt mit Wandlungs- Seltsamkeit zu tun, warum nicht nur eine native swift Version machen?

Hier ist meine Version der gleichen Funktionalität:

extension UIViewController { 

    func presentAlert(title: String, message: String, actions: [UIAlertAction] = [UIAlertAction(title: "OK", style: .cancel, handler: nil)], iPadOrigin: CGRect? = nil, style: UIAlertControllerStyle = .alert, animated: Bool = true, completion: (() ->())? = nil) { 

     let alert = UIAlertController(title: title, message: message, preferredStyle: style) 
     actions.forEach(alert.addAction) 
     alert.popoverPresentationController?.sourceView = self.view 
     if let iPadOrigin = iPadOrigin { 
      alert.popoverPresentationController?.sourceRect = iPadOrigin 
     } 

     present(alert, animated: animated, completion: completion) 
    } 

    func presentAlert(title: String, message: String, actions: [UIAlertAction] = [UIAlertAction(title: "OK", style: .cancel, handler: nil)], iPadButtonOrigin: UIBarButtonItem? = nil, style: UIAlertControllerStyle = .alert, animated: Bool = true, completion: (() ->())? = nil) { 

     let alert = UIAlertController(title: title, message: message, preferredStyle: style) 
     actions.forEach(alert.addAction) 
     alert.view.tintColor = Color.BlueDarker 
     alert.popoverPresentationController?.barButtonItem = iPadButtonOrigin 

     present(alert, animated: animated, completion: completion) 
    } 
} 

Es behandelt auch iPad Unterschiede und einige nette Standardwerte, so dass Sie nur viewController.presentAlert(title: "Error", message: "Something broke") tun könnte, wenn Sie eine einfache Warnung auf iPhone wollen.

1

Das Problem ist, dass ein Swift-Closure eine andere Art von Objekt als ein Objective-C-Block ist, also versucht, es als ein Block abzustürzen. Wenn der Swift-Compiler erkennt, dass Sie eine Schließung an eine Objective-C-Methode mit einem Blocktyp-Parameter übergeben, wird der Swift-Abschluss normalerweise in einen Objective-C-Block konvertiert, aber in diesem Fall sieht er Sie setzen es in ein Array und nicht darauf, was die Methode im Array damit anstellt, so dass es keine Konvertierung durchführt.

Die einzige Art, wie ich herausfinden kann, um es zu bekommen ist so etwas zu arbeiten:

CommonManager.showAlert(withTitle: "", message: "Feedback Sent", 
     buttonTitles: ["Ok"], buttonActions: [ { (action: UIAlertAction) in 

        print("you pressed Ok alert button"); 

        // call method whatever u need 
       } as (@convention(block) (UIAlertAction) -> Void)!], in: self) 
+0

Diese Lösung für mich gearbeitet, dank @newacct –

Verwandte Themen