Bug 22493 - Can't dismiss MFMailComposeViewController
Summary: Can't dismiss MFMailComposeViewController
Status: RESOLVED UPSTREAM
Alias: None
Product: iOS
Classification: Xamarin
Component: Xamarin.iOS.dll ()
Version: 3.x
Hardware: PC Windows
: Normal normal
Target Milestone: Untriaged
Assignee: Bugzilla
URL:
Depends on:
Blocks:
 
Reported: 2014-08-28 23:58 UTC by djvoracious
Modified: 2014-09-04 22:21 UTC (History)
3 users (show)

Tags:
Is this bug a regression?: ---
Last known good build:

Notice (2018-05-24): bugzilla.xamarin.com is now in read-only mode.

Please join us on Visual Studio Developer Community and in the Xamarin and Mono organizations on GitHub to continue tracking issues. Bugzilla will remain available for reference in read-only mode. We will continue to work on open Bugzilla bugs, copy them to the new locations as needed for follow-up, and add the new items under Related Links.

Our sincere thanks to everyone who has contributed on this bug tracker over the years. Thanks also for your understanding as we make these adjustments and improvements for the future.


Please create a new report on Developer Community or GitHub with your current version information, steps to reproduce, and relevant error messages or log files if you are hitting an issue that looks similar to this resolved bug and you do not yet see a matching new report.

Related Links:
Status:
RESOLVED UPSTREAM

Description djvoracious 2014-08-28 23:58:16 UTC
There seems to be a bug when the MFMailComposeViewController is instantiated upon ViewDidLoad. First time the view is opened the View is loaded fine. Clicking 'cancel' causes the view to disappear. However, upon loading it again, the view can't be dismissed. The following code replicates the issue

    [Register("AppDelegate")]
    public class AppDelegate : UIApplicationDelegate
    {
        public UIViewController MainController { get; set; }

        public UIWindow Window { get; set; }

        public override bool FinishedLaunching(UIApplication application, NSDictionary launchOptions)
        {
            Window = new UIWindow(UIScreen.MainScreen.Bounds);

            //MainController = new MyTabController("Some Value");
            MainController = new MySendEmailController();

            Window.RootViewController = MainController;

            Window.MakeKeyAndVisible();

            return true;
        }

    }

    public class MySendEmailController : UITabBarController
    {

        private MyEmailScreen _sendEmailScreen;
        private UIViewController _dummyTab;

        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            _sendEmailScreen = new MyEmailScreen();
            _sendEmailScreen.View.BackgroundColor = UIColor.Black;
            _sendEmailScreen.Title = "Send Email";

            _dummyTab = new UIViewController();
            _dummyTab.Title = "Green";
            _dummyTab.View.BackgroundColor = UIColor.Green;

            var tabs = new UIViewController[]{
                _sendEmailScreen, _dummyTab
            };
            ViewControllers = tabs;

            SelectedViewController = _sendEmailScreen;
        }
  
    }
    
    public class MyEmailScreen : UIViewController
    {
        private UIButton _button;

        private MFMailComposeViewController _mailController;

        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            _button = new UIButton(new RectangleF(0,0, View.Bounds.Width, 100));
            _button.SetTitle("Click me", UIControlState.Normal);
            _button.TouchUpInside +=(sender, args) => 
                    {
                            this.PresentViewController(_mailController, true, null);
                    };

            Add(_button);
 
            _mailController = new MFMailComposeViewController();

            _mailController.SetSubject("Can't dismiss me");

            _mailController.SetMessageBody("Cant dismiss on opening a second time", false);

            _mailController.Finished += FinishedSendingEmail;
        }

        private void FinishedSendingEmail(object s, MFComposeResultEventArgs args)
        {
            Console.WriteLine(args.Result.ToString());
            _mailController.DismissViewController(true, null);
        }
    }
Comment 1 Parmendra Kumar 2014-08-29 08:27:03 UTC
I have checked this issue and able to reproduce this, To reproduce this issue I
have followed the sample code mentioned in bug description. And observed that that 
when we click second time to cancel then the view can't be dismissed.

Screencast:http://screencast.com/t/Vhm90UrAJr2N

Output Log: https://gist.github.com/Parmendrak/eb13c63279188ef8fc7a

Environment info:

Microsoft Visual Studio Professional 2013
Version 12.0.30723.00 Update 3
Microsoft .NET Framework
Version 4.5.51641


Xamarin   3.3.47.0 (0b2a123923812a88ed3091909478dbe9e0111f00)
Visual Studio extension to enable development for Xamarin.iOS and Xamarin.Android
Comment 2 djvoracious 2014-08-29 20:56:23 UTC
The current work around for this is to instantiate the member object on ViewWillAppear(bool animated) method instead of the ViewDidLoad.
Comment 3 Sebastien Pouliot 2014-09-04 22:21:18 UTC
This is a known issue in iOS (since 6.0 according to [1]) where the controller cannot be reused. IOW you need to recreate a new instance of `MFMailComposeViewController` every time.

Here's a modified version of your code that works [2]. Take note that the `Finished` event might be called on any thread, so calling DismissViewController is dangerous [3] and should only be done with a bit of ezra care (to ensure it's called on the main UI thread).

I encourage you to file a bug report (radar) with Apple about it [4]. You won't be the first to file it - but they often assign priorities based on the number of feedback they receive.


[1] http://stackoverflow.com/a/15441244/220643
[2] https://gist.github.com/spouliot/4b88583fdad5ea4ccb73
[3] http://tirania.org/monomac/archive/2012/Sep-10.html
[4] https://bugreport.apple.com/