2011-11-27 59 views
5

UIDocumentサブクラスを持つ文書ベースのiOSアプリケーションがあります。ファイルシステム上で表現されているファイルを移動できる必要があります。私はNSFileManagerでそれを動かすことを考えましたが、これはUIDocumentfileURLプロパティを台無しにするでしょう。どのようにこの小さな難解を解決するための任意のアイデア?UIDocumentをファイルシステム上の新しい場所に移動する適切な方法

答えて

5

UIDocumentの名前を変更するには、まずUIDocumentを閉じてから、完了ハンドラでNSFileManagerを使用してファイルを移動します。

NSURL *directoryURL = [_document.fileURL URLByDeletingLastPathComponent];  
NSFileManager *fileManager = [[NSFileManager alloc] init];  
NSString *filePath = [directoryURL.path stringByAppendingPathComponent:@"NewFileName"]; 

[_document closeWithCompletionHandler:^(BOOL success) { 
    NSError *error; 

    if (success) 
     success = [fileManager moveItemAtPath:_document.fileURL.path toPath:filePath error:&error]; 

    if (success) { 
     NSURL *url = [NSURL fileURLWithPath:filePath]; 

     // I handle opening the document and updating the UI in setDocument: 
     self.document = [[MyDocumentSubclass alloc] initWithFileName:[url lastPathComponent] dateModified:[NSDate date] andURL:url]; 
    } else { 
     UIAlertView *alert = [[UIAlertView alloc] initWithTitle:nil message:@"Unable to rename document" delegate:nil cancelButtonTitle:@"Dismiss" otherButtonTitles:nil]; 
     [alert show]; 
     NSLog(@"Unable to move document: %@", error); 
    } 
}]; 
+0

これでも動作しますが、カプセル化に違反することなく移動する前にドキュメントを閉じることができない場合があります。 – Elland

-1

私はUIDocumentクラス仕様でこれを見つけた(5.1):

実装のファイルが正常に移動された後は、新しいファイルのURLを使用して、UIDocumentのサブクラスの新しいインスタンスを初期化しますNSFilePresenterプロトコル

UIDocumentクラスはNSFilePresenterプロトコルを採用しています。別のクライアントがUIDocumentベースのアプリケーションのドキュメントを読み取ろうとすると、UIDocumentオブジェクトにドキュメントに対する変更を保存する機会が与えられるまで、その読み取りは中断されます。

一部の実装では何も行われませんが、UIDocumentはすべてNSFilePresenterメソッドを実装します。具体的には、UIDocument

はに入ってくるブロックを転送するrelinquishPresentedItemToReader:を実装します。

relinquishPresentedItemToWriter:を実装して、ファイルの変更日が変更されたかどうかを確認します。ファイルが以前よりも新しい場合は、fileURLの値をURLパラメータとしてrevertToContentsOfURL:completionHandler:を呼び出します。

presentedItemDidMoveToURL:を実装して、ドキュメントのファイルURL(fileURL)を更新します。

UIDocumentサブクラスでは、NSFilePresenterメソッドをオーバーライドすると、常にスーパークラスの実装(super)を呼び出すことができます。

私も絶望的でした。私はまだそれをテストしていない - 私は今すぐそれにジャンプしています。

基本的に、ここで何も見逃していない場合は、文書をNSFileManagerで移動してから、ドキュメントにpresentedItemDidMoveToURL:を呼び出す必要があります。あなたはおそらくNSFileCoordinatorを使用してファイルを移動して、問題がないことを確認してください。

この回答のすべてを間違って入力してください。私はまだそのすべてのものでn00bです。

+1

これは正しいアイデアですが、 'presentItemDidMoveToURL:'を直接呼び出すのではなく、ファイルコーディネーターの通知を呼び出すべきだと思います。主な理由は、複数のファイルプレゼンターを開くことができ、通知メソッドを呼び出すことですべてのユーザーが確実に取得できます。 – Elland

2

これは古いかもしれませんが、それでも関連します。

何がやりたいことは以下の通りです:移動するための

:コーディネータのブロック内で、削除するために

[fileCoordinator itemAtURL:URL willMoveToURL:toURL]; 
[fileManager moveItemAtURL:newURL toURL:toURL error:&moveError]; 
[fileCoordinator itemAtURL:URL didMoveToURL:toURL]; 

を呼び出し、NSFileCoordinatorを使用してファイルを移動:あなたのUIDocumentのサブクラスを上書きするか、ファイルを実装プレゼンタープロトコル方法accommodatePresentedItemDeletionWithCompletionHandler:を使用して文書を閉じます。

- (void)accommodatePresentedItemDeletionWithCompletionHandler:(void (^)(NSError *))completionHandler; 
{ 
[self closeWithCompletionHandler:^(BOOL success) { 
    NSError *err; 
    if (!success) 
     err = [NSError error]; // implement your error here if you want 

    completionHandler(err); 
}]; 
} 

このようにして、移動が正しく処理されるようにします。

関連する問題