how to test MFMailComposeViewController in simulator - objective-c

Is there a way to test sending emails from MFMailComposeViewController in iphone simulator ?

No you can't test it on simulator...(I mean your mail won't be delivered).we will be able to test limited things like: how the view will be,what happens when the user clicks on cancel button etc...
To test whether, the mail was delivered or not, you have to use a Device. The device should be configured with some mail(ex:gmail) in your settings.

Actual mail sending is not possible from the simulator.
Install the APP on a phone to test that.
However you can test everything that your APP can do/control/specify in the simulator.
Everything after the pressing of the Send button is Apple, so you can assume that is
working okay.

Read Sending mail with MFMailComposeViewController
First include MessageUI framework an implement MFMailComposeViewControllerDelegate.
#import <MessageUI/MessageUI.h>
#import <MessageUI/MFMailComposeViewController.h>
#interface MainViewController : UIViewController <MFMailComposeViewControllerDelegate> {
}
then implement a method like this one an the delegate method for removing the mail controller.
- (IBAction)pressentMailController:(id)sender {
MFMailComposeViewController *picker = [[MFMailComposeViewController alloc] init];
picker.mailComposeDelegate = self;
[picker setSubject:#"Test subject!"];
// Set up the recipients.
/*NSArray *toRecipients = [NSArray arrayWithObjects:#"first#example.com",
nil];
NSArray *ccRecipients = [NSArray arrayWithObjects:#"second#example.com",
#"third#example.com", nil];
NSArray *bccRecipients = [NSArray arrayWithObjects:#"four#example.com",
nil];
[picker setToRecipients:toRecipients];
[picker setCcRecipients:ccRecipients];
[picker setBccRecipients:bccRecipients];
*/
// Attach an image to the email.
/*NSString *path = [[NSBundle mainBundle] pathForResource:#"ipodnano"
ofType:#"png"];
NSData *myData = [NSData dataWithContentsOfFile:path];
[picker addAttachmentData:myData mimeType:#"image/png"
fileName:#"ipodnano"];
*/
// Fill out the email body text.
NSString *emailBody = #"It is raining in sunny California!";
[picker setMessageBody:emailBody isHTML:NO];
// Present the mail composition interface.
[self presentModalViewController:picker animated:YES];
[picker release]; // Can safely release the controller now.
}
// The mail compose view controller delegate method
- (void)mailComposeController:(MFMailComposeViewController *)controller
didFinishWithResult:(MFMailComposeResult)result
error:(NSError *)error
{
[self dismissModalViewControllerAnimated:YES];
}
The code allows to add recipients, body, subject and attachements. Uncomment the lines as needed.

Related

MFMessageComposeViewController does not show up send button and message body on ios8

MFMessageComposeViewController does not show up send button and message body on ios8, when tapping on recipient list keyboard comes up and also send button,message body shows up. Below is the code for message functionality :
MFMessageComposeViewController *msgController = [[MFMessageComposeViewController alloc] init] ;
if([MFMessageComposeViewController canSendText])
{
if (msgController)
{
msgController = nil;
msgController = [[MFMessageComposeViewController alloc] init] ;
}
NSString *messageBody =#"helloWorld";
msgController.body = messageBody;
msgController.recipients = numberArray;
msgController.messageComposeDelegate = (id)self;
[self presentViewController:msgController animated:YES completion:^{}];
Thanks in advance.
First of all add MessageUI framework to your app frameworks and then
#import <MessageUI/MessageUI.h>
#interface class()
<MFMailComposeViewControllerDelegate>
{
....
}
#end
Then in your class implementation write
if ([MFMailComposeViewController canSendMail])
{
MFMailComposeViewController *mail = [[MFMailComposeViewController alloc] init];
[mail setMailComposeDelegate:self];
[mail setSubject:#"Subject goes here..."];
[mail setMessageBody:#"Message body goes here..." isHTML:NO];
[self presentViewController:mail animated:YES completion:NULL];
}
and also implement the delegate for MFMailcomposeViewController as like
- (void)mailComposeController:(MFMailComposeViewController *)controller didFinishWithResult:(MFMailComposeResult)result error:(NSError *)error {
[controller dismissViewControllerAnimated:YES completion:nil];
}
There should be recipient and some message in the body to enable the "Send" button.
Here is the link for reference:
https://developer.apple.com/library/ios/documentation/UserExperience/Conceptual/SystemMessaging_TopicsForIOS/Articles/SendinganSMSMessage.html#//apple_ref/doc/uid/TP40010416-SW1
http://iosdevelopertips.com/core-services/how-to-send-an-sms-progammatically.html
Hope this helps!

In App Email - MFMailComposeViewController - Error Message

My code is as follows:
ViewController.m:
#import "ViewController.h"
#import "MyScene.h"
#import "MainMenu.h"
#import <MessageUI/MessageUI.h>
#implementation ViewController
- (IBAction)showMailPicker:(id)sender
{
// You must check that the current device can send email messages before you
// attempt to create an instance of MFMailComposeViewController. If the
// device can not send email messages,
// [[MFMailComposeViewController alloc] init] will return nil. Your app
// will crash when it calls -presentViewController:animated:completion: with
// a nil view controller.
if ([MFMailComposeViewController canSendMail])
// The device can send email.
{
[self displayMailComposerSheet];
}
else
// The device can not send email.
{
self.feedbackMsg.hidden = NO;
self.feedbackMsg.text = #"Device not configured to send mail.";
}
}
- (IBAction)showSMSPicker:(id)sender
{
// You must check that the current device can send SMS messages before you
// attempt to create an instance of MFMessageComposeViewController. If the
// device can not send SMS messages,
// [[MFMessageComposeViewController alloc] init] will return nil. Your app
// will crash when it calls -presentViewController:animated:completion: with
// a nil view controller.
if ([MFMessageComposeViewController canSendText])
// The device can send email.
{
[self displaySMSComposerSheet];
}
else
// The device can not send SMS.
{
self.feedbackMsg.hidden = NO;
self.feedbackMsg.text = #"Device not configured to send SMS.";
}
}
- (void)displayMailComposerSheet
{
MFMailComposeViewController *picker = [[MFMailComposeViewController alloc] init];
picker.mailComposeDelegate = self;
[picker setSubject:#"Support for Brick Smasher Extreme"];
// Set up recipients
NSArray *toRecipients = [NSArray arrayWithObject:#"help.bricksx#gmail.com"];
//NSArray *ccRecipients = [NSArray arrayWithObjects:#"second#example.com", #"third#example.com", nil];
//NSArray *bccRecipients = [NSArray arrayWithObject:#"fourth#example.com"];
[picker setToRecipients:toRecipients];
//[picker setCcRecipients:ccRecipients];
//[picker setBccRecipients:bccRecipients];
// Attach an image to the email
//NSString *path = [[NSBundle mainBundle] pathForResource:#"rainy" ofType:#"jpg"];
//NSData *myData = [NSData dataWithContentsOfFile:path];
//[picker addAttachmentData:myData mimeType:#"image/jpeg" fileName:#"rainy"];
// Fill out the email body text
NSString *emailBody = #"Message:";
[picker setMessageBody:emailBody isHTML:YES];
//[self presentViewController:picker animated:YES completion:NULL];
[[[[[UIApplication sharedApplication] delegate] window] rootViewController] presentViewController:picker
animated:YES
completion:nil];
}
- (void)mailComposeController:(MFMailComposeViewController *)controller
didFinishWithResult:(MFMailComposeResult)result error:(NSError*)error
{
self.feedbackMsg.hidden = NO;
// Notifies users about errors associated with the interface
switch (result)
{
case MFMailComposeResultCancelled:
self.feedbackMsg.text = #"Result: Mail sending canceled";
break;
case MFMailComposeResultSaved:
self.feedbackMsg.text = #"Result: Mail saved";
break;
case MFMailComposeResultSent:
self.feedbackMsg.text = #"Result: Mail sent";
break;
case MFMailComposeResultFailed:
self.feedbackMsg.text = #"Result: Mail sending failed";
break;
default:
self.feedbackMsg.text = #"Result: Mail not sent";
break;
}
[self dismissViewControllerAnimated:YES completion:NULL];
}
#end
The error is: Warning: Attempt to present <MFMailComposeViewController: 0xbf95170> on <UIViewController: 0xbf78d10> whose view is not in the window hierarchy!
I'm trying to send email through my app. Using MFMailComposeViewController, it always gives an error (above). But when I use the SMS part, there is no problem at all.
Using: Xcode 5, iOS 7, iPhone Retina 4"
Your problem is likely here:
[[[[[UIApplication sharedApplication] delegate] window] rootViewController] presentViewController:
First of all, you're already calling this from a ViewController, so you can just [self presentViewController:]. It does sound like maybe you're calling your displayMailComposerSheet before ViewController's view is visible (viewDidLoad or viewWillAppear maybe), which would raise the error you're seeing.
use
[self presentViewController:picker animated:YES completion:nil];
instead of
[[[[[UIApplication sharedApplication] delegate] window] rootViewController] presentViewController:picker animated:YES completion:nil];

Compose UIActivityTypeMessage with UIImage

Was wandering if anyone can offer some insight. For the life of me I can't figure out how to send a UIImage with UIActivityTypeMessage all though some say it is possible.
The docs say:
http://developer.apple.com/library/ios/#documentation/UIKit/Reference/UIActivity_Class/Reference/Reference.html
UIActivityTypeMessage
The object posts the provided content to the Messages app. When using this service, you can provide NSString and NSAttributedString objects as data for the activity items. You may also specify NSURL objects whose contents use the sms scheme.
Available in iOS 6.0 and later.
Declared in UIActivity.h.
So to my understanding I can only send NSString/NSURL. I don't see you it is possible.
I'm using this:
UIImage *image; // some image here.
UIActivityViewController *activityViewController = [[UIActivityViewController alloc] initWithActivityItems:#[ image ] applicationActivities:nil];
Any help would be much appreciated.
Here's how to use UIActivityViewController universally, with text and an image.
NSMutableArray *items = [NSMutableArray new];
[items addObject:#"Hello world!"];
[items addObject:[UIImage imageNamed:#"MyImage"]];
NSArray *activityItems = [NSArray arrayWithArray:items];
UIActivityViewController *activityViewController = [[UIActivityViewController alloc] initWithActivityItems:activityItems applicationActivities:nil];
if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPhone) {
[self presentViewController:activityViewController animated:YES completion:nil];
} else if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) {
UIPopoverController *aPopoverController = [[UIPopoverController alloc] initWithContentViewController:activityViewController];
[aPopoverController presentPopoverFromBarButtonItem:self.actionButton permittedArrowDirections:UIPopoverArrowDirectionAny animated:YES];
}
// Examples:
// iPhone:
// http://anglerally.com/wp-content/uploads/2012/09/6-Default-568h#2x.png
// http://anglerally.com/wp-content/uploads/2012/09/7-Default-568h#2x.png
// iPad:
// http://anglerally.com/wp-content/uploads/2012/09/6-Default-Portrait#2xipad.png
// http://anglerally.com/wp-content/uploads/2012/09/7-Default-Portrait#2xipad.png
While it seems possible to get the message app to appear in the share sheet using UIActivityViewController in iOS6, there is some secret to get it to work--iOS7 is a different story, passing the NSURL to the asset works out of the box.
Not sure you are getting your images from the ALAssetsLibrary, but if so, grab the ALAsset using its NSURL rather than pulling the UIImage. The share sheet appears in a fraction of the time. This isn't exactly the code I'm using, but similar. But on iOS6, the activity view controller will not show the messages app so long as there is an image attached.
- (void) presentActivityViewController:(ALAsset*) asset {
// add this to your viewController class
NSDictionary *urls = [asset valueForProperty:ALAssetPropertyURLs];
NSURL *url;
if ([urls count]) {
for (NSString *key in urls) {
// I'm making an assumption that the URL I want is the first URL in the dictionary
url = [urls objectForKey:key];
break;
}
}
NSArray *activityItems = #[url];
UIActivityViewController *activityController = [[UIActivityViewController alloc] initWithActivityItems:activityItems applicationActivities:nil];
[self presentViewController:activityController animated:YES completion:nil];
}

Unable to send email through my app

I am new to iphone development. I am building an app through which i can send the email.I am using the following code
- (IBAction)btnsendPressAction:(id)sender {
if([MFMailComposeViewController canSendMail]){
MFMailComposeViewController *mailer=[[MFMailComposeViewController alloc]init];
mailer.mailComposeDelegate=self;
[mailer setSubject:#"A Message for testing"];
NSArray *toRecipients = [NSArray arrayWithObjects:#"rajshetty2125#gmail.com", #"secondMail#example.com", nil];
[mailer setToRecipients:toRecipients];
UIImage *image=[UIImage imageNamed:#"logo.png"];
NSData *imageData=UIImagePNGRepresentation(image);
[mailer addAttachmentData:imageData mimeType:#"image/png" fileName:#"logo.png"];
NSString *emailBody=#"This is test email";
[mailer setMessageBody:emailBody isHTML:NO];
[self presentModalViewController:mailer animated:YES];
mailer.modalPresentationStyle = UIModalPresentationPageSheet ;
}
else{
UIAlertView *alert=[[UIAlertView alloc]initWithTitle:#"failure" message:#"Alert" delegate:nil cancelButtonTitle:#"OK" otherButtonTitles:nil, nil];
[alert show];
}
}
My problem is mailComposeController delegate is not getting called and I am not able to send email through my app.I went through many links , but every where I found the same method. Can anyone help me on this ?
You won't be able to send email from Simulator. You can only check this functionality on iOS device with any account configured in Mail application.
Here use this link and your add(configured) an account in device then only you can send the mail.
This snippet is working for me:
if ([MFMailComposeViewController canSendMail]) {
self.mailController = [[MFMailComposeViewController alloc] init];
[self.mailController setSubject:#"Invitation"];
[self.mailController setMessageBody:#"Message" isHTML:NO];
self.mailController.mailComposeDelegate = self;
[self presentModalViewController:self.mailController animated:YES];
}
but make sure that you're implement delegate in interface
#interface MyClass() <MFMailComposeViewControllerDelegate>
and check your callback method:
- (void)mailComposeController:(MFMailComposeViewController *)controller didFinishWithResult:(MFMailComposeResult)result error:(NSError *)error
{
}
hey i am not sure but may be it's helpful, replace your last line
mailer.modalPresentationStyle = UIModalPresentationPageSheet ;
with
[self presentModalViewController: mailer animated:YES];

iOS Mail Composer Won't Dismiss

I am trying to take a screenshot and email it using the mail composer. Everything works great except the mail composer won't dismiss. This post seems to have the same problem, but the solution provided did not work for me. Can't dismiss the email composer view in iPhone?
- (IBAction)Email:(id)sender {
UIGraphicsBeginImageContext(self.view.frame.size);
[self.view.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage * image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
NSData * imageData = UIImageJPEGRepresentation(image, 1.0);
if ( [MFMailComposeViewController canSendMail] ) {
MFMailComposeViewController * mailComposer = [[[MFMailComposeViewController alloc] init] autorelease];
mailComposer.delegate = self;
[mailComposer setSubject:#"Risk Assessment"];
[mailComposer addAttachmentData:imageData mimeType:#"image/jpeg" fileName:#"attachment.jpg"];
[self presentModalViewController:mailComposer animated:YES];
}
}
The above code works great. How do I call this bottom portion. It seems like the compiler just skips past it.
-(void)mailComposeController:(MFMailComposeViewController *)controller didFinishWithResult:(MFMailComposeResult)result error:(NSError *)error{
if (error){
NSString *errorTitle = #"Mail Error";
NSString *errorDescription = [error localizedDescription];
UIAlertView *errorView = [[UIAlertView alloc]initWithTitle:errorTitle message:errorDescription delegate:self cancelButtonTitle:nil otherButtonTitles:#"OK", nil];
[errorView show];
[errorView release];
}
[controller dismissModalViewControllerAnimated:YES];
}
Thanks in advance.
Try
mailComposer.mailComposeDelegate = self;
instead of
mailComposer.delegate = self;
From the MFMailComposeViewController documentation:
#property(nonatomic,assign) id<MFMailComposeViewControllerDelegate> mailComposeDelegate;
The delegate object is responsible for dismissing the view presented by this view controller at the appropriate time. Therefore, you should always provide a delegate and that object should implement the methods of the MFMailComposeViewControllerDelegate protocol.
I am pretty sure that last line should be
[self dismissModalViewControllerAnimated:YES];
The ViewController that presented the view modally, also dismisses it.