C.Wetherell
C.Wetherell

Reputation: 215

how to store image (from gallery/camera) in the app to call on it later?

I did already figure this out once, but the way I did it wasn't working too well, and I started having problems that couldn't be answered... so I'm going back to basics again.

In my app I have 2 view controllers (spViewController & secondViewController)

on spViewController I have 2 buttons 1 takes me to camera and the other takes me to camera roll, then after an image has been selected it moves on to secondViewController using an Unwinding Segue all of this is fine. When the view loads (viewDidLoad) i want the image selected to display in the UIImageView ready for use where I'm going to have overlaying images (the overlaying images are irrelevant at the moment)

here is the code I'm using thus far. I'm willing to change all the code if need be.

Here is my RootVC.h (spViewController)

#import <UIKit/UIKit.h>
#import <MobileCoreServices/MobileCoreServices.h>
#import "secondViewController.h"
@interface spViewController : UIViewController


<UIImagePickerControllerDelegate,
UINavigationControllerDelegate>

@property BOOL newMedia;


@property (strong, nonatomic) IBOutlet UIImageView *imageView;
@property (strong, nonatomic) spViewController *secondViewController;
@property (strong, nonatomic) UIImageView *image;
@property (strong, nonatomic) UIImage *myImage;

- (IBAction)useCamera:(id)sender;


- (IBAction)useCameraRoll:(id)sender;


@end  

spViewController.m

#import "spViewController.h"
#import "secondViewController.h"

@interface spViewController ()

@end

@implementation spViewController

- (IBAction)backtohome:(UIStoryboardSegue *)unwindSegue
{
}

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


- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}

- (IBAction)useCamera:(id)sender {
        if ([UIImagePickerController isSourceTypeAvailable:
             UIImagePickerControllerSourceTypeCamera])
        {
            UIImagePickerController *imagePicker =
            [[UIImagePickerController alloc] init];
            imagePicker.delegate = self;
            imagePicker.sourceType =
            UIImagePickerControllerSourceTypeCamera;
            imagePicker.mediaTypes = @[(NSString *) kUTTypeImage];
            imagePicker.allowsEditing = YES;
            [self presentViewController:imagePicker
                               animated:YES completion:nil];
            _newMedia = NO;
        }
    }

- (IBAction)useCameraRoll:(id)sender {

    if ([UIImagePickerController isSourceTypeAvailable:
         UIImagePickerControllerSourceTypeSavedPhotosAlbum])
    {
        UIImagePickerController *imagePicker =
        [[UIImagePickerController alloc] init];
        imagePicker.delegate = self;
        imagePicker.sourceType =
        UIImagePickerControllerSourceTypePhotoLibrary;
        imagePicker.mediaTypes = @[(NSString *) kUTTypeImage];
        imagePicker.allowsEditing = NO;
        [self presentViewController:imagePicker
                           animated:YES completion:nil];
        _newMedia = NO;
    }
}



//image picker delegate
-(void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
{
    UIImage *chosenImage = info[UIImagePickerControllerEditedImage];
    self.myImage = chosenImage; //hear u are getting image from both camera or gallery

    NSString *mediaType = info[UIImagePickerControllerMediaType];

    [self performSelector:@selector(myMethod:) withObject:info afterDelay:0.1];

    if ([mediaType isEqualToString:(NSString *)kUTTypeImage])
    {

        UIImage *image = info[UIImagePickerControllerOriginalImage];

        _imageView.image = image;
        if (_newMedia)
        {
             UIImageWriteToSavedPhotosAlbum(image,self, @selector(image:finishedSavingWithError:contextInfo:), nil); // uncomment this
            if(imageData != nil)
            {
               /*
                NSString *pngPath = @"/imagefolder/imagefrompicker.png";
                NSString *Dir = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0];
                NSString *pngPath = [NSString stringWithFormat:@"%@%@",Dir,pngPath]; //path means ur destination contain's  this format -> "/foldername/picname" pickname must be unique
                if(![[NSFileManager defaultManager] fileExistsAtPath:[pngPath stringByDeletingLastPathComponent]])
                {
                    NSError *error;
                    [[NSFileManager defaultManager] createDirectoryAtPath:[pngPath stringByDeletingLastPathComponent] withIntermediateDirectories:YES attributes:nil error:&error];
                    if(error)
                    {
                        NSLog(@"error in creating dir");
                    }
                }
                [imageData writeToFile:pngPath atomically:YES]; //saving to a file, use it later by using path
               */ end if(imageData != nil)
            }

        }

    }
    else if ([mediaType isEqualToString:(NSString *)kUTTypeMovie])
    {

    }
}

-(void)myMethod:(NSDictionary *)info {
    [self dismissViewControllerAnimated:YES completion:^{
        NSLog(@"Perform segue");
        [self performSegueWithIdentifier:@"Picture Unwind Segue" sender:self];
    }];
}


-(void)image:(UIImage *)image
finishedSavingWithError:(NSError *)error
 contextInfo:(void *)contextInfo




{
    if (error) {
        UIAlertView *alert = [[UIAlertView alloc]
                              initWithTitle: @"Save failed"
                              message: @"Failed to save image"
                              delegate: nil
                              cancelButtonTitle:@"OK"
                              otherButtonTitles:nil];
        [alert show];
    }
}
//cancel delegate

-(void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
    [self dismissViewControllerAnimated:YES completion:nil];
}

-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
    if ([[segue identifier]isEqualToString:@"Picture Unwind Segue"]) {
        secondViewController *destinationViewController = [segue destinationViewController];
        destinationViewController.myImage = self.myImage; //just set the image of secondViewController
    }
}

@end

seconViewController.h

#import <UIKit/UIKit.h>
#import <MobileCoreServices/MobileCoreServices.h>
#import "spViewController.h"

@interface secondViewController : UIViewController

<UIImagePickerControllerDelegate,
UINavigationControllerDelegate>


@property (strong, nonatomic) UIImage *myImage; //changed and synthesised
@property (strong) UIImageView *imageView; //check what it this for 
@property (strong, nonatomic) IBOutlet UIImageView *imageView; //name changed and also see in story bord for correct binding to this outlet 

@end

secondViewController.m

#import "secondViewController.h"
#import "spViewController.h"

@interface secondViewController ()

@end

@implementation secondViewController

@synthesize myImage;


- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if (self) {
        // Custom initialization
    }
    return self;
}

- (void)viewDidLoad
{
   [super viewDidLoad];
    _imageView.image = self.myImage;
   //comment every thing      
   // NSString *Dir = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0];
   // NSString *pngPath = [NSString stringWithFormat:@"%@%@",Dir,InDestination->@/imagefolder/imagefrompicker.png]; //you know already where the image is InDestination->@"/foldername/picname"

   // UIImage *img = [UIImage imageWithContentsOfFile:pngPath]; // get the saved image
   // if (img != nil) {

        // assigning
   //     _imageView.image = img; //use the image

        //size
   //     BOOL adjustToSmallSize = YES;
   //     CGRect smallSize = (CGRect){0,0,100,100};
   //     if (adjustToSmallSize) {
   //         _imageView.bounds = smallSize;
   //     }
   // }
   // else {
   //     NSLog(@"Image hasn't been created");
   // }

}

@end

If any of you'd like to see some more code please do let me know :)

thank you for your help in advance

EDIT: added all code

Upvotes: 1

Views: 258

Answers (2)

Shankar BS
Shankar BS

Reputation: 8402

Try this not sure in spViewController.m

 -(void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
 {
      UIImage *chosenImage = info[UIImagePickerControllerEditedImage]; 
      self.myImage = chosenImage;

      NSString *mediaType = info[UIImagePickerControllerMediaType];

      [self performSelector:@selector(myMethod:) withObject:info afterDelay:0.1];

     if ([mediaType isEqualToString:(NSString *)kUTTypeImage]) 
     {
        UIImage *image = info[UIImagePickerControllerOriginalImage];

       _imageView.image = image;
       if (_newMedia)
        { 
         // UIImageWriteToSavedPhotosAlbum(image,self, @selector(image:finishedSavingWithError:contextInfo:), nil); // change hear, u are saving to album, insted of this save to a folder in your app bundle and use it anywhere
          NSData *imageData = UIImagePNGRepresentation(image); //get the data of image
          if(imageData != nil)
          {
               NSString *DespngPath = @"/imagefolder/imagefrompicker";
               NSString *Dir = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0];
               NSString *pngPath = [NSString stringWithFormat:@"%@%@",Dir,DespngPath]; //path means ur destination contain's  this format -> "/foldername/picname" pickname must be unique
               if(![[NSFileManager defaultManager] fileExistsAtPath:[pngPath stringByDeletingLastPathComponent]])
               {
                NSError *error;
                [[NSFileManager defaultManager] createDirectoryAtPath:[pngPath stringByDeletingLastPathComponent] withIntermediateDirectories:YES attributes:nil error:&error];
                if(error)
                {
                  NSLog(@"error in creating dir");
                }
              }
           [imageData writeToFile:pngPath atomically:YES]; //saving to a file, use it later by using path
         }
    }
    else if ([mediaType isEqualToString:(NSString *)kUTTypeMovie])
    {

    }
  }

in secondViewController.m

  - (void)viewDidLoad
   {
       NSString *Dir = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0];
       NSString *InDestination = @"/imagefolder/imagefrompicker";
       NSString *pngPath = [NSString stringWithFormat:@"%@%@",Dir,InDestination]; //you know already where the image is InDestination->@"/foldername/picname"

       UIImage *img = [UIImage imageWithContentsOfFile:pngPath]; // get the saved image
       if (img != nil) {
       // assigning
      _imageView.image = img; //use the image

       //size
       BOOL adjustToSmallSize = YES;
       CGRect smallSize = (CGRect){0,0,100,100};
       if (adjustToSmallSize) {
         _imageView.bounds = smallSize;
       }
   }
   else {
      NSLog(@"Image hasn't been created");
   }  
   [super viewDidLoad];
 }

Hope this will helps u

Upvotes: 1

Champoul
Champoul

Reputation: 1004

I think you can achieve this by doing something easier than saving the image to disk. You can simply hold the image as a property in your first controller and add a delegate to your second protocol.

In your second controller's .h file :

// outside of the @interface
@protocol SecondControllerDelegate <NSObject> 
- (UIImage *)selectedImage;
@end

// Along with other properties
@property (nonatomic, weak) id<SecondControllerDelegate> delegate;

In your first controller when you initialize your 2nd controller before presenting it :

SecondController *controller = [[SecondController alloc] init];
//your initialization
controller.delegate = self;

In your first controller's .h file :

#import "SecondViewController.h"
    @interface FirstViewController: UIViewController <SecondControllerDelegate>

In your first controller's .m file :

- (UIImage *)selectedImage
{
// return the selected image here that you should store in a property.
}

Finally, in your SecondViewController's .m file, when you need to get the image :

self.myImageView.image = [self.delegate selectedImage];

Upvotes: 0

Related Questions