master 8e952d251c09 cached
37 files
120.0 KB
32.6k tokens
5 symbols
1 requests
Download .txt
Repository: arturgrigor/AGImagePickerController
Branch: master
Commit: 8e952d251c09
Files: 37
Total size: 120.0 KB

Directory structure:
gitextract_fuleemah/

├── AGImagePickerController/
│   ├── AGIPCAlbumsController.h
│   ├── AGIPCAlbumsController.m
│   ├── AGIPCAssetsController.h
│   ├── AGIPCAssetsController.m
│   ├── AGIPCGridCell.h
│   ├── AGIPCGridCell.m
│   ├── AGIPCGridItem.h
│   ├── AGIPCGridItem.m
│   ├── AGIPCToolbarItem.h
│   ├── AGIPCToolbarItem.m
│   ├── AGImagePickerController+Helper.h
│   ├── AGImagePickerController+Helper.m
│   ├── AGImagePickerController.h
│   ├── AGImagePickerController.m
│   ├── AGImagePickerControllerDefines.h
│   ├── ALAsset+AGIPC.h
│   └── ALAsset+AGIPC.m
├── AGImagePickerController Demo/
│   ├── AGAppDelegate.h
│   ├── AGAppDelegate.m
│   ├── AGImagePickerController Demo-Info.plist
│   ├── AGImagePickerController Demo-Prefix.pch
│   ├── AGViewController.h
│   ├── AGViewController.m
│   ├── en.lproj/
│   │   ├── AGViewController_iPad.xib
│   │   ├── AGViewController_iPhone.xib
│   │   └── InfoPlist.strings
│   └── main.m
├── AGImagePickerController Demo.xcodeproj/
│   ├── project.pbxproj
│   ├── project.xcworkspace/
│   │   ├── contents.xcworkspacedata
│   │   └── xcuserdata/
│   │       └── arturgrigor.xcuserdatad/
│   │           ├── UserInterfaceState.xcuserstate
│   │           └── WorkspaceSettings.xcsettings
│   └── xcuserdata/
│       └── arturgrigor.xcuserdatad/
│           ├── xcdebugger/
│           │   └── Breakpoints.xcbkptlist
│           └── xcschemes/
│               ├── AGImagePickerController Demo.xcscheme
│               └── xcschememanagement.plist
├── AGImagePickerController.podspec
├── LICENSE
└── README.md

================================================
FILE CONTENTS
================================================

================================================
FILE: AGImagePickerController/AGIPCAlbumsController.h
================================================
//
//  AGIPCAlbumsController.h
//  AGImagePickerController
//
//  Created by Artur Grigor on 2/16/12.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import <UIKit/UIKit.h>
#import <AssetsLibrary/AssetsLibrary.h>

#import "AGImagePickerController.h"

@interface AGIPCAlbumsController : UITableViewController<UITableViewDataSource, UITableViewDelegate>

@property (strong) AGImagePickerController *imagePickerController;

- (id)initWithImagePickerController:(AGImagePickerController *)imagePickerController;

@end


================================================
FILE: AGImagePickerController/AGIPCAlbumsController.m
================================================
//
//  AGIPCAlbumsController.m
//  AGImagePickerController
//
//  Created by Artur Grigor on 2/16/12.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import "AGIPCAlbumsController.h"

#import "AGImagePickerController.h"
#import "AGIPCAssetsController.h"

@interface AGIPCAlbumsController ()
{
    NSMutableArray *_assetsGroups;
    AGImagePickerController *_imagePickerController;
}

@property (ag_weak, nonatomic, readonly) NSMutableArray *assetsGroups;

@end

@interface AGIPCAlbumsController ()

- (void)registerForNotifications;
- (void)unregisterFromNotifications;

- (void)didChangeLibrary:(NSNotification *)notification;

- (void)loadAssetsGroups;
- (void)reloadData;

- (void)cancelAction:(id)sender;

@end

@implementation AGIPCAlbumsController

#pragma mark - Properties

@synthesize imagePickerController = _imagePickerController;

- (NSMutableArray *)assetsGroups
{
    if (_assetsGroups == nil)
    {
        _assetsGroups = [[NSMutableArray alloc] init];
        [self loadAssetsGroups];
    }
    
    return _assetsGroups;
}

#pragma mark - Object Lifecycle

- (id)initWithImagePickerController:(AGImagePickerController *)imagePickerController
{
    self = [super initWithStyle:UITableViewStylePlain];
    if (self)
    {
        self.imagePickerController = imagePickerController;
    }
    
    return self;
}

- (void)didReceiveMemoryWarning
{
    // Releases the view if it doesn't have a superview.
    [super didReceiveMemoryWarning];
    
    // Release any cached data, images, etc that aren't in use.
}

#pragma mark - View lifecycle

- (void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];
    
    [self.navigationController setToolbarHidden:YES animated:YES];
}

- (void)viewDidLoad
{
    [super viewDidLoad];
    
    // Fullscreen
    if (self.imagePickerController.shouldChangeStatusBarStyle) {
        self.wantsFullScreenLayout = YES;
    }
    
    // Setup Notifications
    [self registerForNotifications];
    
    // Navigation Bar Items
    UIBarButtonItem *cancelButton = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemCancel target:self action:@selector(cancelAction:)];
	self.navigationItem.leftBarButtonItem = cancelButton;
}

- (void)viewDidUnload
{
    [super viewDidUnload];
    
    // Destroy Notifications
    [self unregisterFromNotifications];
}

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    return YES;
}

- (NSUInteger)supportedInterfaceOrientations
{
    return UIInterfaceOrientationMaskAll;
}

#pragma mark - UITableViewDataSource Methods

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    return self.assetsGroups.count;
    self.title = NSLocalizedStringWithDefaultValue(@"AGIPC.Loading", nil, [NSBundle mainBundle], @"Loading...", nil);
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"Cell";
    
    UITableViewCell *cell = [self.tableView dequeueReusableCellWithIdentifier:CellIdentifier];
    if (cell == nil) {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleValue1 reuseIdentifier:CellIdentifier];
    }
    
    ALAssetsGroup *group = (self.assetsGroups)[indexPath.row];
    [group setAssetsFilter:[ALAssetsFilter allPhotos]];
    NSUInteger numberOfAssets = group.numberOfAssets;
    
    cell.textLabel.text = [NSString stringWithFormat:@"%@", [group valueForProperty:ALAssetsGroupPropertyName]];
    cell.detailTextLabel.text = [NSString stringWithFormat:@"%d", numberOfAssets];
    [cell.imageView setImage:[UIImage imageWithCGImage:[(ALAssetsGroup *)self.assetsGroups[indexPath.row] posterImage]]];
	[cell setAccessoryType:UITableViewCellAccessoryDisclosureIndicator];
	
    return cell;
}

#pragma mark - UITableViewDelegate Methods

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
    [self.tableView deselectRowAtIndexPath:indexPath animated:YES];
    
	AGIPCAssetsController *controller = [[AGIPCAssetsController alloc] initWithImagePickerController:self.imagePickerController andAssetsGroup:self.assetsGroups[indexPath.row]];
	[self.navigationController pushViewController:controller animated:YES];
}

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{	
	return 57;
}

#pragma mark - Private

- (void)loadAssetsGroups
{
    __ag_weak AGIPCAlbumsController *weakSelf = self;
    
    [self.assetsGroups removeAllObjects];
    
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_LOW, 0), ^{
        
        @autoreleasepool {
            
            void (^assetGroupEnumerator)(ALAssetsGroup *, BOOL *) = ^(ALAssetsGroup *group, BOOL *stop) 
            {
                if (group == nil) 
                {
                    return;
                }
                
                if (weakSelf.imagePickerController.shouldShowSavedPhotosOnTop) {
                    if ([[group valueForProperty:ALAssetsGroupPropertyType] intValue] == ALAssetsGroupSavedPhotos) {
                        [self.assetsGroups insertObject:group atIndex:0];
                    } else if ([[group valueForProperty:ALAssetsGroupPropertyType] intValue] > ALAssetsGroupSavedPhotos) {
                        [self.assetsGroups insertObject:group atIndex:1];
                    } else {
                        [self.assetsGroups addObject:group];
                    }
                } else {
                    [self.assetsGroups addObject:group];
                }
                
                dispatch_async(dispatch_get_main_queue(), ^{
                    [self reloadData];
                });
            };
            
            void (^assetGroupEnumberatorFailure)(NSError *) = ^(NSError *error) {
                NSLog(@"A problem occured. Error: %@", error.localizedDescription);
                [self.imagePickerController performSelector:@selector(didFail:) withObject:error];
            };	
            
            [[AGImagePickerController defaultAssetsLibrary] enumerateGroupsWithTypes:ALAssetsGroupAll
                                   usingBlock:assetGroupEnumerator 
                                 failureBlock:assetGroupEnumberatorFailure];
            
        }
        
    });
}

- (void)reloadData
{
    [self.tableView reloadData];
    self.title = NSLocalizedStringWithDefaultValue(@"AGIPC.Albums", nil, [NSBundle mainBundle], @"Albums", nil);
}

- (void)cancelAction:(id)sender
{
    [self.imagePickerController performSelector:@selector(didCancelPickingAssets)];
}

#pragma mark - Notifications

- (void)registerForNotifications
{
    [[NSNotificationCenter defaultCenter] addObserver:self 
                                             selector:@selector(didChangeLibrary:) 
                                                 name:ALAssetsLibraryChangedNotification 
                                               object:[AGImagePickerController defaultAssetsLibrary]];
}

- (void)unregisterFromNotifications
{
    [[NSNotificationCenter defaultCenter] removeObserver:self 
                                                    name:ALAssetsLibraryChangedNotification 
                                                  object:[AGImagePickerController defaultAssetsLibrary]];
}

- (void)didChangeLibrary:(NSNotification *)notification
{
    [self loadAssetsGroups];
}

@end


================================================
FILE: AGImagePickerController/AGIPCAssetsController.h
================================================
//
//  AGIPCAssetsController.h
//  AGImagePickerController
//
//  Created by Artur Grigor on 17.02.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import <UIKit/UIKit.h>
#import <AssetsLibrary/AssetsLibrary.h>
#import <CoreLocation/CoreLocation.h>

#import "AGImagePickerController.h"
#import "AGIPCGridItem.h"

@interface AGIPCAssetsController : UITableViewController<UITableViewDataSource, UITableViewDelegate, AGIPCGridItemDelegate>

@property (strong) ALAssetsGroup *assetsGroup;
@property (ag_weak, readonly) NSArray *selectedAssets;
@property (strong) AGImagePickerController *imagePickerController;

- (id)initWithImagePickerController:(AGImagePickerController *)imagePickerController andAssetsGroup:(ALAssetsGroup *)assetsGroup;

@end


================================================
FILE: AGImagePickerController/AGIPCAssetsController.m
================================================
//
//  AGIPCAssetsController.m
//  AGImagePickerController
//
//  Created by Artur Grigor on 17.02.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import "AGIPCAssetsController.h"

#import "AGImagePickerController+Helper.h"

#import "AGIPCGridCell.h"
#import "AGIPCToolbarItem.h"

@interface AGIPCAssetsController ()
{
    ALAssetsGroup *_assetsGroup;
    NSMutableArray *_assets;
    AGImagePickerController *_imagePickerController;
}

@property (nonatomic, strong) NSMutableArray *assets;

@end

@interface AGIPCAssetsController (Private)

- (void)changeSelectionInformation;

- (void)registerForNotifications;
- (void)unregisterFromNotifications;

- (void)didChangeLibrary:(NSNotification *)notification;
- (void)didChangeToolbarItemsForManagingTheSelection:(NSNotification *)notification;

- (BOOL)toolbarHidden;

- (void)loadAssets;
- (void)reloadData;

- (void)setupToolbarItems;

- (NSArray *)itemsForRowAtIndexPath:(NSIndexPath *)indexPath;

- (void)doneAction:(id)sender;
- (void)selectAllAction:(id)sender;
- (void)deselectAllAction:(id)sender;
- (void)customBarButtonItemAction:(id)sender;

@end

@implementation AGIPCAssetsController

#pragma mark - Properties

@synthesize assetsGroup = _assetsGroup, assets = _assets, imagePickerController = _imagePickerController;

- (BOOL)toolbarHidden
{
    if (! self.imagePickerController.shouldShowToolbarForManagingTheSelection)
        return YES;
    else
    {
        if (self.imagePickerController.toolbarItemsForManagingTheSelection != nil) {
            return !(self.imagePickerController.toolbarItemsForManagingTheSelection.count > 0);
        } else {
            return NO;
        }
    }
}

- (void)setAssetsGroup:(ALAssetsGroup *)theAssetsGroup
{
    @synchronized (self)
    {
        if (_assetsGroup != theAssetsGroup)
        {
            _assetsGroup = theAssetsGroup;
            [_assetsGroup setAssetsFilter:[ALAssetsFilter allPhotos]];

            [self reloadData];
        }
    }
}

- (ALAssetsGroup *)assetsGroup
{
    ALAssetsGroup *ret = nil;
    
    @synchronized (self)
    {
        ret = _assetsGroup;
    }
    
    return ret;
}

- (NSArray *)selectedAssets
{
    NSMutableArray *selectedAssets = [NSMutableArray array];
    
	for (AGIPCGridItem *gridItem in self.assets) 
    {		
		if (gridItem.selected)
        {	
			[selectedAssets addObject:gridItem.asset];
		}
	}
    
    return selectedAssets;
}

#pragma mark - Object Lifecycle

- (id)initWithImagePickerController:(AGImagePickerController *)imagePickerController andAssetsGroup:(ALAssetsGroup *)assetsGroup
{
    self = [super initWithStyle:UITableViewStylePlain];
    if (self)
    {
        _assets = [[NSMutableArray alloc] init];
        self.assetsGroup = assetsGroup;
        self.imagePickerController = imagePickerController;
        self.title = NSLocalizedStringWithDefaultValue(@"AGIPC.Loading", nil, [NSBundle mainBundle], @"Loading...", nil);
        self.title = [self.assetsGroup valueForProperty:ALAssetsGroupPropertyName];
        
        self.tableView.allowsMultipleSelection = NO;
        self.tableView.allowsSelection = NO;
        self.tableView.separatorStyle = UITableViewCellSeparatorStyleNone;
        
        // Navigation Bar Items
        UIBarButtonItem *doneButtonItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemDone target:self action:@selector(doneAction:)];
        doneButtonItem.enabled = NO;
        self.navigationItem.rightBarButtonItem = doneButtonItem;
        
        // Setup toolbar items
        [self setupToolbarItems];
        
        // Start loading the assets
        [self loadAssets];
    }
    
    return self;
}

- (void)dealloc
{
    [self unregisterFromNotifications];
}

#pragma mark - UITableViewDataSource Methods

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    if (! self.imagePickerController) return 0;
    
    double numberOfAssets = (double)self.assetsGroup.numberOfAssets;
    NSInteger nr = ceil(numberOfAssets / self.imagePickerController.numberOfItemsPerRow);
    
    return nr;
}

- (NSArray *)itemsForRowAtIndexPath:(NSIndexPath *)indexPath
{
    NSMutableArray *items = [NSMutableArray arrayWithCapacity:self.imagePickerController.numberOfItemsPerRow];
    
    NSUInteger startIndex = indexPath.row * self.imagePickerController.numberOfItemsPerRow, 
                 endIndex = startIndex + self.imagePickerController.numberOfItemsPerRow - 1;
    if (startIndex < self.assets.count)
    {
        if (endIndex > self.assets.count - 1)
            endIndex = self.assets.count - 1;
        
        for (NSUInteger i = startIndex; i <= endIndex; i++)
        {
            [items addObject:(self.assets)[i]];
        }
    }
    
    return items;
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"Cell";
    
    AGIPCGridCell *cell = (AGIPCGridCell *)[self.tableView dequeueReusableCellWithIdentifier:CellIdentifier];
    if (cell == nil) 
    {		        
        cell = [[AGIPCGridCell alloc] initWithImagePickerController:self.imagePickerController items:[self itemsForRowAtIndexPath:indexPath] andReuseIdentifier:CellIdentifier];
    }	
	else 
    {		
		cell.items = [self itemsForRowAtIndexPath:indexPath];
	}
    
    return cell;
}

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{
    CGRect itemRect = self.imagePickerController.itemRect;
    return itemRect.size.height + itemRect.origin.y;
}

#pragma mark - View Lifecycle

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    return YES;
}

- (void)willRotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration
{
    [super willRotateToInterfaceOrientation:toInterfaceOrientation duration:duration];
    
    [self reloadData];
}

- (void)viewWillAppear:(BOOL)animated
{
    // Reset the number of selections
    [AGIPCGridItem performSelector:@selector(resetNumberOfSelections)];
    
    [super viewWillAppear:animated];
}

- (void)viewDidLoad
{
    [super viewDidLoad];
    
    // Fullscreen
    if (self.imagePickerController.shouldChangeStatusBarStyle) {
        self.wantsFullScreenLayout = YES;
    }
    
    // Setup Notifications
    [self registerForNotifications];
}

- (void)viewDidUnload
{
    [super viewDidUnload];
    
    // Destroy Notifications
    [self unregisterFromNotifications];
}

#pragma mark - Private

- (void)setupToolbarItems
{
    if (self.imagePickerController.toolbarItemsForManagingTheSelection != nil)
    {
        NSMutableArray *items = [NSMutableArray array];
        
        // Custom Toolbar Items
        for (id item in self.imagePickerController.toolbarItemsForManagingTheSelection)
        {
            NSAssert([item isKindOfClass:[AGIPCToolbarItem class]], @"Item is not a instance of AGIPCToolbarItem.");
            
            ((AGIPCToolbarItem *)item).barButtonItem.target = self;
            ((AGIPCToolbarItem *)item).barButtonItem.action = @selector(customBarButtonItemAction:);
            
            [items addObject:((AGIPCToolbarItem *)item).barButtonItem];
        }
        
        self.toolbarItems = items;
    } else {
        // Standard Toolbar Items
        UIBarButtonItem *selectAll = [[UIBarButtonItem alloc] initWithTitle:NSLocalizedStringWithDefaultValue(@"AGIPC.SelectAll", nil, [NSBundle mainBundle], @"Select All", nil) style:UIBarButtonItemStyleBordered target:self action:@selector(selectAllAction:)];
        UIBarButtonItem *flexibleSpace = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFlexibleSpace target:nil action:nil];
        UIBarButtonItem *deselectAll = [[UIBarButtonItem alloc] initWithTitle:NSLocalizedStringWithDefaultValue(@"AGIPC.DeselectAll", nil, [NSBundle mainBundle], @"Deselect All", nil) style:UIBarButtonItemStyleBordered target:self action:@selector(deselectAllAction:)];
        
        NSArray *toolbarItemsForManagingTheSelection = @[selectAll, flexibleSpace, deselectAll];
        self.toolbarItems = toolbarItemsForManagingTheSelection;
    }
}

- (void)loadAssets
{
    [self.assets removeAllObjects];
    
    __ag_weak AGIPCAssetsController *weakSelf = self;
    
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), ^{
        
        __strong AGIPCAssetsController *strongSelf = weakSelf;
        
        @autoreleasepool {
            [strongSelf.assetsGroup enumerateAssetsUsingBlock:^(ALAsset *result, NSUInteger index, BOOL *stop) {
                
                if (result == nil) 
                {
                    return;
                }
                if (strongSelf.imagePickerController.shouldShowPhotosWithLocationOnly) {
                    CLLocation *assetLocation = [result valueForProperty:ALAssetPropertyLocation];
                    if (!assetLocation || !CLLocationCoordinate2DIsValid([assetLocation coordinate])) {
                        return;
                    }
                }
                
                AGIPCGridItem *gridItem = [[AGIPCGridItem alloc] initWithImagePickerController:self.imagePickerController asset:result andDelegate:self];
                
                // Drawing must be exectued in main thread. springox(20131220)
                /*
                if (strongSelf.imagePickerController.selection != nil &&
                    [strongSelf.imagePickerController.selection containsObject:result])
                {
                    gridItem.selected = YES;
                }
                 */
                
                //[strongSelf.assets addObject:gridItem];
                // Descending photos, springox(20131225)
                [strongSelf.assets insertObject:gridItem atIndex:0];

            }];
        }
        
        dispatch_async(dispatch_get_main_queue(), ^{
            
            [strongSelf reloadData];
            
        });
    
    });
}

- (void)reloadData
{
    // Don't display the select button until all the assets are loaded.
    [self.navigationController setToolbarHidden:[self toolbarHidden] animated:YES];
    
    [self.tableView reloadData];
    
    //[self setTitle:[self.assetsGroup valueForProperty:ALAssetsGroupPropertyName]];
    [self changeSelectionInformation];
    
    /*
    NSInteger totalRows = [self.tableView numberOfRowsInSection:0];
    //Prevents crash if totalRows = 0 (when the album is empty).
    if (totalRows > 0) {
        [self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:totalRows-1 inSection:0] atScrollPosition:UITableViewScrollPositionBottom animated:NO];
    }
     */
}

- (void)doneAction:(id)sender
{
    [self.imagePickerController performSelector:@selector(didFinishPickingAssets:) withObject:self.selectedAssets];
}

- (void)selectAllAction:(id)sender
{
    for (AGIPCGridItem *gridItem in self.assets) {
        gridItem.selected = YES;
    }
}

- (void)deselectAllAction:(id)sender
{
    for (AGIPCGridItem *gridItem in self.assets) {
        gridItem.selected = NO;
    }
}

- (void)customBarButtonItemAction:(id)sender
{
    for (id item in self.imagePickerController.toolbarItemsForManagingTheSelection)
    {
        NSAssert([item isKindOfClass:[AGIPCToolbarItem class]], @"Item is not a instance of AGIPCToolbarItem.");
        
        if (((AGIPCToolbarItem *)item).barButtonItem == sender)
        {
            if (((AGIPCToolbarItem *)item).assetIsSelectedBlock) {
                
                NSUInteger idx = 0;
                for (AGIPCGridItem *obj in self.assets) {
                    obj.selected = ((AGIPCToolbarItem *)item).assetIsSelectedBlock(idx, ((AGIPCGridItem *)obj).asset);
                    idx++;
                }
                
            }
        }
    }
}

- (void)changeSelectionInformation
{
    if (self.imagePickerController.shouldDisplaySelectionInformation ) {
        if (0 == [AGIPCGridItem numberOfSelections] ) {
            self.navigationController.navigationBar.topItem.prompt = nil;
        } else {
            //self.navigationController.navigationBar.topItem.prompt = [NSString stringWithFormat:@"(%d/%d)", [AGIPCGridItem numberOfSelections], self.assets.count];
            // Display supports up to select several photos at the same time, springox(20131220)
            NSInteger maxNumber = _imagePickerController.maximumNumberOfPhotosToBeSelected;
            if (0 < maxNumber) {
                self.navigationController.navigationBar.topItem.prompt = [NSString stringWithFormat:@"(%d/%d)", [AGIPCGridItem numberOfSelections], maxNumber];
            } else {
                self.navigationController.navigationBar.topItem.prompt = [NSString stringWithFormat:@"(%d/%d)", [AGIPCGridItem numberOfSelections], self.assets.count];
            }
        }
    }
}

#pragma mark - AGGridItemDelegate Methods

- (void)agGridItem:(AGIPCGridItem *)gridItem didChangeNumberOfSelections:(NSNumber *)numberOfSelections
{
    self.navigationItem.rightBarButtonItem.enabled = (numberOfSelections.unsignedIntegerValue > 0);
    [self changeSelectionInformation];
}

- (BOOL)agGridItemCanSelect:(AGIPCGridItem *)gridItem
{
    if (self.imagePickerController.selectionMode == AGImagePickerControllerSelectionModeSingle && self.imagePickerController.selectionBehaviorInSingleSelectionMode == AGImagePickerControllerSelectionBehaviorTypeRadio) {
        for (AGIPCGridItem *item in self.assets)
            if (item.selected)
                item.selected = NO;
        
        return YES;
    } else {
        if (self.imagePickerController.maximumNumberOfPhotosToBeSelected > 0)
            return ([AGIPCGridItem numberOfSelections] < self.imagePickerController.maximumNumberOfPhotosToBeSelected);
        else
            return YES;
    }
}

#pragma mark - Notifications

- (void)registerForNotifications
{
    [[NSNotificationCenter defaultCenter] addObserver:self 
                                             selector:@selector(didChangeLibrary:) 
                                                 name:ALAssetsLibraryChangedNotification 
                                               object:[AGImagePickerController defaultAssetsLibrary]];
}

- (void)unregisterFromNotifications
{
    [[NSNotificationCenter defaultCenter] removeObserver:self 
                                                    name:ALAssetsLibraryChangedNotification 
                                                  object:[AGImagePickerController defaultAssetsLibrary]];
}

- (void)didChangeLibrary:(NSNotification *)notification
{
    [self.navigationController popToRootViewControllerAnimated:YES];
}

- (void)didChangeToolbarItemsForManagingTheSelection:(NSNotification *)notification
{
    NSLog(@"here.");
}

@end


================================================
FILE: AGImagePickerController/AGIPCGridCell.h
================================================
//
//  AGIPCGridCell.h
//  AGImagePickerController
//
//  Created by Artur Grigor on 17.02.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import <UIKit/UIKit.h>

#import "AGImagePickerController.h"

@interface AGIPCGridCell : UITableViewCell

@property (strong) NSArray *items;
@property (strong) AGImagePickerController *imagePickerController;

- (id)initWithImagePickerController:(AGImagePickerController *)imagePickerController items:(NSArray *)items andReuseIdentifier:(NSString *)identifier;

@end


================================================
FILE: AGImagePickerController/AGIPCGridCell.m
================================================
//
//  AGIPCGridCell.m
//  AGImagePickerController
//
//  Created by Artur Grigor on 17.02.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import "AGIPCGridCell.h"
#import "AGIPCGridItem.h"

#import "AGImagePickerController.h"
#import "AGImagePickerController+Helper.h"

@interface AGIPCGridCell ()
{
	NSArray *_items;
    AGImagePickerController *_imagePickerController;
}

@end

@implementation AGIPCGridCell

#pragma mark - Properties

@synthesize items = _items, imagePickerController = _imagePickerController;

- (void)setItems:(NSArray *)items
{
    @synchronized (self)
    {
        if (_items != items)
        {
            _items = items;
            
            for (UIView *view in [self.contentView subviews])
            {
                [view removeFromSuperview];
            }
            
            for (AGIPCGridItem *gridItem in _items)
            {
                [self addSubview:gridItem];
            }
        }
    }
}

- (NSArray *)items
{
    NSArray *array = nil;
    
    @synchronized (self)
    {
        array = _items;
    }
    
    return array;
}

#pragma mark - Object Lifecycle

- (id)initWithImagePickerController:(AGImagePickerController *)imagePickerController items:(NSArray *)items andReuseIdentifier:(NSString *)identifier
{
    self = [super initWithStyle:UITableViewCellStyleDefault reuseIdentifier:identifier];
    if (self)
    {
        self.imagePickerController = imagePickerController;
		self.items = items;
        
        UIView *emptyView = [[UIView alloc] init];
        self.backgroundView = emptyView;
	}
	
	return self;
}

#pragma mark - Layout

- (void)layoutSubviews
{
    CGRect frame = self.imagePickerController.itemRect;
    CGFloat leftMargin = frame.origin.x;
    
	for (AGIPCGridItem *gridItem in self.items)
    {
        // Load image with asset when layout grid items. springox(20131218)
        [gridItem loadImageFromAsset];
        
        [gridItem setFrame:frame];
        UITapGestureRecognizer *selectionGestureRecognizer = [[UITapGestureRecognizer alloc] initWithTarget:gridItem action:@selector(tap)];
        selectionGestureRecognizer.numberOfTapsRequired = 1;
		[gridItem addGestureRecognizer:selectionGestureRecognizer];

		frame.origin.x = frame.origin.x + frame.size.width + leftMargin;
	}
}

@end


================================================
FILE: AGImagePickerController/AGIPCGridItem.h
================================================
//
//  AGIPCGridItem.h
//  AGImagePickerController
//
//  Created by Artur Grigor on 17.02.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import <UIKit/UIKit.h>
#import <AssetsLibrary/AssetsLibrary.h>

#import "AGImagePickerController.h"

@class AGIPCGridItem;

@protocol AGIPCGridItemDelegate <NSObject>

@optional
- (void)agGridItem:(AGIPCGridItem *)gridItem didChangeSelectionState:(NSNumber *)selected;
- (void)agGridItem:(AGIPCGridItem *)gridItem didChangeNumberOfSelections:(NSNumber *)numberOfSelections;
- (BOOL)agGridItemCanSelect:(AGIPCGridItem *)gridItem;

@end

@interface AGIPCGridItem : UIView
{

}

@property (assign) BOOL selected;
@property (strong) ALAsset *asset;

@property (nonatomic, ag_weak) id<AGIPCGridItemDelegate> delegate;

@property (strong) AGImagePickerController *imagePickerController;

- (id)initWithImagePickerController:(AGImagePickerController *)imagePickerController andAsset:(ALAsset *)asset;
- (id)initWithImagePickerController:(AGImagePickerController *)imagePickerController asset:(ALAsset *)asset andDelegate:(id<AGIPCGridItemDelegate>)delegate;

- (void)loadImageFromAsset;

- (void)tap;

+ (NSUInteger)numberOfSelections;

@end


================================================
FILE: AGImagePickerController/AGIPCGridItem.m
================================================
//
//  AGIPCGridItem.m
//  AGImagePickerController
//
//  Created by Artur Grigor on 17.02.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import "AGIPCGridItem.h"


#import "AGImagePickerController+Helper.h"

@interface AGIPCGridItem ()
{
    AGImagePickerController *_imagePickerController;
    ALAsset *_asset;
    id<AGIPCGridItemDelegate> __ag_weak _delegate;
    
    BOOL _selected;
    
    UIImageView *_thumbnailImageView;
    UIView *_selectionView;
    UIImageView *_checkmarkImageView;
}

@property (nonatomic, strong) UIImageView *thumbnailImageView;
@property (nonatomic, strong) UIView *selectionView;
@property (nonatomic, strong) UIImageView *checkmarkImageView;

+ (void)resetNumberOfSelections;

@end

static NSUInteger numberOfSelectedGridItems = 0;

@implementation AGIPCGridItem

#pragma mark - Properties

@synthesize imagePickerController = _imagePickerController, delegate = _delegate, asset = _asset, selected = _selected, thumbnailImageView = _thumbnailImageView, selectionView = _selectionView, checkmarkImageView = _checkmarkImageView;

- (void)setSelected:(BOOL)selected
{
    @synchronized (self)
    {
        if (_selected != selected)
        {
            if (selected) {
                // Check if we can select
                if ([self.delegate respondsToSelector:@selector(agGridItemCanSelect:)])
                {
                    if (![self.delegate agGridItemCanSelect:self])
                        return;
                }
            }
            
            _selected = selected;
            
            self.selectionView.hidden = !_selected;
            self.checkmarkImageView.hidden = !_selected;
            
            if (_selected)
            {
                numberOfSelectedGridItems++;
            }
            else
            {
                if (numberOfSelectedGridItems > 0)
                    numberOfSelectedGridItems--;
            }
            
            dispatch_async(dispatch_get_main_queue(), ^{
               
                if ([self.delegate respondsToSelector:@selector(agGridItem:didChangeSelectionState:)])
                {
                    [self.delegate performSelector:@selector(agGridItem:didChangeSelectionState:) withObject:self withObject:@(_selected)];
                }
                
                if ([self.delegate respondsToSelector:@selector(agGridItem:didChangeNumberOfSelections:)])
                {
                    [self.delegate performSelector:@selector(agGridItem:didChangeNumberOfSelections:) withObject:self withObject:@(numberOfSelectedGridItems)];
                }
                
            });
        }
    }
}

- (BOOL)selected
{
    BOOL ret;
    @synchronized (self) { ret = _selected; }
    
    return ret;
}

- (void)setAsset:(ALAsset *)asset
{
    @synchronized (self)
    {
        if (_asset != asset)
        {
            _asset = asset;
            // Drawing must be exectued in main thread. springox(20131218)
            //self.thumbnailImageView.image = [UIImage imageWithCGImage:_asset.thumbnail];
        }
    }
}

- (ALAsset *)asset
{
    ALAsset *ret = nil;
    @synchronized (self) { ret = _asset; }
    
    return ret;
}

#pragma mark - Object Lifecycle

- (id)initWithImagePickerController:(AGImagePickerController *)imagePickerController andAsset:(ALAsset *)asset
{
    self = [self initWithImagePickerController:imagePickerController asset:asset andDelegate:nil];
    return self;
}

- (id)initWithImagePickerController:(AGImagePickerController *)imagePickerController asset:(ALAsset *)asset andDelegate:(id<AGIPCGridItemDelegate>)delegate
{
    self = [super init];
    if (self)
    {
        self.imagePickerController = imagePickerController;
        
        self.selected = NO;
        self.delegate = delegate;
        
        CGRect frame = self.imagePickerController.itemRect;
        CGRect checkmarkFrame = [self.imagePickerController checkmarkFrameUsingItemFrame:frame];
        
        self.thumbnailImageView = [[UIImageView alloc] initWithFrame:CGRectMake(0, 0, frame.size.width, frame.size.height)];
        // Drawing must be exectued in main thread. springox(20131220)
		//self.thumbnailImageView.contentMode = UIViewContentModeScaleToFill;
		[self addSubview:self.thumbnailImageView];
        
        self.selectionView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, frame.size.width, frame.size.height)];
        // Drawing must be exectued in main thread. springox(20131220)
        //self.selectionView.backgroundColor = [UIColor whiteColor];
        //self.selectionView.alpha = .5f;
        //self.selectionView.hidden = !self.selected;
        [self addSubview:self.selectionView];
        
        // Position the checkmark image in the bottom right corner
        self.checkmarkImageView = [[UIImageView alloc] initWithFrame:checkmarkFrame];
        // Drawing must be exectued in main thread. springox(20131220)
        //if (IS_IPAD())
        //    self.checkmarkImageView.image = [UIImage imageNamed:@"AGImagePickerController.bundle/AGIPC-Checkmark-iPad"];
        //else
        //    self.checkmarkImageView.image = [UIImage imageNamed:@"AGImagePickerController.bundle/AGIPC-Checkmark-iPhone"];
        //self.checkmarkImageView.hidden = !self.selected;
		[self addSubview:self.checkmarkImageView];
        
        self.asset = asset;
    }
    
    return self;
}

- (void)layoutSubviews
{
    [super layoutSubviews];
    
    self.thumbnailImageView.contentMode = UIViewContentModeScaleToFill;

    self.selectionView.backgroundColor = [UIColor whiteColor];
    self.selectionView.alpha = .5f;
    self.selectionView.hidden = !self.selected;

    if (IS_IPAD())
    self.checkmarkImageView.image = [UIImage imageNamed:@"AGImagePickerController.bundle/AGIPC-Checkmark-iPad"];
    else
    self.checkmarkImageView.image = [UIImage imageNamed:@"AGImagePickerController.bundle/AGIPC-Checkmark-iPhone"];
    self.checkmarkImageView.hidden = !self.selected;
}

// Drawing must be exectued in main thread. springox(20131218)
- (void)loadImageFromAsset
{
    self.thumbnailImageView.image = [UIImage imageWithCGImage:_asset.thumbnail];
    if ([self.imagePickerController.selection containsObject:self]) {
        self.selected = YES;
    }
}

#pragma mark - Others

- (void)tap
{
    self.selected = !self.selected;
}

#pragma mark - Private

+ (void)resetNumberOfSelections
{
    numberOfSelectedGridItems = 0;
}

+ (NSUInteger)numberOfSelections
{
    return numberOfSelectedGridItems;
}

@end


================================================
FILE: AGImagePickerController/AGIPCToolbarItem.h
================================================
//
//  AGIPCToolbarItem.h
//  AGImagePickerController
//
//  Created by Artur Grigor on 05.03.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import <Foundation/Foundation.h>
#import <AssetsLibrary/AssetsLibrary.h>

typedef BOOL (^AGIPCAssetIsSelectedBlock)(NSUInteger index, ALAsset *asset);

@interface AGIPCToolbarItem : NSObject
{
    AGIPCAssetIsSelectedBlock assetIsSelectedBlock;
    UIBarButtonItem *barButtonItem;
}

@property (strong) UIBarButtonItem *barButtonItem;
@property (copy) AGIPCAssetIsSelectedBlock assetIsSelectedBlock;

- (id)initWithBarButtonItem:(UIBarButtonItem *)theBarButtonItem;
- (id)initWithBarButtonItem:(UIBarButtonItem *)theBarButtonItem andSelectionBlock:(AGIPCAssetIsSelectedBlock)theSelectionBlock;

@end


================================================
FILE: AGImagePickerController/AGIPCToolbarItem.m
================================================
//
//  AGIPCToolbarItem.m
//  AGImagePickerController
//
//  Created by Artur Grigor on 05.03.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import "AGIPCToolbarItem.h"

@implementation AGIPCToolbarItem

#pragma mark - Properties

@synthesize assetIsSelectedBlock, barButtonItem;

#pragma mark - Object Lifecycle


#pragma mark - Designated Initializer

- (id)initWithBarButtonItem:(UIBarButtonItem *)theBarButtonItem andSelectionBlock:(AGIPCAssetIsSelectedBlock)theSelectionBlock
{
    self = [super init];
    if (self)
    {
        self.barButtonItem = theBarButtonItem;
        self.assetIsSelectedBlock = theSelectionBlock;
    }
    
    return self;
}

#pragma mark - Initializers

- (id)initWithBarButtonItem:(UIBarButtonItem *)theBarButtonItem
{
    return [self initWithBarButtonItem:theBarButtonItem andSelectionBlock:nil];
}

@end


================================================
FILE: AGImagePickerController/AGImagePickerController+Helper.h
================================================
//
//  AGImagePickerController+Helper.h
//  AGImagePickerController Demo
//
//  Created by Artur Grigor on 06.02.2013.
//  Copyright (c) 2013 Artur Grigor. All rights reserved.
//

#import "AGImagePickerController.h"

@interface AGImagePickerController (Helper)

//
//  Configuring Rows
//
- (NSUInteger)defaultNumberOfItemsPerRow;
- (NSUInteger)numberOfItemsPerRow;

//
//  Configuring Selections
//
- (AGImagePickerControllerSelectionBehaviorType)selectionBehaviorInSingleSelectionMode;

//
//  Appearance Configuration
//
- (BOOL)shouldDisplaySelectionInformation;
- (BOOL)shouldShowToolbarForManagingTheSelection;

//
//  Others
//
- (AGDeviceType)deviceType;

//
//  Drawing: Item
//
- (CGPoint)itemTopLeftPoint;
- (CGRect)itemRect;

//
//  Drawing: Checkmark
//
- (CGRect)checkmarkFrameUsingItemFrame:(CGRect)frame;

@end

@interface NSInvocation (Addon)

+ (id)invocationWithProtocol:(Protocol *)targetProtocol selector:(SEL)selector andRequiredFlag:(BOOL)isMethodRequired;

@end

================================================
FILE: AGImagePickerController/AGImagePickerController+Helper.m
================================================
//
//  AGImagePickerController+Helper.m
//  AGImagePickerController Demo
//
//  Created by Artur Grigor on 06.02.2013.
//  Copyright (c) 2013 Artur Grigor. All rights reserved.
//

#import "AGImagePickerController.h"
#import "AGImagePickerController+Helper.h"

#import <objc/runtime.h>

@implementation AGImagePickerController (Helper)

#pragma mark - Configuring Rows

- (NSUInteger)numberOfItemsPerRow
{
    if (_pickerFlags.delegateNumberOfItemsPerRowForDevice)
    {
        AGDeviceType deviceType = self.deviceType;
        UIInterfaceOrientation interfaceOrientation = self.interfaceOrientation;
        
        SEL selector = @selector(agImagePickerController:numberOfItemsPerRowForDevice:andInterfaceOrientation:);
        Protocol *protocol = @protocol(AGImagePickerControllerDelegate);
        
        NSInvocation *invocation = [NSInvocation invocationWithProtocol:protocol selector:selector andRequiredFlag:NO];
        [invocation setSelector:selector];
        [invocation setArgument:(__bridge void *)(self) atIndex:2];
        [invocation setArgument:&deviceType atIndex:3];
        [invocation setArgument:&interfaceOrientation atIndex:4];
        [invocation invokeWithTarget:self.delegate];
        
        if (invocation)
        {
            NSUInteger length = [[invocation methodSignature] methodReturnLength];
            void *buffer = malloc(length);
            [invocation getReturnValue:buffer];
            NSUInteger ret = *(NSUInteger *)buffer;
            free(buffer);
            
            return ret;
        } else
            return self.defaultNumberOfItemsPerRow;
    } else {
        return self.defaultNumberOfItemsPerRow;
    }
}

- (NSUInteger)defaultNumberOfItemsPerRow
{
    NSUInteger numberOfItemsPerRow = 0;
    
    if (IS_IPAD())
    {
        if (UIInterfaceOrientationIsPortrait(self.interfaceOrientation))
        {
            numberOfItemsPerRow = AGIPC_ITEMS_PER_ROW_IPAD_PORTRAIT;
        } else
        {
            numberOfItemsPerRow = AGIPC_ITEMS_PER_ROW_IPAD_LANDSCAPE;
        }
    } else
    {
        if (UIInterfaceOrientationIsPortrait(self.interfaceOrientation))
        {
            numberOfItemsPerRow = AGIPC_ITEMS_PER_ROW_IPHONE_PORTRAIT;
            
        } else
        {
            numberOfItemsPerRow = AGIPC_ITEMS_PER_ROW_IPHONE_LANDSCAPE;
        }
    }
    
    return numberOfItemsPerRow;
}

#pragma mark - Configuring Selections

- (AGImagePickerControllerSelectionBehaviorType)selectionBehaviorInSingleSelectionMode
{
    if (_pickerFlags.delegateSelectionBehaviorInSingleSelectionMode)
    {
        SEL selector = @selector(selectionBehaviorInSingleSelectionModeForAGImagePickerController:);
        Protocol *protocol = @protocol(AGImagePickerControllerDelegate);
        
        NSInvocation *invocation = [NSInvocation invocationWithProtocol:protocol selector:selector andRequiredFlag:NO];
        [invocation setSelector:selector];
        [invocation setArgument:(__bridge void *)(self) atIndex:2];
        [invocation invokeWithTarget:self.delegate];
        
        if (invocation)
        {
            NSUInteger length = [[invocation methodSignature] methodReturnLength];
            void *buffer = malloc(length);
            [invocation getReturnValue:buffer];
            AGImagePickerControllerSelectionBehaviorType ret = *(AGImagePickerControllerSelectionBehaviorType *)buffer;
            free(buffer);
            
            return ret;
        } else
            return SELECTION_BEHAVIOR_IN_SINGLE_SELECTION_MODE;
    } else {
        return SELECTION_BEHAVIOR_IN_SINGLE_SELECTION_MODE;
    }
}

#pragma mark - Appearance Configuration

- (BOOL)shouldDisplaySelectionInformation
{
    if (_pickerFlags.delegateShouldDisplaySelectionInformationInSelectionMode)
    {
        AGImagePickerControllerSelectionMode selectionMode = self.selectionMode;
        
        SEL selector = @selector(agImagePickerController:shouldDisplaySelectionInformationInSelectionMode:);
        Protocol *protocol = @protocol(AGImagePickerControllerDelegate);
        
        NSInvocation *invocation = [NSInvocation invocationWithProtocol:protocol selector:selector andRequiredFlag:NO];
        [invocation setSelector:selector];
        [invocation setArgument:(__bridge void *)(self) atIndex:2];
        [invocation setArgument:&selectionMode atIndex:3];
        [invocation invokeWithTarget:self.delegate];
        
        if (invocation)
        {
            NSUInteger length = [[invocation methodSignature] methodReturnLength];
            void *buffer = malloc(length);
            [invocation getReturnValue:buffer];
            BOOL ret = *(BOOL *)buffer;
            free(buffer);
            
            return ret;
        } else
            return SHOULD_DISPLAY_SELECTION_INFO;
    } else {
        return SHOULD_DISPLAY_SELECTION_INFO;
    }
}

- (BOOL)shouldShowToolbarForManagingTheSelection
{
    if (_pickerFlags.delegateShouldShowToolbarForManagingTheSelectionInSelectionMode)
    {
        AGImagePickerControllerSelectionMode selectionMode = self.selectionMode;
        
        SEL selector = @selector(agImagePickerController:shouldShowToolbarForManagingTheSelectionInSelectionMode:);
        Protocol *protocol = @protocol(AGImagePickerControllerDelegate);
        
        NSInvocation *invocation = [NSInvocation invocationWithProtocol:protocol selector:selector andRequiredFlag:NO];
        [invocation setSelector:selector];
        [invocation setArgument:(__bridge void *)(self) atIndex:2];
        [invocation setArgument:&selectionMode atIndex:3];
        [invocation invokeWithTarget:self.delegate];
        
        if (invocation)
        {
            NSUInteger length = [[invocation methodSignature] methodReturnLength];
            void *buffer = malloc(length);
            [invocation getReturnValue:buffer];
            BOOL ret = *(BOOL *)buffer;
            free(buffer);
            
            return ret;
        } else
            return SHOULD_SHOW_TOOLBAR_FOR_MANAGING_THE_SELECTION;
    } else {
        return SHOULD_SHOW_TOOLBAR_FOR_MANAGING_THE_SELECTION;
    }
}

#pragma mark - Others

- (AGDeviceType)deviceType
{
    return (IS_IPAD() ? AGDeviceTypeiPad : AGDeviceTypeiPhone);
}

#pragma mark - Drawing: Item

- (CGRect)itemRect
{
    CGPoint topLeftPoint = self.itemTopLeftPoint;
    CGSize size = AGIPC_ITEM_SIZE;
    
    return CGRectMake(topLeftPoint.x, topLeftPoint.y, size.width, size.height);
}

- (CGPoint)itemTopLeftPoint
{
    CGRect bounds = [[UIScreen mainScreen] bounds];
    CGFloat width = bounds.size.width;
    
    if (UIInterfaceOrientationIsLandscape(self.interfaceOrientation)) {
        width = bounds.size.height;
    }
    
    CGFloat x = 0, y = 0;
    
    x = (width - (self.numberOfItemsPerRow * AGIPC_ITEM_SIZE.width)) / (self.numberOfItemsPerRow + 1);
    y = x;
    return CGPointMake(x, y);
}

#pragma mark - Drawing: Checkmark

- (CGRect)checkmarkFrameUsingItemFrame:(CGRect)frame
{
    CGRect checkmarkRect = AGIPC_CHECKMARK_RECT;
    
    return CGRectMake(
                      frame.size.width - checkmarkRect.size.width - checkmarkRect.origin.x,
                      frame.size.height - checkmarkRect.size.height - checkmarkRect.origin.y,
                      checkmarkRect.size.width,
                      checkmarkRect.size.height
                      );
}

@end

@implementation NSInvocation (Addon)

#pragma mark - Invocation

+ (id)invocationWithProtocol:(Protocol *)targetProtocol selector:(SEL)selector andRequiredFlag:(BOOL)isMethodRequired
{
	struct objc_method_description desc;
	desc = protocol_getMethodDescription(targetProtocol, selector, isMethodRequired, YES);
	if (desc.name == NULL)
		return nil;
	
	NSMethodSignature *sig = [NSMethodSignature signatureWithObjCTypes:desc.types];
	NSInvocation *inv = [NSInvocation invocationWithMethodSignature:sig];
	[inv setSelector:selector];
	return inv;
}

@end


================================================
FILE: AGImagePickerController/AGImagePickerController.h
================================================
//
//  AGImagePickerController.h
//  AGImagePickerController
//
//  Created by Artur Grigor on 2/16/12.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import <UIKit/UIKit.h>
#import <AssetsLibrary/AssetsLibrary.h>

#import "AGImagePickerControllerDefines.h"

@class AGImagePickerController;

@protocol AGImagePickerControllerDelegate

@optional

#pragma mark - Configuring Rows
- (NSUInteger)agImagePickerController:(AGImagePickerController *)picker
   numberOfItemsPerRowForDevice:(AGDeviceType)deviceType
        andInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation;

#pragma mark - Configuring Selections
- (AGImagePickerControllerSelectionBehaviorType)selectionBehaviorInSingleSelectionModeForAGImagePickerController:(AGImagePickerController *)picker;

#pragma mark - Appearance Configuration
- (BOOL)agImagePickerController:(AGImagePickerController *)picker
shouldDisplaySelectionInformationInSelectionMode:(AGImagePickerControllerSelectionMode)selectionMode;
- (BOOL)agImagePickerController:(AGImagePickerController *)picker
shouldShowToolbarForManagingTheSelectionInSelectionMode:(AGImagePickerControllerSelectionMode)selectionMode;

#pragma mark - Managing Selections
- (void)agImagePickerController:(AGImagePickerController *)picker didFinishPickingMediaWithInfo:(NSArray *)info;
- (void)agImagePickerController:(AGImagePickerController *)picker didFail:(NSError *)error;

@end

@interface AGImagePickerController : UINavigationController
{
    id __ag_weak _pickerDelegate;
    
    struct {
        unsigned int delegateSelectionBehaviorInSingleSelectionMode:1;
        unsigned int delegateNumberOfItemsPerRowForDevice:1;
        unsigned int delegateShouldDisplaySelectionInformationInSelectionMode:1;
        unsigned int delegateShouldShowToolbarForManagingTheSelectionInSelectionMode:1;
        unsigned int delegateDidFinishPickingMediaWithInfo:1;
        unsigned int delegateDidFail:1;
    } _pickerFlags;
    
    BOOL _shouldChangeStatusBarStyle;
    BOOL _shouldShowSavedPhotosOnTop;
    UIStatusBarStyle _oldStatusBarStyle;
    
    AGIPCDidFinish _didFinishBlock;
    AGIPCDidFail _didFailBlock;
    
    NSUInteger _maximumNumberOfPhotosToBeSelected;
    
    NSArray *_toolbarItemsForManagingTheSelection;
    NSArray *_selection;
}

@property (nonatomic) BOOL shouldChangeStatusBarStyle;
@property (nonatomic) BOOL shouldShowSavedPhotosOnTop;
@property (nonatomic) BOOL shouldShowPhotosWithLocationOnly;
@property (nonatomic) NSUInteger maximumNumberOfPhotosToBeSelected;

@property (nonatomic, ag_weak) id delegate;

@property (nonatomic, copy) AGIPCDidFail didFailBlock;
@property (nonatomic, copy) AGIPCDidFinish didFinishBlock;

@property (nonatomic, strong) NSArray *toolbarItemsForManagingTheSelection;
@property (nonatomic, strong) NSArray *selection;

@property (nonatomic, readonly) AGImagePickerControllerSelectionMode selectionMode;

+ (ALAssetsLibrary *)defaultAssetsLibrary;

- (id)initWithDelegate:(id)delegate;
- (id)initWithFailureBlock:(AGIPCDidFail)failureBlock
           andSuccessBlock:(AGIPCDidFinish)successBlock;
- (id)initWithDelegate:(id)delegate
          failureBlock:(AGIPCDidFail)failureBlock
          successBlock:(AGIPCDidFinish)successBlock
maximumNumberOfPhotosToBeSelected:(NSUInteger)maximumNumberOfPhotosToBeSelected
shouldChangeStatusBarStyle:(BOOL)shouldChangeStatusBarStyle
toolbarItemsForManagingTheSelection:(NSArray *)toolbarItemsForManagingTheSelection
andShouldShowSavedPhotosOnTop:(BOOL)shouldShowSavedPhotosOnTop;

@end




================================================
FILE: AGImagePickerController/AGImagePickerController.m
================================================
//
//  AGImagePickerController.m
//  AGImagePickerController
//
//  Created by Artur Grigor on 2/16/12.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#import "AGImagePickerController.h"

#import "AGIPCAlbumsController.h"
#import "AGIPCGridItem.h"

@interface AGImagePickerController ()
{
    
}

- (void)didFinishPickingAssets:(NSArray *)selectedAssets;
- (void)didCancelPickingAssets;
- (void)didFail:(NSError *)error;

@end

@implementation AGImagePickerController

#pragma mark - Properties

@synthesize
    delegate = _pickerDelegate,
    maximumNumberOfPhotosToBeSelected = _maximumNumberOfPhotosToBeSelected,
    shouldChangeStatusBarStyle = _shouldChangeStatusBarStyle,
    shouldShowSavedPhotosOnTop = _shouldShowSavedPhotosOnTop;

@synthesize
    didFailBlock,
    didFinishBlock;

@synthesize
    toolbarItemsForManagingTheSelection = _toolbarItemsForManagingTheSelection,
    selection = _selection;

- (AGImagePickerControllerSelectionMode)selectionMode
{
    return (self.maximumNumberOfPhotosToBeSelected == 1 ? AGImagePickerControllerSelectionModeSingle : AGImagePickerControllerSelectionModeMultiple);
}

- (void)setDelegate:(id)delegate
{
    _pickerDelegate = delegate;
    
    _pickerFlags.delegateSelectionBehaviorInSingleSelectionMode = _pickerDelegate && [_pickerDelegate respondsToSelector:@selector(selectionBehaviorInSingleSelectionModeForAGImagePickerController:)];
    _pickerFlags.delegateNumberOfItemsPerRowForDevice = _pickerDelegate && [_pickerDelegate respondsToSelector:@selector(agImagePickerController:numberOfItemsPerRowForDevice:andInterfaceOrientation:)];
    _pickerFlags.delegateShouldDisplaySelectionInformationInSelectionMode = _pickerDelegate && [_pickerDelegate respondsToSelector:@selector(agImagePickerController:shouldDisplaySelectionInformationInSelectionMode:)];
    _pickerFlags.delegateShouldShowToolbarForManagingTheSelectionInSelectionMode = _pickerDelegate && [_pickerDelegate respondsToSelector:@selector(agImagePickerController:shouldShowToolbarForManagingTheSelectionInSelectionMode:)];
    _pickerFlags.delegateDidFinishPickingMediaWithInfo = _pickerDelegate && [_pickerDelegate respondsToSelector:@selector(agImagePickerController:didFinishPickingMediaWithInfo:)];
    _pickerFlags.delegateDidFail = _pickerDelegate && [_pickerDelegate respondsToSelector:@selector(agImagePickerController:didFail:)];
}

- (void)setShouldChangeStatusBarStyle:(BOOL)shouldChangeStatusBarStyle
{
    if (_shouldChangeStatusBarStyle != shouldChangeStatusBarStyle)
    {
        _shouldChangeStatusBarStyle = shouldChangeStatusBarStyle;
        
        if (_shouldChangeStatusBarStyle)
            if (IS_IPAD())
                [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleBlackOpaque animated:YES];
            else
                [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleBlackTranslucent animated:YES];
        else
            [[UIApplication sharedApplication] setStatusBarStyle:_oldStatusBarStyle animated:YES];
    }
}

+ (ALAssetsLibrary *)defaultAssetsLibrary
{
    static ALAssetsLibrary *assetsLibrary = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        assetsLibrary = [[ALAssetsLibrary alloc] init];
        
        // Workaround for triggering ALAssetsLibraryChangedNotification
        [assetsLibrary writeImageToSavedPhotosAlbum:nil metadata:nil completionBlock:^(NSURL *assetURL, NSError *error) { }];
    });
    
    return assetsLibrary;
}

#pragma mark - Object Lifecycle

- (id)init
{
    return [self initWithDelegate:nil failureBlock:nil successBlock:nil maximumNumberOfPhotosToBeSelected:0 shouldChangeStatusBarStyle:SHOULD_CHANGE_STATUS_BAR_STYLE toolbarItemsForManagingTheSelection:nil andShouldShowSavedPhotosOnTop:SHOULD_SHOW_SAVED_PHOTOS_ON_TOP];
}

- (id)initWithDelegate:(id)delegate
{
    return [self initWithDelegate:delegate failureBlock:nil successBlock:nil maximumNumberOfPhotosToBeSelected:0 shouldChangeStatusBarStyle:SHOULD_CHANGE_STATUS_BAR_STYLE toolbarItemsForManagingTheSelection:nil andShouldShowSavedPhotosOnTop:SHOULD_SHOW_SAVED_PHOTOS_ON_TOP];
}

- (id)initWithFailureBlock:(AGIPCDidFail)failureBlock
           andSuccessBlock:(AGIPCDidFinish)successBlock
{
    return [self initWithDelegate:nil failureBlock:failureBlock successBlock:successBlock maximumNumberOfPhotosToBeSelected:0 shouldChangeStatusBarStyle:SHOULD_CHANGE_STATUS_BAR_STYLE toolbarItemsForManagingTheSelection:nil andShouldShowSavedPhotosOnTop:SHOULD_SHOW_SAVED_PHOTOS_ON_TOP];
}

- (id)initWithDelegate:(id)delegate
          failureBlock:(AGIPCDidFail)failureBlock
          successBlock:(AGIPCDidFinish)successBlock
maximumNumberOfPhotosToBeSelected:(NSUInteger)maximumNumberOfPhotosToBeSelected
shouldChangeStatusBarStyle:(BOOL)shouldChangeStatusBarStyle
toolbarItemsForManagingTheSelection:(NSArray *)toolbarItemsForManagingTheSelection
andShouldShowSavedPhotosOnTop:(BOOL)shouldShowSavedPhotosOnTop
{
    self = [super init];
    if (self)
    {
        _oldStatusBarStyle = [UIApplication sharedApplication].statusBarStyle;
        
        self.shouldChangeStatusBarStyle = shouldChangeStatusBarStyle;
        self.shouldShowSavedPhotosOnTop = shouldShowSavedPhotosOnTop;
        
        UIBarStyle barStyle;
        
        if (floor(NSFoundationVersionNumber) <= NSFoundationVersionNumber_iOS_6_1)
        {
            // iOS 6.1 or earlier
            
            barStyle = UIBarStyleBlack;
        }
        else
        {
            // iOS 7 or later
            
            barStyle = UIBarStyleDefault;
        }
        self.navigationBar.barStyle = barStyle;
        self.navigationBar.translucent = YES;
        self.toolbar.barStyle = barStyle;
        self.toolbar.translucent = YES;
        
        self.toolbarItemsForManagingTheSelection = toolbarItemsForManagingTheSelection;
        self.selection = nil;
        self.maximumNumberOfPhotosToBeSelected = maximumNumberOfPhotosToBeSelected;
        self.delegate = delegate;
        self.didFailBlock = failureBlock;
        self.didFinishBlock = successBlock;
        
        self.viewControllers = @[[[AGIPCAlbumsController alloc] initWithImagePickerController:self]];
    }
    
    return self;
}

#pragma mark - View lifecycle

- (NSUInteger)supportedInterfaceOrientations
{
    return UIInterfaceOrientationMaskAll;
}

#pragma mark - Private

- (void)didFinishPickingAssets:(NSArray *)selectedAssets
{
    [self popToRootViewControllerAnimated:NO];
    
    // Reset the number of selections
    [AGIPCGridItem performSelector:@selector(resetNumberOfSelections)];
    
    if (self.didFinishBlock)
        self.didFinishBlock(selectedAssets);
    
	if (_pickerFlags.delegateDidFinishPickingMediaWithInfo)
    {
		[self.delegate performSelector:@selector(agImagePickerController:didFinishPickingMediaWithInfo:) withObject:self withObject:selectedAssets];
	}
}

- (void)didCancelPickingAssets
{
    [self popToRootViewControllerAnimated:NO];
    
    // Reset the number of selections
    [AGIPCGridItem performSelector:@selector(resetNumberOfSelections)];
    
    if (self.didFailBlock)
        self.didFailBlock(nil);
    
    if (_pickerFlags.delegateDidFail)
    {
		[self.delegate performSelector:@selector(agImagePickerController:didFail:) withObject:self withObject:nil];
	}
}

- (void)didFail:(NSError *)error
{
    [self popToRootViewControllerAnimated:NO];
    
    // Reset the number of selections
    [AGIPCGridItem performSelector:@selector(resetNumberOfSelections)];
    
    if (self.didFailBlock)
        self.didFailBlock(error);
    
    if (_pickerFlags.delegateDidFail)
    {
		[self.delegate performSelector:@selector(agImagePickerController:didFail:) withObject:self withObject:error];
	}
}

@end


================================================
FILE: AGImagePickerController/AGImagePickerControllerDefines.h
================================================
//
//  AGImagePickerControllerDefines.h
//  AGImagePickerController
//
//  Created by Artur Grigor on 28.02.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//  
//  For the full copyright and license information, please view the LICENSE
//  file that was distributed with this source code.
//  

#pragma mark ARC

#if __has_feature(objc_arc_weak)
    #define ag_weak weak
    #define __ag_weak __weak
#elif __has_feature(objc_arc)
    #define ag_weak unsafe_unretained
    #define __ag_weak __unsafe_unretained
#else
    #define ag_weak
    #define __ag_weak
#endif

#pragma mark - Utilities

#define IS_IPAD()                                                               ([[UIDevice currentDevice] respondsToSelector:@selector(userInterfaceIdiom)] && \
[[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPad)

#pragma mark - Constants

#define SHOULD_CHANGE_STATUS_BAR_STYLE                                          1
#define SHOULD_DISPLAY_SELECTION_INFO                                           1
#define SHOULD_SHOW_SAVED_PHOTOS_ON_TOP                                         1
#define SHOULD_SHOW_TOOLBAR_FOR_MANAGING_THE_SELECTION                          1
#define SELECTION_BEHAVIOR_IN_SINGLE_SELECTION_MODE                             0

// Size in points
#define AGIPC_CHECKMARK_WIDTH                                                   28.f
#define AGIPC_CHECKMARK_HEIGHT                                                  28.f
#define AGIPC_CHECKMARK_RIGHT_MARGIN                                            4.f
#define AGIPC_CHECKMARK_BOTTOM_MARGIN                                           4.f

#define AGIPC_CHECKMARK_BOTTOM_RIGHT_POINT                                      CGPointMake(AGIPC_CHECKMARK_RIGHT_MARGIN, AGIPC_CHECKMARK_BOTTOM_MARGIN)
#define AGIPC_CHECKMARK_SIZE                                                    CGSizeMake(AGIPC_CHECKMARK_WIDTH, AGIPC_CHECKMARK_HEIGHT)
#define AGIPC_CHECKMARK_RECT                                                    CGRectMake(AGIPC_CHECKMARK_BOTTOM_RIGHT_POINT.x, AGIPC_CHECKMARK_BOTTOM_RIGHT_POINT.y, AGIPC_CHECKMARK_SIZE.width, AGIPC_CHECKMARK_SIZE.height)

#define AGIPC_ITEMS_PER_ROW_IPHONE_PORTRAIT                                     4
#define AGIPC_ITEMS_PER_ROW_IPHONE_LANDSCAPE                                    6
#define AGIPC_ITEMS_PER_ROW_IPAD_PORTRAIT                                       8
#define AGIPC_ITEMS_PER_ROW_IPAD_LANDSCAPE                                      12

#define AGIPC_ITEM_WIDTH                                                        75.f
#define AGIPC_ITEM_HEIGHT                                                       75.f

#define AGIPC_ITEM_SIZE                                                         CGSizeMake(AGIPC_ITEM_WIDTH, AGIPC_ITEM_HEIGHT)

#pragma mark - Types

typedef void (^AGIPCDidFinish)(NSArray *info);
typedef void (^AGIPCDidFail)(NSError *error);

typedef NS_ENUM(NSUInteger, AGDeviceType)
{
    AGDeviceTypeiPad,
    AGDeviceTypeiPhone
};

typedef NS_ENUM(NSUInteger, AGImagePickerControllerSelectionMode)
{
    AGImagePickerControllerSelectionModeSingle,
    AGImagePickerControllerSelectionModeMultiple
};

typedef NS_ENUM(NSUInteger, AGImagePickerControllerSelectionBehaviorType)
{
    AGImagePickerControllerSelectionBehaviorTypeCheckbox,
    AGImagePickerControllerSelectionBehaviorTypeRadio
};

================================================
FILE: AGImagePickerController/ALAsset+AGIPC.h
================================================
//
//  ALAsset+AGIPC.h
//  AGImagePickerController Demo
//
//  Created by Artur Grigor on 19.06.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//

#import <AssetsLibrary/AssetsLibrary.h>

@interface ALAsset (AGIPC)

- (BOOL)isEqual:(id)object;

@end


================================================
FILE: AGImagePickerController/ALAsset+AGIPC.m
================================================
//
//  ALAsset+AGIPC.m
//  AGImagePickerController Demo
//
//  Created by Artur Grigor on 19.06.2012.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//

#import "ALAsset+AGIPC.h"

@implementation ALAsset (AGIPC)

- (BOOL)isEqual:(id)other
{
    if (other == self)
        return YES;
    if (!other || ![other isKindOfClass:[self class]])
        return NO;
    
    ALAsset *otherAsset = (ALAsset *)other;
    NSDictionary *selfUrls = [self valueForProperty:ALAssetPropertyURLs];
    NSDictionary *otherUrls = [otherAsset valueForProperty:ALAssetPropertyURLs];
    
    return [selfUrls isEqualToDictionary:otherUrls];
}

@end


================================================
FILE: AGImagePickerController Demo/AGAppDelegate.h
================================================
//
//  AGAppDelegate.h
//  AGImagePickerController Demo
//
//  Created by Artur Grigor on 2/16/12.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//

#import <UIKit/UIKit.h>

@class AGViewController;

@interface AGAppDelegate : UIResponder <UIApplicationDelegate>

@property (strong, nonatomic) UIWindow *window;

@property (strong, nonatomic) AGViewController *viewController;

@end


================================================
FILE: AGImagePickerController Demo/AGAppDelegate.m
================================================
//
//  AGAppDelegate.m
//  AGImagePickerController Demo
//
//  Created by Artur Grigor on 2/16/12.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//

#import "AGAppDelegate.h"

#import "AGViewController.h"

@implementation AGAppDelegate

@synthesize window = _window;
@synthesize viewController = _viewController;


- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    // Override point for customization after application launch.
    if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone) {
        self.viewController = [[AGViewController alloc] initWithNibName:@"AGViewController_iPhone" bundle:nil];
    } else {
        self.viewController = [[AGViewController alloc] initWithNibName:@"AGViewController_iPad" bundle:nil];
    }
    self.window.rootViewController = self.viewController;
    [self.window makeKeyAndVisible];
    return YES;
}

- (void)applicationWillResignActive:(UIApplication *)application
{
    /*
     Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
     Use this method to pause ongoing tasks, disable timers, and throttle down OpenGL ES frame rates. Games should use this method to pause the game.
     */
}

- (void)applicationDidEnterBackground:(UIApplication *)application
{
    /*
     Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later. 
     If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
     */
}

- (void)applicationWillEnterForeground:(UIApplication *)application
{
    /*
     Called as part of the transition from the background to the inactive state; here you can undo many of the changes made on entering the background.
     */
}

- (void)applicationDidBecomeActive:(UIApplication *)application
{
    /*
     Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
     */
}

- (void)applicationWillTerminate:(UIApplication *)application
{
    /*
     Called when the application is about to terminate.
     Save data if appropriate.
     See also applicationDidEnterBackground:.
     */
}

@end


================================================
FILE: AGImagePickerController Demo/AGImagePickerController Demo-Info.plist
================================================
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
	<key>CFBundleDevelopmentRegion</key>
	<string>en</string>
	<key>CFBundleDisplayName</key>
	<string>${PRODUCT_NAME}</string>
	<key>CFBundleExecutable</key>
	<string>${EXECUTABLE_NAME}</string>
	<key>CFBundleIconFiles</key>
	<array>
		<string>AGImagePickerController-icon.png</string>
		<string>AGImagePickerController-icon@2x.png</string>
	</array>
	<key>CFBundleIcons</key>
	<dict>
		<key>CFBundlePrimaryIcon</key>
		<dict>
			<key>CFBundleIconFiles</key>
			<array>
				<string>AGImagePickerController-icon.png</string>
				<string>AGImagePickerController-icon@2x.png</string>
			</array>
		</dict>
	</dict>
	<key>CFBundleIdentifier</key>
	<string>me.arturgrigor.${PRODUCT_NAME:rfc1034identifier}</string>
	<key>CFBundleInfoDictionaryVersion</key>
	<string>6.0</string>
	<key>CFBundleName</key>
	<string>${PRODUCT_NAME}</string>
	<key>CFBundlePackageType</key>
	<string>APPL</string>
	<key>CFBundleShortVersionString</key>
	<string>1.0</string>
	<key>CFBundleSignature</key>
	<string>????</string>
	<key>CFBundleVersion</key>
	<string>1.0</string>
	<key>LSRequiresIPhoneOS</key>
	<true/>
	<key>UIRequiredDeviceCapabilities</key>
	<array>
		<string>armv7</string>
	</array>
	<key>UISupportedInterfaceOrientations</key>
	<array>
		<string>UIInterfaceOrientationPortrait</string>
		<string>UIInterfaceOrientationLandscapeLeft</string>
		<string>UIInterfaceOrientationLandscapeRight</string>
	</array>
	<key>UISupportedInterfaceOrientations~ipad</key>
	<array>
		<string>UIInterfaceOrientationPortrait</string>
		<string>UIInterfaceOrientationPortraitUpsideDown</string>
		<string>UIInterfaceOrientationLandscapeLeft</string>
		<string>UIInterfaceOrientationLandscapeRight</string>
	</array>
</dict>
</plist>


================================================
FILE: AGImagePickerController Demo/AGImagePickerController Demo-Prefix.pch
================================================
//
// Prefix header for all source files of the 'AGImagePickerController Demo' target in the 'AGImagePickerController Demo' project
//

#import <Availability.h>

#ifndef __IPHONE_4_0
#warning "This project uses features only available in iOS SDK 4.0 and later."
#endif

#ifdef __OBJC__
    #import <UIKit/UIKit.h>
    #import <Foundation/Foundation.h>
#endif


================================================
FILE: AGImagePickerController Demo/AGViewController.h
================================================
//
//  AGViewController.h
//  AGImagePickerController Demo
//
//  Created by Artur Grigor on 2/16/12.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//

#import <UIKit/UIKit.h>

#import "AGImagePickerController.h"

@interface AGViewController : UIViewController<AGImagePickerControllerDelegate>
{
    NSMutableArray *selectedPhotos;
}

- (IBAction)openAction:(id)sender;

@property (nonatomic, strong) NSMutableArray *selectedPhotos;

@end


================================================
FILE: AGImagePickerController Demo/AGViewController.m
================================================
//
//  AGViewController.m
//  AGImagePickerController Demo
//
//  Created by Artur Grigor on 2/16/12.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//

#import "AGViewController.h"

#import "AGIPCToolbarItem.h"

@interface AGViewController ()
{
    AGImagePickerController *ipc;
}

@end

@implementation AGViewController

#pragma mark - Properties

@synthesize selectedPhotos;

#pragma mark - Object Lifecycle


- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if (self)
    {
        self.selectedPhotos = [NSMutableArray array];
        
        __block AGViewController *blockSelf = self;
        
        ipc = [[AGImagePickerController alloc] initWithDelegate:self];
        ipc.didFailBlock = ^(NSError *error) {
            NSLog(@"Fail. Error: %@", error);
            
            if (error == nil) {
                [blockSelf.selectedPhotos removeAllObjects];
                NSLog(@"User has cancelled.");
                
                [blockSelf dismissModalViewControllerAnimated:YES];
            } else {
                
                // We need to wait for the view controller to appear first.
                double delayInSeconds = 0.5;
                dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, delayInSeconds * NSEC_PER_SEC);
                dispatch_after(popTime, dispatch_get_main_queue(), ^(void){
                    [blockSelf dismissModalViewControllerAnimated:YES];
                });
            }
            
            [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleDefault animated:YES];
            
        };
        ipc.didFinishBlock = ^(NSArray *info) {
            [blockSelf.selectedPhotos setArray:info];
            
            NSLog(@"Info: %@", info);
            [blockSelf dismissModalViewControllerAnimated:YES];
            
            [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleDefault animated:YES];
        };
    }
    
    return self;
}

- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];
    // Release any cached data, images, etc that aren't in use.
}

#pragma mark - View lifecycle

- (void)viewDidLoad
{
    [super viewDidLoad];
	// Do any additional setup after loading the view, typically from a nib.
}

- (void)viewDidUnload
{
    [super viewDidUnload];
    // Release any retained subviews of the main view.
    // e.g. self.myOutlet = nil;
}

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    return YES;
}

- (NSUInteger)supportedInterfaceOrientations
{
    return UIInterfaceOrientationMaskAll;
}

#pragma mark - Public methods

- (void)openAction:(id)sender
{    
    // Show saved photos on top
    ipc.shouldShowSavedPhotosOnTop = NO;
    ipc.shouldChangeStatusBarStyle = YES;
    ipc.selection = self.selectedPhotos;
//    ipc.maximumNumberOfPhotosToBeSelected = 10;
    
    // Custom toolbar items
    AGIPCToolbarItem *selectAll = [[AGIPCToolbarItem alloc] initWithBarButtonItem:[[UIBarButtonItem alloc] initWithTitle:@"+ Select All" style:UIBarButtonItemStyleBordered target:nil action:nil] andSelectionBlock:^BOOL(NSUInteger index, ALAsset *asset) {
        return YES;
    }];
    AGIPCToolbarItem *flexible = [[AGIPCToolbarItem alloc] initWithBarButtonItem:[[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFlexibleSpace target:nil action:nil] andSelectionBlock:nil]; 
    AGIPCToolbarItem *selectOdd = [[AGIPCToolbarItem alloc] initWithBarButtonItem:[[UIBarButtonItem alloc] initWithTitle:@"+ Select Odd" style:UIBarButtonItemStyleBordered target:nil action:nil] andSelectionBlock:^BOOL(NSUInteger index, ALAsset *asset) {
        return !(index % 2);
    }];
    AGIPCToolbarItem *deselectAll = [[AGIPCToolbarItem alloc] initWithBarButtonItem:[[UIBarButtonItem alloc] initWithTitle:@"- Deselect All" style:UIBarButtonItemStyleBordered target:nil action:nil] andSelectionBlock:^BOOL(NSUInteger index, ALAsset *asset) {
        return NO;
    }];  
    ipc.toolbarItemsForManagingTheSelection = @[selectAll, flexible, selectOdd, flexible, deselectAll];
//    imagePickerController.toolbarItemsForManagingTheSelection = [NSArray array];
    
//    imagePickerController.maximumNumberOfPhotos = 3;
    [self presentModalViewController:ipc animated:YES];
}

#pragma mark - AGImagePickerControllerDelegate methods

- (NSUInteger)agImagePickerController:(AGImagePickerController *)picker
   numberOfItemsPerRowForDevice:(AGDeviceType)deviceType
        andInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    if (deviceType == AGDeviceTypeiPad)
    {
        if (UIInterfaceOrientationIsLandscape(interfaceOrientation))
            return 7;
        else
            return 6;
    } else {
        if (UIInterfaceOrientationIsLandscape(interfaceOrientation))
            return 5;
        else
            return 4;
    }
}

- (BOOL)agImagePickerController:(AGImagePickerController *)picker shouldDisplaySelectionInformationInSelectionMode:(AGImagePickerControllerSelectionMode)selectionMode
{
    return (selectionMode == AGImagePickerControllerSelectionModeSingle ? NO : YES);
}

- (BOOL)agImagePickerController:(AGImagePickerController *)picker shouldShowToolbarForManagingTheSelectionInSelectionMode:(AGImagePickerControllerSelectionMode)selectionMode
{
    return (selectionMode == AGImagePickerControllerSelectionModeSingle ? NO : YES);    
}

- (AGImagePickerControllerSelectionBehaviorType)selectionBehaviorInSingleSelectionModeForAGImagePickerController:(AGImagePickerController *)picker
{
    return AGImagePickerControllerSelectionBehaviorTypeRadio;
}

@end


================================================
FILE: AGImagePickerController Demo/en.lproj/AGViewController_iPad.xib
================================================
<?xml version="1.0" encoding="UTF-8"?>
<archive type="com.apple.InterfaceBuilder3.CocoaTouch.iPad.XIB" version="8.00">
	<data>
		<int key="IBDocument.SystemTarget">1552</int>
		<string key="IBDocument.SystemVersion">12C60</string>
		<string key="IBDocument.InterfaceBuilderVersion">3084</string>
		<string key="IBDocument.AppKitVersion">1187.34</string>
		<string key="IBDocument.HIToolboxVersion">625.00</string>
		<object class="NSMutableDictionary" key="IBDocument.PluginVersions">
			<string key="NS.key.0">com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
			<string key="NS.object.0">2083</string>
		</object>
		<array key="IBDocument.IntegratedClassDependencies">
			<string>IBProxyObject</string>
			<string>IBUIButton</string>
			<string>IBUIView</string>
		</array>
		<array key="IBDocument.PluginDependencies">
			<string>com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
		</array>
		<object class="NSMutableDictionary" key="IBDocument.Metadata">
			<string key="NS.key.0">PluginDependencyRecalculationVersion</string>
			<integer value="1" key="NS.object.0"/>
		</object>
		<array class="NSMutableArray" key="IBDocument.RootObjects" id="1000">
			<object class="IBProxyObject" id="841351856">
				<string key="IBProxiedObjectIdentifier">IBFilesOwner</string>
				<string key="targetRuntimeIdentifier">IBIPadFramework</string>
			</object>
			<object class="IBProxyObject" id="606714003">
				<string key="IBProxiedObjectIdentifier">IBFirstResponder</string>
				<string key="targetRuntimeIdentifier">IBIPadFramework</string>
			</object>
			<object class="IBUIView" id="766721923">
				<reference key="NSNextResponder"/>
				<int key="NSvFlags">274</int>
				<array class="NSMutableArray" key="NSSubviews">
					<object class="IBUIButton" id="91824616">
						<reference key="NSNextResponder" ref="766721923"/>
						<int key="NSvFlags">301</int>
						<string key="NSFrame">{{353, 480}, {63, 44}}</string>
						<reference key="NSSuperview" ref="766721923"/>
						<reference key="NSWindow"/>
						<reference key="NSNextKeyView"/>
						<string key="NSReuseIdentifierKey">_NS:9</string>
						<bool key="IBUIOpaque">NO</bool>
						<string key="targetRuntimeIdentifier">IBIPadFramework</string>
						<int key="IBUIContentHorizontalAlignment">0</int>
						<int key="IBUIContentVerticalAlignment">0</int>
						<int key="IBUIButtonType">1</int>
						<string key="IBUINormalTitle">Open</string>
						<object class="NSColor" key="IBUIHighlightedTitleColor">
							<int key="NSColorSpace">3</int>
							<bytes key="NSWhite">MQA</bytes>
						</object>
						<object class="NSColor" key="IBUINormalTitleColor">
							<int key="NSColorSpace">1</int>
							<bytes key="NSRGB">MC4xOTYwNzg0MzQ2IDAuMzA5ODAzOTMyOSAwLjUyMTU2ODY1NgA</bytes>
						</object>
						<object class="NSColor" key="IBUINormalTitleShadowColor">
							<int key="NSColorSpace">3</int>
							<bytes key="NSWhite">MC41AA</bytes>
						</object>
						<object class="IBUIFontDescription" key="IBUIFontDescription">
							<int key="type">2</int>
							<double key="pointSize">15</double>
						</object>
						<object class="NSFont" key="IBUIFont">
							<string key="NSName">Helvetica-Bold</string>
							<double key="NSSize">15</double>
							<int key="NSfFlags">16</int>
						</object>
					</object>
				</array>
				<string key="NSFrame">{{0, 20}, {768, 1004}}</string>
				<reference key="NSSuperview"/>
				<reference key="NSWindow"/>
				<reference key="NSNextKeyView" ref="91824616"/>
				<object class="NSColor" key="IBUIBackgroundColor">
					<int key="NSColorSpace">3</int>
					<bytes key="NSWhite">MQA</bytes>
					<object class="NSColorSpace" key="NSCustomColorSpace">
						<int key="NSID">2</int>
					</object>
				</object>
				<object class="IBUISimulatedStatusBarMetrics" key="IBUISimulatedStatusBarMetrics">
					<int key="IBUIStatusBarStyle">2</int>
				</object>
				<string key="targetRuntimeIdentifier">IBIPadFramework</string>
			</object>
		</array>
		<object class="IBObjectContainer" key="IBDocument.Objects">
			<array class="NSMutableArray" key="connectionRecords">
				<object class="IBConnectionRecord">
					<object class="IBCocoaTouchOutletConnection" key="connection">
						<string key="label">view</string>
						<reference key="source" ref="841351856"/>
						<reference key="destination" ref="766721923"/>
					</object>
					<int key="connectionID">3</int>
				</object>
				<object class="IBConnectionRecord">
					<object class="IBCocoaTouchEventConnection" key="connection">
						<string key="label">openAction:</string>
						<reference key="source" ref="91824616"/>
						<reference key="destination" ref="841351856"/>
						<int key="IBEventType">7</int>
					</object>
					<int key="connectionID">5</int>
				</object>
			</array>
			<object class="IBMutableOrderedSet" key="objectRecords">
				<array key="orderedObjects">
					<object class="IBObjectRecord">
						<int key="objectID">0</int>
						<array key="object" id="0"/>
						<reference key="children" ref="1000"/>
						<nil key="parent"/>
					</object>
					<object class="IBObjectRecord">
						<int key="objectID">-1</int>
						<reference key="object" ref="841351856"/>
						<reference key="parent" ref="0"/>
						<string key="objectName">File's Owner</string>
					</object>
					<object class="IBObjectRecord">
						<int key="objectID">-2</int>
						<reference key="object" ref="606714003"/>
						<reference key="parent" ref="0"/>
					</object>
					<object class="IBObjectRecord">
						<int key="objectID">2</int>
						<reference key="object" ref="766721923"/>
						<array class="NSMutableArray" key="children">
							<reference ref="91824616"/>
						</array>
						<reference key="parent" ref="0"/>
					</object>
					<object class="IBObjectRecord">
						<int key="objectID">4</int>
						<reference key="object" ref="91824616"/>
						<reference key="parent" ref="766721923"/>
					</object>
				</array>
			</object>
			<dictionary class="NSMutableDictionary" key="flattenedProperties">
				<string key="-1.CustomClassName">AGViewController</string>
				<string key="-1.IBPluginDependency">com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
				<string key="-2.CustomClassName">UIResponder</string>
				<string key="-2.IBPluginDependency">com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
				<string key="2.IBPluginDependency">com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
				<string key="4.IBPluginDependency">com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
			</dictionary>
			<dictionary class="NSMutableDictionary" key="unlocalizedProperties"/>
			<nil key="activeLocalization"/>
			<dictionary class="NSMutableDictionary" key="localizations"/>
			<nil key="sourceID"/>
			<int key="maxID">5</int>
		</object>
		<object class="IBClassDescriber" key="IBDocument.Classes">
			<array class="NSMutableArray" key="referencedPartialClassDescriptions">
				<object class="IBPartialClassDescription">
					<string key="className">AGViewController</string>
					<string key="superclassName">UIViewController</string>
					<object class="NSMutableDictionary" key="actions">
						<string key="NS.key.0">openAction:</string>
						<string key="NS.object.0">id</string>
					</object>
					<object class="NSMutableDictionary" key="actionInfosByName">
						<string key="NS.key.0">openAction:</string>
						<object class="IBActionInfo" key="NS.object.0">
							<string key="name">openAction:</string>
							<string key="candidateClassName">id</string>
						</object>
					</object>
					<object class="IBClassDescriptionSource" key="sourceIdentifier">
						<string key="majorKey">IBProjectSource</string>
						<string key="minorKey">./Classes/AGViewController.h</string>
					</object>
				</object>
			</array>
		</object>
		<int key="IBDocument.localizationMode">0</int>
		<string key="IBDocument.TargetRuntimeIdentifier">IBIPadFramework</string>
		<bool key="IBDocument.PluginDeclaredDependenciesTrackSystemTargetVersion">YES</bool>
		<int key="IBDocument.defaultPropertyAccessControl">3</int>
		<string key="IBCocoaTouchPluginVersion">2083</string>
	</data>
</archive>


================================================
FILE: AGImagePickerController Demo/en.lproj/AGViewController_iPhone.xib
================================================
<?xml version="1.0" encoding="UTF-8"?>
<archive type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="8.00">
	<data>
		<int key="IBDocument.SystemTarget">1552</int>
		<string key="IBDocument.SystemVersion">12C60</string>
		<string key="IBDocument.InterfaceBuilderVersion">3084</string>
		<string key="IBDocument.AppKitVersion">1187.34</string>
		<string key="IBDocument.HIToolboxVersion">625.00</string>
		<object class="NSMutableDictionary" key="IBDocument.PluginVersions">
			<string key="NS.key.0">com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
			<string key="NS.object.0">2083</string>
		</object>
		<array key="IBDocument.IntegratedClassDependencies">
			<string>IBProxyObject</string>
			<string>IBUIButton</string>
			<string>IBUIView</string>
		</array>
		<array key="IBDocument.PluginDependencies">
			<string>com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
		</array>
		<object class="NSMutableDictionary" key="IBDocument.Metadata">
			<string key="NS.key.0">PluginDependencyRecalculationVersion</string>
			<integer value="1" key="NS.object.0"/>
		</object>
		<array class="NSMutableArray" key="IBDocument.RootObjects" id="1000">
			<object class="IBProxyObject" id="372490531">
				<string key="IBProxiedObjectIdentifier">IBFilesOwner</string>
				<string key="targetRuntimeIdentifier">IBCocoaTouchFramework</string>
			</object>
			<object class="IBProxyObject" id="843779117">
				<string key="IBProxiedObjectIdentifier">IBFirstResponder</string>
				<string key="targetRuntimeIdentifier">IBCocoaTouchFramework</string>
			</object>
			<object class="IBUIView" id="774585933">
				<reference key="NSNextResponder"/>
				<int key="NSvFlags">274</int>
				<array class="NSMutableArray" key="NSSubviews">
					<object class="IBUIButton" id="76253951">
						<reference key="NSNextResponder" ref="774585933"/>
						<int key="NSvFlags">301</int>
						<string key="NSFrame">{{129, 208}, {63, 44}}</string>
						<reference key="NSSuperview" ref="774585933"/>
						<reference key="NSWindow"/>
						<string key="NSReuseIdentifierKey">_NS:9</string>
						<bool key="IBUIOpaque">NO</bool>
						<string key="targetRuntimeIdentifier">IBCocoaTouchFramework</string>
						<int key="IBUIContentHorizontalAlignment">0</int>
						<int key="IBUIContentVerticalAlignment">0</int>
						<int key="IBUIButtonType">1</int>
						<string key="IBUINormalTitle">Open</string>
						<object class="NSColor" key="IBUIHighlightedTitleColor">
							<int key="NSColorSpace">3</int>
							<bytes key="NSWhite">MQA</bytes>
						</object>
						<object class="NSColor" key="IBUINormalTitleColor">
							<int key="NSColorSpace">1</int>
							<bytes key="NSRGB">MC4xOTYwNzg0MzQ2IDAuMzA5ODAzOTMyOSAwLjUyMTU2ODY1NgA</bytes>
						</object>
						<object class="NSColor" key="IBUINormalTitleShadowColor">
							<int key="NSColorSpace">3</int>
							<bytes key="NSWhite">MC41AA</bytes>
						</object>
						<object class="IBUIFontDescription" key="IBUIFontDescription">
							<int key="type">2</int>
							<double key="pointSize">15</double>
						</object>
						<object class="NSFont" key="IBUIFont">
							<string key="NSName">Helvetica-Bold</string>
							<double key="NSSize">15</double>
							<int key="NSfFlags">16</int>
						</object>
					</object>
				</array>
				<string key="NSFrame">{{0, 20}, {320, 460}}</string>
				<reference key="NSSuperview"/>
				<reference key="NSWindow"/>
				<reference key="NSNextKeyView" ref="76253951"/>
				<object class="NSColor" key="IBUIBackgroundColor">
					<int key="NSColorSpace">3</int>
					<bytes key="NSWhite">MC43NQA</bytes>
					<object class="NSColorSpace" key="NSCustomColorSpace">
						<int key="NSID">2</int>
					</object>
				</object>
				<bool key="IBUIClearsContextBeforeDrawing">NO</bool>
				<object class="IBUISimulatedStatusBarMetrics" key="IBUISimulatedStatusBarMetrics"/>
				<string key="targetRuntimeIdentifier">IBCocoaTouchFramework</string>
			</object>
		</array>
		<object class="IBObjectContainer" key="IBDocument.Objects">
			<array class="NSMutableArray" key="connectionRecords">
				<object class="IBConnectionRecord">
					<object class="IBCocoaTouchOutletConnection" key="connection">
						<string key="label">view</string>
						<reference key="source" ref="372490531"/>
						<reference key="destination" ref="774585933"/>
					</object>
					<int key="connectionID">7</int>
				</object>
				<object class="IBConnectionRecord">
					<object class="IBCocoaTouchEventConnection" key="connection">
						<string key="label">openAction:</string>
						<reference key="source" ref="76253951"/>
						<reference key="destination" ref="372490531"/>
						<int key="IBEventType">7</int>
					</object>
					<int key="connectionID">9</int>
				</object>
			</array>
			<object class="IBMutableOrderedSet" key="objectRecords">
				<array key="orderedObjects">
					<object class="IBObjectRecord">
						<int key="objectID">0</int>
						<array key="object" id="0"/>
						<reference key="children" ref="1000"/>
						<nil key="parent"/>
					</object>
					<object class="IBObjectRecord">
						<int key="objectID">-1</int>
						<reference key="object" ref="372490531"/>
						<reference key="parent" ref="0"/>
						<string key="objectName">File's Owner</string>
					</object>
					<object class="IBObjectRecord">
						<int key="objectID">-2</int>
						<reference key="object" ref="843779117"/>
						<reference key="parent" ref="0"/>
					</object>
					<object class="IBObjectRecord">
						<int key="objectID">6</int>
						<reference key="object" ref="774585933"/>
						<array class="NSMutableArray" key="children">
							<reference ref="76253951"/>
						</array>
						<reference key="parent" ref="0"/>
					</object>
					<object class="IBObjectRecord">
						<int key="objectID">8</int>
						<reference key="object" ref="76253951"/>
						<reference key="parent" ref="774585933"/>
					</object>
				</array>
			</object>
			<dictionary class="NSMutableDictionary" key="flattenedProperties">
				<string key="-1.CustomClassName">AGViewController</string>
				<string key="-1.IBPluginDependency">com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
				<string key="-2.CustomClassName">UIResponder</string>
				<string key="-2.IBPluginDependency">com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
				<string key="6.IBPluginDependency">com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
				<string key="8.IBPluginDependency">com.apple.InterfaceBuilder.IBCocoaTouchPlugin</string>
			</dictionary>
			<dictionary class="NSMutableDictionary" key="unlocalizedProperties"/>
			<nil key="activeLocalization"/>
			<dictionary class="NSMutableDictionary" key="localizations"/>
			<nil key="sourceID"/>
			<int key="maxID">9</int>
		</object>
		<object class="IBClassDescriber" key="IBDocument.Classes">
			<array class="NSMutableArray" key="referencedPartialClassDescriptions">
				<object class="IBPartialClassDescription">
					<string key="className">AGViewController</string>
					<string key="superclassName">UIViewController</string>
					<object class="NSMutableDictionary" key="actions">
						<string key="NS.key.0">openAction:</string>
						<string key="NS.object.0">id</string>
					</object>
					<object class="NSMutableDictionary" key="actionInfosByName">
						<string key="NS.key.0">openAction:</string>
						<object class="IBActionInfo" key="NS.object.0">
							<string key="name">openAction:</string>
							<string key="candidateClassName">id</string>
						</object>
					</object>
					<object class="IBClassDescriptionSource" key="sourceIdentifier">
						<string key="majorKey">IBProjectSource</string>
						<string key="minorKey">./Classes/AGViewController.h</string>
					</object>
				</object>
			</array>
		</object>
		<int key="IBDocument.localizationMode">0</int>
		<string key="IBDocument.TargetRuntimeIdentifier">IBCocoaTouchFramework</string>
		<bool key="IBDocument.PluginDeclaredDependenciesTrackSystemTargetVersion">YES</bool>
		<int key="IBDocument.defaultPropertyAccessControl">3</int>
		<string key="IBCocoaTouchPluginVersion">2083</string>
	</data>
</archive>


================================================
FILE: AGImagePickerController Demo/en.lproj/InfoPlist.strings
================================================
/* Localized versions of Info.plist keys */



================================================
FILE: AGImagePickerController Demo/main.m
================================================
//
//  main.m
//  AGImagePickerController Demo
//
//  Created by Artur Grigor on 2/16/12.
//  Copyright (c) 2012 - 2013 Artur Grigor. All rights reserved.
//

#import <UIKit/UIKit.h>

#import "AGAppDelegate.h"

int main(int argc, char *argv[])
{
    @autoreleasepool {
        return UIApplicationMain(argc, argv, nil, NSStringFromClass([AGAppDelegate class]));
    }
}


================================================
FILE: AGImagePickerController Demo.xcodeproj/project.pbxproj
================================================
// !$*UTF8*$!
{
	archiveVersion = 1;
	classes = {
	};
	objectVersion = 46;
	objects = {

/* Begin PBXBuildFile section */
		54A1E5551882A31E00D556FD /* CoreLocation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 54A1E5541882A31E00D556FD /* CoreLocation.framework */; };
		FE1E332914ED167800F6A6A2 /* UIKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = FE1E332814ED167800F6A6A2 /* UIKit.framework */; };
		FE1E332B14ED167800F6A6A2 /* Foundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = FE1E332A14ED167800F6A6A2 /* Foundation.framework */; };
		FE1E333314ED167800F6A6A2 /* InfoPlist.strings in Resources */ = {isa = PBXBuildFile; fileRef = FE1E333114ED167800F6A6A2 /* InfoPlist.strings */; };
		FE1E333514ED167800F6A6A2 /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = FE1E333414ED167800F6A6A2 /* main.m */; };
		FE1E333914ED167800F6A6A2 /* AGAppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = FE1E333814ED167800F6A6A2 /* AGAppDelegate.m */; };
		FE1E333C14ED167800F6A6A2 /* AGViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = FE1E333B14ED167800F6A6A2 /* AGViewController.m */; };
		FE1E333F14ED167800F6A6A2 /* AGViewController_iPhone.xib in Resources */ = {isa = PBXBuildFile; fileRef = FE1E333D14ED167800F6A6A2 /* AGViewController_iPhone.xib */; };
		FE1E334214ED167800F6A6A2 /* AGViewController_iPad.xib in Resources */ = {isa = PBXBuildFile; fileRef = FE1E334014ED167800F6A6A2 /* AGViewController_iPad.xib */; };
		FE3850CB1501B8A10053C9DD /* README.md in Resources */ = {isa = PBXBuildFile; fileRef = FE3850CA1501B8A10053C9DD /* README.md */; };
		FE3851AF1504CF7B00A9F7F8 /* AGIPCToolbarItem.m in Sources */ = {isa = PBXBuildFile; fileRef = FE3851AE1504CF7B00A9F7F8 /* AGIPCToolbarItem.m */; };
		FE3BAF8814EE80E7001BF3EC /* AGIPCAssetsController.m in Sources */ = {isa = PBXBuildFile; fileRef = FE3BAF8714EE80E7001BF3EC /* AGIPCAssetsController.m */; };
		FE465F991590B25A00C30A1D /* ALAsset+AGIPC.m in Sources */ = {isa = PBXBuildFile; fileRef = FE465F981590B25A00C30A1D /* ALAsset+AGIPC.m */; };
		FE4DE10116C2546B0075E499 /* Default-568h@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = FE4DE10016C2546B0075E499 /* Default-568h@2x.png */; };
		FE4DE10416C267410075E499 /* AGImagePickerController+Helper.m in Sources */ = {isa = PBXBuildFile; fileRef = FE4DE10316C267410075E499 /* AGImagePickerController+Helper.m */; };
		FEA599CC14ED1C500057FF9C /* AGImagePickerController.m in Sources */ = {isa = PBXBuildFile; fileRef = FEA599CA14ED1C500057FF9C /* AGImagePickerController.m */; };
		FEA599E814ED38EE0057FF9C /* AGIPCAlbumsController.m in Sources */ = {isa = PBXBuildFile; fileRef = FEA599E714ED38ED0057FF9C /* AGIPCAlbumsController.m */; };
		FECDC90114EDB9C30038006D /* AGIPCGridCell.m in Sources */ = {isa = PBXBuildFile; fileRef = FECDC90014EDB9C30038006D /* AGIPCGridCell.m */; };
		FECDC90514EDBB690038006D /* AGIPCGridItem.m in Sources */ = {isa = PBXBuildFile; fileRef = FECDC90414EDBB690038006D /* AGIPCGridItem.m */; };
		FEDAA95516C2F3D600234FF0 /* AssetsLibrary.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = FEA599E114ED30140057FF9C /* AssetsLibrary.framework */; };
		FEDAA95716C3089600234FF0 /* AGImagePickerController.bundle in Resources */ = {isa = PBXBuildFile; fileRef = FEDAA95616C3089600234FF0 /* AGImagePickerController.bundle */; };
		FEE0F35D16C509EF001A077B /* AGImagePickerController.podspec in Resources */ = {isa = PBXBuildFile; fileRef = FEE0F35C16C509EF001A077B /* AGImagePickerController.podspec */; };
		FEF247F2150DF461008FEFAD /* AGImagePickerController-icon.png in Resources */ = {isa = PBXBuildFile; fileRef = FEF247F1150DF461008FEFAD /* AGImagePickerController-icon.png */; };
		FEF247F5150DF463008FEFAD /* AGImagePickerController-icon@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = FEF247F4150DF463008FEFAD /* AGImagePickerController-icon@2x.png */; };
/* End PBXBuildFile section */

/* Begin PBXFileReference section */
		54A1E5541882A31E00D556FD /* CoreLocation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreLocation.framework; path = System/Library/Frameworks/CoreLocation.framework; sourceTree = SDKROOT; };
		FE1E332414ED167800F6A6A2 /* AGImagePickerController Demo.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = "AGImagePickerController Demo.app"; sourceTree = BUILT_PRODUCTS_DIR; };
		FE1E332814ED167800F6A6A2 /* UIKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = UIKit.framework; path = System/Library/Frameworks/UIKit.framework; sourceTree = SDKROOT; };
		FE1E332A14ED167800F6A6A2 /* Foundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Foundation.framework; path = System/Library/Frameworks/Foundation.framework; sourceTree = SDKROOT; };
		FE1E332C14ED167800F6A6A2 /* CoreGraphics.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreGraphics.framework; path = System/Library/Frameworks/CoreGraphics.framework; sourceTree = SDKROOT; };
		FE1E333014ED167800F6A6A2 /* AGImagePickerController Demo-Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = "AGImagePickerController Demo-Info.plist"; sourceTree = "<group>"; };
		FE1E333214ED167800F6A6A2 /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = en.lproj/InfoPlist.strings; sourceTree = "<group>"; };
		FE1E333414ED167800F6A6A2 /* main.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = main.m; sourceTree = "<group>"; };
		FE1E333614ED167800F6A6A2 /* AGImagePickerController Demo-Prefix.pch */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "AGImagePickerController Demo-Prefix.pch"; sourceTree = "<group>"; };
		FE1E333714ED167800F6A6A2 /* AGAppDelegate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = AGAppDelegate.h; sourceTree = "<group>"; };
		FE1E333814ED167800F6A6A2 /* AGAppDelegate.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = AGAppDelegate.m; sourceTree = "<group>"; };
		FE1E333A14ED167800F6A6A2 /* AGViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = AGViewController.h; sourceTree = "<group>"; };
		FE1E333B14ED167800F6A6A2 /* AGViewController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = AGViewController.m; sourceTree = "<group>"; };
		FE1E333E14ED167800F6A6A2 /* en */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = en; path = en.lproj/AGViewController_iPhone.xib; sourceTree = "<group>"; };
		FE1E334114ED167800F6A6A2 /* en */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = en; path = en.lproj/AGViewController_iPad.xib; sourceTree = "<group>"; };
		FE3850CA1501B8A10053C9DD /* README.md */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = README.md; sourceTree = SOURCE_ROOT; };
		FE3851AD1504CF7B00A9F7F8 /* AGIPCToolbarItem.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AGIPCToolbarItem.h; sourceTree = "<group>"; };
		FE3851AE1504CF7B00A9F7F8 /* AGIPCToolbarItem.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AGIPCToolbarItem.m; sourceTree = "<group>"; };
		FE3BAF8614EE80E7001BF3EC /* AGIPCAssetsController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AGIPCAssetsController.h; sourceTree = "<group>"; };
		FE3BAF8714EE80E7001BF3EC /* AGIPCAssetsController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AGIPCAssetsController.m; sourceTree = "<group>"; };
		FE465F971590B25A00C30A1D /* ALAsset+AGIPC.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "ALAsset+AGIPC.h"; sourceTree = "<group>"; };
		FE465F981590B25A00C30A1D /* ALAsset+AGIPC.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "ALAsset+AGIPC.m"; sourceTree = "<group>"; };
		FE4DE10016C2546B0075E499 /* Default-568h@2x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = "Default-568h@2x.png"; path = "../Default-568h@2x.png"; sourceTree = "<group>"; };
		FE4DE10216C267400075E499 /* AGImagePickerController+Helper.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "AGImagePickerController+Helper.h"; sourceTree = "<group>"; };
		FE4DE10316C267410075E499 /* AGImagePickerController+Helper.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "AGImagePickerController+Helper.m"; sourceTree = "<group>"; };
		FE6E796014FCDC8A006612F0 /* AGImagePickerControllerDefines.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AGImagePickerControllerDefines.h; sourceTree = "<group>"; };
		FEA599C914ED1C500057FF9C /* AGImagePickerController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AGImagePickerController.h; sourceTree = "<group>"; };
		FEA599CA14ED1C500057FF9C /* AGImagePickerController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AGImagePickerController.m; sourceTree = "<group>"; };
		FEA599E114ED30140057FF9C /* AssetsLibrary.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AssetsLibrary.framework; path = System/Library/Frameworks/AssetsLibrary.framework; sourceTree = SDKROOT; };
		FEA599E614ED38ED0057FF9C /* AGIPCAlbumsController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AGIPCAlbumsController.h; sourceTree = "<group>"; };
		FEA599E714ED38ED0057FF9C /* AGIPCAlbumsController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AGIPCAlbumsController.m; sourceTree = "<group>"; };
		FECDC8FF14EDB9C30038006D /* AGIPCGridCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AGIPCGridCell.h; sourceTree = "<group>"; };
		FECDC90014EDB9C30038006D /* AGIPCGridCell.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AGIPCGridCell.m; sourceTree = "<group>"; };
		FECDC90314EDBB690038006D /* AGIPCGridItem.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AGIPCGridItem.h; sourceTree = "<group>"; };
		FECDC90414EDBB690038006D /* AGIPCGridItem.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AGIPCGridItem.m; sourceTree = "<group>"; };
		FEDAA95616C3089600234FF0 /* AGImagePickerController.bundle */ = {isa = PBXFileReference; lastKnownFileType = "wrapper.plug-in"; path = AGImagePickerController.bundle; sourceTree = "<group>"; };
		FEE0F35C16C509EF001A077B /* AGImagePickerController.podspec */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = AGImagePickerController.podspec; sourceTree = "<group>"; };
		FEF247F1150DF461008FEFAD /* AGImagePickerController-icon.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = "AGImagePickerController-icon.png"; path = "../AGImagePickerController-icon.png"; sourceTree = "<group>"; };
		FEF247F4150DF463008FEFAD /* AGImagePickerController-icon@2x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = "AGImagePickerController-icon@2x.png"; path = "../AGImagePickerController-icon@2x.png"; sourceTree = "<group>"; };
/* End PBXFileReference section */

/* Begin PBXFrameworksBuildPhase section */
		FE1E332114ED167800F6A6A2 /* Frameworks */ = {
			isa = PBXFrameworksBuildPhase;
			buildActionMask = 2147483647;
			files = (
				54A1E5551882A31E00D556FD /* CoreLocation.framework in Frameworks */,
				FEDAA95516C2F3D600234FF0 /* AssetsLibrary.framework in Frameworks */,
				FE1E332914ED167800F6A6A2 /* UIKit.framework in Frameworks */,
				FE1E332B14ED167800F6A6A2 /* Foundation.framework in Frameworks */,
			);
			runOnlyForDeploymentPostprocessing = 0;
		};
/* End PBXFrameworksBuildPhase section */

/* Begin PBXGroup section */
		FE1E331914ED167800F6A6A2 = {
			isa = PBXGroup;
			children = (
				FEE0F35C16C509EF001A077B /* AGImagePickerController.podspec */,
				FEA599C714ED1A8C0057FF9C /* AGImagePickerController */,
				FE1E332E14ED167800F6A6A2 /* AGImagePickerController Demo */,
				FE1E332714ED167800F6A6A2 /* Frameworks */,
				FE1E332514ED167800F6A6A2 /* Products */,
			);
			sourceTree = "<group>";
		};
		FE1E332514ED167800F6A6A2 /* Products */ = {
			isa = PBXGroup;
			children = (
				FE1E332414ED167800F6A6A2 /* AGImagePickerController Demo.app */,
			);
			name = Products;
			sourceTree = "<group>";
		};
		FE1E332714ED167800F6A6A2 /* Frameworks */ = {
			isa = PBXGroup;
			children = (
				54A1E5541882A31E00D556FD /* CoreLocation.framework */,
				FEA599E114ED30140057FF9C /* AssetsLibrary.framework */,
				FE1E332814ED167800F6A6A2 /* UIKit.framework */,
				FE1E332A14ED167800F6A6A2 /* Foundation.framework */,
				FE1E332C14ED167800F6A6A2 /* CoreGraphics.framework */,
			);
			name = Frameworks;
			sourceTree = "<group>";
		};
		FE1E332E14ED167800F6A6A2 /* AGImagePickerController Demo */ = {
			isa = PBXGroup;
			children = (
				FE1E333714ED167800F6A6A2 /* AGAppDelegate.h */,
				FE1E333814ED167800F6A6A2 /* AGAppDelegate.m */,
				FE1E333A14ED167800F6A6A2 /* AGViewController.h */,
				FE1E333B14ED167800F6A6A2 /* AGViewController.m */,
				FE1E333D14ED167800F6A6A2 /* AGViewController_iPhone.xib */,
				FE1E334014ED167800F6A6A2 /* AGViewController_iPad.xib */,
				FE1E332F14ED167800F6A6A2 /* Supporting Files */,
			);
			path = "AGImagePickerController Demo";
			sourceTree = "<group>";
		};
		FE1E332F14ED167800F6A6A2 /* Supporting Files */ = {
			isa = PBXGroup;
			children = (
				FE4DE10016C2546B0075E499 /* Default-568h@2x.png */,
				FEF247F4150DF463008FEFAD /* AGImagePickerController-icon@2x.png */,
				FEF247F1150DF461008FEFAD /* AGImagePickerController-icon.png */,
				FE3850CA1501B8A10053C9DD /* README.md */,
				FE1E333014ED167800F6A6A2 /* AGImagePickerController Demo-Info.plist */,
				FE1E333114ED167800F6A6A2 /* InfoPlist.strings */,
				FE1E333414ED167800F6A6A2 /* main.m */,
				FE1E333614ED167800F6A6A2 /* AGImagePickerController Demo-Prefix.pch */,
			);
			name = "Supporting Files";
			sourceTree = "<group>";
		};
		FEA599C714ED1A8C0057FF9C /* AGImagePickerController */ = {
			isa = PBXGroup;
			children = (
				FE4DE10216C267400075E499 /* AGImagePickerController+Helper.h */,
				FE4DE10316C267410075E499 /* AGImagePickerController+Helper.m */,
				FEDAA95616C3089600234FF0 /* AGImagePickerController.bundle */,
				FEA599C914ED1C500057FF9C /* AGImagePickerController.h */,
				FEA599CA14ED1C500057FF9C /* AGImagePickerController.m */,
				FE6E796014FCDC8A006612F0 /* AGImagePickerControllerDefines.h */,
				FEA599E614ED38ED0057FF9C /* AGIPCAlbumsController.h */,
				FEA599E714ED38ED0057FF9C /* AGIPCAlbumsController.m */,
				FE3BAF8614EE80E7001BF3EC /* AGIPCAssetsController.h */,
				FE3BAF8714EE80E7001BF3EC /* AGIPCAssetsController.m */,
				FECDC8FF14EDB9C30038006D /* AGIPCGridCell.h */,
				FECDC90014EDB9C30038006D /* AGIPCGridCell.m */,
				FECDC90314EDBB690038006D /* AGIPCGridItem.h */,
				FECDC90414EDBB690038006D /* AGIPCGridItem.m */,
				FE3851AD1504CF7B00A9F7F8 /* AGIPCToolbarItem.h */,
				FE3851AE1504CF7B00A9F7F8 /* AGIPCToolbarItem.m */,
				FE465F971590B25A00C30A1D /* ALAsset+AGIPC.h */,
				FE465F981590B25A00C30A1D /* ALAsset+AGIPC.m */,
			);
			path = AGImagePickerController;
			sourceTree = "<group>";
		};
/* End PBXGroup section */

/* Begin PBXNativeTarget section */
		FE1E332314ED167800F6A6A2 /* AGImagePickerController Demo */ = {
			isa = PBXNativeTarget;
			buildConfigurationList = FE1E334514ED167800F6A6A2 /* Build configuration list for PBXNativeTarget "AGImagePickerController Demo" */;
			buildPhases = (
				FE1E332014ED167800F6A6A2 /* Sources */,
				FE1E332114ED167800F6A6A2 /* Frameworks */,
				FE1E332214ED167800F6A6A2 /* Resources */,
			);
			buildRules = (
			);
			dependencies = (
			);
			name = "AGImagePickerController Demo";
			productName = "AGImagePickerController Demo";
			productReference = FE1E332414ED167800F6A6A2 /* AGImagePickerController Demo.app */;
			productType = "com.apple.product-type.application";
		};
/* End PBXNativeTarget section */

/* Begin PBXProject section */
		FE1E331B14ED167800F6A6A2 /* Project object */ = {
			isa = PBXProject;
			attributes = {
				LastUpgradeCheck = 0460;
				ORGANIZATIONNAME = "Artur Grigor";
			};
			buildConfigurationList = FE1E331E14ED167800F6A6A2 /* Build configuration list for PBXProject "AGImagePickerController Demo" */;
			compatibilityVersion = "Xcode 3.2";
			developmentRegion = English;
			hasScannedForEncodings = 0;
			knownRegions = (
				en,
			);
			mainGroup = FE1E331914ED167800F6A6A2;
			productRefGroup = FE1E332514ED167800F6A6A2 /* Products */;
			projectDirPath = "";
			projectRoot = "";
			targets = (
				FE1E332314ED167800F6A6A2 /* AGImagePickerController Demo */,
			);
		};
/* End PBXProject section */

/* Begin PBXResourcesBuildPhase section */
		FE1E332214ED167800F6A6A2 /* Resources */ = {
			isa = PBXResourcesBuildPhase;
			buildActionMask = 2147483647;
			files = (
				FE1E333314ED167800F6A6A2 /* InfoPlist.strings in Resources */,
				FE1E333F14ED167800F6A6A2 /* AGViewController_iPhone.xib in Resources */,
				FE1E334214ED167800F6A6A2 /* AGViewController_iPad.xib in Resources */,
				FE3850CB1501B8A10053C9DD /* README.md in Resources */,
				FEF247F2150DF461008FEFAD /* AGImagePickerController-icon.png in Resources */,
				FEF247F5150DF463008FEFAD /* AGImagePickerController-icon@2x.png in Resources */,
				FE4DE10116C2546B0075E499 /* Default-568h@2x.png in Resources */,
				FEDAA95716C3089600234FF0 /* AGImagePickerController.bundle in Resources */,
				FEE0F35D16C509EF001A077B /* AGImagePickerController.podspec in Resources */,
			);
			runOnlyForDeploymentPostprocessing = 0;
		};
/* End PBXResourcesBuildPhase section */

/* Begin PBXSourcesBuildPhase section */
		FE1E332014ED167800F6A6A2 /* Sources */ = {
			isa = PBXSourcesBuildPhase;
			buildActionMask = 2147483647;
			files = (
				FE1E333514ED167800F6A6A2 /* main.m in Sources */,
				FE1E333914ED167800F6A6A2 /* AGAppDelegate.m in Sources */,
				FE1E333C14ED167800F6A6A2 /* AGViewController.m in Sources */,
				FEA599CC14ED1C500057FF9C /* AGImagePickerController.m in Sources */,
				FEA599E814ED38EE0057FF9C /* AGIPCAlbumsController.m in Sources */,
				FECDC90114EDB9C30038006D /* AGIPCGridCell.m in Sources */,
				FECDC90514EDBB690038006D /* AGIPCGridItem.m in Sources */,
				FE3BAF8814EE80E7001BF3EC /* AGIPCAssetsController.m in Sources */,
				FE3851AF1504CF7B00A9F7F8 /* AGIPCToolbarItem.m in Sources */,
				FE465F991590B25A00C30A1D /* ALAsset+AGIPC.m in Sources */,
				FE4DE10416C267410075E499 /* AGImagePickerController+Helper.m in Sources */,
			);
			runOnlyForDeploymentPostprocessing = 0;
		};
/* End PBXSourcesBuildPhase section */

/* Begin PBXVariantGroup section */
		FE1E333114ED167800F6A6A2 /* InfoPlist.strings */ = {
			isa = PBXVariantGroup;
			children = (
				FE1E333214ED167800F6A6A2 /* en */,
			);
			name = InfoPlist.strings;
			sourceTree = "<group>";
		};
		FE1E333D14ED167800F6A6A2 /* AGViewController_iPhone.xib */ = {
			isa = PBXVariantGroup;
			children = (
				FE1E333E14ED167800F6A6A2 /* en */,
			);
			name = AGViewController_iPhone.xib;
			sourceTree = "<group>";
		};
		FE1E334014ED167800F6A6A2 /* AGViewController_iPad.xib */ = {
			isa = PBXVariantGroup;
			children = (
				FE1E334114ED167800F6A6A2 /* en */,
			);
			name = AGViewController_iPad.xib;
			sourceTree = "<group>";
		};
/* End PBXVariantGroup section */

/* Begin XCBuildConfiguration section */
		FE1E334314ED167800F6A6A2 /* Debug */ = {
			isa = XCBuildConfiguration;
			buildSettings = {
				ALWAYS_SEARCH_USER_PATHS = NO;
				ARCHS = "$(ARCHS_STANDARD_32_BIT)";
				CLANG_WARN_CONSTANT_CONVERSION = YES;
				CLANG_WARN_ENUM_CONVERSION = YES;
				CLANG_WARN_INT_CONVERSION = YES;
				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
				CODE_SIGN_IDENTITY = "";
				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
				COPY_PHASE_STRIP = NO;
				GCC_C_LANGUAGE_STANDARD = gnu99;
				GCC_DYNAMIC_NO_PIC = NO;
				GCC_OPTIMIZATION_LEVEL = 0;
				GCC_PREPROCESSOR_DEFINITIONS = (
					"DEBUG=1",
					"$(inherited)",
				);
				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
				GCC_VERSION = com.apple.compilers.llvm.clang.1_0;
				GCC_WARN_ABOUT_MISSING_PROTOTYPES = YES;
				GCC_WARN_ABOUT_RETURN_TYPE = YES;
				GCC_WARN_UNINITIALIZED_AUTOS = YES;
				GCC_WARN_UNUSED_VARIABLE = YES;
				IPHONEOS_DEPLOYMENT_TARGET = 5.0;
				SDKROOT = iphoneos;
				TARGETED_DEVICE_FAMILY = "1,2";
			};
			name = Debug;
		};
		FE1E334414ED167800F6A6A2 /* Release */ = {
			isa = XCBuildConfiguration;
			buildSettings = {
				ALWAYS_SEARCH_USER_PATHS = NO;
				ARCHS = "$(ARCHS_STANDARD_32_BIT)";
				CLANG_WARN_CONSTANT_CONVERSION = YES;
				CLANG_WARN_ENUM_CONVERSION = YES;
				CLANG_WARN_INT_CONVERSION = YES;
				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
				CODE_SIGN_IDENTITY = "";
				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
				COPY_PHASE_STRIP = YES;
				GCC_C_LANGUAGE_STANDARD = gnu99;
				GCC_VERSION = com.apple.compilers.llvm.clang.1_0;
				GCC_WARN_ABOUT_MISSING_PROTOTYPES = YES;
				GCC_WARN_ABOUT_RETURN_TYPE = YES;
				GCC_WARN_UNINITIALIZED_AUTOS = YES;
				GCC_WARN_UNUSED_VARIABLE = YES;
				IPHONEOS_DEPLOYMENT_TARGET = 5.0;
				OTHER_CFLAGS = "-DNS_BLOCK_ASSERTIONS=1";
				SDKROOT = iphoneos;
				TARGETED_DEVICE_FAMILY = "1,2";
				VALIDATE_PRODUCT = YES;
			};
			name = Release;
		};
		FE1E334614ED167800F6A6A2 /* Debug */ = {
			isa = XCBuildConfiguration;
			buildSettings = {
				CLANG_ENABLE_OBJC_ARC = YES;
				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
				GCC_PRECOMPILE_PREFIX_HEADER = YES;
				GCC_PREFIX_HEADER = "AGImagePickerController Demo/AGImagePickerController Demo-Prefix.pch";
				INFOPLIST_FILE = "AGImagePickerController Demo/AGImagePickerController Demo-Info.plist";
				IPHONEOS_DEPLOYMENT_TARGET = 4.3;
				PRODUCT_NAME = "$(TARGET_NAME)";
				"PROVISIONING_PROFILE[sdk=iphoneos*]" = "";
				WRAPPER_EXTENSION = app;
			};
			name = Debug;
		};
		FE1E334714ED167800F6A6A2 /* Release */ = {
			isa = XCBuildConfiguration;
			buildSettings = {
				CLANG_ENABLE_OBJC_ARC = YES;
				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
				GCC_PRECOMPILE_PREFIX_HEADER = YES;
				GCC_PREFIX_HEADER = "AGImagePickerController Demo/AGImagePickerController Demo-Prefix.pch";
				INFOPLIST_FILE = "AGImagePickerController Demo/AGImagePickerController Demo-Info.plist";
				IPHONEOS_DEPLOYMENT_TARGET = 4.3;
				PRODUCT_NAME = "$(TARGET_NAME)";
				WRAPPER_EXTENSION = app;
			};
			name = Release;
		};
/* End XCBuildConfiguration section */

/* Begin XCConfigurationList section */
		FE1E331E14ED167800F6A6A2 /* Build configuration list for PBXProject "AGImagePickerController Demo" */ = {
			isa = XCConfigurationList;
			buildConfigurations = (
				FE1E334314ED167800F6A6A2 /* Debug */,
				FE1E334414ED167800F6A6A2 /* Release */,
			);
			defaultConfigurationIsVisible = 0;
			defaultConfigurationName = Release;
		};
		FE1E334514ED167800F6A6A2 /* Build configuration list for PBXNativeTarget "AGImagePickerController Demo" */ = {
			isa = XCConfigurationList;
			buildConfigurations = (
				FE1E334614ED167800F6A6A2 /* Debug */,
				FE1E334714ED167800F6A6A2 /* Release */,
			);
			defaultConfigurationIsVisible = 0;
			defaultConfigurationName = Release;
		};
/* End XCConfigurationList section */
	};
	rootObject = FE1E331B14ED167800F6A6A2 /* Project object */;
}


================================================
FILE: AGImagePickerController Demo.xcodeproj/project.xcworkspace/contents.xcworkspacedata
================================================
<?xml version="1.0" encoding="UTF-8"?>
<Workspace
   version = "1.0">
   <FileRef
      location = "self:AGImagePickerController Demo.xcodeproj">
   </FileRef>
</Workspace>


================================================
FILE: AGImagePickerController Demo.xcodeproj/project.xcworkspace/xcuserdata/arturgrigor.xcuserdatad/WorkspaceSettings.xcsettings
================================================
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
	<key>HasAskedToTakeAutomaticSnapshotBeforeSignificantChanges</key>
	<true/>
	<key>SnapshotAutomaticallyBeforeSignificantChanges</key>
	<false/>
</dict>
</plist>


================================================
FILE: AGImagePickerController Demo.xcodeproj/xcuserdata/arturgrigor.xcuserdatad/xcdebugger/Breakpoints.xcbkptlist
================================================
<?xml version="1.0" encoding="UTF-8"?>
<Bucket
   type = "1"
   version = "1.0">
</Bucket>


================================================
FILE: AGImagePickerController Demo.xcodeproj/xcuserdata/arturgrigor.xcuserdatad/xcschemes/AGImagePickerController Demo.xcscheme
================================================
<?xml version="1.0" encoding="UTF-8"?>
<Scheme
   LastUpgradeVersion = "0460"
   version = "1.3">
   <BuildAction
      parallelizeBuildables = "YES"
      buildImplicitDependencies = "YES">
      <BuildActionEntries>
         <BuildActionEntry
            buildForTesting = "YES"
            buildForRunning = "YES"
            buildForProfiling = "YES"
            buildForArchiving = "YES"
            buildForAnalyzing = "YES">
            <BuildableReference
               BuildableIdentifier = "primary"
               BlueprintIdentifier = "FE1E332314ED167800F6A6A2"
               BuildableName = "AGImagePickerController Demo.app"
               BlueprintName = "AGImagePickerController Demo"
               ReferencedContainer = "container:AGImagePickerController Demo.xcodeproj">
            </BuildableReference>
         </BuildActionEntry>
      </BuildActionEntries>
   </BuildAction>
   <TestAction
      selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
      selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
      shouldUseLaunchSchemeArgsEnv = "YES"
      buildConfiguration = "Debug">
      <Testables>
      </Testables>
      <MacroExpansion>
         <BuildableReference
            BuildableIdentifier = "primary"
            BlueprintIdentifier = "FE1E332314ED167800F6A6A2"
            BuildableName = "AGImagePickerController Demo.app"
            BlueprintName = "AGImagePickerController Demo"
            ReferencedContainer = "container:AGImagePickerController Demo.xcodeproj">
         </BuildableReference>
      </MacroExpansion>
   </TestAction>
   <LaunchAction
      selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
      selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
      launchStyle = "0"
      useCustomWorkingDirectory = "NO"
      buildConfiguration = "Debug"
      ignoresPersistentStateOnLaunch = "NO"
      debugDocumentVersioning = "YES"
      allowLocationSimulation = "YES">
      <BuildableProductRunnable>
         <BuildableReference
            BuildableIdentifier = "primary"
            BlueprintIdentifier = "FE1E332314ED167800F6A6A2"
            BuildableName = "AGImagePickerController Demo.app"
            BlueprintName = "AGImagePickerController Demo"
            ReferencedContainer = "container:AGImagePickerController Demo.xcodeproj">
         </BuildableReference>
      </BuildableProductRunnable>
      <AdditionalOptions>
      </AdditionalOptions>
   </LaunchAction>
   <ProfileAction
      shouldUseLaunchSchemeArgsEnv = "YES"
      savedToolIdentifier = ""
      useCustomWorkingDirectory = "NO"
      buildConfiguration = "Release"
      debugDocumentVersioning = "YES">
      <BuildableProductRunnable>
         <BuildableReference
            BuildableIdentifier = "primary"
            BlueprintIdentifier = "FE1E332314ED167800F6A6A2"
            BuildableName = "AGImagePickerController Demo.app"
            BlueprintName = "AGImagePickerController Demo"
            ReferencedContainer = "container:AGImagePickerController Demo.xcodeproj">
         </BuildableReference>
      </BuildableProductRunnable>
   </ProfileAction>
   <AnalyzeAction
      buildConfiguration = "Debug">
   </AnalyzeAction>
   <ArchiveAction
      buildConfiguration = "Release"
      revealArchiveInOrganizer = "YES">
   </ArchiveAction>
</Scheme>


================================================
FILE: AGImagePickerController Demo.xcodeproj/xcuserdata/arturgrigor.xcuserdatad/xcschemes/xcschememanagement.plist
================================================
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
	<key>SchemeUserState</key>
	<dict>
		<key>AGImagePickerController Demo.xcscheme</key>
		<dict>
			<key>orderHint</key>
			<integer>0</integer>
		</dict>
	</dict>
	<key>SuppressBuildableAutocreation</key>
	<dict>
		<key>FE1E332314ED167800F6A6A2</key>
		<dict>
			<key>primary</key>
			<true/>
		</dict>
	</dict>
</dict>
</plist>


================================================
FILE: AGImagePickerController.podspec
================================================
Pod::Spec.new do |s|
  s.name         = "AGImagePickerController"
  s.version      = "2.0.1"
  s.summary      = "AGImagePickerController is a image picker controller that allows you to select multiple photos and can be used for all iOS devices."
  s.homepage     = "https://github.com/arturgrigor/AGImagePickerController"
  s.license      = 'MIT'
  s.author       = { "Artur Grigor" => "arturgrigor@gmail.com" }
  s.source       = { :git => "https://github.com/arturgrigor/AGImagePickerController.git", :tag => s.version.to_s }
  s.platform     = :ios
  s.source_files = 'AGImagePickerController/*.{h,m}'
  s.resources    = 'AGImagePickerController/AGImagePickerController.bundle'
  s.framework    = 'AssetsLibrary'
  s.requires_arc = true
end


================================================
FILE: LICENSE
================================================
Copyright (c) 2012 - 2013 Artur Grigor <arturgrigor@gmail.com>
 
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is furnished
to do so, subject to the following conditions:
 
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
 
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.

================================================
FILE: README.md
================================================
[![No Maintenance Intended](http://unmaintained.tech/badge.svg)](http://unmaintained.tech/)
[![CocoaPods Compatible](https://img.shields.io/cocoapods/v/AGImagePickerController.svg)](https://img.shields.io/cocoapods/v/AGImagePickerController.svg)
[![Platform](https://img.shields.io/cocoapods/p/AGImagePickerController.svg?style=flat)](http://cocoadocs.org/docsets/AGImagePickerController)
[![Twitter](https://img.shields.io/badge/twitter-@arturgrigor-blue.svg?style=flat)](http://twitter.com/arturgrigor)

## AGImagePickerController

AGImagePickerController is a image picker controller that allows you to select multiple photos and can be used for all iOS devices.

![Screenshot](http://dl.dropbox.com/u/2387405/Screenshots/AGImagePickerController.png)

## Installation

Copy over the files from the AGImagePickerController folder to your project folder.

## Usage

Wherever you want to use AGImagePickerController, import the appropriate header file and initialize as follows:

``` objective-c
#import "AGImagePickerController.h"
```

### Basic

``` objective-c
AGImagePickerController *imagePickerController = [[AGImagePickerController alloc] initWithFailureBlock:^(NSError *error) {

        if (error == nil)
        {
            NSLog(@"User has cancelled.");
            [self dismissModalViewControllerAnimated:YES];
        } else
        {     
            NSLog(@"Error: %@", error);
        
            // Wait for the view controller to show first and hide it after that
            double delayInSeconds = 0.5;
            dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, delayInSeconds * NSEC_PER_SEC);
            dispatch_after(popTime, dispatch_get_main_queue(), ^(void){
                [self dismissModalViewControllerAnimated:YES];
            });
        }
            
        [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleDefault animated:YES];
        
    } andSuccessBlock:^(NSArray *info) {
        NSLog(@"Info: %@", info);
        [self dismissModalViewControllerAnimated:YES];
        
        [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleDefault animated:YES];
    }];
    
    [self presentModalViewController:imagePickerController animated:YES];
    [imagePickerController release];
```

## Contact

- [GitHub](http://github.com/arturgrigor)
- [Twitter](http://twitter.com/arturgrigor)

Let me know if you're using or enjoying this product.
Download .txt
gitextract_fuleemah/

├── AGImagePickerController/
│   ├── AGIPCAlbumsController.h
│   ├── AGIPCAlbumsController.m
│   ├── AGIPCAssetsController.h
│   ├── AGIPCAssetsController.m
│   ├── AGIPCGridCell.h
│   ├── AGIPCGridCell.m
│   ├── AGIPCGridItem.h
│   ├── AGIPCGridItem.m
│   ├── AGIPCToolbarItem.h
│   ├── AGIPCToolbarItem.m
│   ├── AGImagePickerController+Helper.h
│   ├── AGImagePickerController+Helper.m
│   ├── AGImagePickerController.h
│   ├── AGImagePickerController.m
│   ├── AGImagePickerControllerDefines.h
│   ├── ALAsset+AGIPC.h
│   └── ALAsset+AGIPC.m
├── AGImagePickerController Demo/
│   ├── AGAppDelegate.h
│   ├── AGAppDelegate.m
│   ├── AGImagePickerController Demo-Info.plist
│   ├── AGImagePickerController Demo-Prefix.pch
│   ├── AGViewController.h
│   ├── AGViewController.m
│   ├── en.lproj/
│   │   ├── AGViewController_iPad.xib
│   │   ├── AGViewController_iPhone.xib
│   │   └── InfoPlist.strings
│   └── main.m
├── AGImagePickerController Demo.xcodeproj/
│   ├── project.pbxproj
│   ├── project.xcworkspace/
│   │   ├── contents.xcworkspacedata
│   │   └── xcuserdata/
│   │       └── arturgrigor.xcuserdatad/
│   │           ├── UserInterfaceState.xcuserstate
│   │           └── WorkspaceSettings.xcsettings
│   └── xcuserdata/
│       └── arturgrigor.xcuserdatad/
│           ├── xcdebugger/
│           │   └── Breakpoints.xcbkptlist
│           └── xcschemes/
│               ├── AGImagePickerController Demo.xcscheme
│               └── xcschememanagement.plist
├── AGImagePickerController.podspec
├── LICENSE
└── README.md
Download .txt
SYMBOL INDEX (5 symbols across 3 files)

FILE: AGImagePickerController Demo/AGViewController.h
  function interface (line 13) | interface AGViewController : UIViewController<AGImagePickerControllerDel...

FILE: AGImagePickerController/AGIPCToolbarItem.h
  function interface (line 17) | interface AGIPCToolbarItem : NSObject

FILE: AGImagePickerController/AGImagePickerControllerDefines.h
  type AGDeviceTypeiPad (line 63) | typedef NS_ENUM(NSUInteger, AGDeviceType)
  type AGImagePickerControllerSelectionModeSingle (line 69) | typedef NS_ENUM(NSUInteger, AGImagePickerControllerSelectionMode)
  type AGImagePickerControllerSelectionBehaviorTypeCheckbox (line 75) | typedef NS_ENUM(NSUInteger, AGImagePickerControllerSelectionBehaviorType)
Condensed preview — 37 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (133K chars).
[
  {
    "path": "AGImagePickerController/AGIPCAlbumsController.h",
    "chars": 671,
    "preview": "//\n//  AGIPCAlbumsController.h\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 2/16/12.\n//  Copyright (c) "
  },
  {
    "path": "AGImagePickerController/AGIPCAlbumsController.m",
    "chars": 7612,
    "preview": "//\n//  AGIPCAlbumsController.m\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 2/16/12.\n//  Copyright (c) "
  },
  {
    "path": "AGImagePickerController/AGIPCAssetsController.h",
    "chars": 907,
    "preview": "//\n//  AGIPCAssetsController.h\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 17.02.2012.\n//  Copyright ("
  },
  {
    "path": "AGImagePickerController/AGIPCAssetsController.m",
    "chars": 14990,
    "preview": "//\n//  AGIPCAssetsController.m\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 17.02.2012.\n//  Copyright ("
  },
  {
    "path": "AGImagePickerController/AGIPCGridCell.h",
    "chars": 668,
    "preview": "//\n//  AGIPCGridCell.h\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 17.02.2012.\n//  Copyright (c) 2012 "
  },
  {
    "path": "AGImagePickerController/AGIPCGridCell.m",
    "chars": 2458,
    "preview": "//\n//  AGIPCGridCell.m\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 17.02.2012.\n//  Copyright (c) 2012 "
  },
  {
    "path": "AGImagePickerController/AGIPCGridItem.h",
    "chars": 1338,
    "preview": "//\n//  AGIPCGridItem.h\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 17.02.2012.\n//  Copyright (c) 2012 "
  },
  {
    "path": "AGImagePickerController/AGIPCGridItem.m",
    "chars": 6660,
    "preview": "//\n//  AGIPCGridItem.m\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 17.02.2012.\n//  Copyright (c) 2012 "
  },
  {
    "path": "AGImagePickerController/AGIPCToolbarItem.h",
    "chars": 906,
    "preview": "//\n//  AGIPCToolbarItem.h\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 05.03.2012.\n//  Copyright (c) 20"
  },
  {
    "path": "AGImagePickerController/AGIPCToolbarItem.m",
    "chars": 1009,
    "preview": "//\n//  AGIPCToolbarItem.m\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 05.03.2012.\n//  Copyright (c) 20"
  },
  {
    "path": "AGImagePickerController/AGImagePickerController+Helper.h",
    "chars": 986,
    "preview": "//\n//  AGImagePickerController+Helper.h\n//  AGImagePickerController Demo\n//\n//  Created by Artur Grigor on 06.02.2013.\n/"
  },
  {
    "path": "AGImagePickerController/AGImagePickerController+Helper.m",
    "chars": 7930,
    "preview": "//\n//  AGImagePickerController+Helper.m\n//  AGImagePickerController Demo\n//\n//  Created by Artur Grigor on 06.02.2013.\n/"
  },
  {
    "path": "AGImagePickerController/AGImagePickerController.h",
    "chars": 3672,
    "preview": "//\n//  AGImagePickerController.h\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 2/16/12.\n//  Copyright (c"
  },
  {
    "path": "AGImagePickerController/AGImagePickerController.m",
    "chars": 7912,
    "preview": "//\n//  AGImagePickerController.m\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 2/16/12.\n//  Copyright (c"
  },
  {
    "path": "AGImagePickerController/AGImagePickerControllerDefines.h",
    "chars": 3361,
    "preview": "//\n//  AGImagePickerControllerDefines.h\n//  AGImagePickerController\n//\n//  Created by Artur Grigor on 28.02.2012.\n//  Co"
  },
  {
    "path": "AGImagePickerController/ALAsset+AGIPC.h",
    "chars": 274,
    "preview": "//\n//  ALAsset+AGIPC.h\n//  AGImagePickerController Demo\n//\n//  Created by Artur Grigor on 19.06.2012.\n//  Copyright (c) "
  },
  {
    "path": "AGImagePickerController/ALAsset+AGIPC.m",
    "chars": 646,
    "preview": "//\n//  ALAsset+AGIPC.m\n//  AGImagePickerController Demo\n//\n//  Created by Artur Grigor on 19.06.2012.\n//  Copyright (c) "
  },
  {
    "path": "AGImagePickerController Demo/AGAppDelegate.h",
    "chars": 402,
    "preview": "//\n//  AGAppDelegate.h\n//  AGImagePickerController Demo\n//\n//  Created by Artur Grigor on 2/16/12.\n//  Copyright (c) 201"
  },
  {
    "path": "AGImagePickerController Demo/AGAppDelegate.m",
    "chars": 2720,
    "preview": "//\n//  AGAppDelegate.m\n//  AGImagePickerController Demo\n//\n//  Created by Artur Grigor on 2/16/12.\n//  Copyright (c) 201"
  },
  {
    "path": "AGImagePickerController Demo/AGImagePickerController Demo-Info.plist",
    "chars": 1878,
    "preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE plist PUBLIC \"-//Apple//DTD PLIST 1.0//EN\" \"http://www.apple.com/DTDs/P"
  },
  {
    "path": "AGImagePickerController Demo/AGImagePickerController Demo-Prefix.pch",
    "chars": 359,
    "preview": "//\n// Prefix header for all source files of the 'AGImagePickerController Demo' target in the 'AGImagePickerController De"
  },
  {
    "path": "AGImagePickerController Demo/AGViewController.h",
    "chars": 458,
    "preview": "//\n//  AGViewController.h\n//  AGImagePickerController Demo\n//\n//  Created by Artur Grigor on 2/16/12.\n//  Copyright (c) "
  },
  {
    "path": "AGImagePickerController Demo/AGViewController.m",
    "chars": 5756,
    "preview": "//\n//  AGViewController.m\n//  AGImagePickerController Demo\n//\n//  Created by Artur Grigor on 2/16/12.\n//  Copyright (c) "
  },
  {
    "path": "AGImagePickerController Demo/en.lproj/AGViewController_iPad.xib",
    "chars": 8131,
    "preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<archive type=\"com.apple.InterfaceBuilder3.CocoaTouch.iPad.XIB\" version=\"8.00\">\n\t"
  },
  {
    "path": "AGImagePickerController Demo/en.lproj/AGViewController_iPhone.xib",
    "chars": 8121,
    "preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<archive type=\"com.apple.InterfaceBuilder3.CocoaTouch.XIB\" version=\"8.00\">\n\t<data"
  },
  {
    "path": "AGImagePickerController Demo/en.lproj/InfoPlist.strings",
    "chars": 45,
    "preview": "/* Localized versions of Info.plist keys */\n\n"
  },
  {
    "path": "AGImagePickerController Demo/main.m",
    "chars": 370,
    "preview": "//\n//  main.m\n//  AGImagePickerController Demo\n//\n//  Created by Artur Grigor on 2/16/12.\n//  Copyright (c) 2012 - 2013 "
  },
  {
    "path": "AGImagePickerController Demo.xcodeproj/project.pbxproj",
    "chars": 23886,
    "preview": "// !$*UTF8*$!\n{\n\tarchiveVersion = 1;\n\tclasses = {\n\t};\n\tobjectVersion = 46;\n\tobjects = {\n\n/* Begin PBXBuildFile section *"
  },
  {
    "path": "AGImagePickerController Demo.xcodeproj/project.xcworkspace/contents.xcworkspacedata",
    "chars": 173,
    "preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<Workspace\n   version = \"1.0\">\n   <FileRef\n      location = \"self:AGImagePickerCo"
  },
  {
    "path": "AGImagePickerController Demo.xcodeproj/project.xcworkspace/xcuserdata/arturgrigor.xcuserdatad/WorkspaceSettings.xcsettings",
    "chars": 333,
    "preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE plist PUBLIC \"-//Apple//DTD PLIST 1.0//EN\" \"http://www.apple.com/DTDs/P"
  },
  {
    "path": "AGImagePickerController Demo.xcodeproj/xcuserdata/arturgrigor.xcuserdatad/xcdebugger/Breakpoints.xcbkptlist",
    "chars": 91,
    "preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<Bucket\n   type = \"1\"\n   version = \"1.0\">\n</Bucket>\n"
  },
  {
    "path": "AGImagePickerController Demo.xcodeproj/xcuserdata/arturgrigor.xcuserdatad/xcschemes/AGImagePickerController Demo.xcscheme",
    "chars": 3387,
    "preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<Scheme\n   LastUpgradeVersion = \"0460\"\n   version = \"1.3\">\n   <BuildAction\n      "
  },
  {
    "path": "AGImagePickerController Demo.xcodeproj/xcuserdata/arturgrigor.xcuserdatad/xcschemes/xcschememanagement.plist",
    "chars": 500,
    "preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE plist PUBLIC \"-//Apple//DTD PLIST 1.0//EN\" \"http://www.apple.com/DTDs/P"
  },
  {
    "path": "AGImagePickerController.podspec",
    "chars": 744,
    "preview": "Pod::Spec.new do |s|\n  s.name         = \"AGImagePickerController\"\n  s.version      = \"2.0.1\"\n  s.summary      = \"AGImage"
  },
  {
    "path": "LICENSE",
    "chars": 1089,
    "preview": "Copyright (c) 2012 - 2013 Artur Grigor <arturgrigor@gmail.com>\n \nPermission is hereby granted, free of charge, to any pe"
  },
  {
    "path": "README.md",
    "chars": 2434,
    "preview": "[![No Maintenance Intended](http://unmaintained.tech/badge.svg)](http://unmaintained.tech/)\n[![CocoaPods Compatible](htt"
  }
]

// ... and 1 more files (download for full content)

About this extraction

This page contains the full source code of the arturgrigor/AGImagePickerController GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 37 files (120.0 KB), approximately 32.6k tokens, and a symbol index with 5 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.

Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.

Copied to clipboard!