objective c - NSFileWrapper, lazy loading and saving -
i have nsdocument based application uses filewrappers save , load data. document can have kinds of resources, don't want load memory. might doing fundamentally wrong, change 1 (inner) file , save, can't read file hasn't been loaded memory.
i have separated relevant code separate project reproduce behaviour, , same results. basic flow this:
- i load existing document disk. main filewrapper directory filewrapper (i'll call main) containing 2 other filewrappers (sub1 , sub2). 2 inner filewrappers not loaded @ point.
- when user wants edit sub1, loaded disk.
- the user saves document
if user wants edit other file (sub2), cannot load. error appears:
-[nsfilewrapper regularfilecontents] tried read file wrapper's contents lazily error occurred: file couldn’t opened because doesn’t exist.
here relevant code in project:
this code might easier read in gist: https://gist.github.com/bob-codingdutchmen/6869871
#define filename01 @"testfile1.txt" #define filename02 @"testfile2.txt" /** * called when initializing new document */ -(id)initwithtype:(nsstring *)typename error:(nserror *__autoreleasing *)outerror { self = [self init]; if (self) { self.mywrapper = [[nsfilewrapper alloc] initdirectorywithfilewrappers:nil]; nslog(@"initializing new document..."); nsstring *teststring1 = @"lorem ipsum first sub file"; nsstring *teststring2 = @"this second sub file unrelated contents"; nsfilewrapper *w1 = [[nsfilewrapper alloc] initregularfilewithcontents:[teststring1 datausingencoding:nsutf8stringencoding]]; nsfilewrapper *w2 = [[nsfilewrapper alloc] initregularfilewithcontents:[teststring2 datausingencoding:nsutf8stringencoding]]; w1.preferredfilename = filename01; w2.preferredfilename = filename02; [self.mywrapper addfilewrapper:w1]; [self.mywrapper addfilewrapper:w2]; } return self; } -(nsfilewrapper *)filewrapperoftype:(nsstring *)typename error:(nserror *__autoreleasing *)outerror { // wouldn't happen here normally, illustrates // how contents of first file replaced nsfilewrapper *w1 = [self.mywrapper.filewrappers objectforkey:filename01]; [self.mywrapper removefilewrapper:w1]; nsfilewrapper *new1 = [[nsfilewrapper alloc] initregularfilewithcontents:[@"new file contents" datausingencoding:nsutf8stringencoding]]; new1.preferredfilename = filename01; [self.mywrapper addfilewrapper:new1]; return self.mywrapper; } -(bool)readfromfilewrapper:(nsfilewrapper *)filewrapper oftype:(nsstring *)typename error:(nserror *__autoreleasing *)outerror { self.mywrapper = filewrapper; return yes; } - (ibaction)button1pressed:(id)sender { // read file1 , show result in field1 nsfilewrapper *w1 = [[self.mywrapper filewrappers] objectforkey:filename01]; nsstring *string1 = [[nsstring alloc] initwithdata:w1.regularfilecontents encoding:nsutf8stringencoding]; [self.field1 setstringvalue:string1]; } - (ibaction)button2pressed:(id)sender { // read file2 , show result in field2 nsfilewrapper *w2 = [[self.mywrapper filewrappers] objectforkey:filename02]; nsstring *string2 = [[nsstring alloc] initwithdata:w2.regularfilecontents encoding:nsutf8stringencoding]; [self.field2 setstringvalue:string2]; } the bottom 2 methods updating ui can see happens.
to change contents of file, remove existing filewrapper , add new one. way i've found change contents of file, , way i've seen done in other answers.
when document loaded disk, keep filewrapper around can use (called mywrapper in code above)
the apple docs nsfilewrapper supports lazy loading , incremental saving, i'm assuming code has fundamental flaw can't see.
an nsfilewrapper wrapper around unix file node. if file moved wrapper stays valid.
the problem yo seem have creating new file wrapper during saving new folder. , system deletes previous wrapper including sub2.
to achieve want need change incremental saving, i.e. saving changed parts in place. see "save in place" in nsdocument.
Comments
Post a Comment