Tkinter 中的嵌入式图:断开 y 轴并限制刻度和标签到子图
Embedded Plot in Tkinter: disconnect y-axis & limit ticks and label to subplot
我设置了一个应用程序,其中嵌入了交互式绘图 window。我想将几个子图放在彼此之上,具有共享的 x 轴和独立的 y 轴。整件事都是为了数据分析。
我设置了子图,但由于某种原因,第一个子图的 y 轴以某种方式连接到其他子图,而不是相反。
此外,刻度线和标签重叠,而不是停留在各自的子图中。
我尝试使用 pyplot.subplots
函数,它解决了独立轴和 ticks/labels 的问题,但是当我调用它而不是嵌入时,这会打开另一个 window它。
展示问题的工作示例代码 (Python 3.7):
# -*- coding: utf-8 -*-
import tkinter as tk
from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg, NavigationToolbar2Tk
from matplotlib.figure import Figure
from tkinter import ttk
import numpy as np
import pandas as pd
class window(tk.Tk):
def __init__(self,*args,**kwargs):
tk.Tk.__init__(self,*args,**kwargs)
self.generate_data()
self.plotPane = self.plot_pane(self)
def generate_data(self):
self.data = pd.DataFrame()
x = [1,2,3,4,5]
y = np.zeros((len(x)))
for i,yy in enumerate(y):
y[i] = yy + 10.*float(np.random.random())
self.data['x'] = x
self.data['y'] = y
class plot_pane():
def __init__(self,parent):
self.parent = parent
self.labelframe = ttk.Labelframe(self.parent,text="Plot")
replotButton = ttk.Button(self.parent,text="replot",command=self.update_plot)
self.labelframe.grid(row=0, column=0)
replotButton.grid(row=1,column=0)
self.figure = Figure(figsize=(6,3),dpi=100)
self.figure.subplots_adjust(left=0.11,bottom=0.09,right=0.77,top=0.92)# BaMa:. subplot margins, so labels are visible
self.sub = self.figure.add_subplot(111)
# toolbar and canvas for live plot
canvas = FigureCanvasTkAgg(self.figure,self.labelframe)
canvas.get_tk_widget().grid(row=1,column=1,rowspan=2,sticky="NSEW",pady=20)
canvas._tkcanvas.grid(row=1,column=1,rowspan=2, sticky="NSEW")
toolbar_frame = tk.Frame(self.labelframe)
toolbar_frame.grid(row=0,column=1,sticky="SEW")
toolbar = NavigationToolbar2Tk(canvas,toolbar_frame)
toolbar.update()
self.update_plot()
def update_plot(self,*args):
# clear figure
self.figure.clf()
stackAx = []
for i in range(0,2):
# generate new random data
self.parent.generate_data()
testX = self.parent.data['x']
testY = self.parent.data['y']
# add subplots
if i == 0:
stackAx.append(self.figure.add_subplot(i+1,1,1))# y-axis of this subplot is somehow connected to the other
else:
stackAx.append(self.figure.add_subplot(i+1,1,1,sharex=stackAx[0]))
# plot, add labels, ticks and grid
stackAx[i].plot(testX,testY)
stackAx[i].set_ylabel("ax-"+str(i))
stackAx[i].tick_params('y')
stackAx[i].grid()
self.figure.canvas.draw()
window = window()
window.mainloop()
因此,当您移动顶部的子图时,底部的 y 轴也会移动,并且 "ax-0" 标签 + 刻度线会破坏上方的子图。当您移动下图时,上图的 y 轴 不会 移动(应该移动)
我明白了。显然 add_subplot
和 pyplot.subplots
的功能有些不同,我没有理解正确。
以下更新功能有效:
def update_plot(self,*args):
# clear figure
self.figure.clf()
stackAx = []
numberOfPlots = 2
for i in range(0,numberOfPlots):
# generate new random data
self.parent.generate_data()
testX = self.parent.data['x']
testY = self.parent.data['y']
# add subplots
if i == 0:
stackAx.append(self.figure.add_subplot(numberOfPlots,1,i+1))
else:
stackAx.append(self.figure.add_subplot(numberOfPlots,1,i+1,sharex=stackAx[0]))
# plot, add labels, ticks and grid
stackAx[i].plot(testX,testY)
stackAx[i].set_ylabel("ax-"+str(i))
stackAx[i].tick_params('y')
stackAx[i].grid()
self.figure.canvas.draw()
我是从这里得到的:https://pythonprogramming.net/subplot2grid-add_subplot-matplotlib-tutorial/
我设置了一个应用程序,其中嵌入了交互式绘图 window。我想将几个子图放在彼此之上,具有共享的 x 轴和独立的 y 轴。整件事都是为了数据分析。
我设置了子图,但由于某种原因,第一个子图的 y 轴以某种方式连接到其他子图,而不是相反。 此外,刻度线和标签重叠,而不是停留在各自的子图中。
我尝试使用 pyplot.subplots
函数,它解决了独立轴和 ticks/labels 的问题,但是当我调用它而不是嵌入时,这会打开另一个 window它。
展示问题的工作示例代码 (Python 3.7):
# -*- coding: utf-8 -*-
import tkinter as tk
from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg, NavigationToolbar2Tk
from matplotlib.figure import Figure
from tkinter import ttk
import numpy as np
import pandas as pd
class window(tk.Tk):
def __init__(self,*args,**kwargs):
tk.Tk.__init__(self,*args,**kwargs)
self.generate_data()
self.plotPane = self.plot_pane(self)
def generate_data(self):
self.data = pd.DataFrame()
x = [1,2,3,4,5]
y = np.zeros((len(x)))
for i,yy in enumerate(y):
y[i] = yy + 10.*float(np.random.random())
self.data['x'] = x
self.data['y'] = y
class plot_pane():
def __init__(self,parent):
self.parent = parent
self.labelframe = ttk.Labelframe(self.parent,text="Plot")
replotButton = ttk.Button(self.parent,text="replot",command=self.update_plot)
self.labelframe.grid(row=0, column=0)
replotButton.grid(row=1,column=0)
self.figure = Figure(figsize=(6,3),dpi=100)
self.figure.subplots_adjust(left=0.11,bottom=0.09,right=0.77,top=0.92)# BaMa:. subplot margins, so labels are visible
self.sub = self.figure.add_subplot(111)
# toolbar and canvas for live plot
canvas = FigureCanvasTkAgg(self.figure,self.labelframe)
canvas.get_tk_widget().grid(row=1,column=1,rowspan=2,sticky="NSEW",pady=20)
canvas._tkcanvas.grid(row=1,column=1,rowspan=2, sticky="NSEW")
toolbar_frame = tk.Frame(self.labelframe)
toolbar_frame.grid(row=0,column=1,sticky="SEW")
toolbar = NavigationToolbar2Tk(canvas,toolbar_frame)
toolbar.update()
self.update_plot()
def update_plot(self,*args):
# clear figure
self.figure.clf()
stackAx = []
for i in range(0,2):
# generate new random data
self.parent.generate_data()
testX = self.parent.data['x']
testY = self.parent.data['y']
# add subplots
if i == 0:
stackAx.append(self.figure.add_subplot(i+1,1,1))# y-axis of this subplot is somehow connected to the other
else:
stackAx.append(self.figure.add_subplot(i+1,1,1,sharex=stackAx[0]))
# plot, add labels, ticks and grid
stackAx[i].plot(testX,testY)
stackAx[i].set_ylabel("ax-"+str(i))
stackAx[i].tick_params('y')
stackAx[i].grid()
self.figure.canvas.draw()
window = window()
window.mainloop()
因此,当您移动顶部的子图时,底部的 y 轴也会移动,并且 "ax-0" 标签 + 刻度线会破坏上方的子图。当您移动下图时,上图的 y 轴 不会 移动(应该移动)
我明白了。显然 add_subplot
和 pyplot.subplots
的功能有些不同,我没有理解正确。
以下更新功能有效:
def update_plot(self,*args):
# clear figure
self.figure.clf()
stackAx = []
numberOfPlots = 2
for i in range(0,numberOfPlots):
# generate new random data
self.parent.generate_data()
testX = self.parent.data['x']
testY = self.parent.data['y']
# add subplots
if i == 0:
stackAx.append(self.figure.add_subplot(numberOfPlots,1,i+1))
else:
stackAx.append(self.figure.add_subplot(numberOfPlots,1,i+1,sharex=stackAx[0]))
# plot, add labels, ticks and grid
stackAx[i].plot(testX,testY)
stackAx[i].set_ylabel("ax-"+str(i))
stackAx[i].tick_params('y')
stackAx[i].grid()
self.figure.canvas.draw()
我是从这里得到的:https://pythonprogramming.net/subplot2grid-add_subplot-matplotlib-tutorial/