1

Here is a link to a simple app with same issue: https://drive.google.com/folderview?id=0B1t60Ehs8m62Wjl3QXl1YjY4TmM&usp=sharing

Here is the zip file on my server: http://xbsjason.com/test/DemoMessageUI.zip

Had to post on Google Drive as Dropbox required me to enter certain email addresses to view/edit.

I am having a problem with this piece of code for sending mail. When the user presses the mail button (form filled or not) after about 10 seconds the app crashes. In the simulator I can see that it has something to do with this code but I'm not sure what the problem is as I have nearly identical code running in another app with no issues. Can anyone spot an error here?

FYI I looked at related questions but none seem to address my error/crash. Thanks.

/* MAIL Sharing ====================================================*/
@IBAction func mailButt(sender: AnyObject) {
    var subjectText = "Glass Quote Request"
    var name = nameInput.text
    var phone = phoneNumber.text
    var year = carYear.text
    var make = carMake.text
    var model = carModel.text
    var glass = glassNeeded.text
    var messageText = "Please process quote for glass:<p>Respond to <b>\(name)</b> at     <b>\(phone)</b>. <p>The following glass is required: <p>Glass type: <b>\(glass)</b><p>For the following car:<p><b>\(year) \(make) \(model)</b> "

    var mailComposer: MFMailComposeViewController = MFMailComposeViewController()
    mailComposer.mailComposeDelegate = self
    mailComposer.setSubject(subjectText)
    mailComposer.setMessageBody(messageText, isHTML: true)
    mailComposer.setToRecipients(["validemail@gmail.com"])

    self.presentViewController(mailComposer, animated: true, completion: nil)
}
// Email results ================
func mailComposeController(controller:MFMailComposeViewController, didFinishWithResult result:MFMailComposeResult, error:NSError) {
    switch result.value {
    case MFMailComposeResultCancelled.value:
        NSLog("Mail cancelled")
    case MFMailComposeResultSaved.value:
        NSLog("Mail saved")
    case MFMailComposeResultSent.value:
        NSLog("Mail sent")
    case MFMailComposeResultFailed.value:
        NSLog("Mail sent failure: %@", [error.localizedDescription])
    default:
        break
    }
    self.dismissViewControllerAnimated(false, completion: nil)
}
Jason Rybka
  • 157
  • 2
  • 15
  • Create as small a single view project that has the problem as possible, zip it, and post on DropBox. Update question with link. It's good to get points here as you can offer a bounty for a solution, but not an option today. – David H Dec 03 '14 at 12:59
  • Posted the link in the original question, had to use Google Drive. Thanks. – Jason Rybka Dec 03 '14 at 14:15
  • GRRR - I really dislike Google. I can see you project and files, but I cannot download them - there is no option. What I (and anyone else) really need is the project zipped, and put somewhere that it can be downloaded. – David H Dec 03 '14 at 14:28
  • Sorry, added on my server and linked in question. – Jason Rybka Dec 03 '14 at 14:35
  • I reproduced the problem. There are many threads here on problems like this, and the error I see, but frankly right now I suspect that this won't work in the Simulator, even though it says it will. I'll dig further later, ran out of lunch time to spend on it. – David H Dec 03 '14 at 19:43
  • Thanks for taking the time David. Appreciated. – Jason Rybka Dec 03 '14 at 19:44
  • Works fine on my iPad - see if MFMailComposeViewController.canSendMail() in ObjectiveC returns yes in the Simulator too. Well, looks like its not suppose to work there: http://stackoverflow.com/questions/6439932/how-to-test-mfmailcomposeviewcontroller-in-simulator – David H Dec 03 '14 at 19:55
  • i'm reverting to sending data via sms for now, obviously no simulator use but works fine on device.... will still need to switch it to email when I can. – Jason Rybka Dec 03 '14 at 21:37

2 Answers2

2

var mailComposer: MFMailComposeViewController is your problem. You need to keep a strong reference to this until its completely finished - use an ivar to hold it.

David H
  • 40,852
  • 12
  • 92
  • 138
  • OK, so I have tried everything. This code I posted previously works fine on a real device now that I have made it a class, declared it at the top of view controller, and initialized it in viedDidLoad... the problem is it is still basically dismissing the mail controller within 10 seconds in a simulator, and this is causing my app to be rejected at the app store... I would post my code but not sure how to in a comment like this, but I think you get the idea. Are there any alternatives, I need the client's customers to be able to quickly shoot an email to them. And yes I wrapped in ifCanSendMail – Jason Rybka Dec 03 '14 at 06:01
  • The Simulator should not be returning true for canSendMail, if it cannot. rdar://19134686 – David H Dec 03 '14 at 22:42
2

Try checking +canSendMail before running that code. If you haven't set up a mail account on the device, your app will crash.

Looking a bit deeper, it looks there are also specific issues with MFMailComposeViewController similar to what David H said. See I have REAL misunderstanding with MFMailComposeViewController in Swift (iOS8) in Simulator

Community
  • 1
  • 1
EricS
  • 9,650
  • 2
  • 38
  • 34
  • Your link is very insightful. First, it won't work in the Simulator even though MFMailComposeViewController.canSendMail() returns true. I've heard lots of problems with this class, and the recycle feature may well be needed if you make heavy use of email. Really, Apple ?!?!? – David H Dec 03 '14 at 22:36