diff --git a/MyQrCode/Views/QRCodeStyleView.swift b/MyQrCode/Views/QRCodeStyleView.swift index 7f02d80..b1104dd 100644 --- a/MyQrCode/Views/QRCodeStyleView.swift +++ b/MyQrCode/Views/QRCodeStyleView.swift @@ -2,6 +2,32 @@ import SwiftUI import QRCode import CoreData +// MARK: - 标签类型枚举 +enum TabType: String, CaseIterable { + case colors = "colors" + case dots = "dots" + case eyes = "eyes" + case logos = "logos" + + var displayName: String { + switch self { + case .colors: return "颜色" + case .dots: return "点类型" + case .eyes: return "眼睛" + case .logos: return "Logo" + } + } + + var iconName: String { + switch self { + case .colors: return "paintpalette" + case .dots: return "circle.grid.3x3" + case .eyes: return "eye" + case .logos: return "photo" + } + } +} + // MARK: - 自定义二维码样式界面 struct QRCodeStyleView: View { let qrCodeContent: String @@ -25,6 +51,9 @@ struct QRCodeStyleView: View { @State private var qrCodeImage: UIImage? @State private var isLoading = false + // 选中的标签类型 + @State private var selectedTabType: TabType = .colors + // 创建QRCode文档 private func createQRCodeDocument() -> QRCode.Document { let d = try! QRCode.Document(engine: QRCodeEngineExternal()) @@ -95,6 +124,69 @@ struct QRCodeStyleView: View { // MARK: - 样式选择区域 private var styleSelectionSection: some View { + VStack(spacing: 0) { + // 标签类型选择 + tabTypeSelection + + // 内容区域 + contentArea + } + .background(Color(.systemGroupedBackground)) + } + + // MARK: - 标签类型选择 + private var tabTypeSelection: some View { + HStack(spacing: 0) { + ForEach(TabType.allCases, id: \.self) { tabType in + Button(action: { + selectedTabType = tabType + }) { + VStack(spacing: 4) { + Image(systemName: tabType.iconName) + .font(.system(size: 20)) + .foregroundColor(selectedTabType == tabType ? .blue : .gray) + + Text(tabType.displayName) + .font(.caption) + .foregroundColor(selectedTabType == tabType ? .blue : .gray) + } + .frame(maxWidth: .infinity) + .padding(.vertical, 12) + .background( + Rectangle() + .fill(selectedTabType == tabType ? Color.blue.opacity(0.1) : Color.clear) + ) + } + } + } + .background(Color(.systemBackground)) + .overlay( + Rectangle() + .frame(height: 1) + .foregroundColor(Color(.separator)), + alignment: .bottom + ) + } + + // MARK: - 内容区域 + private var contentArea: some View { + Group { + switch selectedTabType { + case .colors: + colorsContent + case .dots: + dotsContent + case .eyes: + eyesContent + case .logos: + logosContent + } + } + .frame(maxHeight: 400) + } + + // MARK: - 颜色内容 + private var colorsContent: some View { ScrollView { VStack(spacing: 24) { // 前景色选择 @@ -110,59 +202,21 @@ struct QRCodeStyleView: View { colors: QRCodeColor.backgroundColors, selectedColor: $selectedBackgroundColor ) - - // 点类型选择 - dotTypeSelectionSection - - // 眼睛类型选择 - eyeTypeSelectionSection - - // Logo选择 - logoSelectionSection } .padding() } - .background(Color(.systemGroupedBackground)) - } - - // MARK: - 颜色选择区域 - private func colorSelectionSection( - title: String, - colors: [QRCodeColor], - selectedColor: Binding - ) -> some View { - VStack(alignment: .leading, spacing: 12) { - Text(title) - .font(.headline) - .foregroundColor(.primary) - - LazyVGrid(columns: Array(repeating: GridItem(.flexible()), count: 6), spacing: 12) { - ForEach(colors, id: \.self) { color in - Button(action: { - selectedColor.wrappedValue = color - }) { - RoundedRectangle(cornerRadius: 8) - .fill(color.color) - .frame(height: 40) - .overlay( - RoundedRectangle(cornerRadius: 8) - .stroke(selectedColor.wrappedValue == color ? Color.blue : Color.clear, lineWidth: 3) - ) - } - } - } - } } - // MARK: - 点类型选择区域 - private var dotTypeSelectionSection: some View { - VStack(alignment: .leading, spacing: 12) { - Text("点类型") - .font(.headline) - .foregroundColor(.primary) - - ScrollView(.horizontal, showsIndicators: false) { - HStack(spacing: 12) { + // MARK: - 点类型内容 + private var dotsContent: some View { + ScrollView { + VStack(spacing: 16) { + Text("选择点类型") + .font(.title2) + .fontWeight(.bold) + .padding(.top) + + LazyVGrid(columns: Array(repeating: GridItem(.flexible()), count: 3), spacing: 16) { ForEach(QRCodeDotType.allCases, id: \.self) { dotType in Button(action: { selectedDotType = dotType @@ -172,16 +226,16 @@ struct QRCodeStyleView: View { Image(uiImage: image) .resizable() .aspectRatio(contentMode: .fit) - .frame(width: 40, height: 40) + .frame(width: 60, height: 60) .background(Color.white) - .cornerRadius(8) + .cornerRadius(12) } else { - RoundedRectangle(cornerRadius: 8) + RoundedRectangle(cornerRadius: 12) .fill(Color.gray.opacity(0.3)) - .frame(width: 40, height: 40) + .frame(width: 60, height: 60) .overlay( Text("?") - .font(.caption) + .font(.title2) .foregroundColor(.secondary) ) } @@ -189,14 +243,15 @@ struct QRCodeStyleView: View { Text(dotType.displayName) .font(.caption) .foregroundColor(.primary) + .multilineTextAlignment(.center) } - .padding(8) + .padding(12) .background( - RoundedRectangle(cornerRadius: 12) + RoundedRectangle(cornerRadius: 16) .fill(selectedDotType == dotType ? Color.blue.opacity(0.1) : Color.clear) .overlay( - RoundedRectangle(cornerRadius: 12) - .stroke(selectedDotType == dotType ? Color.blue : Color.clear, lineWidth: 2) + RoundedRectangle(cornerRadius: 16) + .stroke(selectedDotType == dotType ? Color.blue : Color.clear, lineWidth: 3) ) ) } @@ -207,15 +262,16 @@ struct QRCodeStyleView: View { } } - // MARK: - 眼睛类型选择区域 - private var eyeTypeSelectionSection: some View { - VStack(alignment: .leading, spacing: 12) { - Text("眼睛类型") - .font(.headline) - .foregroundColor(.primary) - - ScrollView(.horizontal, showsIndicators: false) { - HStack(spacing: 12) { + // MARK: - 眼睛类型内容 + private var eyesContent: some View { + ScrollView { + VStack(spacing: 16) { + Text("选择眼睛类型") + .font(.title2) + .fontWeight(.bold) + .padding(.top) + + LazyVGrid(columns: Array(repeating: GridItem(.flexible()), count: 3), spacing: 16) { ForEach(QRCodeEyeType.allCases, id: \.self) { eyeType in Button(action: { selectedEyeType = eyeType @@ -225,16 +281,16 @@ struct QRCodeStyleView: View { Image(uiImage: image) .resizable() .aspectRatio(contentMode: .fit) - .frame(width: 40, height: 40) + .frame(width: 60, height: 60) .background(Color.white) - .cornerRadius(8) + .cornerRadius(12) } else { - RoundedRectangle(cornerRadius: 8) + RoundedRectangle(cornerRadius: 12) .fill(Color.gray.opacity(0.3)) - .frame(width: 40, height: 40) + .frame(width: 60, height: 60) .overlay( Text("?") - .font(.caption) + .font(.title2) .foregroundColor(.secondary) ) } @@ -242,14 +298,15 @@ struct QRCodeStyleView: View { Text(eyeType.displayName) .font(.caption) .foregroundColor(.primary) + .multilineTextAlignment(.center) } - .padding(8) + .padding(12) .background( - RoundedRectangle(cornerRadius: 12) + RoundedRectangle(cornerRadius: 16) .fill(selectedEyeType == eyeType ? Color.blue.opacity(0.1) : Color.clear) .overlay( - RoundedRectangle(cornerRadius: 12) - .stroke(selectedEyeType == eyeType ? Color.blue : Color.clear, lineWidth: 2) + RoundedRectangle(cornerRadius: 16) + .stroke(selectedEyeType == eyeType ? Color.blue : Color.clear, lineWidth: 3) ) ) } @@ -260,40 +317,42 @@ struct QRCodeStyleView: View { } } - // MARK: - Logo选择区域 - private var logoSelectionSection: some View { - VStack(alignment: .leading, spacing: 12) { - Text("Logo") - .font(.headline) - .foregroundColor(.primary) - - ScrollView(.horizontal, showsIndicators: false) { - HStack(spacing: 12) { + // MARK: - Logo内容 + private var logosContent: some View { + ScrollView { + VStack(spacing: 16) { + Text("选择Logo") + .font(.title2) + .fontWeight(.bold) + .padding(.top) + + LazyVGrid(columns: Array(repeating: GridItem(.flexible()), count: 3), spacing: 16) { // 无Logo选项 Button(action: { selectedLogo = nil }) { VStack(spacing: 8) { - RoundedRectangle(cornerRadius: 8) + RoundedRectangle(cornerRadius: 12) .fill(Color.gray.opacity(0.3)) - .frame(width: 40, height: 40) + .frame(width: 60, height: 60) .overlay( Text("无") - .font(.caption) + .font(.title2) .foregroundColor(.secondary) ) Text("无Logo") .font(.caption) .foregroundColor(.primary) + .multilineTextAlignment(.center) } - .padding(8) + .padding(12) .background( - RoundedRectangle(cornerRadius: 12) + RoundedRectangle(cornerRadius: 16) .fill(selectedLogo == nil ? Color.blue.opacity(0.1) : Color.clear) .overlay( - RoundedRectangle(cornerRadius: 12) - .stroke(selectedLogo == nil ? Color.blue : Color.clear, lineWidth: 2) + RoundedRectangle(cornerRadius: 16) + .stroke(selectedLogo == nil ? Color.blue : Color.clear, lineWidth: 3) ) ) } @@ -308,16 +367,16 @@ struct QRCodeStyleView: View { Image(uiImage: image) .resizable() .aspectRatio(contentMode: .fit) - .frame(width: 40, height: 40) + .frame(width: 60, height: 60) .background(Color.white) - .cornerRadius(8) + .cornerRadius(12) } else { - RoundedRectangle(cornerRadius: 8) + RoundedRectangle(cornerRadius: 12) .fill(Color.gray.opacity(0.3)) - .frame(width: 40, height: 40) + .frame(width: 60, height: 60) .overlay( Text("?") - .font(.caption) + .font(.title2) .foregroundColor(.secondary) ) } @@ -325,14 +384,15 @@ struct QRCodeStyleView: View { Text(logo.displayName) .font(.caption) .foregroundColor(.primary) + .multilineTextAlignment(.center) } - .padding(8) + .padding(12) .background( - RoundedRectangle(cornerRadius: 12) + RoundedRectangle(cornerRadius: 16) .fill(selectedLogo == logo ? Color.blue.opacity(0.1) : Color.clear) .overlay( - RoundedRectangle(cornerRadius: 12) - .stroke(selectedLogo == logo ? Color.blue : Color.clear, lineWidth: 2) + RoundedRectangle(cornerRadius: 16) + .stroke(selectedLogo == logo ? Color.blue : Color.clear, lineWidth: 3) ) ) } @@ -343,6 +403,37 @@ struct QRCodeStyleView: View { } } + // MARK: - 颜色选择区域 + private func colorSelectionSection( + title: String, + colors: [QRCodeColor], + selectedColor: Binding + ) -> some View { + VStack(alignment: .leading, spacing: 12) { + Text(title) + .font(.headline) + .foregroundColor(.primary) + + LazyVGrid(columns: Array(repeating: GridItem(.flexible()), count: 6), spacing: 12) { + ForEach(colors, id: \.self) { color in + Button(action: { + selectedColor.wrappedValue = color + }) { + RoundedRectangle(cornerRadius: 8) + .fill(color.color) + .frame(height: 40) + .overlay( + RoundedRectangle(cornerRadius: 8) + .stroke(selectedColor.wrappedValue == color ? Color.blue : Color.clear, lineWidth: 3) + ) + } + } + } + } + } + + + // MARK: - 保存二维码 private func saveQRCode() { guard let qrCodeImage = qrCodeImage else { return }