• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            隨筆 - 41, 文章 - 8, 評論 - 8, 引用 - 0
            數據加載中……

            [Python][PyQt4]在 PyQt4 中定制組件

            在 PyQt4 中定制組件

            PyQt4 有豐富的組件。但是不可能提供所有的組件。PyQt4 中僅僅提供最常用的組件,像按鈕,文本框,滑塊等。如果我們需要特殊的組件,我們必須要自己創建。

            自定制組件可以使用工具包畫制工具創建。有兩種可能,一個程序員可以修改或提升一個已存在的工具,或是從零開始創建。

            Burning widget

            這是一個組件,我們可以在 Nero,K3B 或其它 CD/DVD 刻錄軟件。

            #!/usr/bin/python
            # -*- coding: utf-8 -*-
            """
            ZetCode PyQt4 tutorial
            In this example, we create a custom widget.
            author: Jan Bodnar
            website: zetcode.com
            last edited: October 2011
            """
            import sys
            from PyQt4 import QtGui, QtCore
            class Communicate(QtCore.QObject):
                updateBW = QtCore.pyqtSignal(int)
            class BurningWidget(QtGui.QWidget):
                def __init__(self):
                    super(BurningWidget, self).__init__()
                    self.initUI()
                def initUI(self):
                    self.setMinimumSize(1, 30)
                    self.value = 75
                    self.num = [75, 150, 225, 300, 375, 450, 525, 600, 675]
                def setValue(self, value):
                    self.value = value
                def paintEvent(self, e):
                    qp = QtGui.QPainter()
                    qp.begin(self)
                    self.drawWidget(qp)
                    qp.end()
                def drawWidget(self, qp):
                    font = QtGui.QFont('Serif', 7, QtGui.QFont.Light)
                    qp.setFont(font)
                    size = self.size()
                    w = size.width()
                    h = size.height()
                    step = int(round(w / 10.0))
                    till = int(((w / 750.0) * self.value))
                    full = int(((w / 750.0) * 700))
                    if self.value >= 700:
                        qp.setPen(QtGui.QColor(255, 255, 255))
                        qp.setBrush(QtGui.QColor(255, 255, 184))
                        qp.drawRect(0, 0, full, h)
                        qp.setPen(QtGui.QColor(255, 175, 175))
                        qp.setBrush(QtGui.QColor(255, 175, 175))
                        qp.drawRect(full, 0, till-full, h)
                    else:
                        qp.setPen(QtGui.QColor(255, 255, 255))
                        qp.setBrush(QtGui.QColor(255, 255, 184))
                        qp.drawRect(0, 0, till, h)
                    pen = QtGui.QPen(QtGui.QColor(20, 20, 20), 1,
                        QtCore.Qt.SolidLine)
                    qp.setPen(pen)
                    qp.setBrush(QtCore.Qt.NoBrush)
                    qp.drawRect(0, 0, w-1, h-1)
                    j = 0
                    for i in range(step, 10*step, step):
                        qp.drawLine(i, 0, i, 5)
                        metrics = qp.fontMetrics()
                        fw = metrics.width(str(self.num[j]))
                        qp.drawText(i-fw/2, h/2, str(self.num[j]))
                        j = j + 1
            class Example(QtGui.QWidget):
                def __init__(self):
                    super(Example, self).__init__()
                    self.initUI()
                def initUI(self):
                    sld = QtGui.QSlider(QtCore.Qt.Horizontal, self)
                    sld.setFocusPolicy(QtCore.Qt.NoFocus)
                    sld.setRange(1, 750)
                    sld.setValue(75)
                    sld.setGeometry(30, 40, 150, 30)
                    self.c = Communicate()
                    self.wid = BurningWidget()
                    self.c.updateBW[int].connect(self.wid.setValue)
                    sld.valueChanged[int].connect(self.changeValue)
                    hbox = QtGui.QHBoxLayout()
                    hbox.addWidget(self.wid)
                    vbox = QtGui.QVBoxLayout()
                    vbox.addStretch(1)
                    vbox.addLayout(hbox)
                    self.setLayout(vbox)
                    self.setGeometry(300, 300, 390, 210)
                    self.setWindowTitle('Burning widget')
                    self.show()
                def changeValue(self, value):
                    self.c.updateBW.emit(value)
                    self.wid.repaint()
            def main():
                app = QtGui.QApplication(sys.argv)
                ex = Example()
                sys.exit(app.exec_())
            if __name__ == '__main__':
                main()
            

            在這個例子中,我們有一個 QtGui.QSlider 和一個自定制組件。滑塊控制了自定制組件。這個組件顯示一個媒介總的容量以及剩余的容量。這里最小的值是 1,最大是 750 。如果我們到達 700 ,我們開始畫紅色。這是用于指示過度燒制。

            組件放在窗口的底部。這通過一個 QtGui.QHBoxLayoutQtGui.QVBoxLayout 實現。

            class BurningWidget(QtGui.QWidget):
                def __init__(self):
                    super(BurningWidget, self).__init__()
            

            這個組件基于 QtGui.QWidget 組件。

            self.setMinimumSize(1, 30)
            

            我們更改了組件最小的大小(高度)。默認的值是一點點小。

            font = QtGui.QFont('Serif', 7, QtGui.QFont.Light)
            qp.setFont(font)
            

            我們用小于默認的字體。這適合于我們的需要。

            size = self.size()
            w = size.width()
            h = size.height()
            step = int(round(w / 10.0))
            till = int(((w / 750.0) * self.value))
            full = int(((w / 750.0) * 700))
            

            我們動態地繪制組件。窗口越大,組件會越大。反之亦然。這就是為何我們要計算組件的大小。參數 till 決定了要畫多少。此值來自于滑塊組件。這是整個區域的部分值。參數 full 決定了什么時候開始繪制紅色部分。注意,此處使用了浮點運算,是為更高的精度。

            真正繪制時包含三個部分。我們先繪制黃色或紅色和黃色的矩形。然后繪制垂直的線,主要用于分割組件。最后是繪制數字,用于指示媒介的大小。

            metrics = qp.fontMetrics()
            fw = metrics.width(str(self.num[j]))
            qp.drawText(i-fw/2, h/2, str(self.num[j]))
            

            我們使用字體度量來繪制文本。我們必須要知道文本的寬度來居中繪制。

            def changeValue(self, value):
                self.c.updateBW.emit(value)
                self.wid.repaint()
            

            我們移動滑塊時, changeValue() 方法就被調用了。在此方法內部,我們發送了自定義的 updateBW 信號,并且帶了一個參數。這個參數是當前滑塊的值。這個值用于計算在 Burning 這個組件中要繪制多少。自定義的組件然后被重繪。


            本部分,我們創建了自己的組件。

            posted on 2012-02-12 10:17 mirguest 閱讀(1212) 評論(0)  編輯 收藏 引用 所屬分類: Python

            久久久久99这里有精品10| 国产伊人久久| 久久久久免费看成人影片| 1000部精品久久久久久久久| 狠狠精品久久久无码中文字幕 | 久久久久久久综合综合狠狠| 蜜桃麻豆WWW久久囤产精品| 精品久久8x国产免费观看| 久久国产精品久久| 久久久午夜精品福利内容| 国产精品免费看久久久| 久久久久18| 久久免费视频观看| 久久精品国产秦先生| 一本久久免费视频| www亚洲欲色成人久久精品| 偷偷做久久久久网站| 99热热久久这里只有精品68| 久久综合亚洲欧美成人| 日韩精品无码久久一区二区三| 精品国产青草久久久久福利| 亚洲精品无码成人片久久| 久久精品无码免费不卡| 国内精品九九久久久精品| 久久精品国产精品亚洲精品| 久久精品无码一区二区三区免费 | 三级三级久久三级久久| 成人午夜精品久久久久久久小说| 久久精品人人做人人爽电影蜜月| 久久久久久噜噜精品免费直播| 久久久精品午夜免费不卡| 久久发布国产伦子伦精品| 人人狠狠综合久久88成人| 中文字幕人妻色偷偷久久| 日韩精品久久久肉伦网站| 久久婷婷色综合一区二区| 思思久久好好热精品国产| 久久精品无码专区免费青青| 久久这里都是精品| 亚洲伊人久久综合中文成人网| 亚洲国产精品成人AV无码久久综合影院|