相册选择MOV文件无响应及多格式文件支持技术求助
解决UIImagePickerController选择MOV无响应问题,并支持多格式文件选择
咱们先搞定你当前遇到的MOV文件无响应问题,再扩展实现你需要的全格式文件支持需求。
一、排查并修复MOV选择无响应问题
你提到iPhone拍摄的MOV正常,但保存到手机的MOV会导致界面卡住、回调不触发,大概率是这两个核心原因:
- 主线程被阻塞:如果在
didFinishPickingMediaWithInfo的闭包里处理MOV文件时做了解码、大文件拷贝这类耗时操作,会直接卡死主线程,导致取消按钮和回调都失效; - 媒体类型配置不明确:未指定
UIImagePickerController的mediaTypes,部分非系统拍摄的MOV可能因UTI识别异常无法触发回调。
调整后的修复代码
把耗时操作移到后台线程,避免阻塞主线程,同时明确配置支持的媒体类型:
// 修复后的picker回调 func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) { dismiss(animated: true) { guard let mediaType = info[.mediaType] as? String else { return } if mediaType == kUTTypeImage as String, let pickedImage = info[.originalImage] as? UIImage { // 图片处理逻辑移到后台 DispatchQueue.global().async { // 这里写你的图片处理代码 DispatchQueue.main.async { self.updateProgress() self.collection.reloadData() } } } else if mediaType == kUTTypeMovie as String { // MOV文件处理必须放后台线程 DispatchQueue.global().async { guard let movieURL = info[.mediaURL] as? URL else { return } // 这里写你的MOV文件处理逻辑(比如拷贝、转码) DispatchQueue.main.async { self.updateProgress() self.collection.reloadData() } } } } } func imagePickerControllerDidCancel(_ picker: UIImagePickerController) { dismiss(animated: true, completion: nil) } // 初始化picker时明确指定支持的媒体类型 let iPicker = UIImagePickerController() iPicker.delegate = self iPicker.mediaTypes = [kUTTypeImage as String, kUTTypeMovie as String]
二、扩展支持所有需要的文件格式
注意:UIImagePickerController仅支持图片和视频类文件,你需要的zip、doc、pdf等文档格式,必须使用系统提供的UIDocumentPickerViewController来实现,这是处理全格式文件选择的标准方案。
1. 初始化文档选择器
func presentDocumentPicker() { // 定义你需要支持的文件UTI列表(对应你的目标格式) let supportedUTIs = [ "com.pkware.zip-archive", // zip "com.microsoft.word.doc", // doc "com.microsoft.outlook.msg", // msg "public.jpeg", // jpg/jpeg "public.avi", // avi "com.microsoft.powerpoint.pps", // pps "public.gif", // gif "public.png", // png "com.microsoft.excel.xls", // xls "public.comma-separated-values-text", // csv "com.adobe.pdf", // pdf "public.plain-text", // txt "com.microsoft.powerpoint.ppt", // ppt "public.tiff", // tiff/tif "com.autodesk.dwg" // dwg ] let documentPicker = UIDocumentPickerViewController( forOpeningContentTypes: supportedUTIs.compactMap { UTType($0) } ) documentPicker.delegate = self documentPicker.allowsMultipleSelection = false // 根据需求设置是否允许多选 present(documentPicker, animated: true) }
2. 实现文档选择器代理方法
extension YourViewController: UIDocumentPickerDelegate { func documentPicker(_ controller: UIDocumentPickerViewController, didPickDocumentsAt urls: [URL]) { guard let fileURL = urls.first else { return } // 文档选择器返回的是临时沙盒URL,需要拷贝到APP自己的目录保存 DispatchQueue.global().async { let destinationDir = self.getAppDocumentDirectory() let destinationURL = destinationDir.appendingPathComponent(fileURL.lastPathComponent) do { // 先删除已存在的同名文件 if FileManager.default.fileExists(atPath: destinationURL.path) { try FileManager.default.removeItem(at: destinationURL) } // 拷贝文件到本地 try FileManager.default.copyItem(at: fileURL, to: destinationURL) // 根据文件类型执行对应处理逻辑 self.handleFile(at: destinationURL) DispatchQueue.main.async { self.updateProgress() self.collection.reloadData() } } catch { print("文件处理失败:\(error.localizedDescription)") DispatchQueue.main.async { // 这里可以给用户弹出错误提示 } } } } func documentPickerWasCancelled(_ controller: UIDocumentPickerViewController) { dismiss(animated: true, completion: nil) } // 辅助方法:获取APP的文档目录 private func getAppDocumentDirectory() -> URL { return FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first! } // 根据文件后缀处理不同类型的文件 private func handleFile(at url: URL) { let fileExt = url.pathExtension.lowercased() switch fileExt { case "jpg", "jpeg", "png", "gif", "tiff", "tif": // 处理图片逻辑 if let image = UIImage(contentsOfFile: url.path) { // do something with image } case "avi", "mov": // 处理视频逻辑 // do something with video URL case "doc", "xls", "ppt", "pps", "pdf", "txt", "csv", "zip", "msg", "dwg": // 处理文档/压缩包等逻辑 // do something with document URL default: break } } }
总结
- 先通过后台线程处理耗时操作+明确配置媒体类型修复当前MOV选择无响应的问题;
- 迁移到
UIDocumentPickerViewController实现全格式支持,这是系统推荐的文档类文件选择方案,既能覆盖你所有目标格式,也能避免UIImagePicker的功能局限性。
内容的提问来源于stack exchange,提问作者user2363025




