Skip to content

Commit

Permalink
UIImage can now be shared
Browse files Browse the repository at this point in the history
  • Loading branch information
sascha committed Aug 31, 2014
1 parent 14cc56f commit 94bc6b6
Show file tree
Hide file tree
Showing 8 changed files with 105 additions and 26 deletions.
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,13 +27,13 @@ Typical usage will look something like this:

[self presentViewController:activityViewController animated:YES completion:nil];

Have a look at the demo app to see it in context.
Please note that you can only share instances of `NSString`, `NSURL` or `UIImage`. WhatsApp does not support sharing text and images at the same time, so as soon as you provide an `UIImage` all `NSString` and `NSURL` instances will be ignored. In addition you can only share **one** `UIImage`. Have a look at the demo app to see it in context.

![Demo screenshot](https://raw.github.com/sascha/SSCWhatsAppActivity/master/screenshot.png)

## Author

Sascha Schwabbauer, sascha[email protected]
Sascha Schwabbauer, sascha@evolved.io

## License

Expand Down
8 changes: 4 additions & 4 deletions SSCWhatsAppActivity.podspec
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
Pod::Spec.new do |s|
s.name = "SSCWhatsAppActivity"
s.version = "1.0"
s.summary = "A UIActivity subclass for sharing messages with WhatsApp."
s.version = "1.1"
s.summary = "A UIActivity subclass for sharing images and messages with WhatsApp."
s.homepage = "https://github.com/sascha/SSCWhatsAppActivity"
s.screenshots = "https://raw.github.com/sascha/SSCWhatsAppActivity/master/screenshot.png"
s.license = { :type => 'MIT', :file => 'LICENSE' }
s.author = { "Sascha Schwabbauer" => "sascha[email protected]" }
s.author = { "Sascha Schwabbauer" => "sascha@evolved.io" }
s.source = { :git => "https://github.com/sascha/SSCWhatsAppActivity.git", :tag => s.version.to_s }
s.social_media_url = 'https://twitter.com/_SaschaS'

Expand All @@ -14,4 +14,4 @@ Pod::Spec.new do |s|

s.source_files = 'SSCWhatsAppActivity/*.{h,m}'
s.resources = 'SSCWhatsAppActivity/*.png'
end
end
81 changes: 69 additions & 12 deletions SSCWhatsAppActivity/SSCWhatsAppActivity.m
Original file line number Diff line number Diff line change
Expand Up @@ -8,22 +8,30 @@

#import "SSCWhatsAppActivity.h"

NSString * const SSCActivityTypePostToWhatsApp = @"net.psyonic.activity.postToWhatsApp";
NSString * const SSCActivityTypePostToWhatsApp = @"io.evolved.activity.postToWhatsApp";

@interface SSCWhatsAppActivity ()
@interface SSCWhatsAppActivity () <UIDocumentInteractionControllerDelegate>

@property (nonatomic, copy) NSString *shareString;
@property (nonatomic, strong) UIDocumentInteractionController *documentInteractionController;
@property (nonatomic, strong) NSMutableArray *stringsToShare;
@property (nonatomic, strong) UIImage *imageToShare;

@end

@implementation SSCWhatsAppActivity

static NSString *encodeByAddingPercentEscapes(NSString *input) {
NSString *encodedValue = (NSString *)CFBridgingRelease(CFURLCreateStringByAddingPercentEscapes(kCFAllocatorDefault, (CFStringRef)input, NULL, (CFStringRef)@"!*'();:@&=+$,/?%#[]", kCFStringEncodingUTF8));
#pragma mark - Accessors

- (NSMutableArray *)stringsToShare {
if (!_stringsToShare) {
_stringsToShare = [NSMutableArray new];
}

return encodedValue;
return _stringsToShare;
}

#pragma mark - UIActivity

- (NSString *)activityType {
return SSCActivityTypePostToWhatsApp;
}
Expand All @@ -46,13 +54,20 @@ + (UIActivityCategory)activityCategory {

- (BOOL)canPerformWithActivityItems:(NSArray *)activityItems {
// No WhatsApp for iPad
if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) return NO;
if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) {
return NO;
}

// Check if WhatsApp is installed
NSURL *whatsAppURL = [NSURL URLWithString:@"whatsapp://app"];
if (![[UIApplication sharedApplication] canOpenURL:whatsAppURL]) return NO;

if (![[UIApplication sharedApplication] canOpenURL:whatsAppURL]) {
return NO;
}

// Check for valid activityItems
for (id item in activityItems) {
if ([item isKindOfClass:[NSString class]] || [item isKindOfClass:[NSURL class]]) {
if ([item isKindOfClass:[NSString class]] || [item isKindOfClass:[NSURL class]] || [item isKindOfClass:[UIImage class]]) {
return YES;
}
}
Expand All @@ -63,17 +78,59 @@ - (BOOL)canPerformWithActivityItems:(NSArray *)activityItems {
- (void)prepareWithActivityItems:(NSArray *)activityItems {
for (id item in activityItems) {
if ([item isKindOfClass:[NSString class]]) {
self.shareString = [(self.shareString ? self.shareString : @"") stringByAppendingFormat:@"%@%@", (self.shareString ? @" " : @""), item];
[self.stringsToShare addObject:item];
} else if ([item isKindOfClass:[NSURL class]]) {
self.shareString = [(self.shareString ? self.shareString : @"") stringByAppendingFormat:@"%@%@", (self.shareString ? @" " : @""), [(NSURL *)item absoluteString]];
[self.stringsToShare addObject:[(NSURL *)item absoluteString]];
} else if ([item isKindOfClass:[UIImage class]]) {
self.imageToShare = item;
}
}
}

- (void)performActivity {
NSURL *whatsAppURL = [NSURL URLWithString:[NSString stringWithFormat:@"whatsapp://send?text=%@", encodeByAddingPercentEscapes(self.shareString)]];
if (self.imageToShare) {
[self sendImageToDocumentInteractionController:self.imageToShare];
} else {
[self sendStringToWhatsApp:[self.stringsToShare componentsJoinedByString:@" "]];
}
}

#pragma mark - Helper methods

static NSString *encodeByAddingPercentEscapes(NSString *input) {
NSString *encodedValue = (NSString *)CFBridgingRelease(CFURLCreateStringByAddingPercentEscapes(kCFAllocatorDefault, (CFStringRef)input, NULL, (CFStringRef)@"!*'();:@&=+$,/?%#[]", kCFStringEncodingUTF8));

return encodedValue;
}

- (void)sendStringToWhatsApp:(NSString *)stringToShare {
NSURL *whatsAppURL = [NSURL URLWithString:[NSString stringWithFormat:@"whatsapp://send?text=%@", encodeByAddingPercentEscapes(stringToShare)]];
BOOL success = [[UIApplication sharedApplication] openURL:whatsAppURL];
[self activityDidFinish:success];
}

- (void)sendImageToDocumentInteractionController:(UIImage *)image {
// Save with .wai extension so that it is only recognized by WhatsApp (see https://www.whatsapp.com/faq/en/iphone/23559013)
NSURL *fileURL = [[NSURL fileURLWithPath:NSTemporaryDirectory() isDirectory:YES] URLByAppendingPathComponent:@"image.wai"];
BOOL success = [UIImageJPEGRepresentation(image, 1.0) writeToURL:fileURL atomically:YES];

if (success) {
self.documentInteractionController = [UIDocumentInteractionController interactionControllerWithURL:fileURL];
self.documentInteractionController.delegate = self;
self.documentInteractionController.UTI = @"net.whatsapp.image";

// Present UIDocumentInteractionController in topmost view
UIView *view = [[UIApplication sharedApplication].keyWindow.subviews lastObject];
[self.documentInteractionController presentOpenInMenuFromRect:view.bounds inView:view animated:YES];
} else {
[self activityDidFinish:NO];
}
}

#pragma mark - UIDocumentInteractionControllerDelegate

- (void)documentInteractionController:(UIDocumentInteractionController *)controller willBeginSendingToApplication:(NSString *)application {
[self activityDidFinish:YES];
}

@end
4 changes: 4 additions & 0 deletions WhatsAppActivityDemo.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
2B1F005A18B0FF9500242DE9 /* [email protected] in Resources */ = {isa = PBXBuildFile; fileRef = 2B1F005818B0FF9500242DE9 /* [email protected] */; };
2B1F005D18B1014100242DE9 /* SSCWhatsAppIcon-iOS6.png in Resources */ = {isa = PBXBuildFile; fileRef = 2B1F005B18B1014000242DE9 /* SSCWhatsAppIcon-iOS6.png */; };
2B1F005E18B1014100242DE9 /* [email protected] in Resources */ = {isa = PBXBuildFile; fileRef = 2B1F005C18B1014100242DE9 /* [email protected] */; };
2B7A0AD019B3458F008DF6A6 /* shareImage.jpg in Resources */ = {isa = PBXBuildFile; fileRef = 2B7A0ACF19B3458F008DF6A6 /* shareImage.jpg */; };
/* End PBXBuildFile section */

/* Begin PBXFileReference section */
Expand All @@ -42,6 +43,7 @@
2B1F005818B0FF9500242DE9 /* [email protected] */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = "[email protected]"; path = "SSCWhatsAppActivity/[email protected]"; sourceTree = "<group>"; };
2B1F005B18B1014000242DE9 /* SSCWhatsAppIcon-iOS6.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = "SSCWhatsAppIcon-iOS6.png"; path = "SSCWhatsAppActivity/SSCWhatsAppIcon-iOS6.png"; sourceTree = "<group>"; };
2B1F005C18B1014100242DE9 /* [email protected] */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = "[email protected]"; path = "SSCWhatsAppActivity/[email protected]"; sourceTree = "<group>"; };
2B7A0ACF19B3458F008DF6A6 /* shareImage.jpg */ = {isa = PBXFileReference; lastKnownFileType = image.jpeg; path = shareImage.jpg; sourceTree = "<group>"; };
/* End PBXFileReference section */

/* Begin PBXFrameworksBuildPhase section */
Expand Down Expand Up @@ -92,6 +94,7 @@
2B1F003018B0FE1C00242DE9 /* SSCAppDelegate.m */,
2B1F005018B0FED300242DE9 /* SSCRootViewController.h */,
2B1F005118B0FED300242DE9 /* SSCRootViewController.m */,
2B7A0ACF19B3458F008DF6A6 /* shareImage.jpg */,
2B1F005318B0FF3000242DE9 /* SSCWhatsAppActivity */,
2B1F003218B0FE1C00242DE9 /* Images.xcassets */,
2B1F002718B0FE1C00242DE9 /* Supporting Files */,
Expand Down Expand Up @@ -179,6 +182,7 @@
2B1F005E18B1014100242DE9 /* [email protected] in Resources */,
2B1F002B18B0FE1C00242DE9 /* InfoPlist.strings in Resources */,
2B1F005D18B1014100242DE9 /* SSCWhatsAppIcon-iOS6.png in Resources */,
2B7A0AD019B3458F008DF6A6 /* shareImage.jpg in Resources */,
2B1F005A18B0FF9500242DE9 /* [email protected] in Resources */,
2B1F005918B0FF9500242DE9 /* SSCWhatsAppIcon.png in Resources */,
2B1F003318B0FE1C00242DE9 /* Images.xcassets in Resources */,
Expand Down
32 changes: 25 additions & 7 deletions WhatsAppActivityDemo/SSCRootViewController.m
Original file line number Diff line number Diff line change
Expand Up @@ -18,22 +18,40 @@ @implementation SSCRootViewController
- (void)viewDidLoad {
[super viewDidLoad];

UIButton *showActivitiesButton = [UIButton buttonWithType:UIButtonTypeRoundedRect];
[showActivitiesButton setTitle:@"Show Activities" forState:UIControlStateNormal];
[showActivitiesButton addTarget:self action:@selector(showActivities:) forControlEvents:UIControlEventTouchUpInside];
[self.view addSubview:showActivitiesButton];
[showActivitiesButton setFrame:CGRectMake(10, 10, 120, 50)];
UIButton *showActivitiesTextButton = [UIButton buttonWithType:UIButtonTypeRoundedRect];
[showActivitiesTextButton setTitle:@"Show Activities (Text)" forState:UIControlStateNormal];
[showActivitiesTextButton addTarget:self action:@selector(showActivitiesWithText:) forControlEvents:UIControlEventTouchUpInside];
[self.view addSubview:showActivitiesTextButton];
[showActivitiesTextButton sizeToFit];
[showActivitiesTextButton setFrame:CGRectMake(10, 20, CGRectGetWidth(showActivitiesTextButton.bounds), 50)];

UIButton *showActivitiesImageButton = [UIButton buttonWithType:UIButtonTypeRoundedRect];
[showActivitiesImageButton setTitle:@"Show Activities (Image)" forState:UIControlStateNormal];
[showActivitiesImageButton addTarget:self action:@selector(showActivitiesWithImage:) forControlEvents:UIControlEventTouchUpInside];
[self.view addSubview:showActivitiesImageButton];
[showActivitiesImageButton sizeToFit];
[showActivitiesImageButton setFrame:CGRectMake(10, 60, CGRectGetWidth(showActivitiesImageButton.bounds), 50)];
}

- (void)showActivities:(id)sender {
- (void)showActivitiesWithText:(id)sender {
NSString *stringToShare = @"This is a message I'd like to share via WhatsApp";
NSURL *urlToShare = [NSURL URLWithString:@"https://github.com/sascha/SSCWhatsAppActivity"];

SSCWhatsAppActivity *whatsAppActivity = [[SSCWhatsAppActivity alloc] init];

UIActivityViewController *activityViewController = [[UIActivityViewController alloc] initWithActivityItems:@[stringToShare, urlToShare] applicationActivities:@[whatsAppActivity]];

[self presentViewController:activityViewController animated:YES completion:nil];
}

- (void)showActivitiesWithImage:(id)sender {
UIImage *imageToShare = [UIImage imageNamed:@"shareImage.jpg"];

SSCWhatsAppActivity *whatsAppActivity = [[SSCWhatsAppActivity alloc] init];

UIActivityViewController *activityViewController = [[UIActivityViewController alloc] initWithActivityItems:@[imageToShare] applicationActivities:@[whatsAppActivity]];

[self presentViewController:activityViewController animated:YES completion:nil];
}

@end
2 changes: 1 addition & 1 deletion WhatsAppActivityDemo/WhatsAppActivityDemo-Info.plist
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
<key>CFBundleExecutable</key>
<string>${EXECUTABLE_NAME}</string>
<key>CFBundleIdentifier</key>
<string>net.psyonic.${PRODUCT_NAME:rfc1034identifier}</string>
<string>io.evolved.${PRODUCT_NAME:rfc1034identifier}</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundleName</key>
Expand Down
Binary file added WhatsAppActivityDemo/shareImage.jpg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified screenshot.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.

0 comments on commit 94bc6b6

Please sign in to comment.