【SwiftUI】 iOS / macOS の レイアウト記述を typealias で切り替える

よくある入力欄を iOS で作ります。


// iOS

Form {
  Section(header: Text("Name of Living Accommodation")) {
    Group {
      TextField("Enter place name here…", text: $placeName)
    }
  }
  Section(header: Text("Address of Living Accommodation")) {
    Group {
      TextField("Enter address here…", text: $address)
    }
  }
}

いい感じです。

👉 Form | Apple Developer Documentation hatena-bookmark
👉 Group | Apple Developer Documentation hatena-bookmark

macOS に切り替えてみます。

なんか気持ちが悪いです。

以下のようにレイアウト記述を書き換えます。


 iOS   | macOS
-------+----------
 Form  → List
 Group → GroupBox


// macOS

List { // *
  Section(header: Text("Name of Living Accommodation")) {
    GroupBox { // *
      TextField("Enter place name here…", text: $placeName)
    }
  }
  Section(header: Text("Address of Living Accommodation")) {
    GroupBox { // *
      TextField("Enter address here…", text: $address)
    }
  }
}

いい感じになりました。

👉 List | Apple Developer Documentation hatena-bookmark
👉 GroupBox | Apple Developer Documentation hatena-bookmark

自動で切り替えるようにしておきます。


// iOS and macOS

#if os(iOS)

Form {
  Section(header: Text("Name of Living Accommodation")) {
    Group {
      TextField("Enter place name here…", text: $placeName)
    }
  }
  Section(header: Text("Address of Living Accommodation")) {
    Group {
      TextField("Enter address here…", text: $address)
    }
  }
}

#else

List { 
  Section(header: Text("Name of Living Accommodation")) {
    GroupBox { 
      TextField("Enter place name here…", text: $placeName)
    }
  }
  Section(header: Text("Address of Living Accommodation")) {
    GroupBox { 
      TextField("Enter address here…", text: $address)
    }
  }
}

#endif

長ったらしいですね。

たった3か所の置き換えだけなのに。

■ typealias を使う

レイアウト記述の同名のエイリアスを作ってそれらを OS で切り分けます。


// iOS and macOS

#if os(iOS)
typealias TripForm = Form
typealias TripGroupBox = Group
#else
typealias TripForm = List
typealias TripGroupBox = GroupBox
#endif


 typealias    | iOS   | macOS
--------------+-------+----------
 TripForm     | Form  | List
 TripGroupBox | Group | GroupBox

それらエイリアスを使って本体は記述する。


// iOS and macOS

TripForm { // *
  Section(header: Text("Name of Living Accommodation")) {
    TripGroupBox { // *
      TextField("Enter place name here…", text: $placeName)
    }
  }
  Section(header: Text("Address of Living Accommodation")) {
    TripGroupBox { // *
      TextField("Enter address here…", text: $address)
    }
  }
}

これできれいに切り替えできました !

typealias を切り替えることで、

本体コードの挙動を置き換えてます。

さすが、Apple 公式サンプルコードは勉強になります。


Trip/Trips-SwiftData/Trips/EditLivingAccommodationsView.swift
Trip/Trips-SwiftData/Trips/SwiftUIHelper.swift

以下、Apple ページ「Download」からどうぞ。


👉 Adopting SwiftData for a Core Data app | Apple Developer Documentation hatena-bookmark