网络知识 娱乐 PyQt5实现UI自适应屏幕大小且可缩放

PyQt5实现UI自适应屏幕大小且可缩放

文章目录

  • 固定尺寸UI
  • PyQt5检测屏幕分辨率
  • PyQt5界面自适应屏幕大小并居中显示
  • PyQt5部件QWidgets自适UI界面大小

代码已上传,欢迎自取:https://blog.csdn.net/lavinia_chen007/article/details/118606477

本文主要的出发点是,开发者本人在24寸大屏幕使用PyQt5开发的UI界面,由于使用了固定的尺寸,在用户14寸的小屏无法显示完全。

解决办法是:能够实现UI根据屏幕分辨率自动计算适合屏幕大小的初始尺寸。这也就意味着,不止界面本身的大小不能够固定尺寸,包括界面中的所有尺寸,都不应该固定尺寸,而应该根据请情况做自适应的调整。

固定尺寸UI

下面我们先实现一个UI界面大小和Widget大小和位置都固定的界面。
这里界面包含了:菜单栏,QListWidget和QLabel
我们通过.resize设置大小,.move设置Widget的位置。

class MainWindow(QMainWindow):
    def __init__(self):
        super().__init__()
        self.title = "固定尺寸UI"
        self.height = 800
        self.width = 1080

        self.resize(self.width,self.height)
        self.wid = QWidget(self)
        self.setCentralWidget(self.wid)
        self.setWindowTitle(self.title)
        self.initUI()

    def initUI(self):
        self.initMenu()
        self.initBrowser()
        self.initImageWindow()

    def initMenu(self):
        openImageFolderAct = QAction("打开",self)
        openImageFolderAct.setStatusTip("选择一个文件夹,开始标注")
        openImageFolderAct.setShortcut("Ctrl+O")

        menubar = self.menuBar()
        fileMenu = menubar.addMenu('&文件')
        fileMenu.addAction(openImageFolderAct)

    def initBrowser(self):
        self.imageBrowser = QListWidget(self)
        self.imageBrowser.resize(200,750)
        self.imageBrowser.move(20,30)
        
    def initImageWindow(self):
        self.imageWindow = QLabel("Hello World!",self)
        self.imageWindow.resize(800,750)
        self.imageWindow.move(250,30)
        self.imageWindow.setStyleSheet("background-color: darkgray;border: 1px solid black;")

获得如下效在这里插入图片描述
看起来没啥问题。

注意,因为所有尺寸位置都是写定了,开发过程中不会发现任何问题,但如果,使用者用的是小屏幕,就很有可能出现显示不全的问题。

好,下面一步一步来改。

要实现不同屏幕大小的自适应,首先要知道屏幕大小。

PyQt5检测屏幕分辨率

class MainWindow(QMainWindow):
    def __init__(self):
        super().__init__()
        self.title = "固定尺寸UI"
        self.height = 800
        self.width = 1080

        #获取显示器分辨率
        self.desktop = QApplication.desktop()
        self.screenRect = self.desktop.screenGeometry()
        self.screenheight = self.screenRect.height()
        self.screenwidth = self.screenRect.width()

        print("Screen height {}".format(self.screenheight))
        print("Screen width {}".format(self.screenwidth))

        self.resize(self.width,self.height)
        self.wid = QWidget(self)
        self.setCentralWidget(self.wid)
        self.setWindowTitle(self.title)
        self.initUI()

添加了一段检测屏幕分辨率并打印的代码,输出为:
在这里插入图片描述
也就是说,在每次初始化的时候,这段代码会自动获取当前屏幕的分辨率,那么下面我们就可以根据这个结果来做想要的自适应了。

PyQt5界面自适应屏幕大小并居中显示

UI界面的宽和高,在想做自适应屏幕大小的时候,可以将其设置为屏幕宽和高的一定比例。假设都按0.7的比例来设置。

class MainWindow(QMainWindow):
    def __init__(self):
        super().__init__()
        self.title = "自适应屏幕大小UI"
        
        #获取显示器分辨率
        self.desktop = QApplication.desktop()
        self.screenRect = self.desktop.screenGeometry()
        self.screenheight = self.screenRect.height()
        self.screenwidth = self.screenRect.width()
		
		self.height = int(self.screenheight * 0.7)
        self.width = int(self.screenwidth * 0.7)

        print("Screen height {}".format(self.screenheight))
        print("Screen width {}".format(self.screenwidth))

        self.resize(self.width,self.height)
        self.wid = QWidget(self)
        self.setCentralWidget(self.wid)
        self.setWindowTitle(self.title)
        self.initUI()

在这里插入图片描述界面是按照屏幕宽和高的0.7来设置了UI界面的宽和高。但我们发现,了这时候Widgets的显示都出了问题。下面就做QWidgets的自适应。

PyQt5部件QWidgets自适UI界面大小

要实现部件自适应UI界面大小,就需要用到PyQt5的layout。
PyQt5有几种layout选择:

  • QHBoxLayout 将部件按照横向排列
  • QVBoxLayout 将部件按照横向排列
  • QGridLayout 在网格布局中排列部件
  • QFormLayout 在两列中排列部件

个人感觉QGridLayout可定制的空间比较大,这边就选用QGridLayout。

class MainWindow(QMainWindow):
    def __init__(self):
        super().__init__()
        self.title = "自适应屏幕大小UI"

        #获取显示器分辨率
        self.desktop = QApplication.desktop()
        self.screenRect = self.desktop.screenGeometry()
        self.screenheight = self.screenRect.height()
        self.screenwidth = self.screenRect.width()

        print("Screen height {}".format(self.screenheight))
        print("Screen width {}".format(self.screenwidth))

        self.height = int(self.screenheight * 0.7)
        self.width = int(self.screenwidth * 0.7)

        self.resize(self.width,self.height)
        self.wid = QWidget(self)
        self.setCentralWidget(self.wid)
        self.setWindowTitle(self.title)
        self.initUI()

    def initUI(self):
        self.layout = QGridLayout()
        #预览四个边都预留20pixs的边界
        self.layout.setContentsMargins(20, 20, 20, 20)
        #网格之间设置10pixs的间隔
        self.layout.setSpacing(10)

        self.initMenu()
        self.initBrowser()
        self.initImageWindow()

        self.statusBar().showMessage("准备就绪")
        self.wid.setLayout(self.layout)

    def initMenu(self):
        openImageFolderAct = QAction("打开",self)
        openImageFolderAct.setStatusTip("选择一个文件夹,开始标注")
        openImageFolderAct.setShortcut("Ctrl+O")

        menubar = self.menuBar()
        fileMenu = menubar.addMenu('&文件')
        fileMenu.addAction(openImageFolderAct)

    def initBrowser(self):
        self.imageBrowser = QListWidget(self)
        # self.imageBrowser.resize(200,750)
        # self.imageBrowser.move(20,30)
        #将imageBrowser放置到网格的第0行,第0列
        self.layout.addWidget(self.imageBrowser,0,0)

    def initImageWindow(self):
        self.imageWindow = QLabel("Hello World!",self)
        # self.imageWindow.resize(800,750)
        # self.imageWindow.move(250,30)
        self.imageWindow.setStyleSheet("background-color: darkgray;border: 1px solid black;")
        #将imageBrowser放置到网格的第0行,第1列
        self.layout.addWidget(self.imageWindow,0,1)

在这里插入图片描述这个效果明显不是我们想要的。下面修改一下设置

def initBrowser(self):
        self.imageBrowser = QListWidget(self)
        # self.imageBrowser.resize(200,750)
        # self.imageBrowser.move(20,30)
        #设置最小的大小,还是以界面大小为基准
        self.imageBrowserWidth = self.width*0.1
        self.imageBrowserHeight = self.height 
        self.imageBrowser.setMinimumSize(self.imageBrowserWidth,self.imageBrowserHeight)
        #将imageBrowser放置到网格的第0行,第0列
        self.layout.addWidget(self.imageBrowser,0,0)

    def initImageWindow(self):
        self.imageWindow = QLabel("Hello World!",self)
        # self.imageWindow.resize(800,750)
        # self.imageWindow.move(250,30)
        self.imageWindow.setStyleSheet("background-color: darkgray;border: 1px solid black;")
    
        #设置最小的大小,还是以界面大小为基准
        self.imageWindowWidth = self.width*0.9
        self.imageWindowHeight = self.height 
        self.imageWindow.setMinimumSize(self.imageWindowWidth,self.imageWindowHeight)
        #将imageBrowser放置到网格的第0行,第1列
        self.layout.addWidget(self.imageWindow,0,1)

在这里插入图片描述这样就能保证UI界面和里面的部件都能根据屏幕分辨率做自适应了。