Tkinterの`pack`メソッド解説 ～具体例付き～

# 概要

TkinterはPythonでGUIアプリケーションを作成するための標準ライブラリです。
ウィジェット（ボタン、ラベル、エントリーなど）を配置するために、
`pack`、`grid`、`place`といった複数のレイアウトマネージャを提供しています。
本記事では、その中でも最も基本的な`pack`メソッドについて、具体的な例を交えて詳しく解説します。
これを参考にして、誰でも簡単にTkinterのレイアウトを作成できるようになります。

## `pack`メソッドとは？

`pack`は、ウィジェットを親コンテナ（ウィンドウやフレーム）の中に自動的に配置するためのシンプルなレイアウトマネージャです。
ウィジェットを上下または左右に積み重ねるように配置します。
`pack`は配置の順序や位置を簡単に指定できるため、シンプルなレイアウトを作成する際に非常に便利です。

### 主なオプション

- **`side`**: ウィジェットを配置する側。`TOP`（デフォルト）、`BOTTOM`、`LEFT`、`RIGHT`から選択します。
- **`fill`**: ウィジェットが親コンテナの空間をどのように埋めるか。`X`（水平方向）、`Y`（垂直方向）、`BOTH`、`NONE`（デフォルト）。
- **`expand`**: 親コンテナがリサイズされたときにウィジェットが追加のスペースをどれだけ占めるか。`True`または`False`。

## 具体例

以下に、`pack`メソッドを使用した簡単なTkinterアプリケーションの例を示します。この例では、ボタンを異なる位置に配置します。

```python
import tkinter as tk

# メインウィンドウの作成
root = tk.Tk()
root.title("Packメソッドの例")
root.geometry("300x200")

# ボタンの作成
btn_top = tk.Button(root, text="トップ")
btn_bottom = tk.Button(root, text="ボトム")
btn_left = tk.Button(root, text="左")
btn_right = tk.Button(root, text="右")
btn_fill = tk.Button(root, text="フィル", bg="lightblue")

# ウィジェットの配置
btn_top.pack(side=tk.TOP, fill=tk.X)
btn_bottom.pack(side=tk.BOTTOM, fill=tk.X)
btn_left.pack(side=tk.LEFT, fill=tk.Y)
btn_right.pack(side=tk.RIGHT, fill=tk.Y)
btn_fill.pack(expand=True, fill=tk.BOTH)

# メインループの開始
root.mainloop()
```

↓実行するとこんな画面になります
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2483440/251dd860-0bf7-7dd7-d6e2-50224387df2c.png)


### この例の説明

1. **メインウィンドウの作成**:
    ```python
    root = tk.Tk()
    root.title("Packメソッドの例")
    root.geometry("300x200")
    ```
    - `Tk()`でメインウィンドウを作成し、タイトルとサイズを設定します。

2. **ボタンの作成**:
    ```python
    btn_top = tk.Button(root, text="トップ")
    btn_bottom = tk.Button(root, text="ボトム")
    btn_left = tk.Button(root, text="左")
    btn_right = tk.Button(root, text="右")
    btn_fill = tk.Button(root, text="フィル", bg="lightblue")
    ```
    - 5つのボタンを作成します。それぞれ異なる位置に配置されます。

3. **ウィジェットの配置**:
    ```python
    btn_top.pack(side=tk.TOP, fill=tk.X)
    btn_bottom.pack(side=tk.BOTTOM, fill=tk.X)
    btn_left.pack(side=tk.LEFT, fill=tk.Y)
    btn_right.pack(side=tk.RIGHT, fill=tk.Y)
    btn_fill.pack(expand=True, fill=tk.BOTH)
    ```
    - `btn_top`: 上側に配置され、水平方向に親コンテナの幅いっぱいに広がります。
    - `btn_bottom`: 下側に配置され、水平方向に親コンテナの幅いっぱいに広がります。
    - `btn_left`: 左側に配置され、垂直方向に親コンテナの高さいっぱいに広がります。
    - `btn_right`: 右側に配置され、垂直方向に親コンテナの高さいっぱいに広がります。
    - `btn_fill`: 残りの中央部分を埋めるように配置され、親コンテナの両方向に広がります。`expand=True`により、親ウィンドウがリサイズされたときにこのボタンが追加のスペースを占めます。

### 実行結果

このスクリプトを実行すると、以下のようなレイアウトが表示されます：

- 上部に「トップ」ボタン
- 下部に「ボトム」ボタン
- 左側に「左」ボタン
- 右側に「右」ボタン
- 中央に「フィル」ボタン（背景色がライトブルーで視覚的に分かりやすい）

ウィンドウをリサイズすると、「フィル」ボタンが中央部分のスペースを動的に調整します。

## 追加の例：フレーム内での`pack`の使用

複数のウィジェットをグループ化するために、フレームと`pack`を組み合わせて使用することも一般的です。以下に、フレーム内でボタンを水平に並べる例を示します。

```python
import tkinter as tk

root = tk.Tk()
root.title("フレーム内のPack例")
root.geometry("400x200")

# フレームの作成
frame = tk.Frame(root, bg="gray")
frame.pack(fill=tk.BOTH, expand=True, padx=10, pady=10)

# ボタンの作成
btn1 = tk.Button(frame, text="ボタン1")
btn2 = tk.Button(frame, text="ボタン2")
btn3 = tk.Button(frame, text="ボタン3")

# フレーム内でボタンを横に並べる
btn1.pack(side=tk.LEFT, padx=5, pady=5)
btn2.pack(side=tk.LEFT, padx=5, pady=5)
btn3.pack(side=tk.LEFT, padx=5, pady=5)

root.mainloop()
```

### この例の説明

1. **フレームの作成と配置**:
    ```python
    frame = tk.Frame(root, bg="gray")
    frame.pack(fill=tk.BOTH, expand=True, padx=10, pady=10)
    ```
    - グレーの背景色を持つフレームを作成し、親ウィンドウ全体に広がるように配置します。`padx`と`pady`で外側の余白を設定しています。

2. **ボタンの作成と配置**:
    ```python
    btn1 = tk.Button(frame, text="ボタン1")
    btn2 = tk.Button(frame, text="ボタン2")
    btn3 = tk.Button(frame, text="ボタン3")

    btn1.pack(side=tk.LEFT, padx=5, pady=5)
    btn2.pack(side=tk.LEFT, padx=5, pady=5)
    btn3.pack(side=tk.LEFT, padx=5, pady=5)
    ```
    - 3つのボタンを作成し、フレーム内で左側から順に横に並べます。
各ボタンには左右と上下に5ピクセルの余白を設定しています。

### 実行結果

このスクリプトを実行すると、ウィンドウ内にグレーのフレームが表示され、
その中に「ボタン1」「ボタン2」「ボタン3」が横一列に並んで配置されます。
ウィンドウをリサイズすると、フレームとボタンの配置もそれに応じて調整されます。

## `pack`の利点と制限

### 利点

- **シンプルさ**: 基本的なレイアウトを素早く作成できます。
- **自動配置**: ウィジェットを自動的に積み重ねるため、細かい位置指定が不要です。

### 制限

- **複雑なレイアウトには不向き**: 複雑なウィジェット配置やグリッド状のレイアウトには`grid`や`place`の方が適しています。
- **制御の限界**: 個々のウィジェットの正確な位置やサイズを細かく制御するのが難しい場合があります。

## まとめ

`pack`メソッドは、Tkinterで簡単なGUIレイアウトを作成する際に非常に便利なツールです。
基本的な配置オプションを理解し、具体的な例を試すことで、GUIアプリケーションのレイアウトを効率的に構築できます。
複雑なレイアウトが必要な場合は、`grid`や`place`といった他のレイアウトマネージャも検討すると良いでしょう。