Sharing a plist file using iCloud

前端 未结 2 1551
夕颜
夕颜 2021-02-06 08:13

I have a relativley simple app which persists data to a plist file located in the documents folder. The data loads into a UITableView at startup. The user can then edit, delete

相关标签:
2条回答
  • 2021-02-06 08:36

    To use a plist with UIDocument, you can subclass UIDocument and override the following 2 methods with self.myDictionary (your plist) declared as a NSMutableDictionary.

    - (BOOL)loadFromContents:(id)contents ofType:(NSString *)typeName error:(NSError **)outError
    {    
        if ([contents length] > 0) 
        {
            NSKeyedUnarchiver *unarchiver = [[NSKeyedUnarchiver alloc] initForReadingWithData:(NSData *)contents];
            NSMutableDictionary *dataDictionary = [unarchiver decodeObjectForKey:@"data"];
    
            self.myDictionary = dataDictionary;
            [unarchiver finishDecoding];
            [unarchiver release];
        } 
        else 
        {
            self.myDictionary =  [NSMutableDictionary dictionary];
        }
    
        return YES;    
    }
    
    - (id)contentsForType:(NSString *)typeName error:(NSError **)outError 
    {
        NSMutableData *data = [[[NSMutableData alloc] init] autorelease];
        NSKeyedArchiver *archiver = [[NSKeyedArchiver alloc] initForWritingWithMutableData:data];
        if( !self.myDictionary )
        {
            self.myDictionary = [NSMutableDictionary dictionary];
        }
        [archiver encodeObject:self.myDictionary forKey:@"data"];
    
        [archiver finishEncoding];
        [archiver release];
        return data;
    }
    
    0 讨论(0)
  • 2021-02-06 09:02

    Not sure if anybody still needs a solution for that but I found a nice way to get this to work.

    Since UIDocument only accepts Data as NSData or NSFilewrapper, I first created a Category for the NSDictionary Class that returns a NSDictionary from NSData. Here's the two files for the Category:

    NSDictionary+DictFromData.h:

    #import <Foundation/Foundation.h>
    
    @interface NSDictionary (DictFromData)
    + (id)dictionaryWithData:(NSData *)data;
    - (id)initWithData:(NSData *)data;
    @end
    

    and the NSDictionary+DictFromData.m

    #import "NSDictionary+DictFromData.h"
    @implementation NSDictionary (DictFromData)
    
    + (id)dictionaryWithData:(NSData *)data {
        return [[[NSDictionary alloc] initWithData:data] autorelease];
    }
    
    - (id)initWithData:(NSData *)data {
        NSString *tmp = nil;
    
        self = (NSDictionary *)[NSPropertyListSerialization
                                propertyListFromData:data
                                mutabilityOption:NSPropertyListImmutable
                                format:NULL
                                errorDescription:&tmp];
    
        NSAssert1(tmp == nil,@"Error in plist: %@",tmp);
        return [self retain];
    }
    @end
    

    (source)

    If you now import this Category in your UIDocument Subclass, you can easily load and save your Plist File to your iCloud container.

    To load your Plist from iCloud add this to your UIDocument subclass (The Property contents is an NSDictionary):

    - (BOOL)loadFromContents:(id)contents
                      ofType:(NSString *)
            typeName error:(NSError **)outError {
    
        if ([contents length] > 0){
            self.contents = [NSDictionary dictionaryWithData:contents];
        } else {
            self.contents = nil;
        }
    
        // call some Methods to handle the incoming NSDictionary 
        // maybe overwrite the old Plist file with the new NSDictionary
    
        return YES;
    }
    

    For saving your Data back to the iCloud add this:

    - (id)contentsForType:(NSString *)typeName error:(NSError **)outError {
        NSData * plistData = [[[NSData alloc]initWithContentsOfFile:YOUR_PLIST_FILE]autorelease];
        return plistData;
    }
    

    If you now call:

    [myUIDocument updateChangeCount:UIDocumentChangeDone];
    

    YOUR_PLIST_FILE is getting synchronized. Remember that it takes about 10-15sec for your iCloud Container to update.

    0 讨论(0)
提交回复
热议问题