VMWizardOSOtherView.swift 3.4 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192
  1. //
  2. // Copyright © 2021 osy. All rights reserved.
  3. //
  4. // Licensed under the Apache License, Version 2.0 (the "License");
  5. // you may not use this file except in compliance with the License.
  6. // You may obtain a copy of the License at
  7. //
  8. // http://www.apache.org/licenses/LICENSE-2.0
  9. //
  10. // Unless required by applicable law or agreed to in writing, software
  11. // distributed under the License is distributed on an "AS IS" BASIS,
  12. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. // See the License for the specific language governing permissions and
  14. // limitations under the License.
  15. //
  16. import SwiftUI
  17. struct VMWizardOSOtherView: View {
  18. @ObservedObject var wizardState: VMWizardState
  19. @State private var isFileImporterPresented: Bool = false
  20. private var supportsUefi: Bool {
  21. UTMQemuConfigurationQEMU.uefiImagePrefix(forArchitecture: wizardState.systemArchitecture) != nil
  22. }
  23. var body: some View {
  24. VMWizardContent("Other") {
  25. Picker("Boot Device", selection: $wizardState.bootDevice) {
  26. Text("None").tag(VMBootDevice.none)
  27. Text("CD/DVD Image").tag(VMBootDevice.cd)
  28. if wizardState.legacyHardware {
  29. Text("Floppy Image").tag(VMBootDevice.floppy)
  30. }
  31. Text("Drive Image").tag(VMBootDevice.drive)
  32. }.pickerStyle(.inline)
  33. .onAppear {
  34. if !wizardState.legacyHardware && wizardState.bootDevice == .floppy {
  35. wizardState.bootDevice = .none
  36. } else if wizardState.legacyHardware {
  37. wizardState.systemBootUefi = false
  38. }
  39. }
  40. if wizardState.bootDevice != .none {
  41. Section {
  42. FileBrowseField(url: $wizardState.bootImageURL, isFileImporterPresented: $isFileImporterPresented, hasClearButton: false)
  43. .padding(.leading, 1)
  44. if wizardState.isBusy {
  45. Spinner(size: .large)
  46. }
  47. } header: {
  48. if wizardState.bootDevice == .cd {
  49. Text("Boot ISO Image")
  50. } else if wizardState.bootDevice == .drive {
  51. Text("Import Disk Image")
  52. } else {
  53. Text("Boot IMG Image")
  54. }
  55. }
  56. }
  57. if !wizardState.legacyHardware {
  58. DetailedSection("Options") {
  59. Toggle("UEFI Boot", isOn: $wizardState.systemBootUefi)
  60. .disabled(!supportsUefi)
  61. .onAppear {
  62. if !supportsUefi {
  63. wizardState.systemBootUefi = false
  64. }
  65. }
  66. }
  67. }
  68. }
  69. .fileImporter(isPresented: $isFileImporterPresented, allowedContentTypes: [.data], onCompletion: processImage)
  70. }
  71. private func processImage(_ result: Result<URL, Error>) {
  72. wizardState.busyWorkAsync {
  73. let url = try result.get()
  74. await MainActor.run {
  75. wizardState.bootImageURL = url
  76. }
  77. }
  78. }
  79. }
  80. struct VMWizardOSOtherView_Previews: PreviewProvider {
  81. @StateObject static var wizardState = VMWizardState()
  82. static var previews: some View {
  83. VMWizardOSOtherView(wizardState: wizardState)
  84. }
  85. }