// // ScenicApplicationModels.swift // suixinkan // import Foundation /// 合作类型,对齐 Android `CooperationType`。 enum ScenicCooperationType: Int, CaseIterable, Equatable { case photographer = 1 case resourceProvider = 2 case teamLeader = 3 case photoShop = 4 case efficiencyImprovement = 5 var displayName: String { switch self { case .photographer: "我是摄影师,我想入驻" case .resourceProvider: "我是景区资源方,可以合作" case .teamLeader: "我有摄影师团队,带队入住" case .photoShop: "我是旅拍店,想合作" case .efficiencyImprovement: "我已经在景区运营旅拍了,想使用软件,提高效率" } } static func from(rawValue: Int) -> ScenicCooperationType { ScenicCooperationType(rawValue: rawValue) ?? .photographer } } /// 景区申请待审核记录。 struct ScenicApplicationPendingResponse: Decodable, Equatable { let id: Int let code: String let staffId: Int let scenicId: Int let scenicName: String let scenicImages: String let scenicProvince: String let scenicCity: String let coopType: Int let remark: String? let status: Int let rejectReason: String? let auditedBy: String? let auditedAt: String? let auditNote: String? enum CodingKeys: String, CodingKey { case id case code case staffId = "staff_id" case scenicId = "scenic_id" case scenicName = "scenic_name" case scenicImages = "scenic_images" case scenicProvince = "scenic_province" case scenicCity = "scenic_city" case coopType = "coop_type" case remark case status case rejectReason = "reject_reason" case auditedBy = "audited_by" case auditedAt = "audited_at" case auditNote = "audit_note" } init(from decoder: Decoder) throws { let container = try decoder.container(keyedBy: CodingKeys.self) id = try container.decodeIfPresent(Int.self, forKey: .id) ?? 0 code = try container.decodeIfPresent(String.self, forKey: .code) ?? "" staffId = try container.decodeIfPresent(Int.self, forKey: .staffId) ?? 0 scenicId = try container.decodeIfPresent(Int.self, forKey: .scenicId) ?? 0 scenicName = try container.decodeIfPresent(String.self, forKey: .scenicName) ?? "" scenicImages = try container.decodeIfPresent(String.self, forKey: .scenicImages) ?? "" scenicProvince = try container.decodeIfPresent(String.self, forKey: .scenicProvince) ?? "" scenicCity = try container.decodeIfPresent(String.self, forKey: .scenicCity) ?? "" coopType = try container.decodeIfPresent(Int.self, forKey: .coopType) ?? 0 remark = try container.decodeIfPresent(String.self, forKey: .remark) status = try container.decodeIfPresent(Int.self, forKey: .status) ?? 0 rejectReason = try container.decodeIfPresent(String.self, forKey: .rejectReason) auditedBy = try container.decodeIfPresent(String.self, forKey: .auditedBy) auditedAt = try container.decodeIfPresent(String.self, forKey: .auditedAt) auditNote = try container.decodeIfPresent(String.self, forKey: .auditNote) } init( id: Int = 0, code: String = "", staffId: Int = 0, scenicId: Int = 0, scenicName: String = "", scenicImages: String = "", scenicProvince: String = "", scenicCity: String = "", coopType: Int = 0, remark: String? = nil, status: Int = 0, rejectReason: String? = nil, auditedBy: String? = nil, auditedAt: String? = nil, auditNote: String? = nil ) { self.id = id self.code = code self.staffId = staffId self.scenicId = scenicId self.scenicName = scenicName self.scenicImages = scenicImages self.scenicProvince = scenicProvince self.scenicCity = scenicCity self.coopType = coopType self.remark = remark self.status = status self.rejectReason = rejectReason self.auditedBy = auditedBy self.auditedAt = auditedAt self.auditNote = auditNote } } /// 景区申请待审核列表响应。 struct ScenicApplicationPendingsResponse: Decodable, Equatable { let items: [ScenicApplicationPendingResponse] init(items: [ScenicApplicationPendingResponse] = []) { self.items = items } } /// 景区申请提交请求。 struct ScenicApplicationSubmitRequest: Encodable { let scenicName: String? let scenicImages: [String]? let scenicProvince: String let scenicCity: String let coopType: Int let remark: String let scenicId: Int enum CodingKeys: String, CodingKey { case scenicName = "scenic_name" case scenicImages = "scenic_images" case scenicProvince = "scenic_province" case scenicCity = "scenic_city" case coopType = "coop_type" case remark case scenicId = "scenic_id" } } /// 单张景区申请图片的上传状态。 struct ScenicApplicationImageItem: Equatable, Identifiable { let id: UUID var localData: Data? var fileName: String var remoteURL: String var isUploading: Bool var uploadProgress: Int var errorMessage: String? var isUploaded: Bool { !remoteURL.isEmpty } static func fromRemoteURL(_ url: String) -> ScenicApplicationImageItem { let trimmed = url.trimmingCharacters(in: .whitespacesAndNewlines) let name = URL(string: trimmed)?.lastPathComponent ?? "image.jpg" return ScenicApplicationImageItem( id: UUID(), localData: nil, fileName: name, remoteURL: trimmed, isUploading: false, uploadProgress: 100, errorMessage: nil ) } static func fromLocal(data: Data, fileName: String) -> ScenicApplicationImageItem { ScenicApplicationImageItem( id: UUID(), localData: data, fileName: fileName, remoteURL: "", isUploading: false, uploadProgress: 0, errorMessage: nil ) } } /// 图片上传进度弹窗状态。 struct ScenicApplicationUploadDialogState: Equatable { let title: String let progress: Int }