
【6日でできるPython入門】一筆書きアプリを作ろう①
これから2回にわたり、Tkinter を使ったパズルゲーム 「一筆書きアプリ」 の実装を分解しながら解説していきます。第 1 回となる今回は、ゲーム全体の雰囲気とコードの骨格をつかむことを目的に、以下のトピックをまとめて確認します。各項目では プログラム全体を再掲せず、必要な断片だけを抜粋して説明します。

1.このゲームの遊び方
- 盤面(12×10 マス)のすべてを 一筆書き で塗りつぶせばステージクリア
- ステージは 3 つ。最後まで進むと「ALL STAGES CLEAR!」
- チェックポイント(赤い○)を通過しても構いませんが、塗り残しがあるとクリアになりません
2.操作方法
キー | 動作 |
---|---|
← → ↑ ↓ | ペンを左右・上下に 1 マス移動 |
g / G / 左Shift | ギブアップ確認ダイアログを表示 |
移動できるのは 未塗り(0) または チェックポイントの赤い●(3) のマスだけ。踏んだ瞬間に現在マスを 塗り済み(2) に更新します(後述の move_pen()
参照)。
ゲーム画面イメージ

3.プログラム処理フロー(俯瞰)
game_main() # 0.2 秒おきに root.after で無限ループ
├─ idx == 0 → ステージ準備
├─ idx == 1 → プレイ中
│ └─ move_pen() → プレイヤー操作反映
│ └─ count_tile() が 0 になれば idx = 2
└─ idx == 2 → クリア演出&次ステージ移行
- ゲーム全体を 状態番号
idx
で管理し、タイマーイベントだけで制御しています。 - 描画やロジックが混線しないよう、「準備 → 入力 → 判定 → 演出」 の流れを毎フレーム同じ順序で処理しています。
4.ウィンドウの表示(Tkinter 初期化)
root = tkinter.Tk()
root.title("一筆書きアプリ")
root.resizable(False, False)
cvs = tkinter.Canvas(root, width=W*TS, height=H*TS)
cvs.pack()
- ゲーム画面は
Canvas
1 枚のみ。ウィンドウサイズは タイルサイズTS
× マップ幅/高さ で計算。 - キー操作は
root.bind("<KeyPress>", key_down)
とkey_up
で低レイテンシに取得。
5.画像リソースの読み込みと配置
pen = tkinter.PhotoImage(file="pen.png")
wall = tkinter.PhotoImage(file="wall.png")
- ペンは常に タグ
"PEN"
で 1 枚だけ配置し、座標が変わるたびにdelete → create
。 - 壁は描画時に
create_image()
を使い、背景色 (COL_WALL
) との二重描画で視認性を確保。
6.MAP の座標系とタイルコード
コード | 意味 | 描画 | 初期化場所 |
---|---|---|---|
0 | 未塗りタイル | COL_FLOOR | 各ステージ配列 |
2 | 塗り済みタイル | COL_PAINT | stage_data() 初期マスで設定 |
3 | ゴール | 赤い円 | ステージ配列 |
9 | 壁 | wall.png + 背景色 | ステージ配列 |
※ 配列は maze[y][x]
(左上が (0,0))。ix, iy
はプレイヤー位置。
7.マップ描画処理 draw_bg()
抜粋:
for y in range(H):
for x in range(W):
gx, gy = TS*x, TS*y
v = maze[y][x]
if v == 0 or v == 3:
cvs.create_rectangle(gx, gy, gx+TS, gy+TS,
fill=COL_FLOOR, width=0, tag="BG")
if v == 2:
cvs.create_rectangle(gx, gy, gx+TS, gy+TS,
fill=COL_PAINT, width=0, tag="BG")
if v == 9:
cvs.create_rectangle(gx, gy, gx+TS, gy+TS,
fill=COL_WALL, width=0, tag="BG")
cvs.create_image(gx+TS//2, gy+TS//2, image=wall, tag="BG")
- 描画タグ
"BG"
をまとめて消してから再描画するため、画面更新が一括で行えます。 - ペンだけは
"PEN"
タグで別管理し、プレイ中の再描画コストを抑制。
8.ステージデータ stage_data()
if stage == 1:
ix, iy = 1, 1
maze = [
[9,9,9,9, … ],
[9,0,0,0, … ],
…
]
elif stage == 2:
…
- 各ステージを 二次元リスト で直書き。数字は先ほどのタイルコード。
- 開始位置
(ix, iy)
を決めたあと、maze[iy][ix] = 2
で スタートマスを塗り済みに更新。 - 配列を編集するときは
global maze
を宣言している点に注意。
まとめ ― 次回予告
今回は「一筆書きアプリ」を動かすうえで欠かせない 骨格部分(ウィンドウ生成・描画・ステージ切替えなど)を概観しました。次回 「一筆書きアプリを作ろう②」 では、
- ペンの移動処理
- ステージクリア判定
- ゲームクリア判定
- 改造のポイント
など、より発展的な処理を掘り下げていき「一筆書きアプリ」を完成させます。お楽しみに!