Say you want to tag images taken with your application, and filter them out later. Here’s on way to do it.

In your view controller, create a tiffDictionary and highjack one of it’s values (like kCGImagePropertyTIFFMake) to use as your metadata repository.

- (void)imagePickerController:(UIImagePickerController *)picker
didFinishPickingMediaWithInfo:(NSDictionary *)info
{
    NSString *mediaType = [info objectForKey: UIImagePickerControllerMediaType];
    UIImage *originalImage, *editedImage, *image;
    
    // Handle a still image capture
    if (CFStringCompare ((__bridge CFStringRef) mediaType, kUTTypeImage, 0)
        == kCFCompareEqualTo) {
        
        editedImage = (UIImage *) [info objectForKey:UIImagePickerControllerEditedImage];
        originalImage = (UIImage *) [info objectForKey:UIImagePickerControllerOriginalImage];
        
        if (editedImage) {
            image = editedImage;
        } else {
            image = originalImage;
        }
        
        // Get the image metadata
        UIImagePickerControllerSourceType pickerType = picker.sourceType;
        if(pickerType == UIImagePickerControllerSourceTypeCamera)
        {           
            NSMutableDictionary *tiffDictionary = [NSMutableDictionary dictionary];
            [tiffDictionary setValue:TAKEMYSTUFF_VALUE forKey:(NSString *)kCGImagePropertyTIFFMake];

            NSMutableDictionary *dict = [NSMutableDictionary dictionary];
            [dict setValue:tiffDictionary forKey:(NSString *)kCGImagePropertyTIFFDictionary];
            
            ALAssetsLibrary *al = [[ALAssetsLibrary alloc] init];
            
            [al writeImageToSavedPhotosAlbum:[image CGImage]
                                    metadata:dict
                             completionBlock:^(NSURL *assetURL, NSError *error) {
                                 if (error == nil) {
                                     NSLog(@"Image saved.");
                                 } else {
                                     NSLog(@"Error saving image.");
                                 }
                             }];
            
            
            
        }
    }

    [self dismissImagePicker];
}

Then to read it back, just do this:

- (void) viewWillAppear:(BOOL)animated  {
    
    // collect the photos
    NSMutableArray *collector = [[NSMutableArray alloc] initWithCapacity:0];
    ALAssetsLibrary *al = [CameraTableViewController defaultAssetsLibrary];
    
    [al enumerateGroupsWithTypes:ALAssetsGroupSavedPhotos
                      usingBlock:^(ALAssetsGroup *group, BOOL *stop) 
    {

        [group enumerateAssetsUsingBlock:^(ALAsset *asset, NSUInteger index, BOOL *stop)
         {
             if (asset) {
                 
                 // check for tag
                 NSDictionary *metadata = asset.defaultRepresentation.metadata;
                 for(id key in metadata)
                     NSLog(@"key=%@ value=%@", key, [metadata objectForKey:key]);
                 
                 NSDictionary *tiffDictionary = [metadata objectForKey:(NSString *)kCGImagePropertyTIFFDictionary];
                 NSString *takeMyStuffValue = [tiffDictionary objectForKey:(NSString *)kCGImagePropertyTIFFMake];
                 
                 NSLog(@"takeMyStuffValue: %@", takeMyStuffValue);
                 
                 if (takeMyStuffValue) {
                     NSLog(@"Include");
                     [collector addObject:asset];
                 }
                                  
             }  
         }];
        
        self.photos = collector;
    }
                    failureBlock:^(NSError *error) { NSLog(@"Boom!!!");}
    ];
    
}

Originally I wanted to story my own key/value pairs in the dictionaries, but haven’t been able to figure it out yet. This will have to do until I do.

Here’s some more good reading on images and metadata.

About these ads