Welcome to the Treehouse Community

Want to collaborate on code errors? Have bugs you need feedback on? Looking for an extra set of eyes on your latest project? Get support with fellow developers, designers, and programmers of all backgrounds and skill levels here with the Treehouse Community! While you're at it, check out some resources Treehouse students have shared here.

Looking to learn something new?

Treehouse offers a seven day free trial for new students. Get access to thousands of hours of content and join thousands of Treehouse students and alumni in the community today.

Start your free trial

iOS

Swift Social Framework

I would like to add the ability to send a tweet from my app using the social framework but I am stuck and do not know where to start. I am able to do it using Objective-C but can't seem to translate it over. Thanks

2 Answers

Dimitris Sotiris Tsolis
Dimitris Sotiris Tsolis
27,661 Points

Here is a helper method i use

func tweet(message: String? = nil, image: UIImage? = nil, url: NSURL? = nil) {

    if SLComposeViewController.isAvailableForServiceType(SLServiceTypeTwitter) {
        let controller = SLComposeViewController(forServiceType: SLServiceTypeTwitter)
        controller.setInitialText(message)
        controller.addImage(image)
        controller.addURL(url)
        controller.completionHandler = { (result:SLComposeViewControllerResult) -> Void in
            switch result {
            case SLComposeViewControllerResult.Cancelled:
                NSLog("result: cancelled")
            case SLComposeViewControllerResult.Done:
                // TODO: ADD SOME CODE FOR SUCCESS
                NSLog("result: done")
            }
        }

        self.presentViewController(controller, animated: true, completion: { () -> Void in
            // controller is presented... do something if needed
        })
    } else {
        NSLog("Twitter is not available")
    }

}

Setting default values for the parameters gives you the ability to make a more flexible call. Something like this

self.tweet()
// or
self.tweet(image: UIImage(named: "example_image"))
// or
self.tweet(message: "Sample message")
// or
self.tweet(url: NSURL(string: "http://example.com/"))
// or
self.tweet(message: "Sample message", image: UIImage(named: "example_image"), url: NSURL(string: "http://example.com/"))
// etc

Fantastic! Thank you very much.

Is this the same as sending an iMessage too or does that use another framework?

Dimitris Sotiris Tsolis
Dimitris Sotiris Tsolis
27,661 Points

No but you can use Facebook share if you replace SLServiceTypeTwitter with SLServiceTypeFacebook.

In order to send iMessage or e-mail you have to use MessageUI framework, conform to the MFMessageComposeViewControllerDelegate (for iMessage) and MFMailComposeViewControllerDelegate (for email).

Then, somewhere in your code you can use

//..... some code (maybe a new method)

// Check whether message are supported or not
if MFMessageComposeViewController.canSendText() {
    // new MFMessageComposeViewController instance
    let controller = MFMessageComposeViewController()
    // set the delegate
    controller.messageComposeDelegate = self
    // set the body
    controller.body = "sample message"

    // present the controller
    self.navigationController?.presentViewController(controller, animated: true, completion: nil)
}
//.... some code

After that, you have to dismiss the controller. It won't dismissed by default so, a default implementation could be

func messageComposeViewController(controller: MFMessageComposeViewController!, didFinishWithResult result: MessageComposeResult) {

    switch result.value {
    case MessageComposeResultCancelled.value:
        NSLog("cancelled")
    case MessageComposeResultFailed.value:
        NSLog("cancelled")
    case MessageComposeResultSent.value:
        NSLog("cancelled")
    default:
        NSLog("default...")
    }
    controller.dismissViewControllerAnimated(true, completion: nil)
}

There is an error on this line

controller.messageComposeDelegate.self

The message says: "Expression resolves to an unused l-value"

Do you know what could be wrong? Thanks

Dimitris Sotiris Tsolis
Dimitris Sotiris Tsolis
27,661 Points

It's a typo error. You added a dot instead of the equal sign. Try this

controller.messageComposeDelegate = self

I have changed that and also imported the MessageUI framework. At the top should I add:

class ViewController: UIViewController, MFMessageComposeViewControllerDelegate

I have tried but it shows an error saying "Type 'ViewController' does not conform to protocol 'MFMessageComposeViewControllerDelegate'". Thanks

Dimitris Sotiris Tsolis
Dimitris Sotiris Tsolis
27,661 Points

Yes you have to add MFMessageComposeViewControllerDelegate and it should be ok. If no, try to clean the project and rebuild. That's how it's fixed on my projects.

Great. Thank you. I'll give that a try.