gpt4 book ai didi

numpy - 在 Qt 中显示 matplotlib imshow 输出

转载 作者:行者123 更新时间:2023-12-04 10:32:26 25 4
gpt4 key购买 nike

我有一个 np.float64 类型的二维 numpy 数组,我想在 QLabel(或任何其他有效方式)中将其显示为图像:

self.img = np.rot90(get_my_data()) # this line returns a 2D numpy array of type np.float64
self.qimg = QtGui.QImage(self.img, self.img.shape[0], self.img.shape[1], QtGui.QImage.Format_Grayscale8)
self.myLabel.setPixmap(QtGui.QPixmap(self.qimg))

我上面的代码返回以下错误:

TypeError: arguments did not match any overloaded call:
QImage(): too many arguments
QImage(QSize, QImage.Format): argument 1 has unexpected type 'numpy.ndarray'
QImage(int, int, QImage.Format): argument 1 has unexpected type 'numpy.ndarray'
QImage(bytes, int, int, QImage.Format): argument 1 has unexpected type 'numpy.ndarray'
QImage(sip.voidptr, int, int, QImage.Format): argument 1 has unexpected type 'numpy.ndarray'
QImage(bytes, int, int, int, QImage.Format): argument 1 has unexpected type 'numpy.ndarray'
QImage(sip.voidptr, int, int, int, QImage.Format): argument 1 has unexpected type 'numpy.ndarray'
QImage(List[str]): argument 1 has unexpected type 'numpy.ndarray'
QImage(str, format: str = None): argument 1 has unexpected type 'numpy.ndarray'
QImage(QImage): argument 1 has unexpected type 'numpy.ndarray'
QImage(Any): too many arguments

但是,如果我在第一行末尾添加 .copy(),那么它就可以工作了!但它没有正确显示数据。

self.img = np.rot90(get_my_data()).copy()
self.qimg = QtGui.QImage(self.img, self.img.shape[0], self.img.shape[1], QtGui.QImage.Format_Grayscale8)
self.myLabel.setPixmap(QtGui.QPixmap(self.qimg))

pyplot.imshow() 相比,标签显示的内容如下:

self.img = 20 * np.log10(np.rot90(get_my_data()).copy())
self.qimg = QtGui.QImage(self.img, self.img.shape[0], self.img.shape[1], QtGui.QImage.Format_Grayscale8)
self.myLabel.setPixmap(QtGui.QPixmap(self.qimg))
pyplot.imshow(self.img)
pyplot.show()

pyplot.imshow() 的结果是:

enter image description here

myLabel 显示以下结果:

enter image description here

那么,我的代码有什么问题吗?

是否有更优雅的方式将我的 2D numpy 数组显示为图像?

最佳答案

根据我的阅读,OP 有一个 XY problem ,也就是说,它的目标是在 Qt 窗口中显示 imshow() 的输出,但询问在 QImage 中显示数据的尝试。

imshow()方法不显示原始数据,而是根据文档指示的参数处理信息:

matplotlib.pyplot.imshow(X, cmap=None, norm=None, aspect=None, interpolation=None, alpha=None, vmin=None, vmax=None, origin=None, extent=None, shape=, filternorm=1, filterrad=4.0, imlim=, resample=None, url=None, *, data=None, **kwargs)

所以如果你想用那个数据得到一个图像你必须实现那个算法(你可以查看matplotlib或类似软件的源代码来分析逻辑)

如果我们专注于真正的目标,那么最简单的解决方案是使用 matplotlib 的 Qt 后端来获取合适的 Canvas ,如下所示:

import numpy as np

from PyQt5 import QtWidgets
from matplotlib.backends.backend_qt5agg import FigureCanvas
from matplotlib.figure import Figure


class MainWindow(QtWidgets.QMainWindow):
def __init__(self, parent=None):
super().__init__(parent)

self.figure = Figure(figsize=(5, 3))
self.canvas = FigureCanvas(self.figure)
self.ax = self.figure.subplots()

delta = 0.025
x = y = np.arange(-3.0, 3.0, delta)
X, Y = np.meshgrid(x, y)
Z1 = np.exp(-(X ** 2) - Y ** 2)
Z2 = np.exp(-((X - 1) ** 2) - (Y - 1) ** 2)
Z = (Z1 - Z2) * 2

self.ax.imshow(Z)
self.ax.set_axis_off()

self.setCentralWidget(self.canvas)


if __name__ == "__main__":
import sys

app = QtWidgets.QApplication(sys.argv)
w = MainWindow()
w.resize(640, 480)
w.show()

sys.exit(app.exec_())

enter image description here

更新:

如果你想不时显示数据,那么你可以使用 QTimer 来更新信息,如下所示:

import random
import numpy as np

from PyQt5 import QtCore, QtWidgets
from matplotlib.backends.backend_qt5agg import FigureCanvas
from matplotlib.figure import Figure


class MainWindow(QtWidgets.QMainWindow):
def __init__(self, parent=None):
super().__init__(parent)

self.figure = Figure(figsize=(5, 3))
self.canvas = FigureCanvas(self.figure)
self.ax = self.figure.subplots()
self.ax.set_axis_off()

self.setCentralWidget(self.canvas)

timer = QtCore.QTimer(self)
timer.timeout.connect(self.on_timeout)
timer.start(100)

def on_timeout(self):
x0, y0 = random.uniform(-2, 2), random.uniform(-2, 2)
delta = 0.025
x = y = np.arange(-3.0, 3.0, delta)
X, Y = np.meshgrid(x, y)
Z1 = np.exp(-(X ** 2) - Y ** 2)
Z2 = np.exp(-((X - x0) ** 2) - (Y - y0) ** 2)
Z = (Z1 - Z2) * 2
self.ax.imshow(Z)
self.canvas.draw()


if __name__ == "__main__":
import sys

app = QtWidgets.QApplication(sys.argv)
w = MainWindow()
w.resize(640, 480)
w.show()

sys.exit(app.exec_())

另一方面,如果您想实时拥有软件,那么 GUI 会限制该目标。建议每 N 个样本显示一次数据,这样 GUI 就不会被阻塞,用户可以查看和分析信息。人眼非常慢,所以即使存在每微秒显示图像的技术,我们的视觉也不会欣赏它,我们的视觉需要 60 毫秒来处理图像,因此设备设计为工作在 30Hz,因为如果频率更高观察不到改善。

关于numpy - 在 Qt 中显示 matplotlib imshow 输出,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60358003/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com