Swift中如何将默认打印机保存至UserDefaults?
解决UIPrinter无法保存到UserDefaults的问题
嘿,这个问题我之前做iOS打印功能的时候也遇到过——UIPrinter确实没法直接存进UserDefaults,不过有两个靠谱的解决方案,能帮你搞定默认打印机的保存和恢复:
方法一:利用UIPrinter的URL属性序列化
UIPrinter本身不支持直接存入UserDefaults,但它提供了一个url属性,这个URL是可序列化的,完全可以安全存储。步骤很简单:
保存选中的打印机
当用户在UIPrinterPickerController中选中打印机后,我们把它的URL存进UserDefaults:
if userDidSelect { if let defaultPrinter = printerPicker.selectedPrinter { UserDefaults.standard.set(defaultPrinter.url, forKey: "DefaultPrinterURL") } }
读取并恢复打印机
下次需要使用默认打印机时,从UserDefaults取出URL,再通过系统方法异步恢复UIPrinter实例:
if let printerURL = UserDefaults.standard.url(forKey: "DefaultPrinterURL") { UIPrinter.printer(with: printerURL) { restoredPrinter in guard let printer = restoredPrinter else { // 打印机不可用,可能需要重新让用户选择 return } // 这里就可以用恢复后的printer直接发起打印了 self.printWithDefaultPrinter(printer) } }
这个方法的好处是系统会自动验证URL对应的打印机是否还可用,避免使用已经离线或被移除的设备。
方法二:通过NSKeyedArchiver归档存储
UIPrinter遵循NSSecureCoding协议,所以我们可以把它归档成Data,再存入UserDefaults:
保存打印机
if userDidSelect { if let defaultPrinter = printerPicker.selectedPrinter { do { let printerData = try NSKeyedArchiver.archivedData( withRootObject: defaultPrinter, requiringSecureCoding: true ) UserDefaults.standard.set(printerData, forKey: "DefaultPrinterData") } catch { print("归档打印机失败:\(error.localizedDescription)") } } }
恢复打印机
if let printerData = UserDefaults.standard.data(forKey: "DefaultPrinterData") { do { if let restoredPrinter = try NSKeyedUnarchiver.unarchivedObject( ofClass: UIPrinter.self, from: printerData ) { // 恢复成功,使用打印机 self.printWithDefaultPrinter(restoredPrinter) } } catch { print("解归档打印机失败:\(error.localizedDescription)") } }
这个方法会保存打印机的更多细节,但如果打印机的网络信息发生变化,可能会出现恢复失败的情况,所以更推荐第一种方法。
直接打印(无需预览弹窗)
恢复默认打印机后,你可以直接用UIPrintInteractionController发起打印,跳过预览弹窗:
func printWithDefaultPrinter(_ printer: UIPrinter) { let printInfo = UIPrintInfo.printInfo() printInfo.outputType = .general // 根据你的打印内容调整类型 printInfo.jobName = "我的打印任务" let printController = UIPrintInteractionController.shared printController.printInfo = printInfo printController.printingItem = // 这里传入你的打印内容,比如PDF Data、UIImage等 printController.printer = printer // 直接发送打印任务,不显示预览 printController.print(to: printer, completionHandler: { (_, success, error) in if let error = error { print("打印出错:\(error.localizedDescription)") } else if success { print("打印任务已发送") } }) }
内容的提问来源于stack exchange,提问作者anas.p
相关产品推荐
相关产品推荐

