
- 在HomeFeature中添加MeDynamicFeature以管理用户动态状态。 - 在MainFeature中集成MeDynamicFeature,支持动态内容的加载与展示。 - 新增MeDynamicView以展示用户的动态列表,支持下拉刷新和上拉加载更多功能。 - 更新MeView以集成用户动态视图,提升用户体验。 - 在APIEndpoints中新增getMyDynamic端点以支持获取用户动态信息。 - 更新DynamicsModels以适应新的动态数据结构,确保数据解析的准确性。 - 在OptimizedDynamicCardView中优化图片处理逻辑,提升动态展示效果。 - 更新相关视图组件以支持动态内容的展示与交互,增强用户体验。
92 lines
3.0 KiB
Swift
92 lines
3.0 KiB
Swift
import Foundation
|
|
import ComposableArchitecture
|
|
|
|
@Reducer
|
|
struct MeDynamicFeature: Reducer {
|
|
struct State: Equatable {
|
|
var uid: Int
|
|
var dynamics: [MomentsInfo] = []
|
|
var page: Int = 1
|
|
var pageSize: Int = 20
|
|
var isLoading: Bool = false
|
|
var isRefreshing: Bool = false
|
|
var isLoadingMore: Bool = false
|
|
var hasMore: Bool = true
|
|
var error: String?
|
|
var isInitialized: Bool = false // 首次加载标记
|
|
}
|
|
|
|
enum Action: Equatable {
|
|
case onAppear
|
|
case refresh
|
|
case loadMore
|
|
case fetchResponse(Result<MyMomentsResponse, APIError>)
|
|
}
|
|
|
|
@Dependency(\.apiService) var apiService
|
|
|
|
func reduce(into state: inout State, action: Action) async -> Effect<Action> {
|
|
switch action {
|
|
case .onAppear:
|
|
guard !state.isInitialized else { return .none }
|
|
state.isInitialized = true
|
|
state.page = 1
|
|
state.dynamics = []
|
|
state.hasMore = true
|
|
state.isLoading = true
|
|
state.error = nil
|
|
return fetchDynamics(uid: state.uid, page: 1, pageSize: state.pageSize)
|
|
case .refresh:
|
|
state.page = 1
|
|
state.hasMore = true
|
|
state.isRefreshing = true
|
|
state.error = nil
|
|
state.isInitialized = false // 允许刷新后重新加载
|
|
return fetchDynamics(
|
|
uid: state.uid,
|
|
page: 1,
|
|
pageSize: state.pageSize
|
|
)
|
|
case .loadMore:
|
|
guard !state.isLoadingMore, state.hasMore else { return .none }
|
|
state.isLoadingMore = true
|
|
return fetchDynamics(uid: state.uid, page: state.page + 1, pageSize: state.pageSize)
|
|
case let .fetchResponse(result):
|
|
state.isLoading = false
|
|
state.isRefreshing = false
|
|
state.isLoadingMore = false
|
|
switch result {
|
|
case let .success(resp):
|
|
let newDynamics = resp.data ?? []
|
|
if state.page == 1 {
|
|
state.dynamics = newDynamics
|
|
} else {
|
|
state.dynamics += newDynamics
|
|
}
|
|
state.hasMore = newDynamics.count == state.pageSize
|
|
if state.hasMore { state.page += 1 }
|
|
state.error = nil
|
|
case let .failure(error):
|
|
state.error = error.localizedDescription
|
|
}
|
|
return .none
|
|
}
|
|
}
|
|
|
|
private func fetchDynamics(uid: Int, page: Int, pageSize: Int) -> Effect<Action> {
|
|
let apiService = self.apiService
|
|
return .run { send in
|
|
do {
|
|
let req = GetMyDynamicRequest(fromUid: uid, uid: uid, page: page, pageSize: pageSize)
|
|
let resp = try await apiService.request(req)
|
|
await send(.fetchResponse(.success(resp)))
|
|
} catch {
|
|
await send(.fetchResponse(.failure(error as? APIError ?? .unknown(error.localizedDescription))))
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
|