【问题标题】:Scaling embedded matplotlib widget in qt application written in python problem在用 python 编写的 qt 应用程序中缩放嵌入式 matplotlib 小部件问题
【发布时间】:2011-11-06 12:05:15
【问题描述】:

我正在编写一个简单的数字图像处理程序。为此,我在我的 qt 应用程序中嵌入了一个 mpl 小部件。用户可以对图像进行一些简单的分析,例如箱式汽车过滤器、FFT 等。一切正常,直到我想从显示图像切换到显示图。

如果我先显示一个图,则轴很好(参见图像中的底部图)。但是,如果我先显示一张图片,然后再显示一张图(图片中的顶部图),则比例会压缩。

https://picasaweb.google.com/105163945296073520628/Temp

代码托管在这里https://code.launchpad.net/~marrabld/pymi/trunk

我正在使用 imshow() 来显示图像。和 plot(x,y) 用于绘图。

这是主要的更新方法

def updateImage(self):
    self.ui.mplWidget.canvas.PlotTitle = self.plotTitle
    self.ui.mplWidget.canvas.xtitle = self.xTitle
    self.ui.mplWidget.canvas.ytitle = self.yTitle
    #self.ui.mplWidget.canvas.ax.visible(False)

    self.ui.mplWidget.canvas.format_labels()
    if self.projectProperty == globals.IMAGE:
        if self.lastProjectProperty == globals.PLOT:
            self.myImage = imageFuncs.basic(self.imageFileName)

        self.imPlot = self.ui.mplWidget.canvas.ax.imshow(self.myImage.image,cmap=matplotlib.cm.gray,origin='upper')

    elif self.projectProperty == globals.PLOT:

        if self.lastProjectProperty == globals.IMAGE: # we need to reload the GUI

            self.ui.mplWidget.canvas.ax.hold(False) 

        self.ui.mplWidget.canvas.ax.plot(self.xData,self.yData)

    self.ui.mplWidget.canvas.draw()

还有我正在使用的 mpl 小部件

#!/usr/bin/env python
from PyQt4.QtCore import *
from PyQt4.QtGui import *

from matplotlib.backends.backend_qt4agg import FigureCanvasQTAgg as FigureCanvas
#from matplotlib.backends.backend_qt4 import NavigationToolbar2QT as NavigationToolbar
from matplotlib.backend_bases import NavigationToolbar2

from matplotlib.figure import Figure
from matplotlib import rc

import numpy as N

class MyMplCanvas(FigureCanvas):
    def __init__(self, parent=None, width = 10, height = 12, dpi = 125, sharex = None, sharey = None):

            rc('text', usetex=True)
            rc('font', family='sans-serif')
            rc('legend',fontsize='small' )
            rc('legend',shadow='true')

            self.fig = Figure(figsize = (width, height), dpi=dpi, facecolor = '#FFFFFF')

            self.ax = self.fig.add_subplot(111, sharex = sharex, sharey = sharey)
            self.fig.subplots_adjust(left=0.15, bottom=0.15, right=0.9, top=0.9)
            self.fig.add_axes(yscale='symlog')
            self.xtitle=r"x-Axis"
            self.ytitle=r"y-Axis"
            self.PlotTitle = r"Title"
            self.grid_status = True
            self.xaxis_style = 'linear'
            self.yaxis_style = 'linear'
            #self.fig.yscale = 'log'
            self.format_labels()
            self.ax.hold(True)
            FigureCanvas.__init__(self, self.fig)
            #self.fc = FigureCanvas(self.fig)
            #FigureCanvas.setSizePolicy(self,
             #       QSizePolicy.Expanding,
              #      QSizePolicy.Expanding)
            FigureCanvas.updateGeometry(self)

    def format_labels(self):
            self.ax.set_title(self.PlotTitle)
            self.ax.title.set_fontsize(5)
            self.ax.set_xlabel(self.xtitle, fontsize = 4)
            self.ax.set_ylabel(self.ytitle, fontsize = 4)
            labels_x = self.ax.get_xticklabels()
            labels_y = self.ax.get_yticklabels()

            for xlabel in labels_x:
                    xlabel.set_fontsize(4)
            for ylabel in labels_y:
                    ylabel.set_fontsize(4)
                    ylabel.set_color('b')

    def sizeHint(self):
            w, h = self.get_width_height()
            return QSize(w, h)

    def minimumSizeHint(self):
            return QSize(10, 10)

    def sizeHint(self):
            w, h = self.get_width_height()
            return QSize(w, h)

    def minimumSizeHint(self):
            return QSize(10, 10)




    #mouseClick = pyqtProperty("QPoint",mouseClick,click)






class mplWidget(QWidget):
    def __init__(self, parent = None):
            QWidget.__init__(self, parent)
            self.canvas = MyMplCanvas()
            #self.toolbar = MyNavigationToolbar(self.canvas, self.canvas, direction = 'v')
            self.hbox = QHBoxLayout()
            #self.hbox.addWidget(self.toolbar)
            self.hbox.addWidget(self.canvas)
            self.setLayout(self.hbox)

    def savePlot(self,filePath):
            self.canvas.fig.savefig(filePath)

    def setLegend(self,handle, label):
            self.canvas.fig.legend(handle,label,'upper right')

    def clearPlot(self):
            self.canvas.fig.clear()

            width = 10
            height = 12
            dpi = 125
            sharex = None
            sharey = None

            self.canvas.fig = Figure(figsize = (width, height), dpi=dpi, facecolor = '#FFFFFF')

            self.canvas.ax = self.canvas.fig.add_subplot(111, sharex = sharex, sharey = sharey)
            self.canvas.fig.subplots_adjust(left=0.15, bottom=0.15, right=0.9, top=0.9)
            self.canvas.fig.add_axes(yscale='symlog')
            self.canvas.xtitle=r"x-Axis"
            self.canvas.ytitle=r"y-Axis"
            self.canvas.PlotTitle = r"Title"
            self.canvas.grid_status = True
            self.canvas.xaxis_style = 'linear'
            self.canvas.yaxis_style = 'linear'
            #self.fig.yscale = 'log'
            self.canvas.format_labels()
            self.canvas.ax.hold(True)

            FigureCanvas.__init__(self.canvas, self.canvas.fig)
            #self.fc = FigureCanvas(self.fig)
            FigureCanvas.setSizePolicy(self,
                    QSizePolicy.Expanding,
                    QSizePolicy.Expanding)
            FigureCanvas.updateGeometry(self)

任何帮助将不胜感激。

【问题讨论】:

    标签: python qt pyqt matplotlib


    【解决方案1】:

    你可以使用 imshow() 的 aspect 参数来调整身高和体重的比例:

    from pylab import *
    a = np.zeros((100,10)) # height=100, weight=10
    subplot(211)
    imshow(a)  # ratio = 10
    subplot(212)
    imshow(a, aspect=0.1) # ratio = 1
    show()
    

    但它会拉伸图像。

    或者你可以使用xlim()、ylim()来设置x-y轴的范围。

    imshow(a)
    xlim(-50,50)
    

    编辑:

    imshow() 将 ax 的 aspect 属性设置为“equal”。你需要在调用 plot() 之前重置它:

    self.ui.mplWidget.canvas.ax.set_aspect("auto")
    self.ui.mplWidget.canvas.ax.plot(self.xData,self.yData)
    

    【讨论】:

    • 感谢您的回答,但我的问题不在于显示图像时的纵横比。图像始终正确显示。当我在显示图像后显示绘图时。
    • 是aspect属性的问题,但是我没有仔细看你的代码。查看您的代码后,我编辑了答案。请再次检查。
    猜你喜欢
    • 1970-01-01
    • 2013-08-30
    • 1970-01-01
    • 1970-01-01
    • 2019-09-27
    • 2013-09-14
    • 2010-11-27
    • 1970-01-01
    • 2011-07-05
    相关资源
    最近更新 更多