2

If I am getting information from an album in the users assetslibrary and they add a picture or remove on from it while my app is in the background. Whats the best way to reload them.

Currently I have:

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(assetsLibraryDidChange:) name:ALAssetsLibraryChangedNotification object:_photoListArray];

To get the initial notification and then it calls my assetLibraryDidChange method:

Which looked like this:

- (void)assetsLibraryDidChange:(NSNotification *)note
{

    //dict nil reload
    if(note.userInfo==nil) {
        [self.CoverView reloadData];
        return;
    }

    //dict empty no reload
    if(note.userInfo.count == 0) {
        NSLog(@"empty");
        return;
    }

    else {
        [self.CoverView reloadData];
    }
}

Although I am considering removing all the if's and else and just having it reload every time.


What I'm getting to:

There seems to be a gap between when my app receives the notification and it actually updates. Apple's default photos app seems to be able to do it in around 3-4 seconds while it takes mine almost 10!. Is there a more efficient way to do this?


I went ahead and put a nslog before all the if's to see how many times the method was being called as well.

//Library Updated
- (void)assetsLibraryDidChange:(NSNotification *)note
{
    NSLog(@"photos updated");

    //dict nil reload
    if(note.userInfo==nil) {
        dispatch_async(dispatch_get_main_queue(), ^{
            [self.CoverView reloadData];
            NSLog(@"note: %@", note.userInfo);
            NSLog(@"array: %@", _photoListArray);
            return;
        });
    }

    //dict empty no reload
    if(note.userInfo.count == 0) {
        NSLog(@"empty");
        return;
    }

    else {
        dispatch_async(dispatch_get_main_queue(), ^{
            [self.CoverView reloadData];
            NSLog(@"note2: %@", note.userInfo);
            NSLog(@"array2: %@", _photoListArray);
        });
    }

}

And they resulted in the following:

2013-08-16 10:41:51.622 app[180:1803] photos updated
2013-08-16 10:41:51.635 app[180:60b] note2: {
    ALAssetLibraryUpdatedAssetsKey = "{(\n    assets-library://asset/asset.JPG?id=CCA17BE2-5633-4FFE-A113-F21E37B9882C&ext=JPG,\n    assets-library://asset/asset.JPG?id=7B05283E-87A5-4CFE-BDBE-7703E311E0DF&ext=JPG,\n    assets-library://asset/asset.JPG?id=5B1E736F-E21E-4400-9679-5DE8215AC09D&ext=JPG\n)}";
}
2013-08-16 10:41:51.638 app[180:60b] array2: (
    "<Media: 0x176b3410>",
    "<Media: 0x176b5b00>",
    "<Media: 0x176b5c90>",
    "<Media: 0x176b7590>",
    "<Media: 0x176b47c0>",
    "<Media: 0x176b7e10>",
    "<Media: 0x176b83b0>",
    "<Media: 0x176b8990>",
    "<Media: 0x176b8f40>",
    "<Media: 0x176b9530>",
    "<Media: 0x176ba160>",
    "<Media: 0x176ba960>",
    "<Media: 0x175794d0>",
    "<Media: 0x175503c0>",
    "<Media: 0x17571f80>",
    "<Media: 0x1756dc20>",
    "<Media: 0x17571060>",
    "<Media: 0x1757b0d0>",
    "<Media: 0x1757b8f0>",
    "<Media: 0x1757bee0>",
    "<Media: 0x1757bcf0>",
    "<Media: 0x1757ca80>",
    "<Media: 0x1757cbd0>"
)
2013-08-16 10:41:51.827 app[180:3e07] photos updated
2013-08-16 10:41:51.831 app[180:3e07] empty
2013-08-16 10:41:51.893 app[180:3e07] photos updated
2013-08-16 10:41:51.897 app[180:3e07] empty
2013-08-16 10:41:52.059 app[180:3e07] photos updated
2013-08-16 10:41:52.074 app[180:3e07] empty
2013-08-16 10:41:52.092 app[180:5117] photos updated
2013-08-16 10:41:52.095 app[180:5117] empty

The Media objects are a class which I am just using to add data and have it stored along with them. Name, ext. Nothing that changes the actual image.

Without the dispatch:

2013-08-16 11:37:53.246 app[296:3d07] photos updated
2013-08-16 11:37:53.255 app[296:3d07] note2: {
    ALAssetLibraryUpdatedAssetsKey = "{(\n    assets-library://asset/asset.JPG?id=CCA17BE2-5633-4FFE-A113-F21E37B9882C&ext=JPG,\n    assets-library://asset/asset.PNG?id=D72A00CE-4198-45BE-BCC5-8DEB8419A5C8&ext=PNG,\n    assets-library://asset/asset.JPG?id=5B1E736F-E21E-4400-9679-5DE8215AC09D&ext=JPG\n)}";
}
2013-08-16 11:37:53.260 app[296:3d07] array2: (
    "<Media: 0x176271b0>",
    "<Media: 0x17577920>",
    "<Media: 0x17579c50>",
    "<Media: 0x17579eb0>",
    "<Media: 0x17579e00>",
    "<Media: 0x1757a9b0>",
    "<Media: 0x1757af50>",
    "<Media: 0x1757b540>",
    "<Media: 0x1757baf0>",
    "<Media: 0x1757c0e0>",
    "<Media: 0x17656510>",
    "<Media: 0x176570f0>",
    "<Media: 0x176572b0>",
    "<Media: 0x17657840>",
    "<Media: 0x17657e20>",
    "<Media: 0x17658400>",
    "<Media: 0x176589e0>",
    "<Media: 0x17659270>",
    "<Media: 0x17650470>",
    "<Media: 0x17659380>",
    "<Media: 0x176507a0>",
    "<Media: 0x17650ab0>",
    "<Media: 0x17659cb0>",
    "<Media: 0x1765a340>"
)
2013-08-16 11:37:53.404 app[296:4e17] photos updated
2013-08-16 11:37:53.408 app[296:4e17] empty
2013-08-16 11:37:53.450 app[296:3d07] photos updated
2013-08-16 11:37:53.458 app[296:3d07] empty
2013-08-16 11:37:53.466 app[296:4e17] photos updated
2013-08-16 11:37:53.470 app[296:4e17] empty
lostAstronaut
  • 1,331
  • 5
  • 20
  • 34
  • Is the notification sent on a non-main thread? In that case you have to dispatch `reloadData` to the main thread. – Martin R Aug 16 '13 at 05:08

1 Answers1

0

any UI changing stuff should be done on the main thread.. try:

- (void)assetsLibraryDidChange:(NSNotification *)note
{

    //dict nil reload
    if(note.userInfo==nil) {
        dispatch_async(dispatch_get_main_queue(), ^{
            [self.CoverView reloadData];
            return;
        }
    }

    //dict empty no reload
    if(note.userInfo.count == 0) {
        NSLog(@"empty");
        return;
    }

    else {
        dispatch_async(dispatch_get_main_queue(), ^{            
            [self.CoverView reloadData];
        }
    }
}
abbood
  • 23,101
  • 16
  • 132
  • 246
  • Hey I believe you are missing a ');' in the if and else statement. – lostAstronaut Aug 16 '13 at 14:57
  • 1
    I defiantly fixed the speed issue, it's not reloading the cells though, maybe setNeedsLayout? – lostAstronaut Aug 16 '13 at 14:59
  • Or should I be using batchUpdate? – lostAstronaut Aug 16 '13 at 15:00
  • No reload should be fine.. But just to isolate the issue.. Can you put an nslog statement for note.userinfo as well as_photoListArray under each case and paste the output? – abbood Aug 16 '13 at 15:22
  • @lostAstronaut hum.. so then the issue here is that you are not being notified to any changes in the array.. can you repeat the above NSLog statements but without having the `dispatch_async(dispatch_get_main_queue(),` code? – abbood Aug 16 '13 at 16:11
  • Updated for without dispatch. – lostAstronaut Aug 16 '13 at 16:40
  • So obviously your notification isnt reporting what you want..i will need more code to see whats going on.. Can you put it on a repo like github or something? – abbood Aug 16 '13 at 19:02