Skip to content

Commit

Permalink
Support for localized app names
Browse files Browse the repository at this point in the history
Part of intentkit#3
  • Loading branch information
lazerwalker committed Dec 16, 2013
1 parent 6aa4b36 commit 4f90e08
Show file tree
Hide file tree
Showing 18 changed files with 211 additions and 32 deletions.
2 changes: 2 additions & 0 deletions IntentKit/Apps/1Password/1Password.plist
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>name</key>
<string>1Password</string>
<key>actions</key>
<dict>
<key>openHttpsURL:</key>
Expand Down
6 changes: 4 additions & 2 deletions IntentKit/Apps/Chrome/Chrome.plist
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,16 @@
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>name</key>
<string>Chrome</string>
<key>actions</key>
<dict>
<key>openHttpsURL:</key>
<string>googlechromes://{url}</string>
<key>openHttpURL:</key>
<string>googlechrome://{url}</string>
<key>openURL:withCallback:</key>
<string>googlechrome-x-callback://x-callback-url/open/?x-source={source}&amp;x-success={callback}&amp;url={url}</string>
</dict>
<string>googlechrome-x-callback://x-callback-url/open/?x-source={source}&amp;x-success={callback}&amp;url={url}</string>
</dict>
</dict>
</plist>
2 changes: 2 additions & 0 deletions IntentKit/Apps/Google Maps/Google Maps.plist
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>name</key>
<string>Google Maps</string>
<key>optional</key>
<dict>
<key>zoom</key>
Expand Down
9 changes: 9 additions & 0 deletions IntentKit/Apps/Maps/Maps.plist
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,15 @@
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>name</key>
<dict>
<key>en</key>
<string>Maps</string>
<key>de</key>
<string>Karten</string>
<key>fr</key>
<string>Plans</string>
</dict>
<key>optional</key>
<dict>
<key>zoom</key>
Expand Down
2 changes: 2 additions & 0 deletions IntentKit/Apps/Safari/Safari.plist
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>name</key>
<string>Safari</string>
<key>actions</key>
<dict>
<key>openHttpURL:</key>
Expand Down
2 changes: 2 additions & 0 deletions IntentKit/Apps/Tweetbot/Tweetbot.plist
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>name</key>
<string>Tweetbot</string>
<key>optional</key>
<dict>
<key>callbackURL</key>
Expand Down
2 changes: 2 additions & 0 deletions IntentKit/Apps/Twitter/Twitter.plist
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>name</key>
<string>Twitter</string>
<key>actions</key>
<dict>
<key>showTweetWithId:</key>
Expand Down
2 changes: 2 additions & 0 deletions IntentKit/Apps/Twitterrific/Twitterrific.plist
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>name</key>
<string>Twitterrific</string>
<key>actions</key>
<dict>
<key>showTweetWithId:</key>
Expand Down
24 changes: 21 additions & 3 deletions IntentKit/INKActivity.h
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,14 @@
@warning `INKActivity` currently makes use of the private method `_activityImage` to coax the `UIActivityViewController` into displaying a full-color image rather than creating a black-and-white representation using the `UIImage` returned by `activityImage` as a mask. It remains to be seen whether Apple will allow this private API usage or not. */
@interface INKActivity : UIActivity

/** The name of the app, to be displayed as the `UIActivity` `activityTitle` field. */
@property (strong, nonatomic) NSString *name;
/** The English name of the application */
@property (readonly) NSString *name;

/** The localized name of the application, taking the device's current language
preferences into account. For many applications, this will always be the same
as `name`. */
@property (readonly) NSString *localizedName;


/** A dictionary of URL schemes an application responds to. The keys are command names, and the values are handlebar-templated strings that can be used to construct a valid URL. */
@property (strong, nonatomic) NSDictionary *actions;
Expand All @@ -27,7 +33,7 @@
@property (strong, nonatomic) NSDictionary *optionalParams;


/** Returns an intialized `INKActivity` object.
/** Returns an initialized `INKActivity` object.
@param actions The dictionary mapping commands to valid URL schemes for the third-party application.
@param optionalParams The dictionary listing which optional parameters are accepted.
Expand All @@ -40,6 +46,18 @@
name: (NSString *)name
application:(UIApplication *)application;

/** Returns an intialized `INKActivity` object.
@param actions The dictionary mapping commands to valid URL schemes for the third-party application.
@param optionalParams The dictionary listing which optional parameters are accepted.
@param names A dictionary of localized app names. The keys are short locale names (e.g. `en`, `fr`), the values are strings representing the name for the given locale.
@param application The UIApplication to use when calling `[UIApplication openURL:]` and `[UIApplication canOpenURL:]`. You probably want this to be `[UIApplication sharedApplication]`, but it is injected here for test purposes.
@return an initialized `INKActivity` object. */
- (instancetype)initWithActions:(NSDictionary *)actions
optionalParams:(NSDictionary *)optionalParams
names: (NSDictionary *)names
application:(UIApplication *)application;
/** Checks whether or not the third-party app can accept a custom URL corresponding to a given command
@param command A command to perform. If the third-party app knows how to perform this command, it should have a corresponding key in the activity's `dict` property.
Expand Down
37 changes: 35 additions & 2 deletions IntentKit/INKActivity.m
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,19 @@

#import "INKActivity.h"
#import "NSString+Helpers.h"
#import "IntentKit.h"

@interface INKActivity ()

@property (readonly) UIImage *_activityImage;

@property (strong, nonatomic) UIApplication *application;
@property (strong, nonatomic) IntentKit *intentKit;

@property (strong, nonatomic) NSString *activityCommand;
@property (strong, nonatomic) NSDictionary *activityArguments;
@property (strong, nonatomic) NSDictionary *names;


@end

Expand All @@ -25,11 +30,22 @@ - (instancetype)initWithActions:(NSDictionary *)actions
optionalParams:(NSDictionary *)optionalParams
name: (NSString *)name
application:(UIApplication *)application {
return [self initWithActions:actions
optionalParams:optionalParams
names:@{@"en":name}
application:application];
}

- (instancetype)initWithActions:(NSDictionary *)actions
optionalParams:(NSDictionary *)optionalParams
names: (NSDictionary *)names
application:(UIApplication *)application {
if (self = [super init]) {
self.name = name;
self.names = names;
self.actions = actions;
self.optionalParams = optionalParams;
self.application = application;
self.intentKit = [IntentKit sharedInstance];
}
return self;
}
Expand All @@ -40,13 +56,30 @@ - (BOOL)canPerformCommand:(NSString *)command {
return [self.application canOpenURL:url];
}

- (NSString *)name {
if (self.names[@"en"]) {
return self.names[@"en"];
} else {
return self.names[self.names.allKeys.firstObject];
}
}

- (NSString *)localizedName {
for (NSString *language in [self.intentKit preferredLanguages]) {
if (self.names[language]) {
return self.names[language];
}
}
return self.name;
}

#pragma mark - UIActivity methods
+ (UIActivityCategory)activityCategory {
return UIActivityCategoryAction;
}

- (NSString *)activityTitle {
return self.name;
return self.localizedName;
}

- (NSString *)activityType {
Expand Down
2 changes: 1 addition & 1 deletion IntentKit/INKActivityViewController/INKActivityCell.m
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ - (id)initWithFrame:(CGRect)frame
- (void)updateConstraints {
[super updateConstraints];

NSNumber *iconSize = @(IntentKit.isPad ?
NSNumber *iconSize = @(IntentKit.sharedInstance.isPad ?
INKActivityCellIconSize_Pad : INKActivityCellIconSize_Phone);

NSDictionary *metrics = NSDictionaryOfVariableBindings(iconSize);
Expand Down
4 changes: 2 additions & 2 deletions IntentKit/INKActivityViewController/INKActivityPresenter.m
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ - (void)presentModalActivitySheetFromViewController:(UIViewController *)presenti
- (void)presentActivitySheetFromViewController:(UIViewController *)presentingViewController popoverFromRect:(CGRect)rect inView:(UIView *)view permittedArrowDirections:(UIPopoverArrowDirection)arrowDirections animated:(BOOL)animated {
if (self.activitySheet.numberOfApplications <= 1 && !self.alwaysShowActivityView) {
[self.activitySheet performActivityInFirstAvailableApplication];
} else if (IntentKit.isPad) {
} else if (IntentKit.sharedInstance.isPad) {
self.presentingViewController = presentingViewController;
self.popoverController = [[UIPopoverController alloc] initWithContentViewController:self.activitySheet];
self.popoverController.popoverContentSize = self.activitySheet.view.bounds.size;
Expand All @@ -75,7 +75,7 @@ - (void)presentActivitySheetFromViewController:(UIViewController *)presentingVie

if (self.activitySheet.numberOfApplications <= 1 && !self.alwaysShowActivityView) {
[self.activitySheet performActivityInFirstAvailableApplication];
} else if (IntentKit.isPad) {
} else if (IntentKit.sharedInstance.isPad) {
self.presentingViewController = presentingViewController;
self.popoverController = [[UIPopoverController alloc] initWithContentViewController:self.activitySheet];
[self.popoverController presentPopoverFromBarButtonItem:item permittedArrowDirections:arrowDirections animated:animated];
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ - (instancetype)initWithActivityItems:(NSArray *)activityItems applicationActivi
self.activityItems = activityItems;
self.applicationActivities = applicationActivities;

if (IntentKit.isPad) {
if (IntentKit.sharedInstance.isPad) {
self.contentView = self.view;
} else {
self.contentView = [[UIView alloc] init];
Expand All @@ -72,7 +72,7 @@ - (instancetype)initWithActivityItems:(NSArray *)activityItems applicationActivi
self.blurToolbar = [[UIToolbar alloc] initWithFrame:self.contentView.bounds];
[self.contentView insertSubview:self.blurToolbar atIndex:0];

if (IntentKit.isPad) {
if (IntentKit.sharedInstance.isPad) {
self.collectionViewLayout.itemSize = INKActivityViewControllerItemSize_Pad;
self.collectionViewLayout.sectionInset = INKActivityViewControllerEdgeInsets_Pad;
self.collectionViewLayout.scrollDirection = UICollectionViewScrollDirectionHorizontal;
Expand Down Expand Up @@ -144,7 +144,7 @@ - (void)configureForPhone {

}
- (void)setBounds {
if (IntentKit.isPad) {
if (IntentKit.sharedInstance.isPad) {
[self configureForPad];
} else {
[self configureForPhone];
Expand Down
20 changes: 12 additions & 8 deletions IntentKit/INKApplicationList.m
Original file line number Diff line number Diff line change
Expand Up @@ -39,16 +39,20 @@ - (NSArray *)activities {
inDirectory:nil];
for (NSString *path in appPaths) {
NSDictionary *dict = [NSDictionary dictionaryWithContentsOfFile:path];
NSString *name = [path.pathComponents.lastObject stringByDeletingPathExtension];

if ([@[@"Info", @"IntentKitBundle-Info"] containsObject:name]) {
continue;
if (!(dict[@"actions"] && dict[@"name"])) { continue; }

if ([dict[@"name"] isKindOfClass:[NSDictionary class]]) {
[activities addObject:[[INKActivity alloc] initWithActions:dict[@"actions"]
optionalParams:dict[@"optional"]
names:dict[@"name"]
application:self.application]];
} else {
[activities addObject:[[INKActivity alloc] initWithActions:dict[@"actions"]
optionalParams:dict[@"optional"]
name:dict[@"name"]
application:self.application]];
}

[activities addObject:[[INKActivity alloc] initWithActions:dict[@"actions"]
optionalParams:dict[@"optional"]
name:name
application:self.application]];
}
return [activities copy];
}
Expand Down
11 changes: 9 additions & 2 deletions IntentKit/IntentKit.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,17 @@
#import "INKActivityPresenter.h"
#import "INKActivityViewController.h"

/** A mish-mosh of occasionally-useful global (uh-oh!) methods */
/** A mish-mosh of occasionally-useful methods */
@interface IntentKit : NSObject

/** A static singleton object */
+ (instancetype)sharedInstance;

/** Determines whether or not the current device is an iPad.
@return YES if being run on an iPad (UIUserInterfaceIdiomPad), otherwise no. */
+ (BOOL)isPad;
- (BOOL)isPad;

/** An array of the current device's preferred languages. */
- (NSArray *)preferredLanguages;

@end
16 changes: 15 additions & 1 deletion IntentKit/IntentKit.m
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,21 @@

@implementation IntentKit

+ (BOOL)isPad {
+ (instancetype)sharedInstance {
static id _sharedInstance = nil;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
_sharedInstance = [[self alloc] init];
});

return _sharedInstance;
}

- (BOOL)isPad {
return (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad);
}

- (NSArray *)preferredLanguages {
return [NSLocale preferredLanguages];
}
@end
Loading

0 comments on commit 4f90e08

Please sign in to comment.