feat: 触发生成第一个盲盒
This commit is contained in:
parent
8fb6d5c6b9
commit
e9cdb82b70
111
wake/Utils/ApiClient/BlindBoxApi.swift
Normal file
111
wake/Utils/ApiClient/BlindBoxApi.swift
Normal file
@ -0,0 +1,111 @@
|
|||||||
|
import Foundation
|
||||||
|
|
||||||
|
// MARK: - Generate Blind Box Request Model
|
||||||
|
// struct GenerateBlindBoxRequest: Codable {
|
||||||
|
// let boxType: String
|
||||||
|
// let materialIds: [String]
|
||||||
|
|
||||||
|
// enum CodingKeys: String, CodingKey {
|
||||||
|
// case boxType = "box_type"
|
||||||
|
// case materialIds = "material_ids"
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// MARK: - Generate Blind Box Response Model
|
||||||
|
struct GenerateBlindBoxResponse: Codable {
|
||||||
|
let code: Int
|
||||||
|
let data: BlindBoxDataWrapper?
|
||||||
|
|
||||||
|
struct BlindBoxDataWrapper: Codable {
|
||||||
|
let id: String
|
||||||
|
let boxCode: String
|
||||||
|
let userId: String
|
||||||
|
let name: String
|
||||||
|
let boxType: String
|
||||||
|
let features: String?
|
||||||
|
let resultFile: FileInfo?
|
||||||
|
let status: String
|
||||||
|
let workflowInstanceId: String?
|
||||||
|
let videoGenerateTime: String?
|
||||||
|
let createTime: String
|
||||||
|
let coverFile: FileInfo?
|
||||||
|
let description: String
|
||||||
|
|
||||||
|
// 添加计算属性以获取Int64值
|
||||||
|
var idValue: Int64 { Int64(id) ?? 0 }
|
||||||
|
var userIdValue: Int64 { Int64(userId) ?? 0 }
|
||||||
|
|
||||||
|
struct FileInfo: Codable {
|
||||||
|
let id: String
|
||||||
|
let fileName: String?
|
||||||
|
let url: String?
|
||||||
|
let metadata: [String: String]?
|
||||||
|
|
||||||
|
enum CodingKeys: String, CodingKey {
|
||||||
|
case id
|
||||||
|
case fileName = "file_name"
|
||||||
|
case url
|
||||||
|
case metadata
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
enum CodingKeys: String, CodingKey {
|
||||||
|
case id
|
||||||
|
case boxCode = "box_code"
|
||||||
|
case userId = "user_id"
|
||||||
|
case name
|
||||||
|
case boxType = "box_type"
|
||||||
|
case features
|
||||||
|
case resultFile = "result_file"
|
||||||
|
case status
|
||||||
|
case workflowInstanceId = "workflow_instance_id"
|
||||||
|
case videoGenerateTime = "video_generate_time"
|
||||||
|
case createTime = "create_time"
|
||||||
|
case coverFile = "cover_file"
|
||||||
|
case description
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// MARK: - Blind Box API Client
|
||||||
|
class BlindBoxApi {
|
||||||
|
static let shared = BlindBoxApi()
|
||||||
|
|
||||||
|
private init() {}
|
||||||
|
|
||||||
|
/// 生成盲盒
|
||||||
|
/// - Parameters:
|
||||||
|
/// - boxType: 盲盒类型 (如 "First")
|
||||||
|
/// - materialIds: 素材ID数组
|
||||||
|
/// - completion: 完成回调,返回盲盒数据或错误
|
||||||
|
func generateBlindBox(
|
||||||
|
boxType: String,
|
||||||
|
materialIds: [String],
|
||||||
|
completion: @escaping (Result<GenerateBlindBoxResponse.BlindBoxDataWrapper?, Error>) -> Void
|
||||||
|
) {
|
||||||
|
// 将Codable结构体转换为字典
|
||||||
|
let parameters: [String: Any] = [
|
||||||
|
"box_type": boxType,
|
||||||
|
"material_ids": materialIds
|
||||||
|
]
|
||||||
|
|
||||||
|
NetworkService.shared.postWithToken(
|
||||||
|
path: "/blind_box/generate",
|
||||||
|
parameters: parameters,
|
||||||
|
completion: { (result: Result<GenerateBlindBoxResponse, NetworkError>) in
|
||||||
|
DispatchQueue.main.async {
|
||||||
|
switch result {
|
||||||
|
case .success(let response):
|
||||||
|
if response.code == 0 {
|
||||||
|
completion(.success(response.data))
|
||||||
|
} else {
|
||||||
|
completion(.failure(NetworkError.serverError("服务器返回错误码: \(response.code)")))
|
||||||
|
}
|
||||||
|
case .failure(let error):
|
||||||
|
completion(.failure(error))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
66
wake/Utils/MaterialUpload.swift
Normal file
66
wake/Utils/MaterialUpload.swift
Normal file
@ -0,0 +1,66 @@
|
|||||||
|
import Foundation
|
||||||
|
|
||||||
|
// MARK: - 数据模型
|
||||||
|
struct MaterialRequest: Codable {
|
||||||
|
let fileId: String
|
||||||
|
let previewFileId: String
|
||||||
|
|
||||||
|
enum CodingKeys: String, CodingKey {
|
||||||
|
case fileId = "file_id"
|
||||||
|
case previewFileId = "preview_file_id"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
struct AddMaterialResponse: Codable {
|
||||||
|
let code: Int
|
||||||
|
let data: [String]?
|
||||||
|
}
|
||||||
|
|
||||||
|
// MARK: - 素材上传工具类
|
||||||
|
class MaterialUpload {
|
||||||
|
static let shared = MaterialUpload()
|
||||||
|
|
||||||
|
private init() {}
|
||||||
|
|
||||||
|
/// 添加素材到服务器
|
||||||
|
/// - Parameters:
|
||||||
|
/// - fileId: 文件ID
|
||||||
|
/// - previewFileId: 预览文件ID
|
||||||
|
/// - completion: 完成回调,返回结果ID数组或错误
|
||||||
|
func addMaterial(
|
||||||
|
fileId: String,
|
||||||
|
previewFileId: String,
|
||||||
|
completion: @escaping (Result<[String]?, Error>) -> Void
|
||||||
|
) {
|
||||||
|
// 创建请求数据
|
||||||
|
let materials: [[String: String]] = [[
|
||||||
|
"file_id": fileId,
|
||||||
|
"preview_file_id": previewFileId
|
||||||
|
]]
|
||||||
|
|
||||||
|
// 调试信息:检查参数是否为有效的JSON对象
|
||||||
|
print("🔍 准备发送的参数: \(materials)")
|
||||||
|
|
||||||
|
|
||||||
|
// 使用NetworkService发送请求
|
||||||
|
NetworkService.shared.post(
|
||||||
|
path: "/material",
|
||||||
|
parameters: materials,
|
||||||
|
completion: { (result: Result<AddMaterialResponse, NetworkError>) in
|
||||||
|
DispatchQueue.main.async {
|
||||||
|
switch result {
|
||||||
|
case .success(let response):
|
||||||
|
if response.code == 0 {
|
||||||
|
completion(.success(response.data))
|
||||||
|
} else {
|
||||||
|
completion(.failure(NetworkError.serverError("服务器返回错误码: \(response.code)")))
|
||||||
|
}
|
||||||
|
case .failure(let error):
|
||||||
|
print("❌ 素材上传失败: \(error.localizedDescription)")
|
||||||
|
completion(.failure(error))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
0
wake/View/OnBoarding/SecondBoxUpload.swift
Normal file
0
wake/View/OnBoarding/SecondBoxUpload.swift
Normal file
@ -116,7 +116,7 @@ struct UserInfo: View {
|
|||||||
// Content VStack
|
// Content VStack
|
||||||
VStack(spacing: 20) {
|
VStack(spacing: 20) {
|
||||||
// Title
|
// Title
|
||||||
Text(showUsername ? "Add Your Avatar" : "What's Your Name?")
|
Text(showUsername ? "What's Your Name?" : "Add Your Avatar")
|
||||||
.font(Typography.font(for: .body, family: .quicksandBold))
|
.font(Typography.font(for: .body, family: .quicksandBold))
|
||||||
.frame(maxWidth: .infinity, alignment: .center)
|
.frame(maxWidth: .infinity, alignment: .center)
|
||||||
|
|
||||||
@ -181,11 +181,32 @@ struct UserInfo: View {
|
|||||||
self.userName = userData.username
|
self.userName = userData.username
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 上传头像为素材
|
||||||
|
MaterialUpload.shared.addMaterial(
|
||||||
|
fileId: uploadedFileId ?? "",
|
||||||
|
previewFileId: uploadedFileId ?? ""
|
||||||
|
) { result in
|
||||||
|
switch result {
|
||||||
|
case .success(let data):
|
||||||
|
print("素材添加成功,返回ID: \(data ?? [])")
|
||||||
// 触发盲盒生成
|
// 触发盲盒生成
|
||||||
|
BlindBoxApi.shared.generateBlindBox(
|
||||||
|
boxType: "First",
|
||||||
|
materialIds: data ?? []
|
||||||
|
) { result in
|
||||||
|
switch result {
|
||||||
|
case .success(let blindBoxData):
|
||||||
|
print("✅ 盲盒生成成功: \(blindBoxData?.id ?? "0")")
|
||||||
// 导航到首页盲盒等待用户开启第一个盲盒
|
// 导航到首页盲盒等待用户开启第一个盲盒
|
||||||
Router.shared.navigate(to: .blindBox(mediaType: .image))
|
Router.shared.navigate(to: .blindBox(mediaType: .image))
|
||||||
|
case .failure(let error):
|
||||||
|
print("❌ 盲盒生成失败: \(error.localizedDescription)")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case .failure(let error):
|
||||||
|
print("素材添加失败: \(error.localizedDescription)")
|
||||||
|
}
|
||||||
|
}
|
||||||
case .failure(let error):
|
case .failure(let error):
|
||||||
print("❌ 用户信息更新失败: \(error.localizedDescription)")
|
print("❌ 用户信息更新失败: \(error.localizedDescription)")
|
||||||
self.errorMessage = "更新失败: \(error.localizedDescription)"
|
self.errorMessage = "更新失败: \(error.localizedDescription)"
|
||||||
@ -199,7 +220,8 @@ struct UserInfo: View {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}) {
|
}) {
|
||||||
Text(showUsername ? "Open" : "Continue")
|
// Text(showUsername ? "Open" : "Continue")
|
||||||
|
Text("Continue")
|
||||||
.font(Typography.font(for: .body))
|
.font(Typography.font(for: .body))
|
||||||
.fontWeight(.bold)
|
.fontWeight(.bold)
|
||||||
.frame(maxWidth: .infinity)
|
.frame(maxWidth: .infinity)
|
||||||
|
|||||||
@ -46,10 +46,11 @@ struct WakeApp: App {
|
|||||||
if authState.isAuthenticated {
|
if authState.isAuthenticated {
|
||||||
// 已登录:显示主页面
|
// 已登录:显示主页面
|
||||||
NavigationStack(path: $router.path) {
|
NavigationStack(path: $router.path) {
|
||||||
BlindBoxView(mediaType: .all)
|
// BlindBoxView(mediaType: .all)
|
||||||
.navigationDestination(for: AppRoute.self) { route in
|
// .navigationDestination(for: AppRoute.self) { route in
|
||||||
route.view
|
// route.view
|
||||||
}
|
// }
|
||||||
|
UserInfo()
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// 未登录:显示登录界面
|
// 未登录:显示登录界面
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user