Swift UIとWebとの表示制御の仕方の違い


## はじめに
SwiftUIで作るアプリと、WebのようなHTML、CSSで作る画面の作り方の違いを通してSwift UIというものに触れたいと考えています。

SwiftUIはWebと比較すると、難しい言い方をすると、Viewプロトコルに準拠したコンポーネントを作成してUIを構築するというところです。

SwiftUIはHTMLとCSSでのレイアウトとスタイル指定に似た役割を果たします。

## 例：SwiftUIでの`VStack`と`HStack`
ここでは、SwiftUIの`VStack`と`HStack`を使用した例と、それに相当するHTMLとCSSのコードを示します。
縦に文字を表示する場合、横に表示する場合の例になります。

### SwiftUI の例

SwiftUIでの`VStack`と`HStack`の使用例です。これは縦と横に並べたテキストを表示するシンプルなレイアウトです。

```swift
VStack {
    Text("上のテキスト")
    HStack {
        Text("左のテキスト")
        Text("右のテキスト")
    }
}
```
![スクリーンショット 2024-02-02 14.31.44.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/176603/3fdc73cf-36d9-5506-eed8-c369afcaa006.png)


### HTML と CSS の例

同じレイアウトをHTMLとCSSで実現するためのコードは以下のようになります。


CSSで `display: flex;` と `flex-direction` プロパティを使って、縦方向と横方向のレイアウトを制御しています。


#### HTML

```html
<div class="vstack">
    <div>上のテキスト</div>
    <div class="hstack">
        <div>左のテキスト</div>
        <div>右のテキスト</div>
    </div>
</div>
```

#### CSS

```css
.vstack {
    display: flex;
    flex-direction: column;
}

.hstack {
    display: flex;
    flex-direction: row;
}
```

![スクリーンショット 2024-02-02 14.50.46.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/176603/e4d8ba20-864b-0c17-7ce9-d8f613dcb9fd.png)


このHTMLとCSSの例では、`.vstack` クラスを持つ `div` 要素が `VStack` に相当し、`.hstack` クラスを持つ `div` 要素が `HStack` に相当します。

これらの例から分かるように、SwiftUIの`VStack`と`HStack`は、HTMLとCSSのフレックスボックスレイアウトに相当する機能を提供しています。


## Swift UIでの装飾例
上記SwiftUIの例で、ではどうやって装飾するかを例に挙げます。

SwiftUIでは、モディファイアを使用してビューコンポーネントの見た目や振る舞いをカスタマイズします。モディファイアはビューに対してメソッドチェーンのように適用され、ビューのスタイルを変更したり、特定のレイアウト属性を設定したりすることができます。`VStack`や`HStack`にモディファイアを適用することで、それらの子ビューの配置やスペース、パディング、背景色などを調整することができます。

以下に、`VStack`と`HStack`にモディファイアを適用した例を示します：

```swift
import SwiftUI

struct ContentView: View {
    var body: some View {
        VStack(spacing: 20) { // VStackにスペースを追加
            Text("上のテキスト")
                .font(.headline) // フォントスタイルの変更
                .foregroundColor(.blue) // テキストの色を変更
            HStack(spacing: 40) { // HStackにスペースを追加
                Text("左のテキスト")
                    .font(.subheadline) // フォントスタイルの変更
                    .foregroundColor(.green) // テキストの色を変更
                Text("右のテキスト")
                    .font(.subheadline) // フォントスタイルの変更
                    .foregroundColor(.red) // テキストの色を変更
            }
            .padding() // HStackにパディングを追加
            .background(Color.yellow) // HStackの背景色を変更
            .cornerRadius(10) // 角の丸みを追加
        }
        .padding() // VStackにパディングを追加
        .background(Color.gray.opacity(0.2)) // VStackの背景色を変更、不透明度を設定
        .cornerRadius(15) // 角の丸みを追加
    }
}
```
![スクリーンショット 2024-02-04 12.25.05.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/176603/0c458074-6600-508c-21e6-fd1a39b0d8a9.png)

この例では、`VStack`とその中の`HStack`にいくつかのモディファイアを適用しています。具体的には、以下のようなスタイル変更を行っています：

- `VStack`と`HStack`の子ビュー間のスペースを設定
- テキストのフォントスタイルと色を変更
- `HStack`にパディングを追加し、背景色を設定、角を丸くしています
- `VStack`にもパディングを追加し、背景色を設定（不透明度付き）、角を丸くしています

これらのモディファイアを適用することで、UIコンポーネントのレイアウトとスタイルを細かく調整することが可能になります。


## SwiftUIのコンポーネント例
他に画面表示に使用するビューコンポーネントの例を挙げてみます。
その機能や用途に応じていくつかのカテゴリに分類することができます。ここでは、主要なカテゴリとそれぞれのカテゴリに属するビューコンポーネントの例を挙げていきます。

### 1. 基本的なビュー (Basic Views)

これらは最も基本的なユーザーインターフェース要素です。

- **Text**: テキストを表示するためのビュー。
  ```swift
  Text("Hello, SwiftUI!")
  ```
- **Image**: 画像を表示するためのビュー。
  ```swift
  Image("exampleImage")
  ```
- **Button**: アクションを起動するボタン。
  ```swift
  Button("Click Me") {
      // アクションを実行する
  }
  ```

### 2. コンテナビュー (Container Views)

今回例として使用したビューです。
他のビューをレイアウトするために使用されます。

- **VStack**: 縦にビューを積み重ねる。
  ```swift
  VStack {
      Text("First")
      Text("Second")
  }
  ```
- **HStack**: 横にビューを積み重ねる。
  ```swift
  HStack {
      Text("Left")
      Text("Right")
  }
  ```
- **ZStack**: ビューを重ねる。
  ```swift
  ZStack {
      Text("Back")
      Text("Front")
  }
  ```
- **ScrollView**: スクロール可能なビュー。
  ```swift
  ScrollView {
      Text("Scrollable content")
  }
  ```

### 3. コントロールビュー (Control Views)

ユーザーによる操作を受け付けるビュー。

- **TextField**: テキスト入力フィールド。
  ```swift
  @State private var text = ""
  TextField("Enter text", text: $text)
  ```
- **Slider**: スライダー。
  ```swift
  @State private var value = 0.0
  Slider(value: $value)
  ```
- **Toggle**: トグルスイッチ。
  ```swift
  @State private var isOn = false
  Toggle("Switch", isOn: $isOn)
  ```

### 4. レイアウトビュー (Layout Views)

特定のレイアウトを適用するためのビュー。

- **Spacer**: 空間を作る。
  ```swift
  HStack {
      Text("Left")
      Spacer() // 中央に空間を作る
      Text("Right")
  }
  ```
- **Divider**: 分割線。
  ```swift
  VStack {
      Text("Above")
      Divider()
      Text("Below")
  }
  ```
- **Group**: 複数のビューをグループ化。
  ```swift
  Group {
      Text("First")
      Text("Second")
  }
  ```

### 5. 特殊ビュー (Special Views)

特定の目的や機能を持つ特殊なビュー。

- **NavigationView**: ナビゲーションをサポートするビュー。
  ```swift
  NavigationView {
      Text("Navigation Content")
  }
  ```
- **TabView**: タブによるビュー切り替え。
  ```swift
  TabView {
      Text("First Tab")
          .tabItem {
              Label("First", systemImage: "1.circle")
          }
      Text("Second Tab")
          .tabItem {
              Label("Second", systemImage: "2.circle")
          }
  }
  ```
- **List**: リスト表示。
  ```swift
  List {
      Text("Item 1")
      Text("Item 2")
  }
  ```

これらのビューコンポーネントは、SwiftUIでアプリケーションのユーザーインターフェースを構築する際の基本的な構成要素です。それぞれのビューは修飾子を使用してカスタマイズでき、複雑なレイアウトや機能を持つインターフェースを構築するために組み合わせて使用されます。


## おわりに
今回はSwiftUIとWebで画面の表示の仕方の違いを調査しました。
次は入力やデータ表示等をどうしているのかを調査したいと思います。


## 参考記事

https://qiita.com/atsu123456789/items/3c736254e9d7c9a1951e

https://zenn.dev/rikutosato/books/6cee0a2b8aa796/viewer/cb50dd

https://swiftui.mszpro.com/