第一次构建和运行我的应用程序时,我的UITableView是空的

时间:2012-07-12 17:08:39

标签: objective-c ios uitableview datasource

我正在构建一个以UITableView开头的应用,但是当我第一次在手机上构建并运行我的应用时,UITableView显示为空。如果我停止运行然后重新构建并再次运行它,所有数据都会显示出来。此外,如果该应用已经在我的手机上,它建立并运行正常。它只是第一个初始构建和运行时,它在我的手机上“安装”应用程序,使UITableView为空。我很好奇,如果苹果在审核我的应用程序时会导致苹果出现任何问题吗?有没有什么我做错了才能实现这一目标?

注意:正在从正在移动到文档目录的plist填充UITableView。我最初的想法是UITableView试图在plist成功移动到文档目录之前填充列表。所以我尝试在[self.tableView reloadData];方法结束时调用viewDidLoad,但我得到的结果相同。

@implementation AppDelegate

- (void)createEditableCopyOfDatabaseIfNeeded
{
    //TESTING FOR EXISTENCE
    NSFileManager *fileManager = [NSFileManager defaultManager];
    NSArray *searchPaths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *documentsDirectory = [searchPaths lastObject];
    NSString *writeableDBPath = [documentsDirectory stringByAppendingPathComponent:@"ScotchList.plist"];

    BOOL dbexists = [fileManager fileExistsAtPath:writeableDBPath];
    if (!dbexists) {
        // The writeable database does not exist, so copy the default to the appropriate location.
        NSString *defaultDBPath = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:@"ScotchList.plist"];

        NSError *error;
        BOOL success = [fileManager copyItemAtPath:defaultDBPath toPath:writeableDBPath error:&error];
        if (!success) {
            NSAssert1(0, @"Failed to create writeable database file with message '%@'.", [error localizedDescription]);
        }
    }
}

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    // Override point for customization after application launch.
    if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone) {
        MasterViewController *masterViewController = [[MasterViewController alloc] initWithNibName:@"MasterViewController_iPhone" bundle:nil];
        self.navigationController = [[UINavigationController alloc] initWithRootViewController:masterViewController];

        self.window.rootViewController = self.navigationController;
    } else {
        MasterViewController *masterViewController = [[MasterViewController alloc] initWithNibName:@"MasterViewController_iPad" bundle:nil];
        UINavigationController *masterNavigationController = [[UINavigationController alloc] initWithRootViewController:masterViewController];

        DetailViewController *detailViewController = [[DetailViewController alloc] initWithNibName:@"DetailViewController_iPad" bundle:nil];
        UINavigationController *detailNavigationController = [[UINavigationController alloc] initWithRootViewController:detailViewController];

        masterViewController.detailViewController = detailViewController;

        self.splitViewController = [[UISplitViewController alloc] init];
        self.splitViewController.delegate = detailViewController;
        self.splitViewController.viewControllers = @[masterNavigationController, detailNavigationController];

        self.window.rootViewController = self.splitViewController;
    }
    [self.window makeKeyAndVisible];
    [self createEditableCopyOfDatabaseIfNeeded];
    [application setStatusBarStyle:UIStatusBarStyleBlackOpaque];
    return YES;
}

MasterViewController.m

- (void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];
    self.sections = [[NSMutableDictionary alloc] init];
    BOOL found;

    // Loop through the whiskys and create our keys
    for (NSMutableDictionary *whisky in self.drinks)
    {
        NSString *c = [[whisky objectForKey:NAME_KEY] substringToIndex:1];

        found = NO;

        for (NSString *str in [self.sections allKeys])
        {
            if ([str isEqualToString:c])
            {
                found = YES;
            }
        }

        if (!found)
        {
            [self.sections setValue:[[NSMutableArray alloc] init] forKey:c];
        }
    }
    // Loop again and sort the whiskys into their respective keys
    for (NSMutableDictionary *whisky in self.drinks)
    {
        [[self.sections objectForKey:[[whisky objectForKey:NAME_KEY] substringToIndex:1]] addObject:whisky];
    }
    // Sort each section array
    for (NSString *key in [self.sections allKeys])
    {
        [[self.sections objectForKey:key] sortUsingDescriptors:[NSArray arrayWithObject:[NSSortDescriptor sortDescriptorWithKey:NAME_KEY ascending:YES]]];
    }
        [self.tableView reloadData];
}

- (void)viewDidLoad
{
    [super viewDidLoad];
    // Do any additional setup after loading the view, typically from a nib.582d0e
    self.navigationController.navigationBar.barStyle = UIBarStyleBlack;
    self.navigationController.navigationBar.tintColor = [UIColor colorWithRed:0x015/255.0 green:0x04/255.0 blue:0x04/255.0 alpha:1];
    self.tableView.backgroundColor = [UIColor colorWithPatternImage:[UIImage imageNamed:@"cellBackground.png"]];
    self.navigationItem.leftBarButtonItem = self.editButtonItem;
    self.navigationItem.leftBarButtonItem.tintColor = [UIColor redColor];
    self.navigationItem.backBarButtonItem.tintColor = [UIColor colorWithRed:0x3e/255.0 green:0x3e/255.0 blue:0x3e/255.0 alpha:1];
    UIBarButtonItem *addButton = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemAdd target:self action:@selector(insertNewObject:)];
    self.navigationItem.rightBarButtonItem = addButton;
    self.navigationItem.rightBarButtonItem.tintColor = [UIColor colorWithRed:0x015/255.0 green:0x04/255.0 blue:0x04/255.0 alpha:1];

    UIImage *titleImage = [UIImage imageNamed:@"whiskeyTitle.png"];
    self.navigationItem.titleView = [[UIImageView alloc]initWithImage:titleImage];

    NSArray *searchPaths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *documentsDirectory = [searchPaths lastObject];
    NSString *writeableDBPath = [documentsDirectory stringByAppendingPathComponent:@"ScotchList.plist"];

    NSMutableArray *tmpArray = [[NSMutableArray alloc]initWithContentsOfFile:writeableDBPath];

    self.drinks = tmpArray;
    deletedDrink = [[NSMutableArray alloc]init];
    [[NSNotificationCenter defaultCenter] addObserver:self 
                                             selector:@selector(applicationDidEnterBackground:) 
                                                 name:UIApplicationDidEnterBackgroundNotification
                                               object:nil];

    //Register for application exiting information so we can save data
    [[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(applicationWillTerminate:) name:UIApplicationWillTerminateNotification object:nil];

    bookCover = [[UIImageView alloc]init];
    bookCover.image = [UIImage imageNamed:@"Default.png"];
    openBookButton = [[UIButton alloc]init];
    [openBookButton addTarget:self action:@selector(goToPage:flipUp:) forControlEvents:UIControlEventTouchUpInside];
    bookCover.frame = CGRectMake(0, 0, 320, 480);
    openBookButton.frame = bookCover.frame;

    [self.navigationController.view addSubview:bookCover];
    [self.navigationController.view addSubview:openBookButton];
    [self.tableView reloadData];
}

确定更新

我的NSLog()'数组从viewDidLoad中的plist中拉出,当应用程序最初构建并在手机上运行(安装)时,它会记录为null。如果我停止并重新构建并运行它,则返回plist中的信息(非空)。

2 个答案:

答案 0 :(得分:1)

GOT IT。基本上我的appDelegate.mcreateEditableCopyOfDatabaseIfNeeded)中有一个方法可以检查文档目录中的数据库(在我的例子中是plist)。如果已经存在一个plist,它将不会覆盖它。如果没有plist,那么它会将我随应用程序一起提供的plist移动​​到文档目录中。然后我在applicationDidFinishLaunchingWithOptions:方法内部调用了[self createEditableCopyOfDatabaseIfNeeded];,看起来它应该都是好的。但是在applicationDidFinishLaunchingWithOptions方法内部有if语句来检查currentDevice userInterfaceIdiom我在检查interfaceIdiom的if和else之后调用[self createEditableCopyOfDatabaseIfNeeded];。我只是向上移动到userInterfaceIdiom是iPhone的if语句。

下面我已经评论了问题的位置以及我在哪里解决问题。

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    // Override point for customization after application launch.
    if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone) {
        MasterViewController *masterViewController = [[MasterViewController alloc] initWithNibName:@"MasterViewController_iPhone" bundle:nil];
        self.navigationController = [[UINavigationController alloc] initWithRootViewController:masterViewController];

        self.window.rootViewController = self.navigationController;

        //THIS WAS THE SOLUTION RIGHT BELOW.
        [self createEditableCopyOfDatabaseIfNeeded];
    } else {
        MasterViewController *masterViewController = [[MasterViewController alloc] initWithNibName:@"MasterViewController_iPad" bundle:nil];
        UINavigationController *masterNavigationController = [[UINavigationController alloc] initWithRootViewController:masterViewController];

        DetailViewController *detailViewController = [[DetailViewController alloc] initWithNibName:@"DetailViewController_iPad" bundle:nil];
        UINavigationController *detailNavigationController = [[UINavigationController alloc] initWithRootViewController:detailViewController];

        masterViewController.detailViewController = detailViewController;

        self.splitViewController = [[UISplitViewController alloc] init];
        self.splitViewController.delegate = detailViewController;
        self.splitViewController.viewControllers = @[masterNavigationController, detailNavigationController];

        self.window.rootViewController = self.splitViewController;
    }
    [self.window makeKeyAndVisible];
    //THIS IS WHERE [self createEditableCopyOfDatabaseIfNeeded]; WAS ORIGINALLY WHICH WAS CAUSING THE PROBLEM
    [application setStatusBarStyle:UIStatusBarStyleBlackOpaque];
    return YES;
}

答案 1 :(得分:0)

您确定首次加载时是否已加载并可访问plist文件。尝试这样的事情:

NSFileManager *filemgr;

filemgr = [NSFileManager defaultManager];

if ([filemgr fileExistsAtPath: @"/CacheDirectory/DocumentDirectory/TempDirectory/myfile.txt" ] == YES)
        NSLog (@"File exists");
else
        NSLog (@"File not found");

只是为了确保。如果存在,请尝试记录其中的数据以查看它是否在第一次启动之前是否已完全填充,或者应用程序是否在完全通电话之前打开该文件。当在模拟器中启动时,应用程序会尽快启动,并且可能会出现线程切换或导致文件写入未完全完成的情况,然后应用程序才会从中打开流...如果是我的话我认为,安装在用户iPhone上时不应该出现问题,因为应用程序安装后不会立即启动。

无论如何,任何拥有iPhone并使用Facebook应用程序的人都习惯在打开应用程序时看不到任何内容,他们会重新启动它...; - )