import Foundation let kHeaderFooterFolderPath = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.applicationSupportDirectory, FileManager.SearchPathDomainMask.userDomainMask, true).last?.stringByAppendingPathComponent(Bundle.main.bundleIdentifier!).stringByAppendingPathComponent("headerFooter") let kHeaderFooterPlistPath = kHeaderFooterFolderPath?.stringByAppendingPathComponent("headerFooter.plist") ?? "" let kHeaderFooterRemovedKey = "kHeaderFooterRemovedKey" private let kHeaderFooterInfoSaveKey = "kHeaderFooterInfoSaveKey" let kHeaderFooterManagerInit = "kHeaderFooterManagerInit" class KMHeaderFooterManager: NSObject, NSCoding { var headFooterObjects: [KMHeaderFooterObject] = [] static let defaultManager = KMHeaderFooterManager() override init() { super.init() self.reloadData() } required init?(coder: NSCoder) { if let data = coder.decodeObject(forKey: "headFooterObjects") { headFooterObjects = data as? [KMHeaderFooterObject] ?? [] } } func encode(with coder: NSCoder) { coder.encode(headFooterObjects, forKey: "headFooterObjects") } func reloadData() { do { let pHeadFooterObjects = self.fetchPlistData() self.headFooterObjects = pHeadFooterObjects if let storedData = UserDefaults.standard.value(forKey: kHeaderFooterInfoSaveKey) as? Data { NSKeyedUnarchiver.setClass(KMHeaderFooterObject.self, forClassName: "KMHeaderFooterObject") NSKeyedUnarchiver.setClass(KMHeaderFooterManager.self, forClassName: "KMHeaderFooterManager") if UserDefaults.standard.object(forKey: kHeaderFooterManagerInit) == nil { if let man = NSKeyedUnarchiver.unarchiveObject(with: storedData) as? KMHeaderFooterManager { UserDefaults.standard.set("1", forKey: kHeaderFooterManagerInit) for object in man.headFooterObjects { object.isMigrate = true self.headFooterObjects.append(object) } } self.savePlistData() } } } catch { // 解档失败,处理错误情况 print("Error unarchiving data: \(error)") } } var onlyHeaderFooterObjects: [KMHeaderFooterObject] { return headFooterObjects.filter { !$0.isBates } } var onlyBatesObjects: [KMHeaderFooterObject] { var arr: [KMHeaderFooterObject] = [] for obj in headFooterObjects { if KMDataVersionManager.updateBatesData() { KMDataVersionManager.refrshBatesData(bates: obj) store() } if obj.isBates { arr.append(obj) } } return arr } var dateFormatArray: [String] { return [ "m/d", "m/d/yy", "m/d/yyyy", "mm/dd/yy", "mm/dd/yyyy", "d/m/yy", "d/m/yyyy", "dd/mm/yy", "dd/mm/yyyy", "mm/yy", "mm/yyyy", "m.d.yy", "m.d.yyyy", "mm.dd.yy", "mm.dd.yyyy", "mm.yy", "mm.yyyy", "d.m.yy", "d.m.yyyy", "dd.mm.yy", "dd.mm.yyyy", "yy-mm-dd", "yyyy-mm-dd" ] } func removeHeaderFooter(_ obj: KMHeaderFooterObject) -> Bool { headFooterObjects.removeAll { $0 === obj } store() return true } func removeAllHeaderFooter() -> Bool { headFooterObjects.removeAll() store() return true } func addHeaderFooter(_ obj: KMHeaderFooterObject) -> Bool { headFooterObjects.insert(obj, at: 0) store() return true } func store() { // do { // let encodedObject = try NSKeyedArchiver.archivedData(withRootObject: self, requiringSecureCoding: false) // UserDefaults.standard.set(encodedObject, forKey: kHeaderFooterInfoSaveKey) // UserDefaults.standard.synchronize() // } catch { // print("Error while encoding object: \(error)") // } self.savePlistData() } func clearStored() { UserDefaults.standard.removeObject(forKey: kHeaderFooterInfoSaveKey) UserDefaults.standard.synchronize() try?FileManager.default.removeItem(atPath: kHeaderFooterPlistPath) } func fetchHeaderFooterAvailableName() -> String { var availableIndex = 0 let nameArray = onlyHeaderFooterObjects.map { $0.id } for string in nameArray { if string.hasPrefix("HeaderFooter") { let index = Int(string.suffix(from: "HeaderFooter".endIndex)) ?? 0 if index >= availableIndex { availableIndex = index + 1 } } } return "HeaderFooter\(availableIndex)" } func fetchBatesAvailableName() -> String { var availableIndex = 0 let nameArray = onlyBatesObjects.map { $0.id } for string in nameArray { if string.hasPrefix("Bates") { let index = Int(string.suffix(from: "Bates".endIndex)) ?? 0 if index >= availableIndex { availableIndex = index + 1 } } } return "Bates\(availableIndex)" } } extension KMHeaderFooterManager { func fetchPlistData() -> [KMHeaderFooterObject] { if (!FileManager.default.fileExists(atPath: kHeaderFooterFolderPath!)) { try?FileManager.default.createDirectory(atPath: kHeaderFooterFolderPath!, withIntermediateDirectories: false) } if (!FileManager.default.fileExists(atPath: kHeaderFooterPlistPath)) { FileManager.default.createFile(atPath: kHeaderFooterPlistPath, contents: nil) } print("页眉页脚文件地址 =" + kHeaderFooterPlistPath) let plistData = try NSData(contentsOfFile: kHeaderFooterPlistPath) // 解档 plist 数据 if let headerFooterObjects = try NSKeyedUnarchiver.unarchiveObject(with: plistData as! Data) as? [KMHeaderFooterObject] { // 如果解档成功,可以使用 headerFooterObject print("Header footer object: \(headerFooterObjects)") return headerFooterObjects } else { print("Failed to unarchive header footer object") return [] } } func savePlistData() { // 获取 KMHeaderFooterObject 对象的归档数据 if let archivedData = try? NSKeyedArchiver.archivedData(withRootObject: headFooterObjects, requiringSecureCoding: false) { // 将数据写入 plist 文件 let plistURL = URL(fileURLWithPath: kHeaderFooterPlistPath) do { try archivedData.write(to: plistURL) print("Header footer object saved to plist file") } catch { print("Error writing plist file: \(error)") } } else { print("Failed to archive header footer object") } } }