簡體   English   中英

Tkinter嵌入式圖形更改繪圖軸

[英]Tkinter embedded graph changing plot axes

所以我在這里有一個基本的GUI,其中包含2個框架。 第一頁有兩個下拉菜單,用戶可以在其中從數據框中選擇列。 它還包括一個按鈕,當按下該按鈕時,會將兩個選定的列都輸出到標簽上(這只是為了確保選擇正確)。

我試圖使代碼完成的工作是,使每次在下拉菜單中選擇新列時,圖形都會以新圖更新。 我以為將它們分配給一個字符串變量就這么簡單,但這似乎行不通。

還有第二頁帶有圖形,以防跨框架具有此功能更容易,但理想情況下將其保留在同一頁面上。

import pandas as pd
import tkinter as tk
#from tkinter import filedialog
from tkinter import ttk

import matplotlib

matplotlib.use("TkAgg")

from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg, NavigationToolbar2TkAgg

from matplotlib.figure import Figure

df = pd.DataFrame(
        [[4, 5, 6],
        [7, 8, 9],
        [10, 11, 12]],
        columns=['a', 'b', 'c'])

xList = []
yList = []

Options = df.dtypes.index 

fig = Figure(figsize=(5,4), dpi=100)
ax= fig.add_subplot(111)

LARGE_FONT= ("Verdana", 12)

class GUI(tk.Tk):

    def __init__(self, *args, **kwargs):

        tk.Tk.__init__(self, *args, **kwargs)
        tk.Tk.wm_title(self, "GUI")

        container = tk.Frame(self)
        container.pack(side="top", fill="both", expand = True)
        container.grid_rowconfigure(0, weight=1)
        container.grid_columnconfigure(0, weight=1)

        self.frames = {}

        for F in (Home, Graph):

            frame = F(container, self)

            self.frames[F] = frame

            frame.grid(row=0, column=0, sticky="nsew")

        self.show_frame(Home)




    def show_frame(self, cont):

        frame = self.frames[cont]
        frame.tkraise()


class Home(tk.Frame):

    def __init__(self, parent, controller):
        self.controller = controller
        tk.Frame.__init__(self,parent)
        label = tk.Label(self, text="Start Page", font=LARGE_FONT)
        label.pack(pady=10,padx=10)

        def selectXY():
            x = varX.get()            
            y = varY.get()

            ax.clear() 


            X.config(text=x)
            Y.config(text=y)

            xList = df.loc[:,X]
            yList = df.loc[:,Y]


            return xList
            return yList

        #Y axis select
        varY = tk.StringVar(self)
        # initial value
        varY.set('Select Y axis')

        optionY = tk.OptionMenu(self, varY, *Options)

        optionY.pack()

        #X axis select
        varX = tk.StringVar(self)
        # initial value
        varX.set('Select X axis')

        optionX = tk.OptionMenu(self, varX, *Options)

        optionX.pack()

        button2 = tk.Button(self, text="Plot Axes", command = selectXY)

        button2.pack()

        button2 = ttk.Button(self, text="Graph",
                            command=lambda: controller.show_frame(Graph))
        button2.pack()

        Y = ttk.Label(self, text=yList)
        Y.pack()

        X = ttk.Label(self, text=xList)
        X.pack()


        df.plot.scatter(xList, yList, ax=ax)


        canvas = FigureCanvasTkAgg(fig, self)
        canvas.show()
        canvas.get_tk_widget().pack(side=tk.BOTTOM, fill=tk.BOTH, expand=True)



class Graph(tk.Frame):

    def __init__(self, parent, controller):
        self.controller = controller
        tk.Frame.__init__(self,parent)
        label = tk.Label(self, text="Graph", font=LARGE_FONT)
        label.pack(pady=10,padx=10)


        df.plot.scatter(xList, yList, ax=ax)


        canvas = FigureCanvasTkAgg(fig, self)
        canvas.show()
        canvas.get_tk_widget().pack(side=tk.BOTTOM, fill=tk.BOTH, expand=True)


        button3 = ttk.Button(self, text="Back",
                            command=lambda: controller.show_frame(Home))
        button3.pack()

app = GUI()
app.mainloop()

請考慮以下調整:

  1. 將您的圖形構建移動到selectXY方法中,以便按鈕可以在單擊時運行它。

  2. 將軸按名稱傳遞到以xy作為字符串值的pandas.DataFrame.plot中。 因此,和的XlistyList .loc不需要調用和值能直接衍生出VARx前提的, 具體費用下拉菜單。

  3. 最后,將canvas移至__init__方法以被調用一次,而不是每次都創建一個新的canvas。

以下是家庭班的調整:

class Home(tk.Frame):

    def __init__(self, parent, controller):
        self.controller = controller
        tk.Frame.__init__(self,parent)
        label = tk.Label(self, text="Start Page", font=LARGE_FONT)
        label.pack(pady=10, padx=10)
        canvas = FigureCanvasTkAgg(fig, self)

        def selectXY():
            x = varX.get()            
            y = varY.get()

            X.config(text=x)
            Y.config(text=y)

            ax.clear()
            df.plot.scatter(x, y, ax=ax)

            canvas.draw()
            canvas.get_tk_widget().pack(side=tk.BOTTOM, fill=tk.BOTH, expand=True)

        # Y axis select
        varY = tk.StringVar(self)
        # initial value
        varY.set('Select Y axis')

        optionY = tk.OptionMenu(self, varY, *Options)
        optionY.pack()

        # X axis select
        varX = tk.StringVar(self)
        # initial value
        varX.set('Select X axis')

        optionX = tk.OptionMenu(self, varX, *Options)
        optionX.pack()

        button2 = tk.Button(self, text="Plot Axes", command = selectXY)
        button2.pack()

        button2 = ttk.Button(self, text="Graph",
                             command=lambda: controller.show_frame(Graph))
        button2.pack()

        Y = ttk.Label(self, text=yList)
        Y.pack()

        X = ttk.Label(self, text=xList)
        X.pack()

為了使Graph類復制與Home相同的圖,需要對全局變量, show_frame中的可見性觸發事件以及Graph中的更新屬性進行一些廣泛的調整。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM