Pythonでゲームを作るには何から学ぶ?入門の文法がそのままゲームになる仕組みを解説
「Pythonでゲームを作ってみたい。でも、何から勉強すればいいの?」
「ゲーム用のライブラリの解説を読んだけど、コードの意味がほとんど分からなかった…」
こんな悩み、ありますよね。実はゲームのプログラムは、特別な魔法でできているわけではありません。中身を分解すると、入門で習う変数・if文・for文・リスト・関数の組み合わせです。
この記事では、ゲームの仕組みを「動かす→描く」「リストで管理」「if文で当たり判定」の3つに分けて、Pythonの標準機能だけで1つずつ動かしてみます。最後に、それを組み合わせたミニシューティング(文字だけ版)も作ります。対象は、Pythonを始めたばかり〜文法をひととおり読んだ方です。一緒に見ていきましょう!
ゲームは「動かす → 描く」のくり返し

アクションゲームの画面は、パラパラ漫画と同じです。1コマごとに、
- 動かす:キャラクターや敵の位置(数字)を更新する
- 描く:今の位置で画面を描き直す
を高速にくり返しています。この「くり返し」をゲームループと呼びます。イメージとしては、1秒間に何十回も for 文や while 文が回っている感じです。
まずは横に5マスの画面で、キャラクター(@)を左右に往復させてみます。
# ゲームの基本:「動かす → 描く」をくり返す
WIDTH = 5 # 画面の横幅(マスの数)
x = 0 # キャラクターの位置
dx = 1 # 1回に動く量(右向き)
for frame in range(1, 9):
# ① 動かす:位置を更新する
x = x + dx
if x == WIDTH - 1 or x == 0: # 端に着いたら向きを反転
dx = -dx
# ② 描く:今の位置で画面を作り直す
screen = ["."] * WIDTH
screen[x] = "@"
print(f"{frame}コマ目: {''.join(screen)}")

ポイントをまとめるとこんな感じです👇
- キャラクターの位置は、ただの変数
x(数字) - 「動かす」は
x = x + dxの足し算。dxを-dxにすると逆向きに進む - 「端に着いたら反転」は if文
- 「描く」は、リスト
screenを毎回作り直してprintしているだけ
本物のゲームでは print の代わりにウィンドウへ絵を描きますが、「位置を数字で持って、足し算で動かして、毎コマ描き直す」という考え方はまったく同じです。
敵や弾は「リスト」で管理する
シューティングゲームでは、画面に弾が何十発も飛んでいますよね。1発ごとに変数を作っていたらキリがありません。そこで使うのがリストです。
弾のy座標(上下の位置。0が画面のいちばん上)をリストに入れて、毎コマ「撃つ → 全部動かす → 画面の外に出たものを消す」をくり返します。
# 弾は「リスト」でまとめて管理する
bullets = [] # 画面にある弾のy座標(0が画面のいちばん上)
for frame in range(1, 6):
bullets.append(6) # 毎コマ、y=6(自機の位置)から1発撃つ
bullets = [y - 2 for y in bullets] # 全部の弾を上に2マス動かす
bullets = [y for y in bullets if y >= 0] # 画面の外に出た弾は消す
print(f"{frame}コマ目: 弾 {len(bullets)}発 → {bullets}")
実行結果:
1コマ目: 弾 1発 → [4]
2コマ目: 弾 2発 → [2, 4]
3コマ目: 弾 3発 → [0, 2, 4]
4コマ目: 弾 3発 → [0, 2, 4]
5コマ目: 弾 3発 → [0, 2, 4]
ここが重要です👇
appendで弾を増やす[y - 2 for y in bullets]で全部の弾をまとめて動かす(リスト内包表記。for文で1つずつ書き換えても同じです)[y for y in bullets if y >= 0]で画面の外に出た弾を消す
3コマ目からは、撃つ1発と消える1発がつり合って、画面の弾が3発のまま一定になっていますね。敵キャラも同じで、「敵のリスト」に出現・移動・消滅を書けば、何体いても同じコードで動きます。
当たり判定は「if文」
「弾が敵に当たったか」は、2つの四角形が重なっているかを調べるだけです。それぞれの位置(x, y)と大きさ(幅 w・高さ h)を辞書で持って、関数にまとめます。
# 当たり判定は「if文」:2つの四角が重なっているか調べる
def is_hit(a, b):
return (a["x"] < b["x"] + b["w"] and b["x"] < a["x"] + a["w"] and
a["y"] < b["y"] + b["h"] and b["y"] < a["y"] + a["h"])
bullet = {"x": 12, "y": 30, "w": 2, "h": 6}
enemies = [
{"name": "スライム", "x": 10, "y": 28, "w": 8, "h": 8},
{"name": "コウモリ", "x": 40, "y": 10, "w": 8, "h": 8},
]
for enemy in enemies:
if is_hit(bullet, enemy):
print(f"{enemy['name']}に命中!")
else:
print(f"{enemy['name']}には当たっていない")
実行結果:
スライムに命中!
コウモリには当たっていない
条件が長く見えますが、やっていることは「左右で重なっている、かつ、上下で重なっている」の2つです。
a["x"] < b["x"] + b["w"]:aの左端が、bの右端より左にあるb["x"] < a["x"] + a["w"]:bの左端が、aの右端より左にある- この2つが両方
Trueなら左右で重なっている。上下(yとh)も同じ考え方
これ、実行せずに答えられますか? 弾の x を 12 から 30 に変えると、スライムには当たらなくなります。数字を変えて試してみると、当たり判定の感覚がつかめますよ。
組み合わせると「ミニシューティング」になる
ここまでの3つを組み合わせて、文字だけのミニシューティングを作ってみます。キーボードで操作する代わりに、自機(A)が自動で敵(V)の真下へ移動して撃つようにしました。
# 変数・リスト・for・if・関数だけで作る「ミニシューティング」(自動で遊ぶ版)
W, H = 7, 6 # 画面の幅と高さ(マス)
player_x = 3 # 自機の位置(いちばん下の行)
bullets = [] # 弾 [x, y] のリスト
enemies = [[1, 0], [5, 1]] # 敵 [x, y] のリスト
score = 0
def draw():
rows = [["."] * W for _ in range(H)]
for x, y in enemies:
rows[y][x] = "V"
for x, y in bullets:
rows[y][x] = "|"
rows[H - 1][player_x] = "A"
for row in rows:
print("".join(row))
for frame in range(1, 12):
# ① 動かす:自機はいちばん下にいる敵の真下へ1マス近づき、真下に来たら撃つ
if enemies:
target = max(enemies, key=lambda e: e[1])[0]
if target > player_x:
player_x += 1
elif target < player_x:
player_x -= 1
else:
bullets.append([player_x, H - 1])
bullets = [[x, y - 1] for x, y in bullets if y - 1 >= 0] # 弾は毎コマ上へ1マス
if frame % 3 == 0:
enemies = [[x, y + 1] for x, y in enemies] # 敵は3コマに1回、下へ1マス
# ② 当たり判定:弾と敵が同じマスなら両方消してスコア加算
for b in bullets[:]:
if b in enemies:
bullets.remove(b)
enemies.remove(b)
score += 100
print(f"{frame}コマ目: x={b[0]}, y={b[1]} で命中! スコア {score}")
print("--- 11コマ目の画面 ---")
draw()
print("残りの敵:", len(enemies), "体 / スコア:", score)

使っている文法を並べると、こうなります👇
| ゲームの部品 | 使っている文法 |
|---|---|
| 画面の大きさ・自機の位置・スコア | 変数 |
| 弾と敵(何個あってもOK) | リスト(リストの中に [x, y] のリスト) |
| 1コマずつ進める(ゲームループ) | for文 |
| 敵の方へ動く・真下で撃つ・命中したか | if文 |
| 画面を描く | 関数(def draw()) |
どれも、入門で最初に習う文法ばかりですよね。ゲームを作るための特別な文法は、ひとつも使っていません。
ゲームを作りたいなら、まず何を身につける?
ここまで見てきたとおり、ゲームづくりで毎回使うのは次の文法です。
- 変数と計算:位置・速さ・スコアを数字で持って、足し算で動かす
- if文:端で反転する、当たったら消す、スコアが目標を超えたらクリア
- for文・while文:ゲームループ、敵を1体ずつ調べる
- リストと辞書:敵・弾・アイテムをまとめて管理する
- 関数:「当たり判定」「描く」など、何度も使う処理に名前をつける
画面にウィンドウを出して絵を描く部分は、ゲーム用のライブラリが担当してくれます。ただ、ライブラリが助けてくれるのは「描く」「キーを読む」ところまで。何をどう動かすかを書くのは、結局この5つの文法です。
逆に言えば、ライブラリの解説を読んで分からなかったのは、ライブラリが難しいからではなく、リストやif文がまだ手になじんでいなかっただけということが多いんです。急がば回れで、まず文法を「自分で書ける」ところまで固めるのが、いちばんの近道ですよ。
まとめ
- ゲームは「動かす(位置を足し算で更新)→ 描く」のくり返し。これがゲームループ
- 敵や弾はリストで管理する。増やす・まとめて動かす・消すの3つでOK
- 当たり判定は、四角形が重なっているかを調べるif文
- 変数・if文・for文・リスト・関数だけで、ミニシューティングが動く
- ゲームを作りたいなら、まずこの5つの文法を自分で書けるところまで身につけるのが近道
今回のコードは、すべてPythonの標準機能だけで動きます。数字を変えたり、敵を増やしたりして、ぜひ遊びながら試してみてください🚀
\ Pythonでゲームを作りたい方へ /
筆者はいま、入門を終えた人向けに、画面の中でキャラクターが動き、キーボードで操作するゲームを作るコースを制作中です。その土台になる基本文法は、無料の入門コース「作って学ぶPythonプログラミング入門」(全7章52レッスン)で、数当てゲームやじゃんけんを作りながら身につけられます。無料登録された方には、ゲームコースの公開を最初にメールでお知らせします。
こちらも読まれています
📚 関連商品・おすすめ書籍
※本記事にはアフィリエイトリンクが含まれます。





