【コピペで動く】Pythonで簡単なメモ帳アプリを作ろう!ファイル保存機能つき
「プログラミングで何か形になるものを作ってみたい!」
そう思っているあなたへ。この記事では、プログラミング言語Pythonを使って、文字を入力してファイルに保存できる、自分だけのシンプルな「メモ帳アプリ」の作り方を、世界一わかりやすく解説します。
こんにちは!ほんの数ヶ月前までプログラミング知識ゼロだった、AIの力を借りて独学中のウェブ開発者です。僕も最初は「ファイル保存?呪文か何か?」というレベルでした(笑)。だからこそ、専門用語をできるだけ使わず、同じ初心者だった頃の僕がつまずいたポイントを、皆さんと共有しながら進めていきたいと思います。
この記事のゴールはただ一つ。あなたに「自分で作ったプログラムが動く!」という感動を体験してもらうことです。そのため、難しい話は後回し!まずはコピペで動く完成品を触ってみましょう!
STEP 1:さっそく動かしてみよう!完成コードはこちら
百聞は一見にしかず。まずは下のコードを全部コピーして、memo_app.py という名前で保存し、実行してみてください。Pythonの実行環境がない方は、先に準備してくださいね。
「え、もう完成形?」「解説は?」と思ったあなた、正解です!まず「動く」ことを体験するのが、プログラミングが一番楽しくなる秘訣なんです。
import tkinter as tk
import tkinter.filedialog as filedialog
def save_file():
"""ファイルを保存する関数"""
file_path = filedialog.asksaveasfilename(
defaultextension=".txt",
filetypes=[("テキストファイル", "*.txt"), ("すべてのファイル", "*.*")]
)
if not file_path:
return
try:
with open(file_path, 'w', encoding='utf-8') as file:
text_content = text_area.get(1.0, tk.END)
file.write(text_content)
except Exception as e:
print(f"エラーが発生しました: {e}")
def open_file():
"""ファイルを開く関数"""
file_path = filedialog.askopenfilename(
filetypes=[("テキストファイル", "*.txt"), ("すべてのファイル", "*.*")]
)
if not file_path:
return
try:
with open(file_path, 'r', encoding='utf-8') as file:
text_content = file.read()
text_area.delete(1.0, tk.END)
text_area.insert(tk.END, text_content)
except Exception as e:
print(f"エラーが発生しました: {e}")
# メインウィンドウの作成
window = tk.Tk()
window.title("シンプルなメモ帳")
window.geometry("600x400")
# テキスト入力エリアの作成
text_area = tk.Text(window, wrap=tk.WORD)
text_area.pack(expand=True, fill=tk.BOTH)
# メニューバーの作成
menu_bar = tk.Menu(window)
window.config(menu=menu_bar)
# 「ファイル」メニューの作成
file_menu = tk.Menu(menu_bar, tearoff=0)
menu_bar.add_cascade(label="ファイル", menu=file_menu)
file_menu.add_command(label="開く...", command=open_file)
file_menu.add_command(label="保存する...", command=save_file)
file_menu.add_separator()
file_menu.add_command(label="終了", command=window.quit)
# ウィンドウの表示
window.mainloop()
どうですか?こんな感じのウィンドウが表示されたら大成功です!
文字を入力したり、メニューから「保存する...」や「開く...」を選んでみてください。ちゃんとメモ帳として機能することに、ちょっと感動しませんか?
STEP 2:コードの探検!動く仕組みを覗いてみよう
「動いた!」を体験したところで、今度は「どうして動くの?」を探検していきましょう。さっきのコードをパーツごとに分解して、一つ一つの役割を解説します。
① 魔法の道具箱を準備する (import)
コードの最初の2行は、これから使う「便利な道具」をPythonに読み込ませるための、おまじないのようなものです。
import tkinter as tk
import tkinter.filedialog as filedialog
- `tkinter`: PythonでウィンドウやボタンといったGUI(グラフィカル・ユーザー・インターフェース)を簡単に作るための標準ライブラリです。いわば、アプリの骨格や部品を作るための道具箱です。
- `tkinter.filedialog`: 「ファイルを開く」や「名前を付けて保存」といった、おなじみのダイアログボックスを表示するための専門道具です。
② アプリの土台を作る (ウィンドウ作成)
次に、アプリのメインとなるウィンドウを作成します。家づくりでいうと、基礎工事と骨組みの部分ですね。
# メインウィンドウの作成
window = tk.Tk()
window.title("シンプルなメモ帳")
window.geometry("600x400")
# ... (中略) ...
# ウィンドウの表示
window.mainloop()
- `window = tk.Tk()`: これがウィンドウ本体を作成する命令です。「`tk`道具箱の中の`Tk()`という設計図で、`window`という名前のウィンドウを作ってね」という意味です。
- `window.title(...)`: ウィンドウのタイトルバーに表示される文字を設定します。
- `window.geometry("600x400")`: ウィンドウの初期サイズを「幅600ピクセル × 高さ400ピクセル」に設定します。
- `window.mainloop()`: これが一番大事!作成したウィンドウを表示し、ユーザーが閉じるまで待機させる命令です。これが無いと、プログラムが一瞬で起動して終了してしまい、ウィンドウを見ることすらできません。
③ 文字を書く場所を用意する (テキストエリア)
メモ帳ですから、文字を入力するスペースが必要ですよね。それを作っているのがこの部分です。
# テキスト入力エリアの作成
text_area = tk.Text(window, wrap=tk.WORD)
text_area.pack(expand=True, fill=tk.BOTH)
- `text_area = tk.Text(...)`: `tk`道具箱の`Text`という部品(ウィジェットと呼びます)を使って、テキスト入力エリアを作成しています。`wrap=tk.WORD`は、行の折り返しを単語単位で行う設定で、英文の途中で変に改行されないようにするお作法です。
- `text_area.pack(...)`: 作成した`text_area`を、親である`window`に配置する命令です。`pack`は簡単なレイアウト方法で、`expand=True, fill=tk.BOTH`と指定することで、「ウィンドウサイズが変わったら、テキストエリアもそれに合わせて上下左右にめいっぱい広がってね」という賢い配置ができます。
④ 命令をまとめた箱を作る (関数)
いよいよ、このアプリの心臓部、「ファイルを開く」「ファイルを保存する」という具体的な処理の解説です。これらの処理は、関数という「命令をまとめた便利な箱」として定義されています。
ファイルを保存する: `save_file()` 関数
def save_file():
"""ファイルを保存する関数"""
file_path = filedialog.asksaveasfilename(
defaultextension=".txt",
filetypes=[("テキストファイル", "*.txt"), ("すべてのファイル", "*.*")]
)
if not file_path:
return
try:
with open(file_path, 'w', encoding='utf-8') as file:
text_content = text_area.get(1.0, tk.END)
file.write(text_content)
except Exception as e:
print(f"エラーが発生しました: {e}")
このコードには重要なポイントが詰まっています。
- `filedialog.asksaveasfilename(...)`: これが「名前を付けて保存」ダイアログを表示する命令です。ここでユーザーが選んだ保存場所のパス(ファイル名までの住所のようなもの)が、`file_path`という変数に格納されます。
- `if not file_path: return`: もしユーザーがダイアログで「キャンセル」を押した場合、`file_path`は空になります。その場合は、何もせずに関数を終了させるための、大事な一行です。
- `with open(file_path, 'w', encoding='utf-8') as file:`: ここがファイル入出力のキモ!
- `open()`: 指定したパスのファイルを、指定したモードで開く命令です。
- `'w'`: 書き込みモード (`write`) を意味します。ファイルがなければ新規作成し、あれば上書きします。
- `encoding='utf-8'`: 文字化けを防ぐための超重要なおまじないです。世界中のほとんどの言語を正しく扱うための標準的な文字コード「UTF-8」を指定しています。これを書かないと、日本語が正しく保存できないことがあります。
- `with ... as file:`: この構文を使うと、ブロック内の処理が終わった後にファイルを自動で閉じてくれます。ファイルを閉め忘れると、メモリリークなどの原因になるため、これは非常に安全で推奨される書き方です。(公式ドキュメントでも推奨)
- `text_area.get(1.0, tk.END)`: テキストエリアに入力されている全てのテキストを取得します。
- `file.write(text_content)`: 取得したテキストを、開いたファイルに書き込みます。
同じように、ファイルを開く `open_file()` 関数も、`'r'` (読み込みモード: `read`) を使ってファイルの内容を読み取り、テキストエリアに表示しているだけです。仕組みはほぼ同じですね!
STEP 3:応用編!自分だけのメモ帳に改造しよう
基本的な仕組みがわかったら、今度はもっと面白くしてみましょう!少しコードを追加するだけで、便利な機能を実装できます。
改造例①:ダークモード風デザインにする
最近流行りのダークモード。目に優しいデザインに変更してみましょう。`window`と`text_area`を作成している部分に、背景色と文字色を指定するだけです。
# メインウィンドウの作成
window = tk.Tk()
window.title("ダークなメモ帳")
window.geometry("600x400")
window.config(bg="#2d2d2d") # ウィンドウの背景色を追加
# テキスト入力エリアの作成
text_area = tk.Text(
window,
wrap=tk.WORD,
bg="#1e1e1e", # テキストエリアの背景色
fg="#dcdcdc", # 文字色
insertbackground="#ffffff" # カーソルの色
)
text_area.pack(expand=True, fill=tk.BOTH)
これだけで、グッとモダンな雰囲気になりましたね!
改造例②:ショートカットキーを追加する
毎回メニューを開くのは面倒ですよね。「Ctrl + S」で保存、「Ctrl + O」で開けるようにしましょう。メニューに項目を追加する際に、`accelerator`でショートカットキーを明記し、`window.bind`で実際のキー操作と関数を結びつけます。
まず、メニュー作成部分をこう変更します。
# 「ファイル」メニューの作成
file_menu = tk.Menu(menu_bar, tearoff=0)
menu_bar.add_cascade(label="ファイル", menu=file_menu)
# acceleratorでショートカットキーをヒントとして表示
file_menu.add_command(label="開く...", command=open_file, accelerator="Ctrl+O")
file_menu.add_command(label="保存する...", command=save_file, accelerator="Ctrl+S")
file_menu.add_separator()
file_menu.add_command(label="終了", command=window.quit)
次に、キー操作と関数を結びつける処理を、`window.mainloop()`の直前に追加します。
# ショートカットキーのバインド
# イベント引数を受け取るためにlambdaを使用
window.bind("<Control-s>", lambda event: save_file())
window.bind("<Control-o>", lambda event: open_file())
# ウィンドウの表示
window.mainloop()
`bind`メソッドはイベント(今回はキー入力)が発生したときに関数を呼び出しますが、その際イベントに関する情報(`event`オブジェクト)を引数として渡します。しかし、私たちの`save_file`関数や`open_file`関数は引数を受け取らない設計です。そこで`lambda event:`を使うことで、引数を無視して目的の関数を呼び出す、という仲介役をさせているのです。ちょっとしたテクニックですね!
気をつけるべき点(転ばぬ先の杖)
ファイル操作は、予期せぬエラーが起こりやすい部分です。僕も最初は何度もエラー画面を見て頭を抱えました...。代表的なエラーを知っておくだけでも、パニックにならずに済みますよ。
- `PermissionError`: 書き込みが禁止されているフォルダ(例: `C:\Program Files`など)に保存しようとすると発生します。デスクトップやドキュメントフォルダなど、書き込み権限のある場所を選びましょう。
- `FileNotFoundError`: `open_file`関数で、存在しないファイルを指定した場合に発生します。私たちのコードでは`filedialog`を使っているので、基本的には起こりませんが、コードを改造する際は注意が必要です。
- `UnicodeDecodeError`: `encoding='utf-8'`で読み込めないファイル(例: `Shift_JIS`で保存された古いテキストファイルなど)を開こうとすると発生します。これは非常に根深い問題ですが、まずは「世の中には色々な文字コードがあるんだな」と知っておくだけでOKです。
私たちのコードでは、`try...except`ブロックでエラーを捕捉しているので、万が一エラーが起きてもアプリがクラッシュせず、コンソールにエラーメッセージが表示されるようになっています。これも安全なプログラムを作るための重要なテクニックです。
まとめ:小さな成功が、次への大きな一歩になる
お疲れ様でした!今回はPythonの`Tkinter`を使って、ファイル保存機能付きのシンプルなメモ帳アプリを作成しました。
コピペから始めて、その仕組みを理解し、最後は自分で改造するところまで体験していただけたでしょうか。「自分で書いたコードが、目に見える形で動く」という経験は、何物にも代えがたい喜びであり、プログラミング学習を続ける上で最高のモチベーションになります。
今回作ったアプリは、ほんの始まりに過ぎません。検索機能、文字数カウント、自動保存など、アイデア次第でいくらでも機能を追加できます。ぜひ、この記事を土台にして、あなただけのオリジナルアプリ開発に挑戦してみてください!
次のステップへ
GUIアプリの基本がわかったら、今度は「時間」を操ってみませんか?次の記事では、Pythonの`time`モジュールを使って、指定した時間になると知らせてくれるタイマーアプリの作り方を解説します。アラームやポモドーロタイマーなど、日常で役立つツール作りに挑戦しましょう!
→ Pythonでタイマーアプリを作ってみよう(timeモジュール)おまけ:まるっと動く完全なPythonコード
この記事で解説した、ダークモード風デザインとショートカットキーの応用例をすべて反映した、最終的な完成版Pythonコードです。これをコピペすれば、すぐに高機能なメモ帳アプリが使えます!
<?php
/*
これはPythonのコードであり、Webサーバーで実行されるPHPファイルではありません。
拡張子を.pyに変更して、Pythonインタプリタで実行してください。
例: python your_file_name.py
*/
?>
import tkinter as tk
import tkinter.filedialog as filedialog
def save_file():
"""ファイルを保存する関数"""
file_path = filedialog.asksaveasfilename(
defaultextension=".txt",
filetypes=[("テキストファイル", "*.txt"), ("すべてのファイル", "*.*")]
)
if not file_path:
return
try:
with open(file_path, 'w', encoding='utf-8') as file:
text_content = text_area.get(1.0, tk.END)
file.write(text_content)
except Exception as e:
# 本来はログに出力したり、ユーザーにダイアログで知らせるのが親切
print(f"エラーが発生しました: {e}")
window.title(f"エラー: {e}")
def open_file():
"""ファイルを開く関数"""
file_path = filedialog.askopenfilename(
filetypes=[("テキストファイル", "*.txt"), ("すべてのファイル", "*.*")]
)
if not file_path:
return
try:
with open(file_path, 'r', encoding='utf-8') as file:
text_content = file.read()
text_area.delete(1.0, tk.END)
text_area.insert(tk.END, text_content)
window.title(f"メモ帳 - {file_path}")
except Exception as e:
print(f"エラーが発生しました: {e}")
window.title(f"エラー: {e}")
# --- GUIのセットアップ ---
# メインウィンドウの作成
window = tk.Tk()
window.title("高機能メモ帳")
window.geometry("800x600")
window.config(bg="#2d2d2d") # ウィンドウの背景色
# テキスト入力エリアの作成
text_area = tk.Text(
window,
wrap=tk.WORD,
bg="#1e1e1e", # テキストエリアの背景色
fg="#dcdcdc", # 文字色
insertbackground="#ffffff", # カーソルの色(白で見やすいように)
undo=True, # Undo/Redo機能を有効化
autoseparators=True
)
text_area.pack(expand=True, fill=tk.BOTH, padx=5, pady=5)
# メニューバーの作成
menu_bar = tk.Menu(window)
window.config(menu=menu_bar)
# 「ファイル」メニューの作成
file_menu = tk.Menu(menu_bar, tearoff=0, bg="#2d2d2d", fg="#dcdcdc")
menu_bar.add_cascade(label="ファイル", menu=file_menu)
file_menu.add_command(label="開く...", command=open_file, accelerator="Ctrl+O")
file_menu.add_command(label="保存する...", command=save_file, accelerator="Ctrl+S")
file_menu.add_separator()
file_menu.add_command(label="終了", command=window.quit)
# ショートカットキーのバインド (lambdaでイベント引数を無視する)
window.bind("<Control-s>", lambda event: save_file())
window.bind("<Control-o>", lambda event: open_file())
window.bind("<Control-S>", lambda event: save_file()) # Shiftキー同時押しにも対応
window.bind("<Control-O>", lambda event: open_file()) # Shiftキー同時押しにも対応
# ウィンドウの表示ループ開始
window.mainloop()