I've created aQMainWindow with menubar and 4 dockable widgets. First dockwidget contents multipletabs, second is Qpainter widget, third is Matlabplot and fourth is pdf report.
When I run the code shows up like this below.
I want to be like below.
I want to divide screen into four widget automatically whenever it runs at any screen, And I want to have tabs to resize to its content.
Or do you have any better idea of having such widget, you are welcome to come with it.
Update of code
Resize of Qdockwidget brings this post forward. It seems that Qt Qdockwidget resize has been an issue for long time ago. I find it very difficult to program my Qmainwindow with 4 Qdockwidget, which the dock would fit and resize according to its contents, with other words, child widget. and According to Qt documentation, Qdockwidget resizes and respect the size of child Widgets. to get straight to problem, my mainwindow has 4 qdockwidgets, I would like to have them resizable according to contents.
What I have tried and used so far.
I have used following size functions.
self.sizeHint, self.minimumSize(), self.maximumSize() and self.setFixedSize(self.sizeHint()).
I am able to fix the size of contents in first Qdockwidget by using following codes.
self.setFixedSize(self.sizeHint())
Above code is written in the child widgets Class widgets
But that is not enough in order to work it, despite following codes needed to run and effect.
self.first.setMinimumSize(self.first.sizeHint())
self.grid.setMinimumSize(self.grid.sizeHint())
self.third.setMinimumSize(self.third.sizeHint())
self.adjustSize()
self.first.setMinimumSize(self.first.minimumSizeHint())
self.grid.setMinimumSize(self.grid.minimumSizeHint())
self.third.setMinimumSize(self.third.minimumSizeHint())
Noting that still my dockwindow does not resize according to child widgets. Dockwidget expand and increase. One may ask, Qdockwidgets could arrange and control by resizeDocks(). This code line is used and tried, but still does not get the desired behaviour.
I have been looking around and could find some relevant questions.
C++ resize a docked Qt QDockWidget programmatically?
Forcing a QDockWidget to behave like a central widget when it comes to resizing
Create a QDockWidget that resizes to it's contents
Those questions do not solve my problem.
Visualization of my code launch
1- When code runs and display on screen.
2- Desired and wanted display by first run of software.
3- When user tabs between tabwidgets want to resize to its content as image below.
4- The code is given below.
import sys, os
from PyQt5 import QtCore, QtWidgets, QtGui
from PyQt5.QtWidgets import QMainWindow, QLabel, QGridLayout, QWidget,
QDesktopWidget, QApplication, QAction, QFileDialog,QColorDialog
from PyQt5.QtWidgets import QPushButton, QMessageBox, QDockWidget,
QTabWidget, QVBoxLayout, QGroupBox, QHBoxLayout, QFrame, QSplitter
from PyQt5.QtWidgets import QTableWidget, QRadioButton, QListWidget,
QCheckBox, QTextEdit, QDialog, QSizePolicy
from PyQt5.QtCore import QSize, Qt, QFileInfo, QFile
from PyQt5.QtGui import QIcon, QKeySequence, QPainter, QPalette, QPen,
QBrush, QTextCursor, QFont
import matplotlib.pyplot as plt
#plt.style.use('ggplot')
from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg as FigureCanvas
from matplotlib.backends.backend_qt5agg import NavigationToolbar2QT as NavigationToolbar
import seaborn as sns
iconroot = os.path.dirname(__file__)
class mywindow(QMainWindow):
def __init__(self):
super(mywindow, self).__init__()
self.setMinimumSize(QSize(1200,800))
self.setWindowTitle('My Graphic Window')
centralWidget = QWidget(self)
self.setCentralWidget(centralWidget)
gridLayout = QGridLayout(self)
centralWidget.setLayout(gridLayout)
qtRectangle = self.frameGeometry()
centerPoint = QDesktopWidget().availableGeometry().center()
qtRectangle.moveCenter(centerPoint)
self.move(qtRectangle.topLeft())
imageroot = QFileInfo(__file__).absolutePath()
# Greate new action
newaction = QAction(QIcon(imageroot +'/images/new.png'), '&New', self)
newaction.setShortcut('Ctrl+N')
newaction.setStatusTip('New document')
newaction.triggered.connect(self.newCall)
# Greate menu bar and add action
menubar = self.menuBar()
filemenu = menubar.addMenu('&Test')
filemenu.addAction(newaction)
# Get current screen geometry
self.Screen = QtWidgets.QDesktopWidget().screenGeometry()
print(self.Screen, self.Screen.height(), self.Screen.width())
# def createToolbar(self):
self.filetoolbar = self.addToolBar('File')
self.filetoolbar.addAction(newaction)
self.topleftdockwindow()
self.toprightdockwindow()
def newCall(self):
print('New')
# Greate dockable subwindow.
def topleftdockwindow(self):
topleftwindow = QDockWidget ('Info',self)
# Stick window to left or right
topleftwindow.setAllowedAreas(Qt.LeftDockWidgetArea | Qt.RightDockWidgetArea)
self.addDockWidget(Qt.TopDockWidgetArea, topleftwindow)
topleftwindow.setWidget(createtabwidget())
topleftwindow.resize( topleftwindow.minimumSize() )
bottomleftwindow = QDockWidget("Matplot",self)
bottomleftwindow.setAllowedAreas(Qt.LeftDockWidgetArea | Qt.RightDockWidgetArea)
self.addDockWidget(Qt.BottomDockWidgetArea, bottomleftwindow)
bottomleftwindow.setWidget(createplotwidget())
self.setDockNestingEnabled(True)
topleftwindow.resize( topleftwindow.minimumSize() )
self.splitDockWidget(topleftwindow, bottomleftwindow , Qt.Vertical)
#self.resizeDocks((topleftwindow, bottomleftwindow), (40,20),
#Qt.Horizontal)
# Greate topright dockwindow.
def toprightdockwindow(self):
toprightdock = QDockWidget ('Plot',self)
toprightdock = QDockWidget ('Plot',self)
toprightdock.setAllowedAreas(Qt.LeftDockWidgetArea | Qt.RightDockWidgetArea)
self.addDockWidget(Qt.TopDockWidgetArea, toprightdock)
#self.setDockOptions(self.AnimatedDocks | self.AllowNestedDocks)
toprightdock.setWidget(createpaintwidget())
toprightdock.setFloating( True )
bottomrightdock = QDockWidget("Technical report",self)
bottomrightdock.setAllowedAreas(Qt.LeftDockWidgetArea | Qt.RightDockWidgetArea)
self.addDockWidget(Qt.BottomDockWidgetArea, bottomrightdock)
bottomrightdock.setWidget(QtWidgets.QListWidget())
self.splitDockWidget(toprightdock, bottomrightdock, Qt.Vertical)
class createpaintwidget(QWidget):
def __init__(self):
super().__init__()
self.setBackgroundRole(QPalette.Base)
self.setAutoFillBackground(True)
self.sizeHint()
self.adjustSize()
def paintEvent(self, event):
self.pen = QPen()
self.brush = QBrush(Qt.gray,Qt.Dense7Pattern)
painter = QPainter(self)
painter.setPen(self.pen)
painter.setBrush(self.brush)
painter.drawRect(100,100,250,250)
painter.setBrush(QBrush())
painter.drawEllipse(400,100,200,200)
class createplotwidget(QWidget):
def __init__(self):
super().__init__()
self.initializewidget()
self.plot1()
self.setMaximumSize(self.sizeHint())
self.adjustSize()
def initializewidget(self):
self.setWindowTitle("Plotting M&N")
gridlayout = QGridLayout()
self.setLayout(gridlayout)
self.figure = plt.figure(figsize=(15,5))
self.canvas = FigureCanvas(self.figure)
self.toolbar = NavigationToolbar(self.canvas,self)
gridlayout.addWidget(self.canvas,1,0,1,2)
gridlayout.addWidget(self.toolbar,0,0,1,2)
def plot1(self):
# sns.set()
ax = self.figure.add_subplot(111)
x = [i for i in range(100)]
y = [i**2 for i in x]
ax.plot(x,y, 'b.-')
ax.set_title('Quadratic Plot')
self.canvas.draw()
class createtextdocument(QWidget):
def __init__(self):
super().__init__()
self.textedit()
def textedit(self):
self.textedit = QTextEdit()
self.cursor = self.textedit.textCursor()
class createtabwidget(QDialog):
def __init__(self):
super().__init__()
# Greate tabs in dockable window
tab = QTabWidget()
scroll = QScrollArea()
ncroll = QScrollArea()
mcroll = QScrollArea()
self.first = firsttabgeometry()
self.grid = Grid()
self.third = thirdtabloads()
scroll.setWidget(self.first)
ncroll.setWidget(self.grid)
mcroll.setWidget(self.third)
scroll.setWidgetResizable(True)
self.first.setMinimumSize(self.first.sizeHint())
self.grid.setMinimumSize(self.grid.sizeHint())
self.third.setMinimumSize(self.third.sizeHint())
self.adjustSize()
self.first.setMinimumSize(self.first.minimumSizeHint())
self.grid.setMinimumSize(self.grid.minimumSizeHint())
self.third.setMinimumSize(self.third.minimumSizeHint())
# Adding multiple tabslides
tab.addTab(self.first,'One')
tab.addTab(self.grid,'Two')
tab.addTab(self.third,'Three')
tab.setFont(QFont("Georgia",10,QFont.Normal))
vboxlayout = QVBoxLayout()
vboxlayout.addWidget(tab)
self.setLayout(vboxlayout)
class firsttabgeometry(QWidget):
def __init__(self):
super().__init__()
self.setFixedSize(self.sizeHint())
iconroot = QFileInfo(__file__).absolutePath()
font = QFont("Georgia",10,QFont.Normal)
# Add widget and buttons to tabs
sectiontypegroupbox = QGroupBox('&One',self)
sectiontypegroupbox.setFont(QFont("Georgia",10,QFont.Normal))
tab1button = QPushButton('')
tab1button.setIcon(QIcon(iconroot +'/images/circularcolumn'))
tab1button.setIconSize(QSize(60,60))
tab1button.clicked.connect(self.One)
squarebutton = QPushButton('')
squarebutton.setIcon(QIcon(iconroot +'/images/squarecolumn'))
squarebutton.setIconSize(QSize(60,60))
squarebutton.clicked.connect(self.Two)
wallbutton = QPushButton("")
wallbutton.setIcon(QIcon(iconroot +'/images/wall'))
wallbutton.setIconSize(QSize(60,60))
wallbutton.clicked.connect(self.Three)
circularlabel = QLabel(" One",self)
circularlabel.setSizePolicy(QSizePolicy.Expanding,QSizePolicy.Expanding)
circularlabel.setFont(font)
sclabel = QLabel(" Two",self)
sclabel.setSizePolicy(QSizePolicy.Expanding,QSizePolicy.Expanding)
sclabel.setFont(font)
walllabel = QLabel(" Three",self)
walllabel.setSizePolicy(QSizePolicy.Expanding,QSizePolicy.Expanding)
walllabel.setFont(font)
bottomgroupbox = QGroupBox("Group 2")
vboxlayout = QHBoxLayout()
vboxlayout.addStretch()
radiobutton2 = QRadioButton("Radio Button")
radiobutton3 = QRadioButton("Radio Button")
testbutton2 = QPushButton('Test Button 2')
vboxlayout.addWidget(radiobutton2)
vboxlayout.addWidget(radiobutton3)
vboxlayout.addWidget(testbutton2)
bottomgroupbox.setLayout(vboxlayout)
mainlayout = QGridLayout()
mainlayout.addWidget(tab1button,0,0)
mainlayout.addWidget(circularlabel,0,1)
mainlayout.addWidget(squarebutton,1,0)
mainlayout.addWidget(sclabel,1,1)
mainlayout.addWidget(wallbutton,2,0)
mainlayout.addWidget(walllabel,2,1)
mainlayout.setContentsMargins(200,50,50,50)
sectiontypegroupbox.setLayout(mainlayout)
gridlayout = QGridLayout()
gridlayout.addWidget(sectiontypegroupbox,1,0)
gridlayout.setContentsMargins(25,25,25,25)
self.setLayout(gridlayout)
def One(self):
print('One')
def Two(self):
print('Two')
def Three(self):
print('Three')
class FooWidget(QtWidgets.QWidget):
def __init__(self, path_icon, text, checked=False, parent=None):
super(FooWidget, self).__init__(parent)
lay = QtWidgets.QVBoxLayout(self)
pixmap = QtGui.QPixmap(os.path.join(iconroot, path_icon))
pixmap_label = QtWidgets.QLabel()
pixmap_label.resize(150, 150)
pixmap_label.setPixmap(pixmap.scaled(pixmap_label.size(), QtCore.Qt.KeepAspectRatio))
text_label = QtWidgets.QLabel(text)
checkbox = QtWidgets.QCheckBox(checked=checked)
lay.addWidget(pixmap_label)
lay.addWidget(text_label)
lay.addWidget(checkbox)
class Grid(QtWidgets.QWidget):
def __init__(self, parent=None):
super(Grid, self).__init__(parent)
self.setFixedSize(self.sizeHint())
font = QFont("Georgia",8,QFont.Normal)
lay = QtWidgets.QHBoxLayout(self)
icons = ["images/fixed-fixed.png",
"images/pinned-pinned.png",
"images/fixed-free.png",
"images/fixed-pinned.png"]
texts = ["Ley = 1.0 L\nLec = 1.0 L",
"Ley = 0.699 L\nLec = 0.699 L",
"Ley = 2.0 L\nLec = 2.0 L",
"Ley = 0.5 L\nLec = 0.5 L"]
for path_icon, text in zip(icons, texts):
w = FooWidget(os.path.join(iconroot, path_icon), text)
lay.addWidget(w)
class thirdtabloads(QtWidgets.QWidget):
def __init__(self, parent=None):
super(thirdtabloads, self).__init__(parent)
self.adjustSize()
table = loadtable()
add_button = QtWidgets.QPushButton("Add")
add_button.clicked.connect(table._addrow)
delete_button = QtWidgets.QPushButton("Delete")
delete_button.clicked.connect(table._removerow)
copy_button = QtWidgets.QPushButton("Copy")
copy_button.clicked.connect(table._copyrow)
button_layout = QtWidgets.QVBoxLayout()
button_layout.addWidget(add_button, alignment=QtCore.Qt.AlignBottom)
button_layout.addWidget(delete_button, alignment=QtCore.Qt.AlignTop)
button_layout.addWidget(copy_button, alignment=QtCore.Qt.AlignTop )
tablehbox = QtWidgets.QHBoxLayout()
tablehbox.setContentsMargins(10,10,10,10)
tablehbox.addWidget(table)
grid = QtWidgets.QGridLayout(self)
grid.addLayout(button_layout, 0, 1)
grid.addLayout(tablehbox, 0, 0)
def copy_widget(w):
if isinstance(w, QtWidgets.QWidget):
new_w = type(w)()
if isinstance(w, QtWidgets.QComboBox):
vals = [w.itemText(ix) for ix in range(w.count())]
new_w.addItems(vals)
return new_w
class loadtable(QtWidgets.QTableWidget):
def __init__(self, parent=None):
super(loadtable, self).__init__(1, 5, parent)
self.setFont(QtGui.QFont("Helvetica", 10, QtGui.QFont.Normal, italic=False))
headertitle = ("Load Name","N [kN]","My [kNm]","Mz [kNm]","Load Type")
self.setHorizontalHeaderLabels(headertitle)
self.verticalHeader().hide()
self.horizontalHeader().setHighlightSections(False)
self.horizontalHeader().setSectionResizeMode(QtWidgets.QHeaderView.Fixed)
self.setSelectionMode(QtWidgets.QAbstractItemView.NoSelection)
self.setColumnWidth(0, 130)
combox_lay = QtWidgets.QComboBox(self)
combox_lay.addItems(["ULS","SLS"])
self.setCellWidget(0, 4, combox_lay)
self.cellChanged.connect(self._cellclicked)
#QtCore.pyqtSlot(int, int)
def _cellclicked(self, r, c):
it = self.item(r, c)
it.setTextAlignment(QtCore.Qt.AlignCenter)
#QtCore.pyqtSlot()
def _addrow(self):
rowcount = self.rowCount()
self.insertRow(rowcount)
combox_add = QtWidgets.QComboBox(self)
combox_add.addItems(["ULS","SLS"])
self.setCellWidget(rowcount, 4, combox_add)
#QtCore.pyqtSlot()
def _removerow(self):
if self.rowCount() > 0:
self.removeRow(self.rowCount()-1)
#QtCore.pyqtSlot()
def _copyrow(self):
r = self.currentRow()
if 0 <= r < self.rowCount():
cells = {"items": [], "widgets": []}
for i in range(self.columnCount()):
it = self.item(r, i)
if it:
cells["items"].append((i, it.clone()))
w = self.cellWidget(r, i)
if w:
cells["widgets"].append((i, copy_widget(w)))
self.copy(cells, r+1)
def copy(self, cells, r):
self.insertRow(r)
for i, it in cells["items"]:
self.setItem(r, i, it)
for i, w in cells["widgets"]:
self.setCellWidget(r, i, w)
if __name__ == '__main__':
app = QtWidgets.QApplication(sys.argv)
app.setStyle("Fusion")
mainWin = mywindow()
mainWin.show()
mainWin.showMaximized()
sys.exit(app.exec_())
I would appreciate much any help on this.
If floating windows aren't essential to your tool then you can try dropping QDockWidget and using a series of QSplitter instead. This way you can have your nice box layout while having tabs to resize horizontally and vertically, and still resizing properly when the tool as a whole resizes.
My example is in PySide2, but you'll probably need to do very minor tweaks to PyQt5 (probably just the import names):
from PySide2 import QtCore
from PySide2 import QtGui
from PySide2 import QtWidgets
class SubWindow(QtWidgets.QWidget):
def __init__(self, label, parent=None):
super(SubWindow, self).__init__(parent)
self.label = QtWidgets.QLabel(label, parent=self)
self.label.setAlignment(QtCore.Qt.AlignCenter)
self.label.setStyleSheet("QLabel {font-size:40px;}")
self.main_layout = QtWidgets.QVBoxLayout()
self.main_layout.addWidget(self.label)
self.setLayout(self.main_layout)
class MainWindow(QtWidgets.QWidget):
def __init__(self, parent=None):
super(MainWindow, self).__init__(parent)
self.sub_win_1 = SubWindow("1", parent=self)
self.sub_win_2 = SubWindow("2", parent=self)
self.sub_win_3 = SubWindow("3", parent=self)
self.sub_win_4 = SubWindow("4", parent=self)
self.sub_splitter_1 = QtWidgets.QSplitter(QtCore.Qt.Horizontal, parent=self)
self.sub_splitter_1.addWidget(self.sub_win_1)
self.sub_splitter_1.addWidget(self.sub_win_2)
self.sub_splitter_2 = QtWidgets.QSplitter(QtCore.Qt.Horizontal, parent=self)
self.sub_splitter_2.addWidget(self.sub_win_3)
self.sub_splitter_2.addWidget(self.sub_win_4)
self.splitter = QtWidgets.QSplitter(QtCore.Qt.Vertical, parent=self)
self.splitter.addWidget(self.sub_splitter_1)
self.splitter.addWidget(self.sub_splitter_2)
self.main_layout = QtWidgets.QVBoxLayout()
self.main_layout.addWidget(self.splitter)
self.setLayout(self.main_layout)
self.setWindowTitle("Layout example")
self.resize(500, 500)
inst = MainWindow()
inst.show()
This gives you something like this:
Right now the top/bottom horizontal splitters function separately, but you can easily tie them together with an event.
Hope that helps!
I am trying to create a pop-up window that gets popped-up from pressing on a QPushButton. However, I have a separate QPushButton class that I would like to use. I can't seem to get it working. Anything I am doing wrong?
#import ... statements
import sys
# from ... import ... statements
from PyQt5.QtWidgets import (QMainWindow, QApplication, QPushButton, QGridLayout, QWidget, QHBoxLayout, QLabel,
QVBoxLayout)
from PyQt5.QtCore import Qt
from PyQt5.QtGui import QFont, QFontDatabase, QColor, QPalette, QMovie
from skimage import transform, io
# Create main window of the widget
class MainWindow(QWidget):
def __init__(self):
super().__init__()
#Set a title inside the widget
self.titleLabel = QLabel()
titleText = "some title text"
self.titleLabel.setText(titleText)
# Give the label some flair
self.titleLabel.setFixedWidth(1000)
self.titleLabel.setAlignment(Qt.AlignCenter)
QFontDatabase.addApplicationFont(link_to_custom_font)
font = QFont()
font.setFamily("custom_font_name")
font.setPixelSize(50)
self.titleLabel.setFont(font)
# Set first button - The "Yes" Button
self.btn1 = myButtonOne("Yes")
#Initialize GUI
self.layoutGUI()
self.initUI()
def initUI(self):
self.fromleft = 200
self.fromtop = 100
self.w = 1000
self.h = 500
self.setGeometry(self.fromleft, self.fromtop, self.w, self.h)
def layoutGUI(self):
hbox = QHBoxLayout()
hbox.setSpacing(20)
hbox.addWidget(self.btn1)
vbox = QVBoxLayout()
vbox.addWidget(self.titleLabel)
vbox.addLayout(hbox)
self.setLayout(vbox)
class myButtonOne(QPushButton):
def __init__(self, parent=None):
super(myButtonOne, self).__init__(parent)
# Set maximum border size
imSize = io.imread(imagePath)
imHeight = imSize.shape[1]
imWidth = imSize.shape[0]
# Set first button - The "Yes" Button
yesImage = someImagePath
self.setStyleSheet("background-image: url(" + yesImage + ");"
"background-repeat: none;"
"background-position: center;"
"border: none")
self.setFixedSize(imWidth, imHeight)
self.clicked.connect(self.buttonOnePushed)
def buttonOnePushed(self):
textView().show()
def enterEvent(self, event):
newImage = someOtherImagePath
self.setStyleSheet("background-image: url("+newImage+");"
"background-repeat: none;"
"background-position: center;"
"border: none")
def leaveEvent(self, event):
newImage = someImagePath
self.setStyleSheet("background-image: url("+newImage+");"
"background-repeat: none;"
"background-position: center;"
"border: none")
class textView(QWidget):
def __init(self):
textView.__init__()
theText = QLabel()
#define sizes
self.height = 550
self.width = 250
# Open QWidget
self.initUI()
# Set the text for the QLabel
someText = "Some Text for the label"
theText.setText(someText)
def initUI(self):
self.show()
# Start GUI
if __name__ == '__main__':
app = QApplication(sys.argv)
win = MainWindow()
win.show()
sys.exit(app.exec_())
So, I am trying to keep the QPushButton classes separate, so that I can customize them. I would like to keep it like that, especially to keep it clean and readable.
First off - please read: How to create a Minimal, Complete, and Verifiable example. I had a lot of work minimizing your code, which wasted a good amount of my time.
Nonetheless, here is a minimal working code, with your own button class:
import sys
from PyQt5.QtWidgets import QApplication, QPushButton, QWidget, QLabel, QVBoxLayout
class MainWindow(QWidget):
def __init__(self):
super(MainWindow, self).__init__()
self.titleLabel = QLabel( "some label text" )
self.btn1 = myButtonOne( "button text" )
hbox = QVBoxLayout() # one vertical box seemed enough
hbox.addWidget( self.titleLabel )
hbox.addWidget( self.btn1 )
self.setLayout( hbox )
class myButtonOne(QPushButton):
def __init__(self, text, parent=None):
super(myButtonOne, self).__init__(text, parent)
self.clicked.connect(self.buttonOnePushed)
# add your customizations here
def buttonOnePushed (self) :
self.t = textView()
self.t.show()
class textView(QWidget):
def __init__(self):
super(textView, self).__init__()
self.theText = QLabel('test', self )
if __name__ == '__main__':
app = QApplication(sys.argv)
win = MainWindow()
win.show()
sys.exit(app.exec_())
What have you done wrong in your code?
using textView().show() creates a local version of you textView-class and show()'s it:
def buttonOnePushed(self):
textView().show()
But, show() means that the code continues, where the end of your code comes, which results in cleaning up the locals. End - it's just shown for a microsecond.
def buttonOnePushed (self) :
self.t = textView()
self.t.show()
The code above stores the var as instance-attribute of the button, which is not cleaned up.
Furthermore you misspelled the init in your textView-class:
"__init" should be __init__ - else it is not called when using the constructor:
class textView(QWidget):
def __init(self):
textView.__init__()
Finally, you wanted to called show() twice:
in your textView-init you call initUI() which is calling show()
you calling show manually with textView().show()
Hope this helps! I did not include your personal style adjustments for readability.
I want to make a simple GUI desktop application using python.
I've made a simple window with a background image, and I added a tab-widget on the right corner. It worked properly. But the tab-bar and tab contents area are white.
What I want is that the tab-widget's background shows it's parent window's background image (which means it's transparent). But I don't know how to do it.
Here is my working environment, code and screen shot:
Working environment:
Windows 7
Python 3.4
PyQt5 5.5
Source code:
# coding: utf-8
# There are some unnecessary module.
import sys
from PyQt5.QtWidgets import QApplication, QMainWindow, QTabWidget, QWidget, QLabel, QHBoxLayout, QVBoxLayout, QGridLayout
from PyQt5.QtGui import QPixmap, QPalette, QBrush, QColor
from PyQt5.QtCore import Qt
class Example(QWidget):
def __init__(self):
super().__init__()
self.initUI()
def initUI(self):
tab1 = QWidget()
tab2 = QWidget()
vbox1 = self.makeTab1()
vbox2 = self.makeTab2()
tab1.setLayout(vbox1)
tab2.setLayout(vbox2)
tabs = QTabWidget()
tabs.addTab(tab1, "firstTab")
tabs.addTab(tab2, "secondTab")
picLabel = QLabel(self)
picFile = 'background_img.jpg'
pixmap = QPixmap(picFile)
palette = QPalette()
palette.setBrush(QPalette.Background, QBrush(pixmap))
hboxEX = QHBoxLayout()
hboxEX.addStretch(2)
hboxEX.addWidget(tabs)
hboxEX.setStretchFactor(tabs, 1)
vboxEX = QVBoxLayout()
vboxEX.addStretch(1)
vboxEX.addLayout(hboxEX)
vboxEX.setStretchFactor(hboxEX, 1)
self.setLayout(vboxEX)
self.setPalette(palette)
self.resize(pixmap.width(), pixmap.height())
self.show()
def makeTab1(self):
lbl1 = QLabel(self)
lbl2 = QLabel(self)
lbl3 = QLabel(self)
lbl1.setText("Google")
lbl2.setText("WikiPedia")
lbl3.setText("StackOverflow")
lbl1.setOpenExternalLinks(True)
lbl2.setOpenExternalLinks(True)
lbl3.setOpenExternalLinks(True)
vbox1 = QVBoxLayout()
vbox1.addWidget(lbl1)
vbox1.addWidget(lbl2)
vbox1.addWidget(lbl3)
return vbox1
def makeTab2(self):
lbl4 = QLabel(self)
lbl5 = QLabel(self)
lbl6 = QLabel(self)
lbl4.setText("Python")
lbl5.setText("CentOS")
lbl6.setText("MariaDB")
lbl4.setOpenExternalLinks(True)
lbl5.setOpenExternalLinks(True)
lbl6.setOpenExternalLinks(True)
vbox2 = QVBoxLayout()
vbox2.addWidget(lbl4)
vbox2.addWidget(lbl5)
vbox2.addWidget(lbl6)
return vbox2
if __name__ == '__main__':
app = QApplication(sys.argv)
ex = Example()
sys.exit(app.exec_())
Screen shot:
What I tried:
I added these codes and it changed the tab's color. But it didn't make the tab area look transparent:
tabPalette = QPalette()
tabPalette.setColor(QPalette.Background, QColor("cyan"))
tab1.setAutoFillBackground(True)
tab1.setPalette(tabPalette)
I think it's a Windows problem. You might want to try to switch your application to a different style.
See this page of PyQt reference http://pyqt.sourceforge.net/Docs/PyQt4/qstyle.html
some sample code:
def changeStyle(self, styleName):
QtGui.QApplication.setStyle(QtGui.QStyleFactory.create(styleName))
self.changePalette()
call it with:
changeStyle("plastique")