diff --git a/Demo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo-Info.plist b/Demo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo-Info.plist
index c1e5e66..e9d2540 100644
--- a/Demo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo-Info.plist
+++ b/Demo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo-Info.plist
@@ -39,11 +39,11 @@
CFBundlePackageType
APPL
CFBundleShortVersionString
- 1.0.5
+ 1.1.3
CFBundleSignature
????
CFBundleVersion
- 105
+ 113
LSRequiresIPhoneOS
UIRequiredDeviceCapabilities
diff --git a/Demo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/Controllers/PhotosTableViewController.m b/Demo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/Controllers/PhotosTableViewController.m
index cf9723d..aa24936 100644
--- a/Demo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/Controllers/PhotosTableViewController.m
+++ b/Demo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/ALAssetsLibraryCustomPhotoAlbum_BasicDemo/Controllers/PhotosTableViewController.m
@@ -9,9 +9,7 @@
#import "PhotosTableViewController.h"
#import "PhotoViewController.h"
-
#import "ALAssetsLibrary+CustomPhotoAlbum.h"
-
#import
@@ -21,25 +19,28 @@
@interface PhotosTableViewController () {
@private
- ALAssetsLibrary * assetsLibrary_;
- NSMutableArray * photos_;
+ ALAssetsLibrary * assetsLibrary_;
+ NSMutableArray * photos_;
+ UIImagePickerController * picker_;
+ PhotoViewController * photoViewController_;
}
-@property (nonatomic, strong) ALAssetsLibrary * assetsLibrary;
-@property (nonatomic, copy) NSMutableArray * photos;
+@property (nonatomic, strong) ALAssetsLibrary * assetsLibrary;
+@property (nonatomic, copy) NSMutableArray * photos;
+@property (nonatomic, strong) UIImagePickerController * picker;
+@property (nonatomic, strong) PhotoViewController * photoViewController;
- (void)_takePhoto:(id)sender;
-- (BOOL)_startCameraControllerFromViewController:(UIViewController *)controller
- usingDelegate:(id )delegate;
@end
@implementation PhotosTableViewController
-@synthesize assetsLibrary = assetsLibrary_;
-@synthesize photos = photos_;
+@synthesize assetsLibrary = assetsLibrary_;
+@synthesize photos = photos_;
+@synthesize picker = picker_;
+@synthesize parentViewController = photoViewController_;
- (id)initWithStyle:(UITableViewStyle)style
{
@@ -71,7 +72,6 @@ - (void)viewDidLoad
target:self
action:@selector(_takePhoto:)];
[takePhotoButton setStyle:UIBarButtonItemStyleBordered];
- // [navigationController_.navigationItem setRightBarButtonItem:takePhotoButton];
[self.navigationItem setRightBarButtonItem:takePhotoButton];
}
@@ -83,7 +83,54 @@ - (void)viewDidUnload
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
+
// Dispose of any resources that can be recreated.
+ assetsLibrary_ = nil;
+ picker_ = nil;
+ photoViewController_ = nil;
+}
+
+#pragma mark - Custom Getter
+
+- (ALAssetsLibrary *)assetsLibrary
+{
+ if (assetsLibrary_) {
+ return assetsLibrary_;
+ }
+ assetsLibrary_ = [[ALAssetsLibrary alloc] init];
+ return assetsLibrary_;
+}
+
+- (UIImagePickerController *)picker
+{
+ if (picker_) {
+ return picker_;
+ }
+
+ picker_ = [[UIImagePickerController alloc] init];
+ picker_.sourceType = UIImagePickerControllerSourceTypeCamera;
+
+ // Displays a control that allows the user to choose picture or
+ // movie capture, if both are available:
+ //picker.mediaTypes =
+ // [UIImagePickerController availableMediaTypesForSourceType:UIImagePickerControllerSourceTypeCamera];
+ picker_.mediaTypes = [NSArray arrayWithObject:(NSString *)kUTTypeImage];
+
+ // Hides the controls for moving & scaling pictures, or for
+ // trimming movies. To instead show the controls, use YES.
+ picker_.allowsEditing = NO;
+ picker_.delegate = self;
+
+ return picker_;
+}
+
+- (PhotoViewController *)photoViewController
+{
+ if (photoViewController_) {
+ return photoViewController_;
+ }
+ photoViewController_ = [[PhotoViewController alloc] init];
+ return photoViewController_;
}
#pragma mark - Table view data source
@@ -119,11 +166,10 @@ - (UITableViewCell *)tableView:(UITableView *)tableView
- (void) tableView:(UITableView *)tableView
didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
- PhotoViewController * photoViewController = [[PhotoViewController alloc] init];
- [self.navigationController pushViewController:photoViewController animated:NO];
+ [self.navigationController pushViewController:self.photoViewController animated:NO];
// Get image from Custom Photo Album for the selected photo url.
- __weak PhotoViewController * weakPhotoViewController = photoViewController;
+ __weak PhotoViewController * weakPhotoViewController = self.photoViewController;
[self.assetsLibrary assetForURL:[NSURL URLWithString:[self.photos objectAtIndex:indexPath.row]]
resultBlock:^(ALAsset *asset) {
//
@@ -145,50 +191,22 @@ - (void) tableView:(UITableView *)tableView
// Take photo
- (void)_takePhoto:(id)sender
{
- if (! [self _startCameraControllerFromViewController:self
- usingDelegate:self]) {
- UIAlertView * alertView = [UIAlertView alloc];
- (void)[alertView initWithTitle:@"Camera Unavailable"
- message:@"Sorry, camera unavailable for the current device."
- delegate:self
- cancelButtonTitle:@"Cancel"
- otherButtonTitles:nil, nil];
- [alertView show];
+ if (! [UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera]) {
+ [[[UIAlertView alloc] initWithTitle:@"Camera Unavailable"
+ message:@"Sorry, camera unavailable for the current device."
+ delegate:self
+ cancelButtonTitle:@"Cancel"
+ otherButtonTitles:nil, nil] show];
+ return;
}
- return;
-}
-
-// verifies the prerequisites are satisfied by way of its method signature
-// and a conditional test, and goes on to instantiate, configure,
-// and asynchronously present the camera user interface full screen
-- (BOOL)_startCameraControllerFromViewController:(UIViewController *)controller
- usingDelegate:(id )delegate
-{
- if (([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera] == NO)
- || delegate == nil
- || controller == nil) return NO;
-
- UIImagePickerController * picker = [[UIImagePickerController alloc] init];
- picker.sourceType = UIImagePickerControllerSourceTypeCamera;
-
- // Displays a control that allows the user to choose picture or
- // movie capture, if both are available:
- //picker.mediaTypes =
- // [UIImagePickerController availableMediaTypesForSourceType:UIImagePickerControllerSourceTypeCamera];
- picker.mediaTypes = [NSArray arrayWithObject:(NSString *)kUTTypeImage];
-
- // Hides the controls for moving & scaling pictures, or for
- // trimming movies. To instead show the controls, use YES.
- picker.allowsEditing = NO;
- picker.delegate = delegate;
-
- [controller presentModalViewController:picker animated:YES];
- // No need to release here, as it'll be released after camera action done
- // in |imagePickerControllerDidCancel:| method
- // [picker release];
- return YES;
+ if ([self.navigationController respondsToSelector:
+ @selector(presentViewController:animated:completion:)])
+ {
+ [self.navigationController presentViewController:self.picker animated:YES completion:nil];
+ } else {
+ [self.navigationController presentModalViewController:self.picker animated:YES];
+ }
}
#pragma mark - UIImagePickerController Delegate
@@ -196,104 +214,98 @@ - (BOOL)_startCameraControllerFromViewController:(UIViewController *)controller
// For responding to the user tapping Cancel.
- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
- // Prior to iOS 5.0, if a view did not have a parent view controller
- // and was being presented modally, the view controller that was presenting
- // it would be returned.
- // This is no longer the case. You can get the presenting view controller
- // using the presentingViewController property.
- //
- // Guess |parentViewController| is nil on iOS 5 and that is why the controller
- // will not dismiss.
- // Replacing |parentViewController| with |presentingViewController| will fix
- // this issue.
- //
- // However, you'll have to check for the existence of presentingViewController
- // on UIViewController to provide behavior for iOS versions < 5.0
- if ([picker respondsToSelector:@selector(presentingViewController)])
- [[picker presentingViewController] dismissModalViewControllerAnimated:YES];
- else
- [[picker parentViewController] dismissModalViewControllerAnimated:YES];
+ if ([self.navigationController respondsToSelector:
+ @selector(presentViewController:animated:completion:)])
+ {
+ [picker dismissViewControllerAnimated:YES completion:nil];
+ } else {
+ // Prior to iOS 5.0, if a view did not have a parent view controller
+ // and was being presented modally, the view controller that was presenting
+ // it would be returned.
+ // This is no longer the case. You can get the presenting view controller
+ // using the presentingViewController property.
+ //
+ // Guess |parentViewController| is nil on iOS 5 and that is why the controller
+ // will not dismiss.
+ // Replacing |parentViewController| with |presentingViewController| will fix
+ // this issue.
+ //
+ // However, you'll have to check for the existence of presentingViewController
+ // on UIViewController to provide behavior for iOS versions < 5.0
+ if ([picker respondsToSelector:@selector(presentingViewController)]) {
+ [[picker presentingViewController] dismissModalViewControllerAnimated:YES];
+ } else {
+ [[picker parentViewController] dismissModalViewControllerAnimated:YES];
+ }
+ }
}
// For responding to the user accepting a newly-captured picture or movie
- (void)imagePickerController:(UIImagePickerController *)picker
didFinishPickingMediaWithInfo:(NSDictionary *)info
{
- // dismiss image picker view
+ // Dismiss image picker view
[self dismissModalViewControllerAnimated:YES];
- // manage the media (photo)
+ // Manage the media (photo)
NSString * mediaType = [info objectForKey:UIImagePickerControllerMediaType];
-
// Handle a still image capture
- if (CFStringCompare((CFStringRef)mediaType, kUTTypeImage, 0) == kCFCompareEqualTo) {
- // manage tasks in background thread
- dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
- UIImage * imageToSave = nil;
- UIImage * editedImage = (UIImage *)[info objectForKey:UIImagePickerControllerEditedImage];
- if (editedImage) imageToSave = editedImage;
- else imageToSave = (UIImage *)[info objectForKey:UIImagePickerControllerOriginalImage];
-
- UIImage * finalImageToSave = nil;
- /* Modify image's size before save it to photos album
- *
- * CGSize sizeToSave = CGSizeMake(imageToSave.size.width, imageToSave.size.height);
- * UIGraphicsBeginImageContextWithOptions(sizeToSave, NO, 0.f);
- * [imageToSave drawInRect:CGRectMake(0.f, 0.f, sizeToSave.width, sizeToSave.height)];
- * finalImageToSave = UIGraphicsGetImageFromCurrentImageContext();
- * UIGraphicsEndImageContext();
- */
- finalImageToSave = imageToSave;
-
- /*/ Get the image metadata
- UIImagePickerControllerSourceType pickerType = picker.sourceType;
- if (pickerType == UIImagePickerControllerSourceTypeCamera) {
- NSDictionary * imageMetadata = [info objectForKey:UIImagePickerControllerMediaMetadata];
- NSLog(@"%@", imageMetadata);
-
- // Get the assets library
- ALAssetsLibrary * library = [[ALAssetsLibrary alloc] init];
- ALAssetsLibraryWriteImageCompletionBlock imageWriteCompletionBlock =
- ^(NSURL *newURL, NSError *error) {
- if (error) {
- NSLog( @"Error writing image with metadata to Photo Library: %@", error );
- } else {
- NSLog( @"Wrote image with metadata to Photo Library");
- }
- };
-
- // Save the new image (original or edited) to the Camera Roll
- [library writeImageToSavedPhotosAlbum:[finalImageToSave CGImage]
- metadata:imageMetadata
- completionBlock:imageWriteCompletionBlock];
- }*/
-
- // The completion block to be executed after image taking action process done
- void (^completion)(NSURL *, NSError *) = ^(NSURL *assetURL, NSError *error) {
- if (error) NSLog(@"!!!ERROR, write the image data to the assets library (camera roll): %@",
- [error description]);
- NSLog(@"*** URL %@ | %@ || type: %@ ***", assetURL, [assetURL absoluteString], [assetURL class]);
- // Add new item to |photos_| & table view appropriately
- NSIndexPath * indexPath = [NSIndexPath indexPathForRow:self.photos.count
- inSection:0];
- [self.photos addObject:[assetURL absoluteString]];
+ CFStringRef mediaTypeRef = (__bridge CFStringRef)mediaType;
+ if (CFStringCompare(mediaTypeRef,
+ kUTTypeImage,
+ kCFCompareCaseInsensitive) != kCFCompareEqualTo)
+ {
+ CFRelease(mediaTypeRef);
+ return;
+ }
+ CFRelease(mediaTypeRef);
+
+ // Manage tasks in background thread
+ dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
+ UIImage * imageToSave = nil;
+ UIImage * editedImage = (UIImage *)[info objectForKey:UIImagePickerControllerEditedImage];
+ if (editedImage) imageToSave = editedImage;
+ else imageToSave = (UIImage *)[info objectForKey:UIImagePickerControllerOriginalImage];
+
+ UIImage * finalImageToSave = nil;
+ /* Modify image's size before save it to photos album
+ *
+ * CGSize sizeToSave = CGSizeMake(imageToSave.size.width, imageToSave.size.height);
+ * UIGraphicsBeginImageContextWithOptions(sizeToSave, NO, 0.f);
+ * [imageToSave drawInRect:CGRectMake(0.f, 0.f, sizeToSave.width, sizeToSave.height)];
+ * finalImageToSave = UIGraphicsGetImageFromCurrentImageContext();
+ * UIGraphicsEndImageContext();
+ */
+ finalImageToSave = imageToSave;
+
+ // The completion block to be executed after image taking action process done
+ void (^completion)(NSURL *, NSError *) = ^(NSURL *assetURL, NSError *error) {
+ if (error) NSLog(@"!!!ERROR, write the image data to the assets library (camera roll): %@",
+ [error description]);
+ NSLog(@"*** URL %@ | %@ || type: %@ ***", assetURL, [assetURL absoluteString], [assetURL class]);
+ // Add new item to |photos_| & table view appropriately
+ NSIndexPath * indexPath = [NSIndexPath indexPathForRow:self.photos.count
+ inSection:0];
+ [self.photos addObject:[assetURL absoluteString]];
+ dispatch_async(dispatch_get_main_queue(), ^{
[self.tableView insertRowsAtIndexPaths:@[indexPath]
withRowAnimation:UITableViewRowAnimationFade];
- };
-
- void (^failure)(NSError *) = ^(NSError *error) {
- if (error == nil) return;
- NSLog(@"!!!ERROR, failed to add the asset to the custom photo album: %@", [error description]);
- };
-
- // save image to custom photo album
- if (! self.assetsLibrary) assetsLibrary_ = [[ALAssetsLibrary alloc] init];
- [self.assetsLibrary saveImage:finalImageToSave
- toAlbum:kKYCustomPhotoAlbumName_
- completion:completion
- failure:failure];
- });
- }
+ });
+ };
+
+ void (^failure)(NSError *) = ^(NSError *error) {
+ if (error == nil) return;
+ NSLog(@"!!!ERROR, failed to add the asset to the custom photo album: %@", [error description]);
+ };
+
+ // Save image to custom photo album
+ // The lifetimes of objects you get back from a library instance are tied to
+ // the lifetime of the library instance.
+ [self.assetsLibrary saveImage:finalImageToSave
+ toAlbum:kKYCustomPhotoAlbumName_
+ completion:completion
+ failure:failure];
+ });
}
@end