如何从UIActivityViewController中排除Notes和提醒应用程序?
我正在创build一个UIActivityViewController
并将String
和URL
传递给它。 这显然,configurationUIActivityViewController
使用一些项目,我想排除(我的目标是共享有关我的应用程序的信息)。
我设法排除了大量系统提供的活动(如“添加到阅读列表”),方法是设置适当的excludedActivityTypes
。
但是,我无法排除提醒和Notes应用程序。 有人可以提出一种方法吗? 这些应用程序在列表中显示第3和第4,因此除非用户滚动,否则Twitter和Facebook将不可见。
有一种方法,但涉及私有API 。
有时苹果会制造exception,特别是如果你修复了一个错误。
让我们深入细节…
UIActivityViewController有一个名为“_availableActivitiesForItems:”的私有方法,它返回一个UISocialActivity对象的数组。
UISocialActivity有一个有趣的属性,称为“activityType”,它返回一个域格式的活动types。
经过一些testing后,我发现了Reminder和Notes活动types:
- com.apple.reminders.RemindersEditorExtension
- com.apple.mobilenotes.SharingExtension
不幸的是 ,将这两种types传递给“.excludedActivityTypes”没有任何区别。
“_availableActivitiesForItems:”来拯救!
旧的方式 :
更新 :我发现了一个更好的方法来做到这一点。
我发布的第一个解决scheme在某些情况下不起作用,因此不应该被认为是稳定的。
标题:
#import <UIKit/UIKit.h> @interface UISocialActivity : NSObject - (id)activityType; @end @interface UIActivityViewController (Private) - (id)_availableActivitiesForItems:(id)arg1; @end @interface ActivityViewController : UIActivityViewController @end
执行:
@implementation ActivityViewController - (id)_availableActivitiesForItems:(id)arg1 { id activities = [super _availableActivitiesForItems:arg1]; NSMutableArray *filteredActivities = [NSMutableArray array]; [activities enumerateObjectsUsingBlock:^(UISocialActivity* _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { if (![[obj activityType] isEqualToString:@"com.apple.reminders.RemindersEditorExtension"] && ![[obj activityType] isEqualToString:@"com.apple.mobilenotes.SharingExtension"]) { [filteredActivities addObject:obj]; } }]; return [NSArray arrayWithArray:filteredActivities]; } @end
新方法 :
标题:
@interface UIActivityViewController (Private) - (BOOL)_shouldExcludeActivityType:(UIActivity*)activity; @end @interface ActivityViewController : UIActivityViewController @end
执行:
@implementation ActivityViewController - (BOOL)_shouldExcludeActivityType:(UIActivity *)activity { if ([[activity activityType] isEqualToString:@"com.apple.reminders.RemindersEditorExtension"] || [[activity activityType] isEqualToString:@"com.apple.mobilenotes.SharingExtension"]) { return YES; } return [super _shouldExcludeActivityType:activity]; }
@结束
“非法”,但它的作品。
知道它是否真的通过了苹果validation真是太好了。
Swift 2.2版本。 在iOS9.3中testing 作品。
更新并获得App Store Review的批准。
import UIKit class ActivityViewController: UIActivityViewController { func _shouldExcludeActivityType(activity: UIActivity) -> Bool { let activityTypesToExclude = [ "com.apple.reminders.RemindersEditorExtension", "com.apple.mobilenotes.SharingExtension", UIActivityTypeOpenInIBooks, UIActivityTypePrint, UIActivityTypeAssignToContact, "com.google.Drive.ShareExtension" ] if let actType = activity.activityType() { if activityTypesToExclude.contains(actType) { return true } else if super.excludedActivityTypes != nil { return super.excludedActivityTypes!.contains(actType) } } return false } }
也很有用
"com.apple.mobileslideshow.StreamShareService"
摆脱“云”之一。
如果你不想子类UIActivityViewController
你可以在创build你的UIActivityViewController
时将它们包含在.excludedActivityTypes
。
目标C:
UIActivityViewController *activityController = [[UIActivityViewController alloc]initWithActivityItems:sharingItems applicationActivities:nil]; activityController.excludedActivityTypes = @[ UIActivityTypeAssignToContact, UIActivityTypePrint, UIActivityTypeAddToReadingList, UIActivityTypeSaveToCameraRoll, UIActivityTypeOpenInIBooks, @"com.apple.mobilenotes.SharingExtension", @"com.apple.reminders.RemindersEditorExtension" ]; [self presentViewController:activityController animated:YES completion:nil];
Swift 3:
let activityController = UIActivityViewController(activityItems: sharingItems, applicationActivities: nil) activityController.excludedActivityTypes = [ UIActivityType.assignToContact, UIActivityType.print, UIActivityType.addToReadingList, UIActivityType.saveToCameraRoll, UIActivityType.openInIBooks, UIActivityType(rawValue: "com.apple.reminders.RemindersEditorExtension"), UIActivityType(rawValue: "com.apple.mobilenotes.SharingExtension"), ] present(activityController, animated: true, completion: nil)
您不能排除这些因为Notes和Reminders没有在Apple文档中声明为UIActivities
。 只有iOS9的问题,并希望苹果将提供这个选项。 直到目前为止宣布的UIActivities是:
UIActivityTypePostToFacebook, UIActivityTypePostToTwitter, UIActivityTypePostToWeibo, UIActivityTypeMessage, UIActivityTypeMail, UIActivityTypePrint, UIActivityTypeCopyToPasteboard, UIActivityTypeAssignToContact, UIActivityTypeSaveToCameraRoll, UIActivityTypeAddToReadingList, UIActivityTypePostToFlickr, UIActivityTypePostToVimeo, UIActivityTypePostToTencentWeibo, UIActivityTypeAirDrop
我发现的唯一方法是创build自己的自定义活动,直接传递参数(不通过活动工作表),然后通过活动工作表传递一些随机variables(不是string,URL,图像)。
MyCustomPinterestShareActivity* pinterest = [[MyCustomPinterestShareActivity alloc] init]; MyCustomFacebookGroupsActivity* facebook = [[MyCustomFacebookGroupsActivity alloc] init]; MyCustomInstagramActivity* instagram = [[MyCustomInstagramActivity alloc] init]; NSArray *activities = @[facebook,instagram,pinterest]; NSArray *activityItems = @[someVarThatCanBeWhateverTypeJustNotStringURLOrImg]; UIActivityViewController *activityView = [[UIActivityViewController alloc] initWithActivityItems:activityItems applicationActivities:activities];
但是再一次,如果你不能使用任何function,你为什么要首先使用ActivityViewController?希望稍后会有更好的解决scheme
这次真是万分感谢! 在xcode 8.1,swift 3上,我可以使用得到:
UIActivityType(rawValue:“com.apple.reminders.RemindersEditorExtension”),UIActivityType(rawValue:“com.apple.mobilenotes.SharingExtension”),
对于Swift3 +,不需要任何私人API的黑客攻击。 只需使用UIActivityViewController上的public“excludedTypes”数组。 由于这些内容还没有UIActivityType(因为它们是Apple的内置扩展),所以您需要通过String来引用它。 您也可以将此格式用于任何第三方共享扩展。
例如
let avc = UIActivityViewController(activityItems: ["my item"], applicationActivities: nil) avc.excludedActivityTypes = [ .copyToPasteboard, UIActivityType(rawValue: "com.apple.reminders.RemindersEditorExtension"), UIActivityType(rawValue: "com.apple.mobilenotes.SharingExtension") ] avc.completionWithItemsHandler = { (activity, success, items, error) in print("AVC finished \(success) \(activity as Optional) \(items as Optional) \(error as Optional)") } present(avc, animated: true, completion: nil)
按照Matteo Pacini的build议,我无法将_shouldExcludeActivityType发送到Super,但是我可以这样做:
@interface CustomActivityViewController() - (BOOL)_shouldExcludeActivityType:(UIActivity *)activity; @end @implementation CustomActivityViewController (...) - (BOOL)_shouldExcludeActivityType:(UIActivity *)activity{ if([[activity activityType] isEqualToString:@"com.apple.reminders.RemindersEditorExtension"] || [[activity activityType] isEqualToString:@"com.apple.mobilenotes.SharingExtension"]){ return YES; } return [[super excludedActivityTypes]containsObject:activity.activityType]; }