从 iOS 17 Observation 迁移至 iOS 16 兼容的 Combine 架构
将最低部署版本降至 iOS 16,以 ObservableObject 替换 @Observable,新增导航与 UI 兼容层,并补充登录冒烟 UI 测试。 Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@ -6,20 +6,19 @@
|
||||
//
|
||||
|
||||
import Foundation
|
||||
import Observation
|
||||
import Combine
|
||||
|
||||
@MainActor
|
||||
@Observable
|
||||
/// 押金订单列表 ViewModel,负责分页、核销、退款和操作后刷新。
|
||||
final class DepositOrderListViewModel {
|
||||
private(set) var orders: [DepositOrderListItem] = []
|
||||
private(set) var total = 0
|
||||
private(set) var page = 1
|
||||
private(set) var hasMore = false
|
||||
private(set) var loading = false
|
||||
private(set) var loadingMore = false
|
||||
private(set) var operatingOrderNumber: String?
|
||||
var errorMessage: String?
|
||||
final class DepositOrderListViewModel: ObservableObject {
|
||||
@Published private(set) var orders: [DepositOrderListItem] = []
|
||||
@Published private(set) var total = 0
|
||||
@Published private(set) var page = 1
|
||||
@Published private(set) var hasMore = false
|
||||
@Published private(set) var loading = false
|
||||
@Published private(set) var loadingMore = false
|
||||
@Published private(set) var operatingOrderNumber: String?
|
||||
@Published var errorMessage: String?
|
||||
|
||||
private let pageSize = 10
|
||||
|
||||
@ -134,12 +133,11 @@ final class DepositOrderListViewModel {
|
||||
}
|
||||
|
||||
@MainActor
|
||||
@Observable
|
||||
/// 押金订单详情 ViewModel,负责按门店和订单号加载详情。
|
||||
final class DepositOrderDetailViewModel {
|
||||
private(set) var detail: StoreOrderDetailResponse?
|
||||
private(set) var loading = false
|
||||
var errorMessage: String?
|
||||
final class DepositOrderDetailViewModel: ObservableObject {
|
||||
@Published private(set) var detail: StoreOrderDetailResponse?
|
||||
@Published private(set) var loading = false
|
||||
@Published var errorMessage: String?
|
||||
|
||||
/// 加载押金订单详情,缺少门店或订单号时不请求接口。
|
||||
func load(api: OrderServing, storeId: Int?, orderNumber: String) async {
|
||||
@ -179,12 +177,11 @@ final class DepositOrderDetailViewModel {
|
||||
}
|
||||
|
||||
@MainActor
|
||||
@Observable
|
||||
/// 押金拍摄信息 ViewModel,负责加载单个打卡点的媒体和评分。
|
||||
final class DepositOrderShootingInfoViewModel {
|
||||
private(set) var detail: StoreOrderShootingDetailResponse?
|
||||
private(set) var loading = false
|
||||
var errorMessage: String?
|
||||
final class DepositOrderShootingInfoViewModel: ObservableObject {
|
||||
@Published private(set) var detail: StoreOrderShootingDetailResponse?
|
||||
@Published private(set) var loading = false
|
||||
@Published var errorMessage: String?
|
||||
|
||||
/// 加载押金订单拍摄信息,缺少门店或订单号时不请求接口。
|
||||
func load(api: OrderServing, storeId: Int?, orderNumber: String, scenicSpotId: Int, photogUid: Int) async {
|
||||
@ -229,14 +226,13 @@ final class DepositOrderShootingInfoViewModel {
|
||||
}
|
||||
|
||||
@MainActor
|
||||
@Observable
|
||||
/// 普通订单退款 ViewModel,负责退款入口判断、金额校验和提交保护。
|
||||
final class OrderRefundViewModel {
|
||||
var mode: OrderRefundMode = .full
|
||||
var amount = ""
|
||||
var reason = ""
|
||||
private(set) var submitting = false
|
||||
var errorMessage: String?
|
||||
final class OrderRefundViewModel: ObservableObject {
|
||||
@Published var mode: OrderRefundMode = .full
|
||||
@Published var amount = ""
|
||||
@Published var reason = ""
|
||||
@Published private(set) var submitting = false
|
||||
@Published var errorMessage: String?
|
||||
|
||||
/// 判断订单是否允许展示普通退款入口。
|
||||
func canRefund(_ item: OrderEntity) -> Bool {
|
||||
@ -344,14 +340,13 @@ final class OrderRefundViewModel {
|
||||
}
|
||||
|
||||
@MainActor
|
||||
@Observable
|
||||
/// 历史拍摄 ViewModel,负责按订单号加载多点位历史拍摄媒体。
|
||||
final class HistoricalShootingInfoViewModel {
|
||||
private(set) var projectName = ""
|
||||
private(set) var projectTypeName = ""
|
||||
private(set) var spots: [PhotogSpotItem] = []
|
||||
private(set) var loading = false
|
||||
var errorMessage: String?
|
||||
final class HistoricalShootingInfoViewModel: ObservableObject {
|
||||
@Published private(set) var projectName = ""
|
||||
@Published private(set) var projectTypeName = ""
|
||||
@Published private(set) var spots: [PhotogSpotItem] = []
|
||||
@Published private(set) var loading = false
|
||||
@Published var errorMessage: String?
|
||||
|
||||
/// 加载历史拍摄信息,订单号为空时清空旧数据且不请求接口。
|
||||
func load(api: OrderServing, orderNumber: String) async {
|
||||
@ -390,20 +385,19 @@ final class HistoricalShootingInfoViewModel {
|
||||
}
|
||||
|
||||
@MainActor
|
||||
@Observable
|
||||
/// 多点旅拍任务上传 ViewModel,负责订单号、打卡点、云盘附件、本地附件和素材提交。
|
||||
final class MultiTravelTaskUploadViewModel {
|
||||
var orderNumber = ""
|
||||
var selectedSpotId: Int?
|
||||
private(set) var spots: [MultiTravelVerifiedScenicSpotItem] = []
|
||||
var selectedCloudFiles: [TaskCloudSelectionItem] = []
|
||||
var selectedLocalFiles: [TaskLocalUploadItem] = []
|
||||
private(set) var isLoadingSpots = false
|
||||
private(set) var isSubmitting = false
|
||||
private(set) var didSubmitSuccessfully = false
|
||||
var errorMessage: String?
|
||||
final class MultiTravelTaskUploadViewModel: ObservableObject {
|
||||
@Published var orderNumber = ""
|
||||
@Published var selectedSpotId: Int?
|
||||
@Published private(set) var spots: [MultiTravelVerifiedScenicSpotItem] = []
|
||||
@Published var selectedCloudFiles: [TaskCloudSelectionItem] = []
|
||||
@Published var selectedLocalFiles: [TaskLocalUploadItem] = []
|
||||
@Published private(set) var isLoadingSpots = false
|
||||
@Published private(set) var isSubmitting = false
|
||||
@Published private(set) var didSubmitSuccessfully = false
|
||||
@Published var errorMessage: String?
|
||||
|
||||
private var loadedSpotOrderNumber = ""
|
||||
@Published private var loadedSpotOrderNumber = ""
|
||||
|
||||
/// 当前选中打卡点展示名。
|
||||
var selectedSpotName: String {
|
||||
|
||||
Reference in New Issue
Block a user