天天看點

Qt樣式表詳解

https://www.cnblogs.com/lsgxeva/p/7816938.html

一、QT樣式表簡介

1、QT樣式表簡介

    QSS的主要功能是使界面的表現與界面的元素分離,使得設計皮膚與界面控件分離的軟體成為可能。

QT樣式表是允許使用者定制widgets元件外觀的強大機制,此外,子類化QStyle也可以定制widgets元件外觀。QT樣式表的概念、術語、文法很大程度上受到了CSS層疊樣式表的影響。

樣式表是使用QApplication::setStyleSheet()設定在應用程式或是使用QWidget::setStyleSheet()設定在具體元件及其子對象的文字說明。

例如,以下樣式表指明QLineEdit使用黃色作為背景色,QCheckBox使用紅色作為文本顔色。

    QLineEdit { background: yellow }

    QCheckBox { color: red }

    對于這種定制,樣式表比QPalette更強大。例如,要擷取一個紅色的按鈕,可以設定QPushButton的QPalette::Button角色為紅色。然而,這并不保證對所有的樣式有效,因為樣式的構造者會被不同平台的原則和本地的主題引擎所限制。

    樣式表可以實作那些很難或是不可能使用QPalette實作的所有定制。

    如果想要某些強制字段為黃色背景,按鈕為紅色文字,或是絢麗的複選框,樣式表可以完成。

2、QT樣式表程式設計

A、在代碼中直接設定QSS

    QPushButton *button = new QPushButton(this);

    button->setText("hello");

    button->setStyleSheet("QPushButton{ color:blue}");

B、通過檔案設定QSS

将QSS代碼寫入.qss檔案

将.qss檔案加入資源檔案qrc.qrc中

在代碼中讀取QSS檔案設定元件QSS

    QPushButton *button = new QPushButton(this);

    button->setText("hello");

    QFile file(":/qss/dev.qss");

    file.open(QIODevice::ReadOnly);

    QString stylesheet = QLatin1String(file.readAll());

    button->setStyleSheet(stylesheet);

    file.close();

二、QT樣式表文法

QT樣式表的術語和文法規則與HTML CSS很相似。

1、樣式規則

樣式表由樣式規則序列組成。樣式規則由選擇器和聲明組成。選擇器指定了那些元件受規則影響,聲明指定了元件設定了哪些屬性。例如:

    QPushButton { color: red }

以上樣式規則中,QPushButton是選擇器,{ color: red }是聲明。樣式規則指定了QPushButton及其子類應使用紅色作為前景色。

QT樣式表大小寫不敏感,除了類名、對象名、QT屬性名是大小寫敏感的。

多個選擇器可以指定同一個聲明,使用逗号分隔選擇器。例如以下規則:

    QPushButton, QLineEdit, QComboBox { color: red }

等效于三個規則:

    QPushButton { color: red }

    QLineEdit { color: red }

    QComboBox { color: red }

樣式規則的聲明部分是一個“屬性:值”對的連結清單。聲明部分在{}内,不同的屬性:值”對使用分号分隔。例如:

    QPushButton { color: red; margin: 0px; color: rgb(85, 85, 85); font-family: 宋體, "Arial Narrow", arial, serif;">2、選擇器的類型

到目前為止所有的例子使用的都是最簡單的選擇器類型。QT樣式表支援CSS2定義的所有選擇器。下表總結了最常用的選擇器類型。

選擇器 示例 說明
通用選擇器 * 比對所有的元件
類型選擇器 QPushButton 比對所有QPushButton機器子類的執行個體
屬性選擇器 QPushButton[flat="false"] 比對所有QPushButton的屬性flat為false的執行個體。屬性分為靜态屬性和動态屬性,靜态屬性可以通過Q_PROPERTY()來指定,動态屬性可以使用setProperty來指定。
類選擇器 .QPushButton 比對QPushButton的執行個體,子類除外
ID選擇器 QPushButton#okButton 比對對象名為okButton的所有QPushButton執行個體
後代選擇器 QDialog QPushButton 比對QDialog後代的所有QPushButton執行個體
子選擇器 QDialog > QPushButton 比對QDialog子類對象QPushButton的所有執行個體

3、子控件選擇器

對于樣式複雜的元件,需要通路元件的子控件,如QComboBox的下拉按鈕或QSpinBox的上下箭頭。選擇器可以包含子控件來對元件的特定子控件應用規則。

    QComboBox::drop-down { image: url(dropdown.png) }

以上規則會對所有QComboBox的下拉框應用樣式規則。盡管雙冒号::很像CSS3的僞元素,但QT子控件選擇器在概念上是不同的,有不同的級聯語義。

子控件選擇器通常根據另一個參考元素進行定位。參考元素可以是元件或是另一個子控件選擇器。例如,QComboBox的::drop-down預設放置在QComboBox襯底矩形的右上角。::drop-down預設放置在::drop-down子控件選擇器的内容矩形的中心。

可以使用subcontrol-origin屬性改變原點矩形。例如,如果想要将drop-down放置在邊界矩形而不是預設的襯底矩形,可以指定:

    QComboBox {

      margin-right: 20px;

  }

  QComboBox::drop-down {

      subcontrol-origin: margin;

  }

drop-down在邊界矩形内的對齊方式通過subcontrol-position屬性改變。寬屬性和高屬性用于控制子控件選擇器的大小。注意,設定一幅圖檔會隐式地設定子控件選擇器的大小。

相對定位方法(position:relative)允許子控件選擇器的位置偏離它原來的位置。例如,當QComboBox的下拉按鈕按下,想要一種被按下的效果可以通過指定如下實作:

    QComboBox::down-arrow {

          image: url(down_arrow.png);

      }

      QComboBox::down-arrow:pressed {

          position: relative;

          top: 1px; left: 1px;

      }

絕對定位方法(position:absolute)允許子控件選擇器的位置和大小的改變與參考元素有關。

一旦定位,就可以像元件那樣使用盒子模型對其進行造型。

注意,像QComboBox和QScrollBar這樣複雜的元件,如果有一個屬性或是子控件選擇器被定制,所有其他的屬性或是子控件選擇器也要必須被定制。

常用輔助控制器:

::indicator              單選框、複選框、可選菜單項或可選群組項的訓示器  

::menu-indicator         按鈕的菜單訓示器  

::item                   菜單、菜單欄或狀态欄項  

::up-button              微調框或滾動條的向下按鈕  

::down-button            微調框或滾動條的向上按鈕  

::up-arrow               微調框、滾動條或标題視圖的向上按鈕  

::down-arrow             微調框、滾動條或标題視圖的向下按鈕  

::drop-down              組合框的下拉箭頭  

::title                  群組框的标題

4、僞選擇器

選擇器可能包含限制基于元件狀态的規則應用的僞狀态。僞狀态出現在選擇器的尾部,中間使用分号連接配接。例如,以下規則用于滑鼠懸停在一個QPushButton上:

    QPushButton:hover { color: white }

僞狀态可以使用歎号取反,例如,以下規則用于滑鼠不懸停在QRadioButton:

    QRadioButton:!hover { color: red }

僞狀态可以以邏輯與的方式連接配接使用,例如,以下規則應用于滑鼠懸停在一個選中的QCheckBox上:

    QCheckBox:hover:checked { color: white }

取反僞狀态可以出現在僞狀态鍊中。例如,以下規則用于滑鼠懸停在一個QPsuButton上,但沒有按下:

    QPushButton:hover:!pressed { color: blue; }

    如果需要,使用逗号可以将僞狀态以邏輯或連接配接。

    QCheckBox:hover, QCheckBox:checked { color: white }

    僞狀态可以結合子控件選擇器使用:

    QComboBox::drop-down:hover { image: url(dropdown_bright.png) }

常用狀态:

:disabled                   禁用的視窗部件  

:enabled                    啟用的視窗部件  

:focus                      視窗部件有輸入焦點  

:hover                      滑鼠在視窗部件上懸停  

:pressed                    滑鼠按鍵點選視窗部件  

:checked                    按鈕已被選中  

:unchecked                  按鈕未被選中  

:indeterminate              按鈕被部分選中  

:open                       視窗部件處于打開或擴充的狀态  

:closed                     視窗部件處于關閉或銷毀狀态  

:on                         視窗部件的狀态是on  

:off                        視窗部件的狀态是on  

5、沖突處理

當多個樣式規則使用多個值指定同一個屬性時會産生沖突。

    QPushButton#okButton { color: gray }

    QPushButton { color: red }

    以上兩條規則比對名為okButton的QPushButton執行個體,在color屬性上有沖突。為了解決沖突,需要考慮選擇器的特征。上例中,QPushButton#okButton比QPushButton要更具體,因為QPushButton#okButton指向單個的對象,而不是類的所有執行個體。

類似,僞選擇器比未指定僞狀态的選擇器更具體。因而,以下樣式表指定,當滑鼠懸停在QPushButton上時,QPushButton的文本為白色,否則為紅色。

    QPushButton:hover { color: white }

    QPushButton { color: red }

    嚴謹一點應該是:

    QPushButton:hover { color: white }

    QPushButton:enabled { color: red }

    如果滑鼠懸停在按鈕上,兩個選擇器有相同的特性,則第二條規則優先。如果想要文本為白色,需要重新排序規則:

    QPushButton:enabled { color: red }

    QPushButton:hover { color: white }

    或者,可以使第一條規則更加具體:

    QPushButton:hover:enabled { color: white }

    QPushButton:enabled { color: red }

    和類型選擇器一起使用時,類似的問題也會發生

    QPushButton { color: red }

    QAbstractButton { color: gray }

    以上兩條規則用于QPushButton執行個體(由于QPushButton繼承自QAbstractButton),并有color屬性的沖突。由于QPushButton繼承自QAbstractButton,是以會假設QPushButton比QAbstractButton更具體。然而,對于樣式表的計算,所有的類型選擇器有相同的特性,最後出現的規則優先。換句話說,所有的QAbstractButton的color屬性會被設定為gray,包括QPushButton。如果真的想要QPushButton的文本為red,通常會重新排序規則。

    為了确定規則的特性,QT樣式表遵循CSS2規範:

    選擇器特性的計算方法如下:

    計算選擇器中ID屬性的數量(=a)

    計算選擇器中其他屬性和僞狀态類的數量(=b)

    計算選擇器中元素的數量(=c)

    忽略僞元素(如子控件選擇器)

    串聯的三個數字a-b-c給出了特性。

      *   {}

  LI            {}  

  UL LI         {}  

  UL OL+LI      {}  

  H1 + *[REL=up]{}  

  UL OL LI.red  {}  

  LI.red.level  {}  

  #x34y         {}  

6、級聯

QT樣式表可以設定在應用程式、父元件、子元件上。通過合并元件的祖先(父親、祖父等)可以擷取任意元件的有效樣式表,以及設定在應用程式上的任何樣式表。

沖突發生時,不論沖突規則的特性如何,元件自己的樣式表總是優先于任何繼承而來的樣式表。同樣,父元件的樣式表優先于祖父元件的樣式表。

這樣的結果是,在一個元件上設定樣式規則會自動獲得比祖先元件的樣式表或是應用程式的樣式表指定的其他規則更高的優先級。例如,首先在應用程式設定樣式表

    qApp->setStyleSheet("QPushButton { color: white }");

然後,在QPushButton對象設定一個樣式表

    myPushButton->setStyleSheet("* { color: blue }");

QPushButton的樣式表會強制QPushButton(及其任何子元件)顯示藍色文本,盡管應用程式範圍的樣式表提供了更具體的規則。

下列寫法也會得到相同的結果:

    myPushButton->setStyleSheet("color: blue");

但如果QPushButton有子元件,樣式表不會對子元件有效果。

樣式表級聯是一個複雜的主題,更詳細的内容請參考CSS2規範。QT目前沒有實作。

7、繼承

在經典的CSS中,當元素的字型和顔色沒有顯示設定時,會自動從父元件繼承。使用QT樣式表時,一個元件不會自動繼承父元件設定的字型和顔色。例如,一個QGroupBox包含一個QPushButton:

    qApp->setStyleSheet("QGroupBox { color: red; } ");

QPushButton并沒有顯示設定顔色,是以并不是繼承父元件QGroupBox的顔色,而是擁有系統的顔色。如果要設定QGroupBox及其子元件的顔色,如下:

    qApp->setStyleSheet("QGroupBox, QGroupBox * { color: red; }");

相比之下,使用QWidget::setFont() 和 QWidget::setPalette()為子元件設定字型和畫闆。

8、C++命名空間内部的元件

類型選擇器特殊類型的元件的樣式定制。例如:

class MyPushButton : public QPushButton {

      // ...

  }

  // ...

  qApp->setStyleSheet("MyPushButton { background: yellow; }");

    QT樣式表使用元件的QObject::className() 确定何時應選擇器。當自定義元件在命名空間内部時,QObject::className()會傳回<namespace>::<classname>。這會與子控件選擇器的文法産生沖突。為了解決這個問題,當在命名空間内使用元件的類型選擇器時,必須使用“--”代替“::”。

namespace ns {

      class MyPushButton : public QPushButton {

          // ...

      }

  }

  // ...

  qApp->setStyleSheet("ns--MyPushButton { background: yellow; }");

9、設定QObject屬性

從QT4.3開始,任何可被設計的Q_PROPERTY都可以使用qproperty-<property name>文法設定。

MyLabel { qproperty-pixmap: url(pixmap.png); }

MyGroupBox { qproperty-titleColor: rgb(100, 200, 100); }

QPushButton { qproperty-iconSize: 20px 20px; }

如果屬性引用了Q_ENUMS聲明的枚舉,應該通過名字引用常量值,而不是數字。

三、QT設計器中的樣式表

    Qt Designer是一款預覽樣式表的優秀工具,右擊設計器中的任何元件,選擇Change styleSheet...可以設定樣式表。

    QT4.2開始,Qt Designer包含了一個樣式表文法高亮器和驗證器。如果文法合法或非法,驗證器可以在Edit Style Sheet對話框的左下角訓示。

Qt樣式表詳解

    當點選Ok或Apply按鈕時,Qt Designer會自動使用新樣式表顯示元件。

四、使用樣式表定制QT元件

當使用樣式表時,每個元件會被當作有四個同心矩形:空白矩形、邊界矩形、襯底矩形、内容矩形的盒子。

1、盒子模型

四個同心矩形如下所示:

Qt樣式表詳解

    margin, border-width,padding屬性預設都是0。此時四個矩形完全相同。

    可以使用background-image屬性指定元件的背景。預設,background-image隻會在邊界矩形内被繪制,使用background-clip屬性可以修改。使用background-repeat屬性和background-origin屬性來控制背景圖檔的重複和來源。

    background-image屬性不會縮放元件的大小。為了提供随着元件大小縮放的皮膚或背景,必須使用border-image屬性。由于border-image屬性提供了一個可選擇的背景,當指定border-image屬性時,不會要求指定background-image屬性。當background-image屬性和border-image屬性都被指定時,border-image屬性會被繪制在background-image屬性之上。

    此外,image屬性可以用于在border-image屬性上繪制一幅圖像。當元件的大小與image的大小不比對時,指定的image不會伸縮,對齊方式可以使用image-position屬性設定。與background-image屬性和border-image屬性不同,image屬性可以指定SVG,使image根據元件的大小自動縮放。

    渲染規則的步驟如下:

    A、為整個渲染操作設定clip(border-radius)

    B、繪制背景(background-image)

 C、繪制邊界(border-image,border)

 D、繪制覆寫圖像(image)

2、子控件

一個元件可以看作一顆子控件樹。例如QComboBox繪制下拉按鈕子控件,下拉按鈕子控件繪制了向下箭頭子控件。

    子控件享有父子關系。QComboBox中,向下箭頭的父親是下拉按鈕,下拉按鈕的父親的QComboBox元件本身。子控件可以使用subcontrol-position熟悉和subcontrol-origin屬性定位在父元件内。

    一旦定位,子控件就可以使用盒子模型定制樣式。

注意,像QComboBox和QScrollBar這樣複雜的元件,如果有一個屬性或是子控件選擇器被定制,所有其他的屬性或是子控件選擇器也要必須被定制。

五、QT樣式表參考

QT樣式表支援多種的屬性、狀态和子控件,使得定制元件的外觀成為可能。

1、元件

以下元件都可以使用樣式表定制樣式。

元件 如何設定樣式
QAbstractScrollArea

支援盒子模型。

QAbstractScrollArea的所有繼承類,包括QTextEdit和QAbstractItemView(所有的項視圖類),都支援可滾動的背景,使用background-attachment來設定是否滾動。将background-attachment設定成fixed的話,就會使得background-image不随視口(viewport)而滾動。如果将background-attachment設定成scroll,移動滾動條時,background-image會滾動。

參考自定義QAbstractScrollArea的示例。

QCheckBox

支援盒子模型。選中狀态的訓示器可使用::indicator子控件(subcontrol)來進行樣式設定。預設情況下,訓示器放在元件的内容矩形的左上角。

spacing屬性指定選中狀态訓示器與文字之間的空隙。

參考自定義QCheckBox示例。

QColumnView 可使用image屬性來對收縮狀态進行樣式設定。箭頭訓示器(arrow indicators)可使用::left-arrow和::right-arrow子控件來進行樣式設定。
QComboBox

組合框的架構(frame)可使用盒子模型來進行樣式設定。下拉按鈕可使用::drop-down子控件來進行樣式設定。預設情況下,下拉按鈕放置在元件的襯底區域的右上角。下拉按鈕中的箭頭标志可使用::down-arrow子控件來進行樣式設定。預設情況下,箭頭是放置在下拉按鈕子控件的内容區域的中心。

參考自定義QComboBox示例。

QDialog

隻支援background、background-clip和background-origin屬性。

警告:確定在自定義的元件中定義了Q_OBJECT宏。

QDialogButtonBox 按鈕的布局方式可使用button-layout屬性來改變。
QDockWidget

在停靠狀态(docked),支援對标題欄和标題欄的按鈕進行樣式設定。

停靠元件的邊框(border)可使用border屬性來進行樣式設定。::title子控件可用來對标題欄進行樣式設定。關閉按鈕和懸浮按鈕相對于::title子控件的位置可分别使用::close-button和::float-button來進行設定。如果标題欄是豎直的,會設定:vertical僞類。

此外,根據QDockWidget::DockWidgetFeature值,設定:closable、:floatable和:movable僞狀态。

注意:使用QMainWindow::separator對改變大小的句柄進行樣式設定。

警告:在QDockWidget不處于停靠狀态時,樣式表無效。

參考自定義QDockWidget示例。

QFrame

支援盒子模型。

從QT4.3 開始,對QLabel設定樣式表,會自動将QFrame::frameStyle屬性設定成QFrame::StyledPanel。

參考自定義QFrame示例。

QGroupBox

支援盒子模型。标題可使用::title子控件來進行樣式設定。預設情況下,标題根據QGroupBox::textAlignment 屬性進行定位。

對于選中的QGroupBox,标題包含選中狀态訓示器。訓示器可使用::indicator子控件來進行樣式設定。spacing屬性用來設定文字與訓示器之間的間隔。

參考自定義QGroupBox示例。

QHeaderView

支援盒子模型。表頭視圖的各個區域使用::section子控件來進行樣式設定的。section子控件支援:middle、:first、:last、 only-one、

:next-selected、:previous-selected、:selected和:checked僞狀态。

排序訓示器使用::up-arrow和::down-arrow子控件來進行樣式設定。

參考自定義QHeaderView示例。

QLabel

支援盒子模型。不支援:hover僞狀态。

從QT4.3 開始,對QLabel設定樣式表會自動将QFrame::frameStyle 屬性設定成QFrame::StyledPanel。

參考自定義QFrame示例(QLabel繼承自QFrame)。

QLineEdit

支援盒子模型。

選中的項的顔色和背景分别是使用selection-color和selection-background-color來進行樣式設定。

密碼字元可使用lineedit-password-character屬性來進行樣式設定。

密碼掩碼延遲可使用lineedit-password-mask-delay屬性修改。

參考自定義QLineEdit示例。

QListView/

QListWidget

支援盒子模型。如果交替改變行顔色功能打開,交替的顔色使用alternate-background-color屬性來進行樣式設定。

選中的項的顔色和背景分别是使用selection-color和selection-background-color來進行樣式設定。

選擇行為由show-decoration-selected屬性來進行控制。

使用::item子控件來對QListView中的項進行更精細控制。

參考QAbsractScrollArea以了解對可滾動的背景的樣式設定。

參考自定義QListView示例。

QMainWindow

支援對分隔符進行樣式設定。

在QMainWindow中使用QDockWidget時産生的分隔符使用::separator子控件來進行樣式設定。

參考自定義QMainWindow示例。

QMenu

支援盒子模型。

單個的項使用::item子控件來進行樣式設定。除通常的僞狀态外,item子控件還支援:selected、:default、:exclusive和non-exclusive僞狀态。

複選選的菜單項訓示器是通過::indicator子控件來進行樣式設定。

分隔符是使用::separator子控件進行樣式設定。

對于有子菜單的項,箭頭标記是使用right-arrow和left-arrow進行樣式設定。

滾動器使用::scroller進行樣式設定。

分離菜單使用::tearoff來進行樣式設定。

參考自定義QMenu示例。

QMenuBar

支援盒子模型。spacing屬性指定菜單項之間的空隙大小。

單個的項使用::item子控件進行樣式設定。

警告:在Qt/Mac平台上,菜單欄通常嵌入到系統的全局菜單條中。在這種情況下,樣式單無效。

參考自定義QMenuBar示例。

QMessageBox messagebox-text-interaction-flags屬性用來選擇消息框中文字的互動模式。
QProgressBar

支援盒子模型。進度條的進度塊使用::chunk子控件來進行樣式設定。進度塊顯示在元件的内容區域中。

如果進度條顯示文字,使用text-align屬性來設定文字的位置。

不确定的進度條使用:indeterminate僞狀态設定。

參考自定義QProgressBar示例。

QPushButton

支援盒子模型。支援:default、:flat、:checked僞狀态。

對于帶菜單的QPushButton,其菜單訓示器是使用::menu-indicator子控件來進行樣式設定的。複選的按鈕的外觀可使用:pen和:closed僞狀态進行樣式設定。

警告:如果隻為QPushButton設定background-color,背景可能不會顯示出來,除非将邊框屬性設定成某個值。這是因為,在預設情況下,QPushButton會繪制一個完全覆寫了背景色的本地邊框。例如,

QPushButton { border: none; }

參考自定義QPushButton示例。

QRadioButton

支援盒子模型。選中訓示器使用::indicator子控件進行樣式設定。預設情況下,訓示器放置在元件内容區域的左上角。

spacing屬性指定選中訓示器與文字之間的空隙。

參考自定義QRadioButton示例。

QScrollBar

支援盒子模型。元件中的内容區域就是滑塊滑動的槽。QScrollBar的廣度是使用width或height屬性設定的。要确定方向,使用:horizontal和:vertical僞狀态。

滑塊使用::handle子控件進行樣式設定。設定min-width或min-height按照方向來對滑塊提供尺寸的限制。

::add-line子控件用來對增加一行的按鈕進行樣式設定。預設情況下,add-line子控件放置在元件邊框區域的右下角。預設情況下,箭頭放置在::add-line子控件内容區域的中心。

::sub-line子控件用來對減少一行的按鈕進行樣式設定。預設情況下,sub-line子控件被放置在元件邊框區域的左上角。預設情況下,箭頭放置在sub-line子控件内容區域的中心。

::sub-page子控件用來對減一頁作用的滑塊區域進行樣式設定。::add-page子控件用來對起到加一頁作用的滑塊區域進行樣式設定。

參考自定義QScrollBar示例。

QSizeGrip

支援width、height和image屬性。

參考自定義QSizeGrip示例。

QSlider

支援盒子模型。對于水準滑動器,必須提供min-width和height屬性。對于豎直滑動器,必須提供min-height和width屬性。

滑動器的滑槽使用::groove進行樣式設定。預設情況下,滑槽被放置在元件的内容區域中。滑動器的滑塊使用::handle子控件進行樣式設定。子控件在滑槽的内容區域中移動。

參考自定義QSlider示例。

QSpinBox

QDateEdit

QDateTimeEdit

QDoubleSpinBox

QTimeEdit

旋轉框的架構使用盒子模型來進行樣式設定。

向上按鈕和箭頭可使用::up-button和::up-arrow子控件來進行樣式設定。預設情況下,向上按鈕被放置在元件填充區域的右上角。如果沒有顯式設定尺寸,會占據參考區域的一半高度。向上箭頭被放置在向上按鈕的内容區域的中心。

向下按鈕和箭頭使用::down-button和::down-arrow子控件進行樣式設定。預設情況下,向下按鈕被放置在元件填充區域的右下角。如果沒有顯式設定尺寸,會占據參考區域的一半高度。向下箭頭被放置在向下按鈕的内容區域的中心。

參考自定義QSpinBox示例。

QSplitter

支援盒子模型。分割器的句柄使用::handle子控件進行樣式設定。

參考自定義QSplitter示例。

QStatusBar

隻支援background屬性。單個項的架構使用::item子控件進行樣式設定。

參考自定義QStatusBar示例。

QTabBar

單個标簽使用::tab子控件進行樣式設定。關閉按鈕使用::close-button子控件進行樣式設定。标簽支援 only-one、:first、:last、:middle、:previous–selected、:next-selected、:selected僞狀态。

标簽的方向決定是否有:top、:left、:right、:bottom僞狀态。

對于選中狀态的重疊标簽通過使用負數的邊距或絕對位置模式來建立。

QTabBar的分離訓示器使用::tear子控件進行樣式設定。

QTabBar用兩個QToolButtons作為滾動器,使用QTabBar QToolButton選擇器進行樣式設定。使用::scroller子控件指定滾動按鈕的寬度。

QTabBar中标簽的對齊方式使用alignment屬性進行設定。

警告:要改變QTabWidget中的QTabBar的位置,使用tab-bar子控件。

參考自定義QTabBar示例。

QTabWidget

标簽元件的架構使用::pane子控件進行樣式設定。左邊角和右邊角分别使用::left-corner和::right-corner進行樣式設定。标簽條的位置使用::tab-bar子控件控制。

預設情況下,QTabWidget的子控件的位置按照QWindowsStyle風格來确定。要将QTabBar放置在中央的位置,設定tab-bar子控件的subcontrol-position屬性。

标簽組方向決定是否有:top、:left、:right、:bottom僞狀态。

參考自定義QTabWidget示例。

QTableView

支援盒子模型。如果交替改變行顔色功能開啟,交替的顔色使用alternate-background-color屬性進行樣式設定。

選中的項的顔色和背景分别是使用selection-color和selection-background-color進行樣式設定。

QTableView中的邊角元件由QAbstractButton實作,使用QTableViewQTableCornerButton::section選擇器進行樣式設定。

警告:如果隻在QTableCornerButton上設定背景色,背景可能不會顯示出來,除非将邊框屬性設定成某個值。這是因為,預設情況下,QTableCornerButton會繪制一個完全覆寫背景色的本地邊框。

網格的顔色使用gridline-color屬性進行設定。

參考QAbsractScrollArea以了解如何設定可滾動的背景。

參考自定義QTableView示例。

QTextEdit

支援盒子模型。

選中文字的顔色和背景分别使用selection-color和selection-background-color進行樣式設定。

參考QAbsractScrollArea以了解如何設定可滾動的背景。

QToolBar

支援盒子模型。

工具欄所在的區域(停靠方向)決定是否會有:top、:left、:right、:bottom僞狀态。

:first、:last、:middle、:only-one僞狀态訓示工具欄的位置是一個線性組(參考QStyleOptionToolBar::positionWithinLine)

QToolBar的分隔符使用::separator子控件進行樣式設定。

用來移動工具欄的句柄使用::handle子控件進行樣式設定。

參考自定義QToolBar示例。

QToolButton

支援盒子模型。

如果QToolButton有菜單,::menu-indicator子控件用來對菜單訓示器進行樣式設定。預設情況下,菜單訓示器放置在元件填充區域的右下角。

如果QToolButton是QToolButton::MenuButtonPopup模式,::menu-button子控件用來繪制菜單按鈕。::menu-arrow子控件用來在菜單按鈕裡面繪制菜單箭頭。預設情況下,菜單按鈕子控件位于内容區域的中心。

當QToolButton顯示箭頭時,會使用::up-arrow、::down-arrow、::left-arrow和::right-arrow子控件。

警告:如果隻在QToolButton 設定背景色,背景可能不會顯示出來,除非将邊框屬性設定成某個值。這是因為,預設情況下,QToolButton會繪制一個完全覆寫背景色的本地邊框。例如,

QToolButton { border: none; }

參考自定義QToolButton示例。

QToolBox

支援盒子模型。

單個标簽使用::tab子控件進行樣式設定。标簽支援 :only-one、:first、:last、:middle、:previous-selected、:next-selected、:selected僞狀态。

QToolTip

支援盒子模型。opacity屬性控制工具提示的透明度。

參考自定義QFrame示例(QToolTip是QFrame)。

QTreeView

QTreeWidget

QTableWidget

支援盒子模型。如果交替改變行顔色功能開啟,交替的顔色使用alternate-background-color屬性進行樣式設定。

選中項的顔色和背景分别是使用selection-color和selection-background-color進行樣式設定。

選擇行為由show-decoration-selected屬性進行控制。

樹型視圖的分支使用::branch子控件進行樣式設定。::branch子控件支援:open、:closed、:has-sibling和:has-children僞狀态。

使用::item子控件對QTreeView中的項進行更精細控制。

參考QAbsractScrollArea以了解如何設定可滾動的背景。

參考自定義QTreeView示例以了解如何對分支進行樣式設定。

QWidget

隻支援background、background-clip和background-origin屬性。

如果從QWidget派生子類,需要為自定義元件提供繪制事件處理函數(paintEvent):

void CustomWidget::paintEvent(QPaintEvent *)

{

QStyleOption opt;

opt.init(this);

QPainter p(this);

style()->drawPrimitive(QStyle::PE_Widget, &opt, &p, this);

}

如果沒有設定樣式單,以上的代碼不起任何作用。

警告:確定在自定義元件中定義了Q_OBJECT宏。

六、QT樣式表執行個體

1、樣式表的使用

A、定制前景色和背景色

    設定應用程式中的所有QLineEdit元件的背景色為黃色

    qApp->setStyleSheet("QLineEdit {

    如果隻想要屬性用于具體某個對話框的QLineEdit及子類元件。

    myDialog->setStyleSheet("QLineEdit {

    如果隻想将屬性用于某個具體的QLineEdit元件,可以使用QObject::setObjectName() 和ID選擇器。

    myDialog->setStyleSheet("QLineEdit#nameEdit {

    可以直接設定QLieEdit元件的background-color屬性,忽略選擇器

    nameEdit->setStyleSheet("

    為了確定對比效果,應該指定文本合适的顔色

    nameEdit->setStyleSheet("color: blue;

    修改選中文本的顔色如下:

    nameEdit->setStyleSheet("color: blue;"

                          ""

                          "selection-color: yellow;"

                          "selection-");

B、使用動态屬性定制樣式

為了提示使用者字段是必填的,對這些字段使用黃色作為背景色。要使用QT樣式表是現實很容易的。首先,應該使用應用程式的樣式表:

*[mandatoryField="true"] { margin: 0px; clear: both; height: auto; overflow: hidden; color: rgb(85, 85, 85); font-family: 宋體, "Arial Narrow", arial, serif; text-indent: 28px; text-align: justify;">這意味着mandatoryField字段設定為true的元件的背景色為黃色。

對于每個必備字段元件,我們匆忙中簡單建立了一個mandatoryField屬性并設定為true。

    QLineEdit *nameEdit = new QLineEdit(this);

    nameEdit->setProperty("mandatoryField", true);

    QLineEdit *emailEdit = new QLineEdit(this);

    emailEdit->setProperty("mandatoryField", true);

   QSpinBox *ageSpinBox = new QSpinBox(this);

   ageSpinBox->setProperty("mandatoryField", true);

C、使用盒子模型定制QPushButton

本節我們展示如何建立一個紅色的按鈕。

QPushButton#evilButton

{

      border-style: outset;

      border-width: 2px;

      border-radius: 10px;

      border-color: beige;

      font: bold 14px;

      min-width: 10em;

      padding: 6px;

  }

  QPushButton#evilButton:pressed

{

      border-style: inset;

  }

D、定制按鈕菜單訓示器子控件

    子控件可以通路元件的子元素。例如,按鈕會使用QPushButton::setMenu()關聯菜單與菜單訓示器。定制紅色按鈕的菜單訓示器如下:

QPushButton#evilButton::menu-indicator

{

      image: url(myindicator.png);

 }

    預設,菜單訓示器定位在襯底區域的右下角。通過改變subcontrol-position、subcontrol-origin屬性可以定位訓示器。

QPushButton::menu-indicator

{

      image: url(myindicator.png);

      subcontrol-position: right center;

      subcontrol-origin: padding;

      left: -2px;

  }

    Myindicator.png的位置在按鈕襯底區域的右中心。

E、複雜選擇器示例

    設定應用程式樣式表中QLineEdit文本為紅色。

    QLineEdit { color: red }

    然而,想要設定一個隻讀QLineEdit的文本顔色為灰色如下:

    QLineEdit { color: red }

    QLineEdit[readOnly="true"] { color: gray }

    某些情況下,如果要求系統資料庫單中的所有QLineEdit為棕色。

    QLineEdit { color: red }

     QLineEdit[readOnly="true"] { color: gray }

     #registrationDialog QLineEdit { color: brown }

    如果要求所有對話框中的QLineEdit為棕色。

    QLineEdit { color: red }

    QLineEdit[readOnly="true"] { color: gray }

    QDialog QLineEdit { color: brown }

2、定制特殊元件

本節提供使用樣式表定制特定元件的執行個體。

(1)、定制QAbstractScrollArea

任何QAbstractScrollArea元件(項視圖、QTextEdit、QTextBrowser)的背景都可以使用bakcground屬性設定。例如,設定帶有滾動條滾動的背景圖屬性如下:

QTextEdit, QListView 

{

      background-image: url(draft.png);

      background-attachment: scroll;

  }

如果設定background-image屬性在視口中固定。

QTextEdit, QListView 

{

      background-image: url(draft.png);

      background-attachment: fixed;

  }

(2)、定制QCheckBox

進行QCheckBox樣式設定與QRadioButton樣式設定相同。主要差別在于三态的QCheckBox有一個模糊态。

QCheckBox 

{

      spacing: 5px;

  }

  QCheckBox::indicator

{

      width: 13px;

      height: 13px;

  }

  QCheckBox::indicator:unchecked

{

      image: url(:/images/checkbox_unchecked.png);

  }

  QCheckBox::indicator:unchecked:hover

{

      image: url(:/images/checkbox_unchecked_hover.png);

  }

  QCheckBox::indicator:unchecked:pressed

{

      image: url(:/images/checkbox_unchecked_pressed.png);

  }

  QCheckBox::indicator:checked

{

      image: url(:/images/checkbox_checked.png);

  }

  QCheckBox::indicator:checked:hover

{

      image: url(:/images/checkbox_checked_hover.png);

  }

  QCheckBox::indicator:checked:pressed

{

      image: url(:/images/checkbox_checked_pressed.png);

  }

  QCheckBox::indicator:indeterminate:hover

{

      image: url(:/images/checkbox_indeterminate_hover.png);

  }

  QCheckBox::indicator:indeterminate:pressed {

      image: url(:/images/checkbox_indeterminate_pressed.png);

  }

(3)、定制組合框QComboBox

QComboBox {

      border: 1px solid gray;

      border-radius: 3px;

      padding: 1px 18px 1px 3px;

      min-width: 6em;

  }

  QComboBox:editable {

      background: white;

  }

  QComboBox:!editable, QComboBox::drop-down:editable {

       background: qlineargradient(x1: 0, y1: 0, x2: 0, y2: 1,

                                   stop: 0 #E1E1E1, stop: 0.4 #DDDDDD,

                                   stop: 0.5 #D8D8D8, stop: 1.0 #D3D3D3);

  }

  QComboBox:!editable:on, QComboBox::drop-down:editable:on {

      background: qlineargradient(x1: 0, y1: 0, x2: 0, y2: 1,

                                  stop: 0 #D3D3D3, stop: 0.4 #D8D8D8,

                                  stop: 0.5 #DDDDDD, stop: 1.0 #E1E1E1);

  }

  QComboBox:on {

      padding-top: 3px;

      padding-left: 4px;

  }

  QComboBox::drop-down {

      subcontrol-origin: padding;

      subcontrol-position: top right;

      width: 15px;

      border-left-width: 1px;

      border-left-color: darkgray;

      border-left-style: solid;

      border-top-right-radius: 3px;

      border-bottom-right-radius: 3px;

  }

  QComboBox::down-arrow {

      image: url(/usr/share/icons/crystalsvg/16x16/actions/1downarrow.png);

  }

  QComboBox::down-arrow:on {

      top: 1px;

      left: 1px;

  }

    組合框的彈出菜單是QAbstractItemView,使用後代選擇器進行樣式設定。

  QComboBox QAbstractItemView {

      border: 2px solid darkgray;

      selection-

  }

(4)、定制QDockWidget

QDockWidget的标題欄和按鈕可以按如下進行樣式設定。

QDockWidget

{

    border: 1px solid lightgray;

    titlebar-close-icon: url(close.png);

    titlebar-normal-icon: url(undock.png);

}

QDockWidget::title

{

    text-align: left; 

    background: lightgray;

    padding-left: 5px;

}

QDockWidget::close-button, QDockWidget::float-button

{

    border: 1px solid transparent;

    background: darkgray;

    padding: 0px;

}

QDockWidget::close-button:hover, QDockWidget::float-button:hover

{

    background: gray;

}

QDockWidget::close-button:pressed, QDockWidget::float-button:pressed

{

    padding: 1px -1px -1px 1px;

}

如果要移動停靠元件按鈕到左側,可以使用如下樣式表設定:

QDockWidget 

{

      border: 1px solid lightgray;

      titlebar-close-icon: url(close.png);

      titlebar-normal-icon: url(float.png);

 }

  QDockWidget::title 

  {

      text-align: left;

      background: lightgray;

      padding-left: 35px;

  }

  QDockWidget::close-button, QDockWidget::float-button 

  {

      background: darkgray;

      padding: 0px;

      icon-size: 14px; 

  }

  QDockWidget::close-button:hover, QDockWidget::float-button:hover 

  {

      background: gray;

  }

  QDockWidget::close-button:pressed, QDockWidget::float-button:pressed 

  {

      padding: 1px -1px -1px 1px;

  }

  QDockWidget::close-button 

  {

      subcontrol-position: top left;

      subcontrol-origin: margin;

      position: absolute;

      top: 0px; left: 0px; bottom: 0px;

      width: 14px;

  }

  QDockWidget::float-button 

  {

      subcontrol-position: top left;

      subcontrol-origin: margin;

      position: absolute;

      top: 0px; left: 16px; bottom: 0px;

      width: 14px;

  }

(5)、定制QFrame

QFrame, QLabel, QToolTip 

{

      border: 2px solid green;

      border-radius: 4px;

      padding: 2px;

      background-image: url(images/welcome.png);

}

(6)、定制QGroupBox

QGroupBox

{

    background-color: qlineargradient(x1: 0, y1: 0, x2: 0, y2: 1,

                                      stop: 0 #E0E0E0, stop: 1 #FFFFFF);

    border: 2px solid gray;

    border-radius: 5px;

    margin-top: 1ex; 

}

QGroupBox::title

{

    subcontrol-origin: margin;

    subcontrol-position: top center; 

    padding: 0 3px;

    background-color: qlineargradient(x1: 0, y1: 0, x2: 0, y2: 1,

                                      stop: 0 #FF0ECE, stop: 1 #FFFFFF);

}

QGroupBox::indicator

{

    width: 13px;

    height: 13px;

}

QGroupBox::indicator:unchecked

{

    image: url(:/images/checkbox_unchecked.png);

}

(7)、定制QHeaderView

QHeaderView::section 

{

    background-color: qlineargradient(x1:0, y1:0, x2:0, y2:1,

                                      stop:0 #616161, stop: 0.5 #505050,

                                      stop: 0.6 #434343, stop:1 #656565);

color: white;

    padding-left: 4px;

border: 1px solid #6c6c6c;

}

QHeaderView::section:checked

{

    background-color: red;

}

QHeaderView::down-arrow 

{

    image: url(down_arrow.png);

}

QHeaderView::up-arrow 

{

    image: url(up_arrow.png);

}

(8)、定制QLineEdit

QLineEdit的架構使用盒子模型進行樣式設定。

QLineEdit 

{

    border: 2px solid gray;

    border-radius: 10px;

    padding: 0 8px;

    background: yellow;

    selection-background-color: darkgray;

}

QLineEdit的密碼字元使用QLineEdit::Password顯示模式設定。

QLineEdit[echoMode="2"] 

{

    lineedit-password-character: 9679;

}

隻讀QLineEdit的背景可以如下修改:

QLineEdit:read-only 

{

    background: lightblue;

}

可以參考的文章連結:

http://9291927.blog.51cto.com/9281927/1888380/

http://9291927.blog.51cto.com/9281927/1888395

http://9291927.blog.51cto.com/9281927/1888400

http://blog.csdn.net/goforwardtostep/article/details/60884870

http://blog.csdn.net/GoForwardToStep/article/details/64169734

http://blog.csdn.net/GoForwardToStep/article/details/65451416

Qt

繼續閱讀