PadXcode-iPad/Layout/BuildToolbar.swift

104 lines
4.2 KiB
Swift
Raw Normal View History

2026-04-12 00:46:30 -07:00
import SwiftUI
struct BuildToolbar: View {
let scheme: String
let devices: [ConnectedDevice]
@Binding var selectedDevice: ConnectedDevice?
let isBuilding: Bool
let buildService: BuildService
let onBuild: () -> Void
let onRun: () -> Void
let onRefreshDevices: () -> Void
var onFindInProject: (() -> Void)? = nil
@State private var showHistory = false
var body: some View {
HStack(spacing: 10) {
Label(scheme, systemImage: "hammer")
.font(.system(.subheadline, design: .monospaced))
.foregroundStyle(.secondary).lineLimit(1)
Spacer()
// Device picker
Menu {
Button {
selectedDevice = nil
} label: {
HStack {
Image(systemName: "hammer"); Text("Build Only (No Device)")
if selectedDevice == nil { Image(systemName: "checkmark") }
}
}
Divider()
if devices.isEmpty {
Label("No devices paired", systemImage: "exclamationmark.triangle")
.foregroundStyle(.secondary)
} else {
ForEach(devices) { device in
Button {
selectedDevice = device
} label: {
HStack {
Image(systemName: device.isNetworkConnected
? "iphone.radiowaves.left.and.right" : "iphone")
VStack(alignment: .leading) {
Text(device.name)
Text("\(device.model) · \(device.osVersion)").font(.caption)
}
if selectedDevice?.udid == device.udid { Image(systemName: "checkmark") }
}
}
}
}
Divider()
Button(action: onRefreshDevices) { Label("Refresh Devices", systemImage: "arrow.clockwise") }
} label: {
if let d = selectedDevice {
Label(d.name, systemImage: d.isNetworkConnected ? "iphone.radiowaves.left.and.right" : "iphone")
.font(.subheadline)
} else {
Label("No Device", systemImage: "iphone.slash")
.font(.subheadline).foregroundStyle(.secondary)
}
}
Divider().frame(height: 20)
Button(action: onBuild) {
Label("Build", systemImage: "hammer.fill").font(.subheadline.bold())
}
.disabled(isBuilding).buttonStyle(.bordered)
.keyboardShortcut("b", modifiers: .command)
Button(action: onRun) {
HStack(spacing: 5) {
if isBuilding { ProgressView().scaleEffect(0.7).tint(.white) }
else { Image(systemName: "play.fill") }
Text(isBuilding ? "Building…" : "Run").font(.subheadline.bold())
}
}
.disabled(isBuilding || selectedDevice == nil)
.buttonStyle(.borderedProminent)
.tint(isBuilding || selectedDevice == nil ? .secondary : .green)
.keyboardShortcut("r", modifiers: .command)
Divider().frame(height: 20)
if let findAction = onFindInProject {
Button(action: findAction) { Image(systemName: "magnifyingglass") }
.buttonStyle(.plain).foregroundStyle(.secondary).help("Find in Project ⌘⇧F")
}
Button { showHistory = true } label: { Image(systemName: "clock.arrow.circlepath") }
.buttonStyle(.plain).foregroundStyle(.secondary).help("Build History")
.sheet(isPresented: $showHistory) { BuildHistoryView(historyStore: buildService.historyStore) }
DaemonStatusIndicator(monitor: buildService.healthMonitor)
}
.padding(.horizontal, 14).padding(.vertical, 8)
.background(.bar)
}
}