0

我在 viewController 中有以下代码。我在视图上有一个 NavigationController(这是子视图 - 父视图的代码工作正常)

当我在父级上选择一个选项时会发生什么,这个 viewController 会加载。用户可以从子 viewController 中选择一个选项来打开带有 DocumentInteractionController 的 PDF 文件(效果很好)。

问题是当我尝试返回父视图控制器时,消息被发送到子视图控制器,就好像它仍然被分配一样。我在设置它时看到了类似的东西,因为对子 viewController 中的方法有多次调用。

对我做错了什么有任何想法吗?

#import "DetailViewController.h"

@interface DetailViewController ()

@end

@implementation DetailViewController

@synthesize node;
@synthesize replies;
@synthesize docController;

- (void) viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];
    [self.tableView reloadData];
    [self.tableView setContentOffset:CGPointZero animated:NO];
}

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

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

- (void) dealloc
{
    [self.docController release];
    [super dealloc];
}

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

- (NSInteger) numberOfSectionsInTableView:(UITableView *)tableView
{
    return 1;
}

- (NSInteger) tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    if (self.replies == nil)
    {
        self.replies = [[NSArray alloc] init];
        self.actions = [[NSArray alloc] init];
    }
    if(self.replies.count == 0)
    {
        self.replies = [self.node nodesForXPath:@"./question/reply/text" error:nil];
        self.actions = [self.node nodesForXPath:@"./question/reply/response/action" error:nil];
    }

    return self.replies.count;
}

- (UITableViewCell *) tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"QuestionCell";

    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];

    if (cell == nil)
    {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
    }

    // Get the object to display and set the value in the cell
    NSString *cellText = [[replies objectAtIndex:indexPath.row] stringValue];
    cell.textLabel.text = cellText;
    return cell;
}

- (void) showOptionsMenu:(NSString *) fileName
{

    NSString *fileToOpen = [[NSBundle mainBundle] pathForResource:fileName ofType:@"pdf"];
    NSURL *fileURL = [NSURL fileURLWithPath:fileToOpen];

    self.docController = [self setupControllerWithURL:fileURL usingDelegate:self];

    bool didShow = [self.docController presentOptionsMenuFromRect:CGRectMake(0, 0, 150, 150) inView: self.view animated:YES];

    if(!didShow)
    {
        UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"" message:@"Sorry, app not found" delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil];
        [alert show];
    }

}

- (void) tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
    NSString *action = [[self.actions objectAtIndex:indexPath.row] stringValue];
    [self showOptionsMenu:action];
}

- (UIDocumentInteractionController *) setupControllerWithURL: (NSURL *) fileURL usingDelegate:(id <UIDocumentInteractionControllerDelegate>) interactionDelegate
{
    UIDocumentInteractionController *interactionController = [UIDocumentInteractionController interactionControllerWithURL:fileURL];
    interactionController.delegate = interactionDelegate;
    return interactionController;
}


@end

编辑

添加父视图控制器的代码......也许我在那里做错了什么?我正在使用 GDataXML 根据 XML 文件的内容加载问答应用程序...

@implementation ViewController

@synthesize currentReply;
@synthesize questions;

- (void)viewDidLoad
{
    [super viewDidLoad];
    [self setUpQuestions];
}

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

- (void)dealloc
{
    [super dealloc];
}

- (void) setUpQuestions
{
    // create and init NSXMLParser object

    NSString *filePath = [[NSBundle mainBundle] pathForResource:@"query" ofType:@"xml"];
    NSData *xml_data = [[NSData alloc] initWithContentsOfFile:filePath];
    NSError *error;
    GDataXMLDocument *xmlDoc = [[GDataXMLDocument alloc] initWithData:xml_data options:0 error:&error];

    NSArray *rootDataArray = [xmlDoc.rootElement nodesForXPath:@"//query" error:nil];
    for (GDataXMLElement *rootDataElement in rootDataArray)
    {
        // Allocate the query object
        self->query = [[[Query alloc] init] autorelease];

        // Name
        NSArray *query_title = [rootDataElement elementsForName:@"text"];
        if (query_title.count > 0)
        {
            GDataXMLElement *queryTitle = (GDataXMLElement *) [query_title objectAtIndex:0];

            self->query.queryTitle = [[[NSString alloc] initWithString:queryTitle.stringValue] autorelease];
        }


        NSArray *query_first_question = [rootDataElement elementsForName:@"question"];
        NSArray *replies = [NSArray alloc];
        questions = [[NSMutableArray alloc] init];
        if(query_first_question.count == 1)
        {
            GDataXMLElement *fq = (GDataXMLElement *) [query_first_question objectAtIndex:0];
            replies = [fq elementsForName:@"reply"];
            for (GDataXMLElement *replyElement in replies)
            {
                [questions addObject:replyElement];
            }
        }
    }
}

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
    // Only one section.
    return 1;
}

- (NSInteger) tableView: (UITableView *) tableView numberOfRowsInSection:(NSInteger)section
{
    switch(section)
    {
        case 0:
            return questions.count;
            break;
        case 1:
            return 1;
            break;
    }

}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {

    static NSString *CellIdentifier = @"QuestionCell";

    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];

    if (cell == nil)
    {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
        cell.accessoryType = UITableViewCellAccessoryDetailDisclosureButton;
    }

    // Get the object to display and set the value in the cell.
    GDataXMLElement *questionAtIndex = questions[indexPath.row];
    NSString *cellText = [[[questionAtIndex elementsForName:@"text"] objectAtIndex:0] stringValue];
    cell.textLabel.text = cellText;
    //cell.textLabel.text = [[questionAtIndex elementsForName:@"text"] objectAtIndex:0];
    return cell;
}


- (void) tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
    //NSMutableString *msg = [NSMutableString new];
    //[msg appendString:@"You selected row: "];
    //[msg appendString:[NSString stringWithFormat:@"%i",indexPath.row]];

    //UIAlertView *alertMsg = [[UIAlertView alloc] initWithTitle:@"Row Selected" message:msg delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil, nil];

    //[alertMsg show];
    if (questions != nil)
    {
        GDataXMLElement *selectedReply = (GDataXMLElement *) [questions objectAtIndex:indexPath.row];
        DetailViewController *dvc = [[DetailViewController alloc] initWithNibName:@"DetailViewController" bundle:nil];
        dvc.node = selectedReply;
        [self.navigationController pushViewController:dvc animated:YES];
        [dvc release];
    }
}

编辑

我已经尝试分析和寻找僵尸,但是当崩溃发生时,没有标记僵尸对象。它在控制台中引发以下错误:

[UIView _forgetDependentConstraint:]: message sent to deallocated instance 0x1e8ab810
4

3 回答 3

1

我以前也看过这个问题!!!

回答 : Turn Off "AutoLayout".

我猜这个错误是由于ios被调用的新功能而发生的AutoLayout。看起来 Compiler 已经创建了一些NSLayoutConstraint对象,并且由于某种原因,这些对象的释放量超出了应有的范围。删除和重新创建,迫使Xcode重新建立约束。但是,我不是 100% 确定的。

如果可以解决您的问题,请尝试取消选中“AutoLayout” 。

于 2013-05-24T14:28:14.960 回答
0

您的 DetailViewController 代码很好 - 实际上并不很好,因为您正在泄漏 self.replies 和 self.actions,并且 [self.docController init] 非常奇怪并且可能是错误的(总是一起分配和初始化) - 但是生命周期代码这端看起来不错。几乎可以肯定问题出在父视图控制器中(或者如果您在那里创建保留周期,则可能是文档控制器)。如果父视图控制器持有指向细节视图控制器的指针,它实际上不会被释放,并且访问视图或其任何属性将导致再次调用 -viewDidLoad。

于 2013-05-22T18:34:34.017 回答
0

据我了解,您的父视图控制器正在此处设置节点:

    dvc.node = selectedReply;

并且它永远不会从您的 DetailViewController 中释放出来。

我假设 DetailViewController 标头中的 GDataXMLElement 设置为“保留”。

正如 icodestuff 指出的那样,存在一些泄漏问题。

于 2013-05-23T19:46:32.587 回答