在prepareForSegue方法中防止segue?

Shm*_*idt 247 cocoa-touch storyboard uiviewcontroller ios segue

是否可以取消prepareForSegue:方法中的segue ?

我想在segue之前执行一些检查,如果条件不为真(在这种情况下,如果某些UITextField是空的),则显示错误消息而不是执行segue.

小智 480

在iOS 6及更高版本中可以实现:您必须实现该方法

- (BOOL)shouldPerformSegueWithIdentifier:(NSString *)identifier sender:(id)sender 
Run Code Online (Sandbox Code Playgroud)

在您的视图控制器中.你在那里进行验证,如果没有问题,那么return YES;如果没有,那么return NO;就不会调用prepareForSegue.

请注意,在以编程方式触发segues时,不会自动调用此方法.如果需要执行检查,则必须调用shouldPerformSegueWithIdentifier来确定是否执行segue.

  • 仅供参考,如果通过调用[self performSegueWithIdentifier:@"segueIdentifier"sender:nil]以编程方式触发segue; 永远不会调用shouldPerformSegueWithIdentifier. (104认同)
  • @AubadaTaljo :(格式化道歉)`if([self shouldPerformSegueWithIdentifier:@"segueIdentifier"sender:nil]){[self performSegueWithIdentifier:@"segueIdentifier"sender:nil]; }` (6认同)
  • @Thedude感谢你指出这一点.追踪一个问题并没有达到我的断点.对于任何好奇的人,你只需要调用包含在if语句中的这个方法来获得相同的结果. (3认同)

Mik*_*ock 52

注意:如果您可以定位iOS 6,则接受的答案是最佳方法.对于iOS 5的定位,此答案可以.

我不相信有可能取消一个赛格prepareForSegue.我建议将您的逻辑移动到performSegue首先发送消息的程度.

如果您使用Interface Builder将segue直接连接到控件(例如将segue直接链接到a UIButton),那么您可以通过一些重构来完成此操作.将segue连接到视图控制器而不是特定控件(删除旧的segue链接,然后从视图控制器本身控制拖动到目标视图控制器).然后IBAction在视图控制器中创建一个,并将控件连接到IBAction.然后你可以在你刚创建的IBAction中做你的逻辑(检查空TextField),然后决定是否以performSegueWithIdentifier编程方式.


Ord*_*Dei 16

Swift 3:func shouldPerformSegue(withIdentifier identifier:String,sender:Any?) - > Bool

如果应该执行segue,则返回true;如果应该忽略,则返回false.

示例:

var badParameters:Bool = true

override func shouldPerformSegue(withIdentifier identifier: String, sender: Any?) -> Bool {
    if badParameters  {
         // your code here, like badParameters  = false, e.t.c
         return false
    }
    return true
}
Run Code Online (Sandbox Code Playgroud)


Kao*_*ire 12

或者,提供用户不应按下的按钮会有些不好的行为.您可以将segue连接为支架,但是从禁用按钮开始.然后将UITextField的"editingChanged"连接到视图控件ala上的事件

- (IBAction)nameChanged:(id)sender {
    UITextField *text = (UITextField*)sender;
    [nextButton setEnabled:(text.text.length != 0)];
}
Run Code Online (Sandbox Code Playgroud)


Zum*_*med 11

它很容易在迅速.

override func shouldPerformSegueWithIdentifier(identifier: String,sender: AnyObject?) -> Bool {

    return true
}
Run Code Online (Sandbox Code Playgroud)

  • 咦?你能详细说明这个答案吗?仅限代码的答案对于其他读者来说并不是很有用...... (3认同)

Aec*_*Liu 9

正如亚伯拉罕所说,在以下功能中检查是否有效.

- (BOOL)shouldPerformSegueWithIdentifier:(NSString *)identifier sender:(nullable id)sender
{
     // Check this identifier is OK or NOT.
}
Run Code Online (Sandbox Code Playgroud)

而且,performSegueWithIdentifier:sender:编程调用可以通过覆盖以下方法来阻止.默认情况下,它不会检查是否有效-shouldPerformSegueWithIdentifier:sender:,我们可以手动执行.

- (void)performSegueWithIdentifier:(NSString *)identifier sender:(id)sender
{
    // Check valid by codes
    if ([self shouldPerformSegueWithIdentifier:identifier sender:sender] == NO) {
        return;
    }

    // If this identifier is OK, call `super` method for `-prepareForSegue:sender:` 
    [super performSegueWithIdentifier:identifier sender:sender];
}
Run Code Online (Sandbox Code Playgroud)


Pan*_*rni 7

斯威夫特 4 答案:

以下是取消 segue 的 Swift 4 实现:

override func shouldPerformSegue(withIdentifier identifier: String, sender: Any?) -> Bool {
    if identifier == "EditProfile" {
        if userNotLoggedIn {
            // Return false to cancel segue with identified Edit Profile
            return false
        }
    }
    return true
}
Run Code Online (Sandbox Code Playgroud)


小智 5

应该登录注册登记

-(BOOL)shouldPerformSegueWithIdentifier:(NSString *)identifier sender:(id)sender
{

    [self getDetails];

    if ([identifier isEqualToString:@"loginSegue"])
    {

        if (([_userNameTxtf.text isEqualToString:_uname])&&([_passWordTxtf.text isEqualToString:_upass]))
        {

            _userNameTxtf.text=@"";
            _passWordTxtf.text=@"";

            return YES;
        }
        else
        {
            UIAlertView *loginAlert = [[UIAlertView alloc] initWithTitle:@"Alert" message:@"Invalid Details" delegate:self cancelButtonTitle:@"Try Again" otherButtonTitles:nil];

            [loginAlert show];

            _userNameTxtf.text=@"";
            _passWordTxtf.text=@"";

            return NO;
        }

    }

    return YES;

}

-(void)getDetails
{
    NSArray *dir=NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);

    NSString *dbpath=[NSString stringWithFormat:@"%@/userDb.sqlite",[dir lastObject]];

    sqlite3 *db;

    if(sqlite3_open([dbpath UTF8String],&db)!=SQLITE_OK)
    {
        NSLog(@"Fail to open datadbase.....");
        return;
    }

    NSString *query=[NSString stringWithFormat:@"select * from user where userName = \"%@\"",_userNameTxtf.text];

    const char *q=[query UTF8String];

    sqlite3_stmt *mystmt;

    sqlite3_prepare(db, q, -1, &mystmt, NULL);

    while (sqlite3_step(mystmt)==SQLITE_ROW)
    {
        _uname=[NSString stringWithFormat:@"%s",sqlite3_column_text(mystmt, 0)];

        _upass=[NSString stringWithFormat:@"%s",sqlite3_column_text(mystmt, 2)];
    }

    sqlite3_finalize(mystmt);
    sqlite3_close(db);

}
Run Code Online (Sandbox Code Playgroud)