首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> 關於C語言

打造原生感 Qt 桌面應用(四):Qt Style Sheet (QSS) 實戰指南

     編輯:關於C語言

QSS 與 CSS 的異同

Qt Style Sheet (QSS) 語法、選擇器、屬性名幾乎**完全對標 CSS 2.1**,差異在於:

  • 作用對象是 Qt 組件 (Widget) 而非 DOM 元素。
  • 盒模型基於 QStyle 佈局 (contentsRect, padding, border, margin)。
  • 支援 Qt 特有偽狀態 (:enabled, :pressed, :checked, :focus 等)。
  • 單位預設像素,可用 pt, em, ex。

⚠️ **慎用 QSS 破壞原生感**:過度自定義顏色/邊框會讓應用在各平台顯得「異類」。優先使用 palette(role) 參考系統調色板。

基礎用法:三種套用層級

層級範圍代碼範例
應用程式全域所有組件qApp->setStyleSheet("QToolTip { color: #fff; background: #333; }");
單一 Widget 及其子樹局部widget->setStyleSheet("background: palette(window);");
單一 Widget 自身 (不繼承)精準控制widget->setStyleSheet("QPushButton { ... }"); // 僅影響該按鈕

核心語法精華

1. 使用系統調色板色彩 (保持原生感關鍵)

// 錯誤:硬編碼紅色
label->setStyleSheet("color: red;");

// 正確:引用系統 Highlight 色
label->setStyleSheet("color: palette(highlight);");

// 動態色彩:從 QColor 轉名稱
QColor accent(128, 200, 128);
label->setStyleSheet(QString("color: %1;").arg(accent.name()));

palette(role) 可用角色:window, windowText, base, alternateBase, toolTipBase, toolTipText, text, button, buttonText, brightText, highlight, highlightedText, link, linkVisited 等。

2. 盒模型與邊框圖片


QPushButton {
    border: 2px solid palette(mid);
    border-radius: 4px;
    padding: 6px 12px;
    background: palette(button);
}
QPushButton:pressed {
    background: palette(mid);
}
QPushButton:disabled {
    color: palette(mid);
}

3. 邊框圖片 — 打造蘋果風分段按鈕

準備 4 張圖 (已加入資源系統 :/img/...):

  • btn_left.png (正常左按鈕)
  • btn_left_pressed.png (按下左按鈕)
  • btn_right.png (正常右按鈕)
  • btn_right_pressed.png (按下右按鈕)

QToolButton {
    border-image: url(:/img/btn_left.png);
}
QToolButton:pressed {
    border-image: url(:/img/btn_left_pressed.png);
}
/* 右按鈕需用物件名稱或屬性選擇器區分 */
QToolButton#forwardBtn {
    border-image: url(:/img/btn_right.png);
}
QToolButton#forwardBtn:pressed {
    border-image: url(:/img/btn_right_pressed.png);
}

佈局代碼


QWidget segmentedButton;
QHBoxLayout* lay = new QHBoxLayout(&segmentedButton);
lay->setSpacing(0); lay->setMargin(0);

QToolButton* backBtn = new QToolButton(&segmentedButton);
QToolButton* fwdBtn = new QToolButton(&segmentedButton);
fwdBtn->setObjectName("forwardBtn"); // 對應 QSS 選擇器

backBtn->setFixedSize(28, 23);
fwdBtn->setFixedSize(28, 23);

lay->addWidget(backBtn);
lay->addWidget(fwdBtn);

// 外層容器消除視窗最小尺寸限制
QWidget win;
QHBoxLayout* winLay = new QHBoxLayout(&win);
winLay->setSpacing(0); winLay->setMargin(0);
winLay->setAlignment(Qt::AlignLeft);
winLay->addWidget(&segmentedButton);
win.show();

關鍵技巧:Windows 視窗有最小尺寸,直接 segmentedButton.show() 會導致按鈕分離。嵌套一層 QWidget 並設定 setMargin(0)/setSpacing(0) 可繞過限制。

進階選擇器與偽狀態

效能與除錯提示

  • 避免通用選擇器 * { ... },會遍歷所有組件,啟動慢。
  • 盡量用 ID/屬性選擇器 縮小範圍。
  • 動態屬性觸發重繪:widget->setProperty("state", "error"); widget->style()->unpolish(widget); widget->style()->polish(widget);
  • 除錯工具:QT_STYLESHEET_DEBUG=1 環境變數啟動程式,控制台輸出 QSS 解析與匹配詳情。
  • 檢視器:Qt Designer 整合 QSS 編輯器,可即時預覽。

QSS vs QStyle:如何選擇?

選擇器範例說明
類別選擇器QPushButton所有按鈕
ID 選擇器QPushButton#okBtnobjectName="okBtn" 的按鈕
屬性選擇器QPushButton[flat="true"]flat 屬性為 true 的按鈕
後代選擇器QGroupBox QPushButton群組框內的按鈕
子代選擇器QAbstractScrollArea > QScrollBar直接子組件
偽狀態:hover, :pressed, :checked, :disabled, :focus, :enabled, :selected, :open (選單/下拉)互動狀態
場景推薦方案
顏色、字體、間距、邊框、背景圖調整QSS (聲明式、熱重載、設計師友善)
自定義組件佈局邏輯、複雜繪製行為、像素級控制QProxyStyle / paintEvent (命令式、完整控制)
跨平台原生感微調QSS + palette() 為主,必要時 QProxyStyle 修正平台差異

結語

QSS 是 Qt 視覺定製的「瑞士軍刀」:語法熟悉、效果即時、維護成本低。核心原則——**善用 palette() 而非硬編碼色彩**,讓應用在 Windows 深色模式、macOS Aqua、GNOME Adwaita、KDE Breeze 下都能自然融入。將複雜繪製邏輯留給 QStyle,QSS 專注於「皮膚層」的優雅變裝。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved