我正在尝试使用UIActivityViewController与主题标签共享图像,并且在尝试分享到Twitter,Facebook和Instagram时遇到了一些奇怪的行为。似乎没有关于这些服务的共享扩展的大量文档。
场景1:具有带图像和文本的活动项目数组的Init控制器
如果我像这样初始化控制器,Twitter和Facebook将显示在控制器中(没有Instagram,因为它不支持文本项),并且两者都将以编程方式预先填充文本输入字段中的#标签:
let activityVC = UIActivityViewController(activityItems: [myHashtagString, myImage], applicationActivities: nil)
场景2:仅包含图像的Init控制器
在这种情况下,所有网络都会显示,但我(显然)会丢失自动主题标签功能:
let activityVC = UIActivityViewController(activityItems: [myImage], applicationActivities: nil)
场景3:UIActivityItemSource子类
如果我创建自己的UIActivityItemSource子类,我几乎可以完成所有工作。然而,这是我无法弄清楚的,使用我下面的协议方法导致自动主题标签适用于Facebook,但不是Twitter。这怎么可能 - 推特需要一个特殊的密钥吗?如果它在场景#1 ...
中工作,必须有一种方法可以工作有趣的是,如果我插入一个URL(注释掉),这种方法适用于Twitter和Facebook。那么为什么在地球上赢得Twitter的文字工作呢?
let activityItem = CustomItemSource(image: image, message: "#TestTag")
let activityVC = UIActivityViewController(activityItems: [activityItem], applicationActivities: nil)
...
class CustomItemSource: NSObject, UIActivityItemSource {
private var image: UIImage!
private var message: String!
// MARK: Init
init(image: UIImage, message: String) {
super.init()
self.image = image
self.message = message
}
// MARK: Item Source Protocol
func activityViewControllerPlaceholderItem(_ activityViewController: UIActivityViewController) -> Any {
return image
}
func activityViewController(_ activityViewController: UIActivityViewController, itemForActivityType activityType: UIActivityType) -> Any? {
if activityType == .postToTwitter || activityType == .postToFacebook {
//return ["url": URL(string: "https://www.google.com")!, "image": image]
return ["text": message, "image": image]
}
else {
return ["image": image]
}
}
}
答案 0 :(得分:25)
定义两个UIActivityItemSource
类,一个用于 Image ,另一个用于 Text 。
在第一个中只返回图像。
在第二个中,为placeHolder返回NSObject()
,并根据活动返回Text
或nil
。通过返回NSObject()
,UIActivity将允许所有服务可用。
UIActivityViewController(activityItems: [ImageProvider(), TextProvider()], applicationActivities: nil)
和提供者:
class TextProvider: NSObject, UIActivityItemSource {
func activityViewControllerPlaceholderItem(_ activityViewController: UIActivityViewController) -> Any {
return NSObject()
}
func activityViewController(_ activityViewController: UIActivityViewController, itemForActivityType activityType: UIActivityType) -> Any? {
if activityType == .postToTwitter || activityType == .postToFacebook {
return "Tweet with #Hashtag"
}
return nil
}
}
class ImageProvider: NSObject, UIActivityItemSource {
func activityViewControllerPlaceholderItem(_ activityViewController: UIActivityViewController) -> Any {
return UIImage(named: ...)
}
func activityViewController(_ activityViewController: UIActivityViewController, itemForActivityType activityType: UIActivityType) -> Any? {
return UIImage(named: ...)
}
}
首先,密钥并不是真正敏感,唯一的敏感密钥是电子邮件和支持它的应用程序的“主题”,它在UIActivityController
的API中实现,我们可以直接设置它。如果您向UIImage
提供关键字“图片”或“1”,则无关紧要。
事实证明,如果文本未在...itemForActivity...
方法中直接返回 ,则Twitter活动将无效。因此,解决方案是分离项目来源。
如果placeholder
收到String
以外的其他内容,则Twitter活动也无效,但返回String
Instagram活动将无法正常工作,因此返回NSObject()
类型将会被忽略,所有服务都将可用。
如果您想使用UIActivityViewController.excludedActivityTypes