我有一个带有触发TableViewController
事件的按钮的[NSURLConnection sendAsynchronousRequest...]
,还通过performSegueWithIdentifier:sender:加载一个模态segue,它定位一个小视图控制器。此叠加视图控制器的目的是显示加载图形,并在数据通过NSURLConnection
发送时阻止用户交互。
在NSURLConnection
的完成功能块中,我调用了一种删除TableViewController
中数据的方法(它只是一个批量列表),然后在覆盖视图上调用dismissViewControllerAnimated:completion:
控制器。
除了解除覆盖视图控制器之外,一切都有效,它在调试器中抛出一个警告: “警告:正在进行演示或解雇时尝试从视图控制器中解除!”
我发现了有关此错误的各种问题和答案,特别是关于使用performSelector:object:withDelay
方法的问题,但到目前为止还没有任何效果。
这特别令人讨厌,因为我在应用程序的另一个区域使用了类似的过程,除了从选择UITableViewCell
调用dismissViewController,这样工作正常......
我的代码的相关位如下所示:
#import "ViewBatch.h"
@interface ViewBatch ()
@property (strong, nonatomic) LoadingOverlayViewController *loadingOverlay;
@end
@implementation ViewBatch
@synthesize loadingOverlay;
....
- (IBAction)exportBatch:(id)sender
{
if ([productArray count] > 0) {
[self performSegueWithIdentifier:@"loadingSegue" sender:self];
[self processData];
}
}
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
if ([segue.identifier isEqualToString:@"loadingSegue"]) {
loadingOverlay = segue.destinationViewController;
}
}
- (void)processData
{
// Code to create a file and NSURLRequest...
// ....
NSOperationQueue *queue = [[NSOperationQueue alloc] init];
[NSURLConnection sendAsynchronousRequest:urlRequest
queue:queue
completionHandler:^(NSURLResponse *response, NSData *responseData, NSError *error) {
if ([responseData length] > 0 && error == nil)
{
// Not used for this request yet...
}
else if ([responseData length] == 0 && error == nil)
{
// Success...
[self didSendData];
}
else if (error != nil)
{
// Connection error...
NSLog(@"Error: %@", error);
}
}];
}
- (void)didSendData
{
// Reset the batch...
[productArray removeAllObjects];
[self.tableView reloadData];
[loadingOverlay dismissViewControllerAnimated:YES completion:NULL];
}
加载视图控制器只是:
#import <UIKit/UIKit.h>
@interface LoadingOverlayViewController : UIViewController
@property (weak, nonatomic) IBOutlet UILabel *statusLabel;
@property (weak, nonatomic) IBOutlet UIActivityIndicatorView *activityIndicator;
@end
....
....
#import "LoadingOverlayViewController.h"
@interface LoadingOverlayViewController ()
@end
@implementation LoadingOverlayViewController
- (void)viewDidLoad
{
[super viewDidLoad];
[self.activityIndicator startAnimating];
}
@end
答案 0 :(得分:1)
我不确定问题的确切原因,但这里有一些关于你的代码的观察结果。
您不需要叠加以防止用户互动。只需关闭与-NSApplication beginIgnoringInteractionEvents的用户交互。
您不需要整个视图控制器来显示叠加视图。只是显示视图。例如,我经常在我的视图中间放置一个大的UIActivityIndicatorView,同时发生NSURLConnection。
您不需要NSOperationQueue即可异步使用NSURLConnection。它已经是异步的。只需创建NSURLConnection并等待委托消息到达。事实上,你正在自我鼓励,因为你正在设置一个辅助队列,消息到达该队列,你在桌面上调用didSendData
调用reloadData
- 在后台,这是非法的。如果以正常方式执行此操作,您的委托消息将到达主线程,这正是您想要的。
答案 1 :(得分:0)
没关系,我明白了。 令人惊讶的是半小时休息可以组织一个人的想法......
该过程正在完成并在实际视图甚至完成加载之前调用dismissViewController。来自覆盖的viewDidLoad的简单委托调用将事情排序。
答案 2 :(得分:0)
我也有这个问题。我注意到这是复制并粘贴我的nib文件中的按钮的结果。结果是我不得不将IBActions绑定两个1 UIButton。