After dismiss camera. It give me this warning: Attempt to present on while a presentation is in progress!
- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
[self dismissViewControllerAnimated:YES completion:nil];
}
I don't know if this is a big issue.
More Code:
- (void) viewWillAppear:(BOOL)animated
{
[self takePicture];
}
- (void) takePicture
{
UIImagePickerController *imagePickerController = [[UIImagePickerController alloc] init];
if ([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera]) {
[imagePickerController setSourceType:UIImagePickerControllerSourceTypeCamera];
} else
[imagePickerController setSourceType:UIImagePickerControllerSourceTypePhotoLibrary];
imagePickerController.delegate = self;
[self presentViewController:imagePickerController animated:YES completion:nil];
}
- (void) imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
{
[self dismissViewControllerAnimated:NO completion:nil];
}
- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
[self dismissViewControllerAnimated:NO completion:nil];
}
By the way, "dismissModalViewController" is deprecated.
Fix:
ViewWillAppear will be invoked once there is a new view. That's the problem
You should not present any controller from viewWillAppear because the presentation of the current view controller is not yet completed.
Call takePicture from viewDidAppear because viewDidAppear will be called once the presentation of controller completed .
- (void)viewDidAppear:(BOOL)animated{
[super viewDidAppear:animated];
[self takePicture];
}
Hope this will help you.
You probably have presented some view controller like this
[self presentViewController:someVC animated:YES completion:nil];
and before the animation is get completed your below method is called
imagePickerControllerDidCancel
You can check it by changing it to
[self presentViewController:someVC animated:NO completion:nil];
notice animation:NO above.
Related
I have a problem where the delegate of UIImagePickerController not being called when presented with sourceType = UIImagePickerControllerSourceTypePhotoLibrary.
Oddly enough, it works perfectly fine in camera mode.
Interface declaration:
#interface ChatVC : UIViewController <UIActionSheetDelegate, UIImagePickerControllerDelegate, UINavigationControllerDelegate>
And in implementation:
- (void)takePhotoAction {
if ([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera]) {
UIImagePickerController* imgPickerController = [[UIImagePickerController alloc] init];
imgPickerController.sourceType = UIImagePickerControllerSourceTypeCamera;
imgPickerController.cameraCaptureMode = UIImagePickerControllerCameraCaptureModePhoto;
imgPickerController.allowsEditing = YES;
imgPickerController.delegate = self;
[self presentViewController:imgPickerController animated:YES completion:nil];
}
}
- (void)choosePhotoFromLibraryAction {
if ([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypePhotoLibrary]) {
UIImagePickerController* imgPickerController = [[UIImagePickerController alloc] init];
imgPickerController.sourceType = UIImagePickerControllerSourceTypePhotoLibrary;
imgPickerController.allowsEditing = YES;
imgPickerController.delegate = self;
[self presentViewController:imgPickerController animated:YES completion:nil];
}
}
And here's the delegate method implementation in the same view controller:
- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingImage:(UIImage *)image editingInfo:(NSDictionary<NSString *,id> *)editingInfo {
NSLog(#"Image Picker Controller Picked Image - Deprecated");
[picker dismissViewControllerAnimated:YES completion:nil];
}
- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info {
NSLog(#"Image Picker Controller Picked Image");
[picker dismissViewControllerAnimated:YES completion:nil];
}
- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker {
NSLog(#"Image Picker Controller Cancelled");
[picker dismissViewControllerAnimated:YES completion:nil];
}
When opened in camera mode, everything works just fine, and I can see the appropriate delegate methods being called.
But when opened in photo library mode and I choose a photo, nothing happens and no delegate method is called. However, I can see -imagePickerControllerDidCancel: delegate method being called when I tap on Cancel button.
I even suspected memory warning somehow invalidates the delegate, but it was not the case here.
Please someone help me figure this out.
Thanks in advance!
This application loads the device's camera in viewWillAppear method:
- (void)viewDidAppear:(BOOL)animated{
[super viewDidAppear:animated];
if (self.imageView.image == nil) {
UIImagePickerController *imagePickerController = [[UIImagePickerController alloc] init];
imagePickerController.sourceType = UIImagePickerControllerSourceTypeCamera;
imagePickerController.modalPresentationStyle = UIModalPresentationCurrentContext;
imagePickerController.delegate = self;
[self presentViewController:imagePickerController animated:YES completion:nil];
}
else { }
}
Delegate methods are implemented:
- (void) imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
{
UIImage *image = [info objectForKey:#"UIImagePickerControllerOriginalImage"];
[self dismissViewControllerAnimated:YES completion:nil];
// Pass the image to email composer after dismissing the camera. Delay allowed for cameraVC to dismiss.
[self performSelector:#selector(composeEmail) withObject:image afterDelay:1.0];
}
- (void) imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
[[picker parentViewController] dismissViewControllerAnimated:YES completion:nil];
}
When a photo is taken and I choose the default "Use Photo" button I want to dismiss the camera ViewController and load the emailComposer View Controller, which uses this method:
- (void) composeEmail: (UIImage *)image {
NSString *bodyHeader = #"Here are you directions:";
NSString *mailBody = [NSString stringWithFormat:#"%#\n%#", bodyHeader, googleMapsURL];
MFMailComposeViewController *picker = [[MFMailComposeViewController alloc] init];
picker.mailComposeDelegate = self;
[picker setSubject:#"Google Maps Directions"];
[picker setMessageBody:mailBody isHTML:NO];
[picker setToRecipients:#[#"john.doe#gmail.com"]];
[picker setModalTransitionStyle:UIModalTransitionStyleCrossDissolve];
// Create NSData object as PNG image data from camera image
NSData *data = UIImagePNGRepresentation(image);
// Attach image data to the email
// 'DestinationImage.png' is file name that will be attached to the email
[picker addAttachmentData:data mimeType:#"image/png" fileName:#"DestinationImage"];
[self presentViewController:picker animated:YES completion:nil];
}
(I have left out some of the MessageUI details here but I have tested it and I know it is working)
The image taken should be passed to the emailComposer and attached as an email. When I build this on my device and tap the "Use Photo" button an error is thrown. The error message states "Attempt to present MFMailCompseViewController on ViewController whose view is not in the window hierarchy!" I am using only one ViewController and that VC contains one Image View.
Can anyone help me dismiss the camera and load the email composer?
Much appreciated!
First Dismiss the ImagePicker and then present ur mailcomposer will work then.U r dismissing the parent thta's y its not working [yourpicker dismissViewControllerAnimated:YES completion:nil];
- (void) imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
{
UIImage *image = [info objectForKey:#"UIImagePickerControllerOriginalImage"];
[yourpicker dismissViewControllerAnimated:YES completion:nil];
// Pass the image to email composer after dismissing the camera. Delay allowed for cameraVC to dismiss.
[self performSelector:#selector(composeEmail) withObject:image afterDelay:1.0];
}
To present view controller, use following :
[[[[[UIApplication sharedApplication] delegate] window] rootViewController] presentViewController: picker
animated:YES
completion:nil];
You can also look into this stackoverflow's question for further understanding
This question already has answers here:
Dismiss UIImagePickerController
(4 answers)
Closed 7 years ago.
Single View controller with single image view:
- (void)viewDidAppear:(BOOL)animated{
[super viewDidAppear:animated];
if (self.imageView.image == nil) {
UIImagePickerController *imagePickerController = [[UIImagePickerController alloc] init];
imagePickerController.sourceType = UIImagePickerControllerSourceTypeCamera;
imagePickerController.modalPresentationStyle = UIModalPresentationCurrentContext;
imagePickerController.delegate = self;
[self presentViewController:imagePickerController animated:YES completion:nil];
}
else { }
}
- (void) imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
{
UIImage *image = [info objectForKey:#"UIImagePickerControllerOriginalImage"];
[picker dismissViewControllerAnimated:YES completion:nil];
[self performSelector:#selector(composeEmail:) withObject:image afterDelay:1.0];
}
- (void) imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
[picker dismissViewControllerAnimated:YES completion:nil];
}
What follows is an MFMailComposer but the imagePicker does not dismiss after selecting 'use photo.' The imagePicker seems to dismiss and then reappear.
Here is a link to a Gist For the ViewController:
https://gist.github.com/FIDELHIMSELF/069609eb5489cf4723a1
I get two error warnings:
"Warning: Attempt to present on whose view is not in the window hierarchy!"
and
"Snapshotting a view that has not been rendered results in an empty snapshot. Ensure your view has been rendered at least once before snapshotting or snapshot after screen updates."
try dismissing the view controller like;
[picker dismissViewControllerAnimated:YES completion:nil];
So for example imagePickerControllerDidCancel delegate method would look like;
- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker{
[picker dismissViewControllerAnimated:YES completion:nil];
}
In my application i have used the following code to implement after dismissing the view i have pushed to new view,When i tried to implement the view is not dismissing instead it overlapping.Here my code,
-(IBAction)selectExitingPicture
{
if([UIImagePickerController isSourceTypeAvailable:
UIImagePickerControllerSourceTypePhotoLibrary])
{
UIImagePickerController *picker= [[UIImagePickerController alloc]init];
picker.delegate = self;
picker.sourceType = UIImagePickerControllerSourceTypePhotoLibrary;
[self presentViewController:picker animated:YES completion:nil];
}
}
-(void)imagePickerController:(UIImagePickerController *)picker didFinishPickingImage:(UIImage *)image
editingInfo:(NSDictionary *)editingInfo
{
[picker dismissViewControllerAnimated:YES completion:^{
cropingImageViewCon = [[CropingImageViewControl alloc]initWithNibName:#"CropingImageView" bundle:nil];
cropingImageViewCon.delegate = self;
cropingImageViewCon.originalImg = image;
[self.navigationController presentModalViewController:cropingImageViewCon animated:YES];
}];
}
Whats wrong with my code,Can any one please help out.
If you want to push into CropingImageViewControl then you are going wrong way,
Use
[self.navigationController pushViewController:yourViewCotrollerObject animated:YES];
instead of using presentModalViewController:
This is my application code , which i used for selecting the image picker ,when image picks i want to dismiss the current view controller, Since its not dismissing from current view controller at the dismissal time of image picker itself ,
-(IBAction)selectExitingPicture
{
self.imagePicker = [[GKImagePicker alloc] init];
self.imagePicker.cropSize = CGSizeMake(296, 300);
self.imagePicker.delegate = self;
self.imagePicker.resizeableCropArea = YES;
[self presentViewController:self.imagePicker.imagePickerController animated:YES completion:nil];
}
-(void)imagePicker:(GKImagePicker *)imagePicker pickedImage:(UIImage *)image
{
appDel.im=image;
[self hideImagePicker];
}
- (void)hideImagePicker
{
[self.imagePicker.imagePickerController dismissViewControllerAnimated:YES completion:^{
[self.navigationController pushViewController:viewCont animated:YES ];
}];
}
Please help me to solve this issue, What code should i want add further
You should use this line to dismiss the PickerController :
[self dismissViewControllerAnimated:YES completion:nil];
You may call this line in both delegate methods :
- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
and
- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
.h file
int flg;
.m file
viewDidLoad
flg=0;
-(void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
if(flg==1) {
[self dismissViewControllerAnimated:YES completion:nil];
flg=0;
}
}
- (void)hideImagePicker
{
[self.imagePicker.imagePickerController dismissViewControllerAnimated:YES completion:nil];
}
- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingImage:(UIImage *)image editingInfo:(NSDictionary *)editingInfo{
self.imgView.image = image;
flg=1;
[picker dismissViewControllerAnimated:YES completion:nil];
}