Почему я получаю ошибку при попытке записи в файл plist - PullRequest
1 голос
/ 21 августа 2011

У меня есть 4 NSMutableArray, и при запуске они правильно инициализируются. В разделе моего кода я записываю содержимое этих массивов в отдельные файлы plist, и эти файлы plist были созданы и добавлены в проект. У меня есть 4 экземпляра записи в файл, и по какой-то причине только первые 2 записи в файл успешно (didWrite и didWrite2), но didWrite3 и didWrite 4 все время возвращают "nope", что означает неудачную запись. Вот код, который инициализирует и выделяет массивы в applicationDidFinishLaunching:

NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *DataPath = [[paths objectAtIndex:0] stringByAppendingPathComponent:@"Data.plist"];
    NSString *inkDatesPath = [[paths objectAtIndex:0] stringByAppendingPathComponent:@"inkDates.plist"];
    NSString *inkFontPath = [[paths objectAtIndex:0] stringByAppendingPathComponent:@"inkFont.plist"];
    NSString *inkColorPath = [[paths objectAtIndex:0] stringByAppendingPathComponent:@"inkColor.plist"];
    NSFileManager *fileManager = [NSFileManager defaultManager];

    if (![fileManager fileExistsAtPath: DataPath])
    {
        inks=[[NSMutableArray alloc] init ];
         NSLog(@"initialized inks as new");
    }
    else inks=[[NSMutableArray alloc] initWithContentsOfFile:DataPath];

    if (![fileManager fileExistsAtPath: inkDatesPath])
    {
        inkDates=[[NSMutableArray alloc] init ];
    }
    else inkDates=[[NSMutableArray alloc] initWithContentsOfFile:inkDatesPath];

    if (![fileManager fileExistsAtPath: inkFontPath])
    {
        inkFont=[[NSMutableArray alloc] init ];
    }
    else inkFont=[[NSMutableArray alloc] initWithContentsOfFile:inkFontPath];

    if (![fileManager fileExistsAtPath: inkColorPath])
    {
        inkColor=[[NSMutableArray alloc] init ];
        NSLog(@"initialized inkColor as new");
    }
    else { 
        inkColor=[[NSMutableArray alloc] initWithContentsOfFile:inkColorPath];
        NSLog(@"initialized inkColor as copy");

Когда приложение запускается впервые, я получаю «инициализированный чернильный цвет как новый», но мне все равно не удается написать. Чернила и чернилаDates пишут правильно, а два других - нет. И вот мой код, который пытается записать в файлы plist:

  NSError *error;
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES); //1
    NSString *documentsDirectory = [paths objectAtIndex:0]; //2


    NSString *path = [documentsDirectory stringByAppendingPathComponent:@"Data.plist"]; //3
    NSFileManager *fileManager = [NSFileManager defaultManager];

    if (![fileManager fileExistsAtPath: path])
    {
        NSString *bundle=[[NSBundle mainBundle] pathForResource:@"Data" ofType:@"plist"];
        [fileManager copyItemAtPath:bundle toPath: path error:&error]; //6
    }

    NSString *pathDates = [documentsDirectory stringByAppendingPathComponent:@"inkDates.plist"]; //3
    NSFileManager *fileManagerDates = [NSFileManager defaultManager];

    if (![fileManagerDates fileExistsAtPath: pathDates])
    {
        NSString *bundle=[[NSBundle mainBundle] pathForResource:@"inkDates" ofType:@"plist"];
        [fileManagerDates copyItemAtPath:bundle toPath: pathDates error:&error]; //6
    }

    NSFileManager *fileManagerFont = [NSFileManager defaultManager];
    NSString *pathFont = [documentsDirectory stringByAppendingPathComponent:@"inkFont.plist"];
    if (![fileManagerFont fileExistsAtPath: pathFont])
    {
        NSString *bundle=[[NSBundle mainBundle] pathForResource:@"inkFont" ofType:@"plist"];
        [fileManagerFont copyItemAtPath:bundle toPath: pathFont error:&error]; //6
    }

    NSFileManager *fileManagerColor = [NSFileManager defaultManager];
    NSString *pathColor = [documentsDirectory stringByAppendingPathComponent:@"inkColor.plist"];
    if (![fileManagerFont fileExistsAtPath: pathColor])
    {
        NSString *bundle=[[NSBundle mainBundle] pathForResource:@"inkColor" ofType:@"plist"];
        [fileManagerColor copyItemAtPath:bundle toPath: pathColor error:&error]; //6
    }


    NSDate *date = [NSDate date];
    NSDateFormatter *dateFormat = [[NSDateFormatter alloc] init];
    [dateFormat setDateFormat:@"EEEE, MMMM d, YYYY"];
    NSString *dateString = [dateFormat stringFromDate:date];  
    [dateFormat release];

            [appDelegate.inks addObject:[inkTextField text]];
            [appDelegate.inkDates addObject:dateString];
            [appDelegate.inkFont addObject:[inkTextField font]];
            [appDelegate.inkColor addObject:[inkTextField textColor]];
            NSLog(@"inkColor count: %i", [appDelegate.inkColor count]);
            NSLog(@"Wrote to new index");

    BOOL didWrite=[appDelegate.inks writeToFile: path atomically:YES];
    if(didWrite==YES)
       NSLog(@"didWrite");
    else NSLog(@"nope");



    BOOL didWrite2;
    didWrite2=[appDelegate.inkDates writeToFile: pathDates atomically:YES];
    if(didWrite2==YES)
        NSLog(@"didWrite");
    else NSLog(@"nope");


    BOOL didWrite3;
    didWrite3=[appDelegate.inkFont writeToFile: pathFont atomically:YES];
    if(didWrite3==YES)
        NSLog(@"didWrite");
    else NSLog(@"nope");

    BOOL didWrite4;
    didWrite4=[appDelegate.inkColor writeToFile: pathColor atomically:YES];
    if(didWrite4==YES)
        NSLog(@"didWrite");
    else NSLog(@"nope");

1 Ответ

1 голос
/ 21 августа 2011

Вы используете writeToFile, который пытается записать правильные списки. Его документация гласит:

Этот метод рекурсивно проверяет, что все содержащиеся в нем объекты объекты списка свойств (экземпляры NSData, NSDate, NSNumber, NSString, NSArray или NSDictionary) перед записью файла, и возвращает NO, если все объекты не являются объектами списка свойств, так как результирующий файл не будет правильным списком свойств.

Если содержимое словаря - это все объекты списка свойств, файл написанный этим методом может быть использован для инициализации нового словаря с метод класса dictionaryWithContentsOfFile: или метод экземпляра initWithContentsOfFile:.

UIColor и UIFont отсутствуют в списке.

Как правило, вы можете использовать протокол NSCoding (используя объекты NSCoder), который позволяет более эффективно сериализовать данные. Однако даже тогда нет хорошего способа хранения объектов UIFont - они не соответствуют NSCoding и не могут быть сериализованы. Вам следует сохранить семейство / размер шрифта, а затем иметь собственный код для восстановления шрифта при загрузке данных.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...