Welcome!
This is the community forum for my apps Pythonista and Editorial.
For individual support questions, you can also send an email. If you have a very short question or just want to say hello — I'm @olemoritz on Twitter.
Show objc mail composer without closing view (or relaunching afterward?)
-
I'm generating a PDF using jinja in the background, and then want to email that through the iOS email composer after a button press in the UI. The following code works if I call it without the UI, and if I call view.close() first before calling the mail composer function. But otherwise the mail composer seems to close in the background instantly (without an error) and I never see it. I'm trying to do this in fullscreen mode, though it doesn't seem to make a difference.
Alternatively, is there a way to relaunch the view after the composer is dismissed? When I try to do so it says the view is already being presented even though I've called close().
Call from script:
show_mail_sheet('me@you.com', 'Test', [reference to PDF], 'text/pdf')
function:
# - (void)mailComposeController:(MFMailComposeViewController *)controller didFinishWithResult:(MFMailComposeResult)result error:(NSError *)error def mailComposeController_didFinishWithResult_error_(_self, _cmd, controller, result, error): print('Mail composer finished') # Wrap the controller parameter in an `ObjCInstance`, so we can send messages: mail_vc = ObjCInstance(controller) # Set delegate to nil, and release its memory: mail_vc.setMailComposeDelegate_(None) ObjCInstance(_self).release() # Dismiss the sheet: mail_vc.dismissViewControllerAnimated_completion_(True, None) methods = [mailComposeController_didFinishWithResult_error_] protocols = ['MFMailComposeViewControllerDelegate'] MyMailComposeDelegate = create_objc_class('MyMailComposeDelegate', NSObject, methods=methods, protocols=protocols) @on_main_thread def show_mail_sheet(recipient, subject, filename, mimetype): print("Showing mail sheet") load_framework('MessageUI') MFMailComposeViewController = ObjCClass('MFMailComposeViewController') mail_composer = MFMailComposeViewController.alloc().init().autorelease() # Use our new delegate class: delegate = MyMailComposeDelegate.alloc().init() mail_composer.setMailComposeDelegate_(delegate) mail_composer.setToRecipients([recipient]) mail_composer.setSubject(subject) filepath = os.path.join(os.getcwd(), filename) mail_composer.addAttachmentData_mimeType_fileName_(NSData.dataWithContentsOfFile_(filepath), mimetype, filename ) # Present the mail sheet: root_vc = UIApplication.sharedApplication().keyWindow().rootViewController() root_vc.presentViewController_animated_completion_(mail_composer, True, None)```
-
@blowhard could you check if after your problem a file _objc_exception.txt has been created or updated in the root of Pythonista. Perhaps is your problem coming from an Objectivec exception. If yes, you can post its content.
I think about a thread problem
-
@blowhard, if I understand correctly what you are trying to do, open the composer as a modal subcontroller to your ui.View, instead of a main controller:
vc = SUIViewController.viewControllerForView_( your_view.objc_instance) vc.presentModalViewController_animated_(mail_composer, True)
-
@mikael said:
vc = SUIViewController.viewControllerForView_(
your_view.objc_instance)
vc.presentModalViewController_animated_(mail_composer, True)This worked perfectly. Thanks!