本文介绍了dismissViewController:不工作的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个名为vc0的视图控制器,如下所示:

I have a view controller called vc0 which is presented like this:

[self presentViewController: vc1 animated: YES completion: nil];

在vc1中我有一个按钮来显示另一个视图控制器:

And in vc1 I have a button to present another view controller:

[self presentViewController: vc2 animated: YES completion: nil];

然后在vc2中,我有一个按钮来关闭视图控制器:

Then in vc2, I have a button to dismiss the view controller:

[self dismissViewControllerAnimated:YES completion: ^{
// over here I call one method in vc1
}

正如预期的那样它会返回到vc1 ..但是vc1中有一个按钮可以通过关闭视图返回到vc0像这样的控制器:

And as expected it returns back to vc1.. however there is a button in vc1 to go back to vc0 by dismissing the view controller like this:

    [self dismissViewControllerAnimated:YES completion:nil];

但由于某种原因它不起作用,视图控制器不会被解雇回vc0。当我第一次出现vc1时,我可以按下按钮来关闭视图控制器,它可以工作。但是,当我按下按钮打开vc2,当我将vc2解除回vc1时,然后我按下按钮关闭视图控制器,即它不起作用。

But for some reason it doesn't work, the view controller does not get dismissed back to vc0. When I first present vc1, I can press the button to dismiss the view controller and it works. But when I press the button to open vc2, and when I dismiss vc2 back to vc1, and THEN I press the button to dismiss the view controller, that is when it doesn't work.

对不起,如果问题有点不清楚,说出我想说的话有点难。

Sorry if the question is a bit unclear, it is a bit hard to phrase what I am trying to say.

还有一件事:

我尝试在vc1中替换 dismissViewControllerAnimated:来手动显示vc0,但后来我在控制台中输入一条说我的日志我试图呈现一个vc0但vc1的视图不在窗口层次结构中。这是什么意思?

I tried replacing dismissViewControllerAnimated: in vc1 to manually present vc0, but then I get a log in the console saying that I am trying to present a vc0 but vc1's view is not in the window hierarchy. What does this mean?

感谢您的帮助!

更新:

在这个案例中VC0是 MenuMileIndexViewController - VC1 IS FlightViewController - VC2 IS BookmarksTableViewController

IN THIS CASE VC0 IS MenuMileIndexViewController - VC1 IS FlightViewController - VC2 IS BookmarksTableViewController

以下是涉及的代码:



- (IBAction)goToOriginPage {

FlightRecorder *origin = [[FlightRecorder alloc] init];
[self presentViewController:origin animated:YES completion:nil];

}





    - (void)searchBarBookmarkButtonClicked:(UISearchBar *)searchBar {

        [self bringUpBookmarkkTable];
}

- (void) bringUpBookmarkkTable {

    BookmarkTableViewController *bookmarkTVC = [[BookmarkTableViewController alloc] init];

    [bookmarkTVC setModalTransitionStyle: UIModalTransitionStyleFlipHorizontal];

    [self presentViewController:bookmarkTVC animated:YES completion:nil];
}

- (IBAction)cancel {

[self dismissViewControllerAnimated:YES completion:nil];

}

- (void)endBookmarkProcessWithBookmarkCollection: (NSDictionary *)dict {

    presetBookmarkContext = [dict mutableCopy];

    bookmarkMode = YES;

    NSString *compiledText = nil;

    NSNumber *number1 = [NSNumber numberWithInt: 1];

    if ([dict objectForKey: @"bookmarkTag"] == number1) {

        compiledText = [NSString stringWithFormat: @"%@ to %@", [dict objectForKey: @"origin"], [dict objectForKey: @"destination"]];
    }
    else {

        compiledText = [NSString stringWithFormat: @"%@ to %@", [dict objectForKey: @"destination"], [dict objectForKey: @"origin"]];
    }

    compiledText = [compiledText stringByReplacingOccurrencesOfString:@"Origin: " withString:@""];

    compiledText = [compiledText stringByReplacingOccurrencesOfString:@"Destination: " withString:@""];

    flightContext = [NSDictionary dictionaryWithObjectsAndKeys: [dict objectForKey: @"miles"], @"miles", compiledText, @"location", [[NSUserDefaults standardUserDefaults] objectForKey: @"tempD"], @"date", nil];

    NSString *string = [NSString stringWithFormat: @"\nMiles: %.2f\nFlight: %@\nDate: %@", [[dict objectForKey: @"miles"] floatValue], compiledText, [[NSUserDefaults standardUserDefaults] objectForKey:@"tempD"]];

    UIAlertView *bvkBookmarkAlertView = [[UIAlertView alloc] initWithTitle:@"Confirmation" message:string delegate:self cancelButtonTitle:@"Cancel" otherButtonTitles:@"Add", nil];

    [bvkBookmarkAlertView show];
}



 - (void)alertView:(UIAlertView *)alertView didDismissWithButtonIndex:(NSInteger)buttonIndex {

    if (buttonIndex == 1) {

        [self cancel]; // Even though cancel is an IBAction, IBAction is the same thing as void so it is callable
    }
}

- (void)alertView:(UIAlertView *)alertView clickedButtonAtIndex:(NSInteger)buttonIndex {

    if (buttonIndex == 1) {

        [TheMileIndexViewController addDesiredMilesToIndex: [[flightContext objectForKey: @"miles"] doubleValue]];

        [TravelLogViewController addFlight: flightContext];

        if (!bookmarkMode) {

            if ([checkbox isSelected]) {

                [BookmarkHandler uploadBookmark: bookmarkFlightContext];
            }    
        }
    }

    if (buttonIndex == 0) {

        if ([alertView.title isEqualToString: @"Confirmation"]) {

            bookmarkMode = NO;
        }
    }

}





    - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {

    [tableView deselectRowAtIndexPath:indexPath animated: YES];

    NSDictionary *dict = [[BookmarkHandler bookmarkCollection] objectAtIndex: indexPath.row];

    fl = [[FlightRecorder alloc] init];

    [self dismissViewControllerAnimated:YES completion:^{

        [fl endBookmarkProcessWithBookmarkCollection: dict];
    }];
}

现在,我已经在模拟器中创建了应用程序的屏幕录制,显示了什么是问题。我可以通过电子邮件发送给您以供参考。所以我可以通过电子邮件发送给你。

NOW, I have created a screen recording of the app in simulator showing what is the problem. I can email that to you for reference. So I can email that to you.

推荐答案

我建议总是从实际提出它的VC中解雇VC - 使用代表。这实际上也是Apple推荐的方式 - 正如我之前关于这个问题的问题的答案所指出的那样。

I would recommend to always dismiss a VC from the VC that actually presented it - using a delegate. This is actually also the Apple recommended way - as was pointed out in a previous answer to my question regarding this issue.

所以如果你有VC0呈现VC1,请解雇VC0中的VC1代码也是如此,使用委托方案。

So if you have VC0 presenting VC1, have the dismiss VC1 code in VC0 too, using delegate scheme.

我已经了解到这是处理呈现和解雇的最佳方式 - 尽管有时它会解雇VC1中的VC1本身。

I have learned that this is the savest way to handle presenting and dismissing - even though sometimes it works to dismiss VC1 within VC1 itself.

我问过一个非常相关的问题,你可能也有兴趣检查一下。它显示

I have asked a very related question, you might be interested to check this too. It shows the code...

ps我还读到有些人只关闭VC1 - 这反过来也会解雇VC2。但是,如果我之前的建议有效,我就不会这样做。有时我在执行期间(没有崩溃)获得VC不再存在的信息或与之相关的任何信息 - 所以我认为这不是最好的解决方案。但如果我的明确建议不起作用,你可以尝试第二个。

ps I also read that some dismiss only VC1 - which in turn will also dismiss VC2. However, if my previous suggestion works, I would not do this. Sometimes I get information during execution (no crash) that the VC does not exist anymore or anything related to that - so I assumed this is not the best solution. But if my prvious suggestion does not work, you may try the second one.

虽然不能保证这会持续更新到新的iOS,因为这个问题一直让我对几个iOS更新感到厌烦:-),所以我决定采用标准推荐路线。

Though no guarantee that this will last the updates to new iOS, since this issue keeps hauting me for several iOS updates now :-), so I decided to go the standard recommended route.

编辑:
这是我的修改后的代码 - 它可以正常工作 - 但是在用户响应之后你不清楚你想要发生什么警报以及警报是否应该在VC1或VC0上。无论如何使用委托和回调我没有看到任何问题。如果我错过了您的观点请解释...

This is my modified code - it works without problems - however it is not clear what you intend to happen AFTER the user reponds to the Alert and whether the Alert should be on VC1 or VC0. Anyway using delegate and callbacks I do not see any issue. Please explain should I have missed your point...

FlightViewControllerProtocol.h

FlightViewControllerProtocol.h

@protocol FlightViewControllerProtocol <NSObject>
-(void) dismissVCAndEndBookmark;
@end

FlightViewController.m

FlightViewController.m

#import "FlightViewController.h"
#import "FlightViewControllerProtocol.h"
#import "BookmarksTableViewController.h"
@interface FlightViewController ()

@end

@implementation FlightViewController
@synthesize delegate;

- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if (self) {
        // Custom initialization
    }
    return self;
}

- (void)viewDidLoad
{
    [super viewDidLoad];
    // Do any additional setup after loading the view from its nib.
}

- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}

- (void)searchBarBookmarkButtonClicked:(UISearchBar *)searchBar {

    [self bringUpBookmarkkTable];
}

- (IBAction) bringUpBookmarkkTable {

    BookmarksTableViewController *bookmarkTVC = [[BookmarksTableViewController alloc] init];
    bookmarkTVC.delegate = self;
    [bookmarkTVC setModalTransitionStyle: UIModalTransitionStyleFlipHorizontal];

    [self presentViewController:bookmarkTVC animated:YES completion:nil];
}

- (IBAction)cancel {

    [self dismissViewControllerAnimated:YES completion:nil];

}

- (void)endBookmarkProcessWithBookmarkCollection: (NSDictionary *)dict {

//    presetBookmarkContext = [dict mutableCopy];

//    bookmarkMode = YES;

    NSString *compiledText = nil;

    NSNumber *number1 = [NSNumber numberWithInt: 1];

    if ([dict objectForKey: @"bookmarkTag"] == number1) {

        compiledText = @"Text1";
    }
    else {
        compiledText = @"Text2";
    }


//    flightContext = [NSDictionary dictionaryWithObjectsAndKeys: [dict objectForKey: @"miles"], @"miles", compiledText, @"location", [[NSUserDefaults standardUserDefaults] objectForKey: @"tempD"], @"date", nil];

    NSString *string = compiledText;

    UIAlertView *bvkBookmarkAlertView = [[UIAlertView alloc] initWithTitle:@"Confirmation" message:string delegate:self cancelButtonTitle:@"Cancel" otherButtonTitles:@"Add", nil];

    [bvkBookmarkAlertView show];
}


- (void) dismissVCAndEndBookmark {
    [self dismissViewControllerAnimated:YES completion:nil];
     [self endBookmarkProcessWithBookmarkCollection: nil];
}

- (void)alertView:(UIAlertView *)alertView didDismissWithButtonIndex:(NSInteger)buttonIndex {

    if (buttonIndex == 1) {

        [self cancel]; // Even though cancel is an IBAction, IBAction is the same thing as void so it is callable
    }
}

- (void)alertView:(UIAlertView *)alertView clickedButtonAtIndex:(NSInteger)buttonIndex {

    if (buttonIndex == 1) {

        NSLog(@"alertView1");
           }

    if (buttonIndex == 0) {
        NSLog(@"alertView2");

    }

}

@end

BookmarksTableViewController.h

BookmarksTableViewController.h

 @interface BookmarksTableViewController : UIViewController
{
    id delegate;
}

@property (nonatomic,strong)   id delegate;

@end

BookmarksTableViewController.m

BookmarksTableViewController.m

- (IBAction)goBack {
    [self.delegate dismissVCAndEndBookmark];
}

Esp BookmarksTableViewController.m中的回调似乎是你实现中的主要问题如果我理解你的意图。

Esp the callback in BookmarksTableViewController.m seems to be the main issue in your implementation if I understood your intentions correctly.

这篇关于dismissViewController:不工作的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

11-02 13:59