実装しようとしている共有拡張機能に非常に奇妙な動作があります。私のアプリは、ユーザーが選択した画像を分析のためにサーバーに送信することになっています。ユーザーは写真を 1 枚選択し、post
ボタンを押して送信します。
私が持っている奇妙な行動は次のとおりです。
共有拡張機能を初めて使用したとき、それは
attachment.loadItem
呼び出しを超えません。印刷さえしませんBefore error
。その後、同じワークフローを繰り返すと、うまくいきます。XCodeデバッガーを使用すると、
attachment.loadItem
パートに入ることができません。拡張機能を使用する回数に関係なく。テストを数回繰り返すことができます。私の画像はサーバーに投稿されず、、、Before error
またはThere is no error
印刷There is an error
もされません。また、attachment.loadItem
2回呼び出されます。
didSelectPost
関数に次のコードがあります
override func didSelectPost() {
self.extensionContext!.completeRequest(returningItems: [], completionHandler: nil)
// Make sure we have a valid extension item
if let content = extensionContext!.inputItems[0] as? NSExtensionItem {
let contentType = kUTTypeImage as String
// Verify the provider is valid
if let contents = content.attachments as? [NSItemProvider] {
// Look for images
for attachment in contents {
print ("There is \(contents.count) attachments")
if attachment.hasItemConformingToTypeIdentifier(contentType) {
print ("I'm in the hasItemConforming part")
attachment.loadItem(forTypeIdentifier: contentType, options: nil) { data, error in
print ("Before error")
if error == nil {
print ("There is no error")
let url = data as! URL
self.sendToServer(localUrl: url)
} else {
print ("There is an error")
}
}
}
}
}
}
}
誰かが私を助けてくれたら、とても感謝しています。読んで助けてくれてありがとう。
編集:作業コード。
@IBAction func didSelectButton(_ sender: Any) {
// This is called after the user selects Post. Do the upload of contentText and/or NSExtensionContext attachments.
// Inform the host that we're done, so it un-blocks its UI. Note: Alternatively you could call super's -didSelectPost, which will similarly complete the extension context.
if let inputItem = extensionContext!.inputItems.first as? NSExtensionItem {
if let itemProvider = inputItem.attachments?.first as? NSItemProvider {
if self.isInternetAvailable(){
if itemProvider.hasItemConformingToTypeIdentifier(kUTTypeImage as String) {
progressHUD = MBProgressHUD.showAdded(to: self.view, animated: true)
progressHUD.mode = MBProgressHUDMode.determinate
progressHUD.detailsLabel.text = message
let tap = UITapGestureRecognizer(target: self, action: #selector(cancelButton))
progressHUD.addGestureRecognizer(tap)
var imageExt = String()
let imageName = generateRandomStringWithLength(length: 12)
if itemProvider.hasItemConformingToTypeIdentifier(kUTTypeJPEG as String) {
imageExt = ".jpeg"
print ("le type est \(imageExt)")
}
if itemProvider.hasItemConformingToTypeIdentifier(kUTTypePNG as String) {
imageExt = ".png"
print ("le type est \(imageExt)")
}
if itemProvider.hasItemConformingToTypeIdentifier(kUTTypeGIF as String) {
imageExt = ".gif"
print ("le type est \(imageExt)")
}
if itemProvider.hasItemConformingToTypeIdentifier(kUTTypeTIFF as String) {
imageExt = ".tiff"
print ("le type est \(imageExt)")
}
var myData: Data? = nil
itemProvider.loadItem(forTypeIdentifier: kUTTypeImage as String){ [unowned self] (data, error) in
//let myImage: UIImage?
switch data {
case let image as UIImage:
//myImage = image
myData = UIImagePNGRepresentation(image)
imageExt = ".png"
case let data as Data:
//myImage = UIImage(data: data)
myData = data
case let url as URL:
//let imageData = NSData(contentsOf: url.absoluteURL)
//myImage = UIImage(data: imageData! as Data)
//let sourcePath = Bundle.main.path(forResource: url.absoluteString, ofType: "gif")
//print ("Le source path est \(type(of: sourcePath))")
do{
try myData = Data(contentsOf: url)
}catch let error{
print ("Error \(error)")
}
default:
//There may be other cases...
print("Unexpected data:", type(of: data))
//myImage = nil
}
//imageName is set depending on the extension
let myImageName = imageName.appending(imageExt)
print ("final name is \(myImageName)")
self.sendToServer(imageData: myData!, imageName: myImageName)
}
} else if itemProvider.hasItemConformingToTypeIdentifier("public.movie") {
let pre = NSLocale.preferredLanguages[0]
var message = String()
if pre.hasPrefix("fr-") {
message = "Annuler"
}
else{
message = "Tap to cancel"
}
progressHUD = MBProgressHUD.showAdded(to: self.view, animated: true)
progressHUD.mode = MBProgressHUDMode.determinate
progressHUD.detailsLabel.text = message
let tap = UITapGestureRecognizer(target: self, action: #selector(self.cancelButton))
progressHUD.addGestureRecognizer(tap)
itemProvider.loadItem(forTypeIdentifier: "public.movie", options: nil, completionHandler: { (url, error) in
//////TOUT ÇA EST À CORRIGER, ce n'est pas propre ///////////////
var urlString = url.debugDescription as! String
var urlString2 : String?
urlString2 = urlString.replacingOccurrences(of: "Optional(file://", with: "")
urlString2 = urlString2?.replacingOccurrences(of: ")", with: "")
//////TOUT ÇA EST À CORRIGER ///////////////
print("Video Selected")
let appGroupDirectory = self.appGroupContainerURL()
let frameCount = 64
let delayTime = Float(0.2)
let loopCount = 0 // 0 means loop forever
let fnameTmp = self.generateRandomStringWithLength(length: 8)
let fname = fnameTmp+".jpg"
let fnameGif = appGroupDirectory?.appendingPathComponent(fnameTmp+".gif")
Regift.createGIFFromSource(url as! URL, destinationFileURL : fnameGif, frameCount: frameCount, delayTime: delayTime, loopCount: loopCount) { (result) in
print("Gif saved to \(result)")
}
let snapshot = self.videoSnapshot(filePathLocal: urlString2! as NSString)
let jpgImageData = UIImageJPEGRepresentation(snapshot!, 0.4)!
let newFname = fnameTmp+".gif"
let mimetype = "image/gif"
//dataToSend = regift
var dataToSend = Data()
do {
dataToSend = try NSData(contentsOf: fnameGif!) as Data
} catch {
print(error)
return
}
let fileManager = FileManager.default
do {
if fileManager.fileExists(atPath: (fnameGif?.path)!) {
try fileManager.removeItem(atPath: (fnameGif?.path)!)
}
} catch let error as NSError {
print(error.debugDescription)
}
let filePath = appGroupDirectory?.appendingPathComponent(fname)
do{
try jpgImageData.write(to: (filePath)!)
}catch let error{
print ("Error \(error)")
}
self.sendToServer(imageData: dataToSend, imageName: newFname)
})
}
}
else{
DispatchQueue.main.async(execute: {
let noInternetHud = MBProgressHUD.showAdded(to: self.view, animated: true)
noInternetHud.mode = MBProgressHUDMode.text
noInternetHud.label.text = "No Internet Available"
noInternetHud.hide(animated: true, afterDelay: 2)
})
}
}
}
}