2012-01-27 55 views
4

我見過的iCloud文件示例代碼爲iOS和我用它來一個同步,並從iCloud中,現在我想用上同步的iCloud一個沒有UIDocument的Mac OSX應用程序。如何同步的NSDocument在Mac OSX到iPad/iPhone與iCloud的

我試圖將UIDocument更改爲NSDocument,但與同步的所有方法都不同。除了的文檔外,我還沒有找到任何示例代碼或教程,這些文檔非常混亂,寫得不好。

例如,下面的方法,從UIDocument iOS上不NSDocument存在於OS X:

//doc is an instance of subclassed UIDocument 
[doc openWithCompletionHandler:nil]; 

蘋果文檔提供了OS X這樣的代碼:

- (void)checkIfCloudAvaliable { 
    NSURL *ubiquityContainerURL = [[[NSFileManager defaultManager] 
            URLForUbiquityContainerIdentifier:nil] 
            URLByAppendingPathComponent:@"Documents"]; 
    if (ubiquityContainerURL == nil) { 
     NSDictionary *dict = [NSDictionary dictionaryWithObjectsAndKeys: 
           NSLocalizedString(@"iCloud does not appear to be configured.", @""), 
           NSLocalizedFailureReasonErrorKey, nil]; 
     NSError *error = [NSError errorWithDomain:@"Application" code:404 
             userInfo:dict]; 
     [self presentError:error modalForWindow:[self windowForSheet] delegate:nil 
     didPresentSelector:NULL contextInfo:NULL]; 
     return; 
    } 
    dest = [ubiquityContainerURL URLByAppendingPathComponent: 
      [[self fileURL] lastPathComponent]]; 
} 

- (void)moveToOrFromCloud { 
    dispatch_queue_t globalQueue = 
    dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0); 
    dispatch_async(globalQueue, ^(void) { 
     NSFileManager *fileManager = [[NSFileManager alloc] init]; 
     NSError *error = nil; 
     // Move the file. 
     BOOL success = [fileManager setUbiquitous:YES itemAtURL:[self fileURL] 
            destinationURL:dest error:&error]; 
     dispatch_async(dispatch_get_main_queue(), ^(void) { 
      if (! success) { 
       [self presentError:error modalForWindow:[self windowForSheet] 
          delegate:nil didPresentSelector:NULL contextInfo:NULL]; 
      } 
     }); 
    }); 
    [self setFileURL:dest]; 
    [self setFileModificationDate:nil]; 
} 

哪有我在iOS和OS X之間同步(因爲iOS上不存在NSDocument,而OS X上不存在UIDocument)?有誰知道我可以在哪裏找到適用於Mac OSX的示例(NSDocument同步)?

+1

不是所有的人找到文件「混亂和寫得不好」。 – Abizern 2012-01-28 19:15:14

+0

我使用了文檔,它不適合我。 – 2012-01-28 19:29:11

+1

另外 - 爲什麼不顯示你試過的一些代碼,而不是尋找你可以剪切和粘貼的東西。你已經在iOS上完成了 - 所以你必須對流程有一些瞭解。 – Abizern 2012-01-28 19:44:15

回答

5

我設法讓它工作!這裏是我的代碼從子類文件在OS X:

頭文件

#import <Cocoa/Cocoa.h> 
#import <Foundation/Foundation.h> 

@interface subclassedNSDocument : NSDocument 

@property (strong) NSData *myData; 

@end 

實現文件:

- (BOOL)readFromData:(NSData *)data ofType:(NSString *)typeName error:(NSError **)outError 
{ 
    BOOL readSuccess = NO; 
    if (data) 
    { 
     readSuccess = YES; 
     [self setMyData:data]; 
    } 

    [[NSNotificationCenter defaultCenter] postNotificationName:@"dataModified" 
                 object:self]; 

    return readSuccess; 
} 

- (NSData *)dataOfType:(NSString *)typeName error:(NSError **)outError 
{ 
    if (!myData && outError) { 
     *outError = [NSError errorWithDomain:NSCocoaErrorDomain 
             code:NSFileWriteUnknownError userInfo:nil]; 
    } 
    return myData; 
} 

,並在AppDelegate.m文件:

#define kFILENAME @"mydocument.dox" 

- (void)applicationDidFinishLaunching:(NSNotification *)aNotification 
{ 
    NSURL *ubiq = [[NSFileManager defaultManager] 
        URLForUbiquityContainerIdentifier:nil]; 
    if (ubiq) { 
     NSLog(@"iCloud access at %@", ubiq); 
     // TODO: Load document... 
     [self loadDocument]; 
    } 
    else 
    { 
     NSLog(@"No iCloud access"); 
    } 

    [[NSNotificationCenter defaultCenter] addObserver:self 
              selector:@selector(dataReloaded:) 
               name:@"dataModified" object:nil]; 
} 

- (void)update_iCloud 
{ 
    NSURL *ubiq = [[NSFileManager defaultManager] URLForUbiquityContainerIdentifier:nil]; 
    NSURL *ubiquitousPackage = [[ubiq URLByAppendingPathComponent:@"Documents"] URLByAppendingPathComponent:kFILENAME]; 
    self.doc.myData = [NSKeyedArchiver archivedDataWithRootObject:[@"Your Data Array or any data", nil]]; 
    [self.doc saveToURL:ubiquitousPackage ofType:@"dox" forSaveOperation:NSSaveOperation error:nil]; 
} 

- (void)loadData:(NSMetadataQuery *)query { 

    if ([query resultCount] == 1) { 

     NSMetadataItem *item = [query resultAtIndex:0]; 
     NSURL *url = [item valueForAttribute:NSMetadataItemURLKey]; 
     NSLog(@"url = %@",url); 
     subclassedNSDocument *doc = [[subclassedNSDocument alloc] initWithContentsOfURL:url ofType:@"dox" error:nil]; 
     [doc setFileURL:url]; 
     self.doc = doc; 
    } 
    else { 

     NSURL *ubiq = [[NSFileManager defaultManager] URLForUbiquityContainerIdentifier:nil]; 
     NSURL *ubiquitousPackage = [[ubiq URLByAppendingPathComponent:@"Documents"] URLByAppendingPathComponent:kFILENAME]; 

     dataUrls *doc = [[dataUrls alloc] init]; 
     [self.doc setFileURL:ubiquitousPackage]; 
     self.doc = doc; 
     [self.doc saveToURL:ubiquitousPackage ofType:@"dox" forSaveOperation:NSSaveOperation error:nil]; 
    } 

} 

- (void)queryDidFinishGathering:(NSNotification *)notification { 

    NSMetadataQuery *query = [notification object]; 
    [query disableUpdates]; 
    [query stopQuery]; 

    [[NSNotificationCenter defaultCenter] removeObserver:self 
                name:NSMetadataQueryDidFinishGatheringNotification 
                object:query]; 

    _query = nil; 

    [self loadData:query]; 

} 

- (void)loadDocument { 

    NSMetadataQuery *query = [[NSMetadataQuery alloc] init]; 
    _query = query; 
    [query setSearchScopes:[NSArray arrayWithObject:NSMetadataQueryUbiquitousDocumentsScope]]; 
    NSPredicate *pred = [NSPredicate predicateWithFormat: @"%K == %@", NSMetadataItemFSNameKey, kFILENAME]; 
    [query setPredicate:pred]; 
    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(queryDidFinishGathering:) name:NSMetadataQueryDidFinishGatheringNotification object:query]; 

    [query startQuery]; 

} 

- (void)dataReloaded:(NSNotification *)notification 
{ 
    self.doc = notification.object; 

    NSArray *arrFromCloud = [NSKeyedUnarchiver unarchiveObjectWithData:self.doc.myData]; 

    //Update you UI with new data 
} 

我沒有工作的唯一的事情是,如果我更改文檔的數據iPad,Mac應用程序不會調用readFromData從iCloud進行更新的方法,有誰知道我錯過了什麼?

在iOS上,每當更改iCloud中的UIDocument時,都會自動調用等效方法loadFromContents。在OS X上,readFromData在加載時被調用一次,但從未再次調用。

希望我的代碼可以幫助,對我而言,它是從Mac到iPad的單向工作方式。

+0

你有沒有得到它的工作,從ipad更新到mac? – Olof 2012-12-28 19:44:35

+0

@ user1173374您不應在StackOverflow的答案中提出更多問題。相反,開始一個新的問題。在你的新問題中,你可以鏈接回這個答案以供參考。 – 2013-01-01 23:32:30

+0

@Olof我發佈了從iPad更新到Mac的問題: http://stackoverflow.com/questions/20984512/how-to-sync-an-nsdocument-from-ipad-iphone-to-mac-osx-與-icloud的 – 2014-01-08 00:06:01

2

我認爲NSMetadataQueryDidUpdateNotification是你正在尋找檢測文件更新。可以使用NSMetadataQueryDidFinishGatheringNotification