適当のごった煮

Pythonと境界標とQGISを中心にいろいろと

tkinter

スポンサードリンク

tkinterとは

GUI作成用モジュールです。Python3からモジュール名が、Tkinterからtkinterへ変更になっています。

importの形式はいくつかありますが、「import tkinter as tk」を使います。

アプリの作成方法と部品配置の方法にいくつかのやり方があります。作成対象のアプリの規模に合わせて使い分ければいいのですが、最初のころは参考するサイトや資料によって違いがあるので、結構混乱した記憶があります。

目次

GUIアプリの作成手順

アプリの作成方法の流れは以下の手順です。

  1. 大元のウィンドウを作成
  2. 部品を作成、ウィンドウに配置する
  3. 部品に機能を割り当てる
  4. mainloopで動かす

アプリの作成方法

GUIアプリの作成方法にはいくつかやり方がありますが、だいたい次の三通りのどれかのパターンに落ち着くようです。

一番単純な方法

単純で分かりやすいですが、部品数が多くなると配置を細かくいじりたくなってきます。最初はこの方法で色々な部品を試してtkinterに慣れると良いかもしれません。

import tkinter as tk

root = tk.Tk()
# 部品(ラベルやボタン)の作成、配置

root.mainloop()

次の二通りが、作成対象のアプリケーションそのものをクラスとして作成する方法。

親ウィンドウの引数を必要とするアプリケーションクラス作成方法

import tkinter as tk

class App:
    def __init__(self, master):
        # 部品の作成、配置

root = tk.Tk()
app = App(root)
app.mainloop()

Frameクラスを継承してアプリケーションクラスを作成し、単独で起動できるパターン

個人的にはこれが一番分かりやすいと思います。

import tkinter as tk

class App(tk.Frame):
    def __init__(self, master = None):
        tk.Frame.__init__(self, master)
        self.pack()
        # 部品の作成、配置

app = App()
app.mainloop()

部品の作成方法

tkinterでは使える部品(ラベルやボタン等いろいろ)のことをウィジットと呼びます。これらを親ウィンドウ上に配置してアプリケーションを作成していきます。

基本書式と作成例

widget = widgetclass(master, option=value, …)
例:button1 = tk.Button(self, text = "Hello", command = self.hello)

部品の配置方法

配置方法も三通りの方法があります。それぞれオプションもあってかなり細かく指定できますが、配置にこだわりはじめるとやたらと時間がかかることがあるので、とりあえずpackを使って試作して、gridである程度整えるくらいで済ませています。

配置方法と例

配置方法特徴
pack 空いている場所に配置 widget.pack()
grid 指定された二次元格子状に配置
(縦方向がrow、横方向がcolumn)
widget.grid(row=0, column=2)
place 指定された絶対的位置に配置 widget.place(x = 20, y = 30, width=120, height=25)

ウィジットに機能を割り当てる

二つの方法があります。

ボタン作成時にコマンドを割り当てる

よく使われる方法で、イベント関連の情報を使うとか、複雑なキー操作による処理を考えていなければ、こちらで十分間に合います。

def btn_click(event):
  print('ボタンがクリックされました。')

btn = tk.Button(root, text='Button', command = btn_click)
# アプリクラス内であれば、self.btn = tk.Button(self, text='Button', command = self.btn_click)

bindを使ってウィジットにメソッドを割り当てる

既に作成されているウィジットに対して、そのウィジット上で何か操作をしたときに発生する機能を割り当てます。

# キャンバス上をマウスカーソルが動くたびに位置情報を表示させる
def callback(event):
  line = 'x:' + str(event.x) + ' ' + 'y:' + str(event.y)
  ent.delete(0, 20)
  ent.insert(0, line)

root = tk.Tk()
ent = tk.Entry(root)
ent.pack()
cvs = tk.Canvas(root, height=200, width=200, bg='white')
cvs.pack()

cvs.bind('<Motion>', callback) # アプリクラス内でbindするときは、self.wiget.bind~

イベントの種類は、単純にマウスをクリックしたときからマウスポインタが対象のウィジットから離れたときまで、様々あります。「python tkinter event」で検索するとたくさん出てきます。

参考