Python tkinter マウスクリックした座標をcsv出力する方法

まくまく
まくまく
前回書いた「マウスイベントを出力するプログラム」の応用です。tkinterでGUIアプリっぽくしてみました。

出力


左側のフレームにボタンがふたつ。右側のエリアは座標表示用です。必要最小限のシンプルな構成にしています。


「ファイル選択」ボタンを押すとファイルダイアログが立ち上がるので、そこで任意の画像ファイルを選択します。

画像は別ウインドウで立ち上がるので、適当な場所をクリックしましょう。クリックが終わればこのウインドウは必要ないのでescで消しておきます。


クリックと同時に右側のテキストエリアに座標が表示されます。




「csv保存」ボタンを押すと、プログラムと同じフォルダに座標がcsv出力されます。

無事に座標をcsvで書き出して、エクセルで開くことができました。A列がX座標、B列がY座標になっています。

以下がサンプルプログラムとなります。(Pythonは学習中のため無駄な記述などがある場合があることご了承ください)

サンプルプログラム

#ライブラリのインポート
import tkinter as tk
import tkinter.filedialog
import cv2
import pandas as pd

#画像選択、表示する関数
def getfile():
    global img
    f_path = tk.filedialog.askopenfilename(title="ファイル選択", initialdir="ディレクトリを入力", \
                                           filetypes=[("Image file", ".png .jpg .jpeg")])
    str_file_path = str(f_path)
    text_widget.delete("1.0","end")
    points[:0]
    img = cv2.imread(str_file_path)
    #cv2.namedWindow('img',cv2.WINDOW_NORMAL)
    cv2.imshow('img', img)
    cv2.setMouseCallback('img',coordinates)
    cv2.waitKey(0)
    cv2.destroyAllWindows()
    exit()

#マウスイベント
#クリックした座標をリストに格納する
def coordinates(event,x,y, flags,param):
    if event == cv2.EVENT_LBUTTONDOWN:
        points.append([x,y])
        text_widget.insert("insert +1lines",str(x)+","+str(y)+"\n")

#csvファイルを保存
def save():
    df = pd.DataFrame(points)
    df.to_csv("test.csv", encoding="utf-8", header=False, index=False)

#ウインドウの作成
root = tk.Tk()
#ウインドウのタイトル
root.title("マウスクリック to csv")
#ウインドウサイズと位置指定 幅,高さ,x座標,y座標 
root.geometry("350x470+50+50")
#フレームの作成
frame = tk.Frame(root, width=330, height=450, bg="#D9D9D9")
frame.place(x=10, y=10)
frame_menu = tk.Frame(frame, relief=tk.FLAT, bg="#E6E6E6", bd=2)
frame_menu.place(x=10, y=10, width=150, height=430)
frame_img = tk.Frame(frame, relief=tk.FLAT, bg="#E6E6E6", bd=2)
frame_img.place(x=170, y=10, width=150, height=430)

#座標用 空のリスト
points = []

#テキストボックスの作成
text_widget = tk.Text(frame_img, height=30, width=19)
text_widget.grid(row=0, column=0, sticky = tk.W)

#ボタン作成
button = tk.Button(frame_menu, text="ファイル選択", command=getfile)
button.grid(row=1, column=0, sticky = tk.W)
button_save = tk.Button(frame_menu, text="csv保存", command=save)
button_save.grid(row=14, column=0, sticky = tk.W)

#イベントループ
root.mainloop()
「initialdir」にはディレクトリを入力してください。

追記

大きな画像を扱うときはcv2.namedWindwの行を有効にしてください。ただ、環境が変わると挙動が異なるかもしれません。

タイトルとURLをコピーしました