MatPlotLib PyQt5 Layout Problems

让人想犯罪 __ 提交于 2020-01-25 22:56:16

问题


MatPlotLib PyQt5 Layout Problems:

Using horizontal and vertical layouts, it seems to be very difficult to get the widgets where I want them. Maybe there is another way of doing it, for instance:

  1. If one can put the canvas and toolbar in a container or some kind of widget. Then you can size it and put it where you want.
  2. If one can limit the size of the plot so that the UI in the background is visible. This seems impossible though.
  3. What about using QGridLayout?

I have tried many things, but am very confused and nothing seems to work.

The problems I have (using the current horizontal and vertical layouts) are:

  1. The labels drift and are not aligned with the widgets.
  2. The buttonbox is too wide. Can the buttons be split between the last two columns?

Here is some code. Sorry for the formatting. (It's hard to get the 4 spaces right):

import sys
from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg as FigureCanvas
from matplotlib.backends.backend_qt5agg import NavigationToolbar2QT as NavigationToolbar
import matplotlib.pyplot as plt
import random
from PyQt5.QtWidgets import QPushButton, QVBoxLayout, QHBoxLayout, QApplication, QDialog, QGridLayout, QLayout
from PyQt5 import QtCore, QtGui, QtWidgets


class Ui_Dialog(QDialog):
def __init__(self, parent=None):
    super(Ui_Dialog, self).__init__(parent)
    self.setupUi(self)
    self.setupPlot()

def setupUi(self, Dialog):
    Dialog.setObjectName("Dialog")
    Dialog.resize(719, 353)
    Dialog.setWindowTitle("Task")
    self.buttonBox = QtWidgets.QDialogButtonBox(Dialog)
    self.buttonBox.setGeometry(QtCore.QRect(590, 310, 121, 32))
    self.buttonBox.setOrientation(QtCore.Qt.Horizontal)
    self.buttonBox.setStandardButtons(QtWidgets.QDialogButtonBox.Cancel|QtWidgets.QDialogButtonBox.Ok)
    self.buttonBox.setObjectName("buttonBox")
    self.label1 = QtWidgets.QLabel(Dialog)
    self.label1.setGeometry(QtCore.QRect(590, 40, 51, 16))
    self.label1.setText("label1:")
    self.label1.setObjectName("label1")
    self.label2 = QtWidgets.QLabel(Dialog)
    self.label2.setGeometry(QtCore.QRect(590, 70, 41, 16))
    self.label2.setText("label2:")
    self.label2.setObjectName("label2")
    self.cBox1 = QtWidgets.QComboBox(Dialog)
    self.cBox1.setGeometry(QtCore.QRect(650, 40, 61, 22))
    self.cBox1.setLayoutDirection(QtCore.Qt.LeftToRight)
    self.cBox1.setEditable(False)
    self.cBox1.setCurrentText("Option0")
    self.cBox1.setMaxVisibleItems(2)
    self.cBox1.setObjectName("cBox1")
    self.cBox1.addItem("")
    self.cBox1.setItemText(0, "Option0")
    self.cBox1.addItem("")
    self.cBox1.setItemText(1, "Option1")
    self.label5 = QtWidgets.QLabel(Dialog)
    self.label5.setGeometry(QtCore.QRect(590, 160, 51, 16))
    self.label5.setText("label5:")
    self.label5.setObjectName("label5")
    self.dSpinBox5 = QtWidgets.QDoubleSpinBox(Dialog)
    self.dSpinBox5.setGeometry(QtCore.QRect(650, 160, 62, 22))
    self.dSpinBox5.setAlignment(QtCore.Qt.AlignRight|QtCore.Qt.AlignTrailing|QtCore.Qt.AlignVCenter)
    self.dSpinBox5.setMaximum(1999.99)
    self.dSpinBox5.setObjectName("dSpinBox5")
    self.dSpinBox4 = QtWidgets.QDoubleSpinBox(Dialog)
    self.dSpinBox4.setGeometry(QtCore.QRect(650, 130, 62, 22))
    self.dSpinBox4.setAlignment(QtCore.Qt.AlignRight|QtCore.Qt.AlignTrailing|QtCore.Qt.AlignVCenter)
    self.dSpinBox4.setMaximum(1999.99)
    self.dSpinBox4.setObjectName("dSpinBox4")
    self.label0 = QtWidgets.QLabel(Dialog)
    self.label0.setGeometry(QtCore.QRect(590, 10, 41, 16))
    self.label0.setText("label0:")
    self.label0.setObjectName("label0")
    self.dSpinBox3 = QtWidgets.QDoubleSpinBox(Dialog)
    self.dSpinBox3.setGeometry(QtCore.QRect(650, 100, 62, 22))
    self.dSpinBox3.setAlignment(QtCore.Qt.AlignRight|QtCore.Qt.AlignTrailing|QtCore.Qt.AlignVCenter)
    self.dSpinBox3.setMaximum(1999.99)
    self.dSpinBox3.setObjectName("dSpinBox3")
    self.label3 = QtWidgets.QLabel(Dialog)
    self.label3.setGeometry(QtCore.QRect(590, 100, 61, 16))
    self.label3.setText("label3:")
    self.label3.setObjectName("label3")
    self.lineEdit0 = QtWidgets.QLineEdit(Dialog)
    self.lineEdit0.setGeometry(QtCore.QRect(650, 10, 61, 20))
    self.lineEdit0.setInputMask("")
    self.lineEdit0.setText("")
    self.lineEdit0.setObjectName("lineEdit0")
    self.label4 = QtWidgets.QLabel(Dialog)
    self.label4.setGeometry(QtCore.QRect(590, 130, 41, 16))
    self.label4.setText("label4:")
    self.label4.setObjectName("label4")
    self.spinBox2 = QtWidgets.QSpinBox(Dialog)
    self.spinBox2.setGeometry(QtCore.QRect(650, 70, 61, 22))
    self.spinBox2.setAlignment(QtCore.Qt.AlignRight|QtCore.Qt.AlignTrailing|QtCore.Qt.AlignVCenter)
    self.spinBox2.setMaximum(999)
    self.spinBox2.setSingleStep(10)
    self.spinBox2.setProperty("value", 50)
    self.spinBox2.setObjectName("spinBox2")
    self.label6 = QtWidgets.QLabel(Dialog)
    self.label6.setGeometry(QtCore.QRect(590, 190, 41, 16))
    self.label6.setText("label6:")
    self.label6.setObjectName("label6")
    self.dSpinBox6 = QtWidgets.QDoubleSpinBox(Dialog)
    self.dSpinBox6.setGeometry(QtCore.QRect(650, 190, 62, 22))
    self.dSpinBox6.setAlignment(QtCore.Qt.AlignRight|QtCore.Qt.AlignTrailing|QtCore.Qt.AlignVCenter)
    self.dSpinBox6.setReadOnly(True)
    self.dSpinBox6.setButtonSymbols(QtWidgets.QAbstractSpinBox.NoButtons)
    self.dSpinBox6.setObjectName("dSpinBox6")
    self.label7 = QtWidgets.QLabel(Dialog)
    self.label7.setGeometry(QtCore.QRect(590, 220, 47, 16))
    self.label7.setText("label7:")
    self.label7.setObjectName("label7")
    self.spinBox7 = QtWidgets.QSpinBox(Dialog)
    self.spinBox7.setGeometry(QtCore.QRect(650, 220, 61, 22))
    self.spinBox7.setAlignment(QtCore.Qt.AlignRight|QtCore.Qt.AlignTrailing|QtCore.Qt.AlignVCenter)
    self.spinBox7.setMaximum(999)
    self.spinBox7.setProperty("value", 50)
    self.spinBox7.setObjectName("spinBox7")
    self.checkBox8 = QtWidgets.QCheckBox(Dialog)
    self.checkBox8.setGeometry(QtCore.QRect(650, 250, 61, 20))
    self.checkBox8.setLayoutDirection(QtCore.Qt.RightToLeft)
    self.checkBox8.setText("")
    self.checkBox8.setCheckable(False)
    self.checkBox8.setObjectName("checkBox8")
    self.checkBox9 = QtWidgets.QCheckBox(Dialog)
    self.checkBox9.setGeometry(QtCore.QRect(650, 280, 61, 20))
    self.checkBox9.setLayoutDirection(QtCore.Qt.RightToLeft)
    self.checkBox9.setText("")
    self.checkBox9.setCheckable(False)
    self.checkBox9.setObjectName("checkBox9")
    self.label8 = QtWidgets.QLabel(Dialog)
    self.label8.setGeometry(QtCore.QRect(590, 250, 51, 16))
    self.label8.setText("label8")
    self.label8.setObjectName("label8")
    self.label9 = QtWidgets.QLabel(Dialog)
    self.label9.setGeometry(QtCore.QRect(590, 276, 47, 16))
    self.label9.setText("label9")
    self.label9.setObjectName("label9")

    self.buttonBox.accepted.connect(Dialog.accept)
    self.buttonBox.rejected.connect(Dialog.reject)
    QtCore.QMetaObject.connectSlotsByName(Dialog)

def setupPlot(self):
    self.setLayout(QHBoxLayout())
    self.layout().setContentsMargins(0, 0, 0, 0)
    self.figure = plt.figure()
    self.figure.set_facecolor("none")
    self.canvas = FigureCanvas(self.figure)

    self.toolbar = NavigationToolbar(self.canvas, self)

    self.widget = QtWidgets.QWidget()
    layout = QVBoxLayout()
    self.widget.setLayout(layout)
    layout.addWidget(self.toolbar)
    layout.addWidget(self.canvas)
    self.layout().addWidget(self.widget)

    self.widget = QtWidgets.QWidget()
    layout = QVBoxLayout()
    self.widget.setLayout(layout)
    layout.addWidget(self.label0)
    layout.addWidget(self.label1)
    layout.addWidget(self.label2)
    layout.addWidget(self.label3)
    layout.addWidget(self.label4)
    layout.addWidget(self.label5)
    layout.addWidget(self.label6)
    layout.addWidget(self.label7)
    layout.addWidget(self.label8)
    layout.addWidget(self.label9)
    self.layout().addWidget(self.widget)

    self.widget = QtWidgets.QWidget()
    layout = QVBoxLayout()
    self.widget.setLayout(layout)
    layout.addWidget(self.lineEdit0)
    layout.addWidget(self.cBox1)
    layout.addWidget(self.spinBox2)
    layout.addWidget(self.dSpinBox3)
    layout.addWidget(self.dSpinBox4)
    layout.addWidget(self.dSpinBox5)
    layout.addWidget(self.dSpinBox6)
    layout.addWidget(self.spinBox7)
    layout.addWidget(self.checkBox8)
    layout.addWidget(self.checkBox9)
    layout.addWidget(self.buttonBox)
    self.layout().addWidget(self.widget)

    self.plot()

def plot(self):
    data = [random.random() for i in range(10)]
    self.figure.clear()
    ax = self.figure.add_subplot(111)
    ax.plot(data, '*-')
    self.canvas.draw()


if __name__ == '__main__':
    app = QApplication(sys.argv)
    main = Ui_Dialog()
    main.show()
    sys.exit(app.exec_())

回答1:


@ImportanceOfBeingErnest Your comment is what solved the question. Appreciated:

  1. Removed all the setGeometry calls.
  2. Created a QGridLayout .
  3. Added widgets to the gridLayout like this: self.layout().addWidget(self.checkBoxDone, 3, 4, 1, 1)

NB: Be careful not to confuse the parameters:

  1. widget
  2. start row (from 0 at the top)
  3. start column (from 0 on the left)
  4. number of rows to span (downwards)
  5. number of columns to span (to the right)


来源:https://stackoverflow.com/questions/44483538/matplotlib-pyqt5-layout-problems

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!