182 lines
8.1 KiB
C++
182 lines
8.1 KiB
C++
#include "ElaMenuBarStyle.h"
|
|
|
|
#include <QDebug>
|
|
#include <QPainter>
|
|
#include <QStyleOption>
|
|
|
|
#include "ElaMenuBar.h"
|
|
#include "ElaTheme.h"
|
|
ElaMenuBarStyle::ElaMenuBarStyle(QStyle *style) {
|
|
_themeMode = eTheme->getThemeMode();
|
|
connect(eTheme, &ElaTheme::themeModeChanged, this, [=](ElaThemeType::ThemeMode themeMode) { _themeMode = themeMode; });
|
|
}
|
|
|
|
ElaMenuBarStyle::~ElaMenuBarStyle() {}
|
|
|
|
void ElaMenuBarStyle::drawPrimitive(PrimitiveElement element, const QStyleOption *option, QPainter *painter, const QWidget *widget) const {
|
|
switch (element) {
|
|
case QStyle::PE_PanelButtonTool: {
|
|
return;
|
|
}
|
|
default: {
|
|
break;
|
|
}
|
|
}
|
|
QProxyStyle::drawPrimitive(element, option, painter, widget);
|
|
}
|
|
|
|
void ElaMenuBarStyle::drawControl(ControlElement element, const QStyleOption *option, QPainter *painter, const QWidget *widget) const {
|
|
switch (element) {
|
|
case QStyle::CE_ToolButtonLabel: {
|
|
if (const QStyleOptionToolButton *topt = qstyleoption_cast<const QStyleOptionToolButton *>(option)) {
|
|
painter->save();
|
|
painter->setRenderHints(QPainter::Antialiasing | QPainter::SmoothPixmapTransform);
|
|
painter->setPen(Qt::NoPen);
|
|
if (topt->state.testFlag(QStyle::State_Enabled) && topt->state.testFlag(QStyle::State_MouseOver)) {
|
|
painter->setBrush(ElaThemeColor(_themeMode, BasicHoverAlpha));
|
|
painter->drawRect(topt->rect);
|
|
}
|
|
// 展开图标
|
|
painter->setPen(!topt->state.testFlag(QStyle::State_Enabled) ? Qt::gray : ElaThemeColor(_themeMode, BasicText));
|
|
QFont iconFont = QFont("ElaAwesome");
|
|
iconFont.setPixelSize(18);
|
|
painter->setFont(iconFont);
|
|
painter->drawText(topt->rect, Qt::AlignCenter, QChar((unsigned short)ElaIconType::AngleRight));
|
|
painter->restore();
|
|
}
|
|
return;
|
|
}
|
|
case QStyle::CE_MenuBarEmptyArea: {
|
|
return;
|
|
}
|
|
case QStyle::CE_MenuBarItem: {
|
|
if (const QStyleOptionMenuItem *mopt = qstyleoption_cast<const QStyleOptionMenuItem *>(option)) {
|
|
if (mopt->menuItemType == QStyleOptionMenuItem::Separator) {
|
|
return;
|
|
}
|
|
int menuBarHeight = widget->height();
|
|
QRect menuItemRect = mopt->rect;
|
|
painter->save();
|
|
painter->setRenderHints(QPainter::Antialiasing | QPainter::SmoothPixmapTransform);
|
|
// 背景绘制
|
|
painter->setPen(Qt::NoPen);
|
|
if (mopt->state.testFlag(QStyle::State_Enabled)) {
|
|
if (mopt->state.testFlag(QStyle::State_Sunken)) {
|
|
painter->setBrush(ElaThemeColor(_themeMode, BasicPressAlpha));
|
|
} else if (mopt->state.testFlag(QStyle::State_Selected)) {
|
|
painter->setBrush(ElaThemeColor(_themeMode, BasicSelectedAlpha));
|
|
}
|
|
painter->drawRoundedRect(menuItemRect, 3, 3);
|
|
}
|
|
// 图标和文字绘制
|
|
QIcon icon = mopt->icon;
|
|
QString menuText = mopt->text;
|
|
QString iconText;
|
|
menuText = menuText.replace("&", "");
|
|
const ElaMenuBar *menuBar = dynamic_cast<const ElaMenuBar *>(widget);
|
|
if (menuBar) {
|
|
QAction *action = menuBar->actionAt(menuItemRect.center());
|
|
if (action) {
|
|
iconText = action->property("ElaIconType").toString();
|
|
}
|
|
}
|
|
if (menuText.isEmpty()) {
|
|
// 图标
|
|
if (!iconText.isEmpty()) {
|
|
painter->save();
|
|
painter->setPen(!mopt->state.testFlag(QStyle::State_Enabled) ? ElaThemeColor(_themeMode, BasicTextDisable)
|
|
: ElaThemeColor(_themeMode, BasicText));
|
|
QFont iconFont = QFont("ElaAwesome");
|
|
iconFont.setPixelSize(menuBarHeight * 0.7);
|
|
painter->setFont(iconFont);
|
|
painter->drawText(menuItemRect, Qt::AlignCenter, iconText);
|
|
painter->restore();
|
|
} else if (!icon.isNull()) {
|
|
QRect menuIconRect(menuItemRect.center().x() - menuBarHeight * 0.4, menuItemRect.center().y() - menuBarHeight * 0.4,
|
|
menuBarHeight * 0.8, menuBarHeight * 0.8);
|
|
painter->drawPixmap(menuIconRect, icon.pixmap(menuBarHeight * 0.8, menuBarHeight * 0.8));
|
|
}
|
|
} else {
|
|
// 图标 + 文字
|
|
painter->setPen(!mopt->state.testFlag(QStyle::State_Enabled) ? ElaThemeColor(_themeMode, BasicTextDisable)
|
|
: ElaThemeColor(_themeMode, BasicText));
|
|
if (icon.isNull() && iconText.isEmpty()) {
|
|
painter->drawText(menuItemRect, Qt::AlignCenter, menuText);
|
|
} else {
|
|
if (!iconText.isEmpty()) {
|
|
QRectF menuIconRect(menuItemRect.x() + menuBarHeight * 0.1 + _menuBarItemMargin, menuBarHeight * 0.1, menuBarHeight * 0.8,
|
|
menuBarHeight * 0.8);
|
|
painter->save();
|
|
QFont iconFont = QFont("ElaAwesome");
|
|
iconFont.setPixelSize(menuBarHeight * 0.7);
|
|
painter->setFont(iconFont);
|
|
painter->drawText(menuIconRect, Qt::AlignCenter, iconText);
|
|
painter->restore();
|
|
painter->drawText(QRect(menuIconRect.right(), menuItemRect.y(), menuItemRect.width() - menuIconRect.width(), menuBarHeight),
|
|
Qt::AlignCenter, menuText);
|
|
} else {
|
|
QRect menuIconRect(menuItemRect.x() + menuBarHeight * 0.1 + _menuBarItemMargin, menuBarHeight * 0.1, menuBarHeight * 0.8,
|
|
menuBarHeight * 0.8);
|
|
painter->drawPixmap(menuIconRect, icon.pixmap(menuBarHeight * 0.8, menuBarHeight * 0.8));
|
|
painter->drawText(QRect(menuIconRect.right(), menuItemRect.y(), menuItemRect.width() - menuIconRect.width(), menuBarHeight),
|
|
Qt::AlignCenter, menuText);
|
|
}
|
|
}
|
|
}
|
|
painter->restore();
|
|
}
|
|
return;
|
|
}
|
|
default: {
|
|
break;
|
|
}
|
|
}
|
|
|
|
QProxyStyle::drawControl(element, option, painter, widget);
|
|
}
|
|
|
|
QSize ElaMenuBarStyle::sizeFromContents(ContentsType type, const QStyleOption *option, const QSize &size, const QWidget *widget) const {
|
|
switch (type) {
|
|
case QStyle::CT_MenuBar: {
|
|
QSize menuBarHeight = QProxyStyle::sizeFromContents(type, option, size, widget);
|
|
menuBarHeight.setHeight(widget->height());
|
|
return menuBarHeight;
|
|
}
|
|
case QStyle::CT_MenuBarItem: {
|
|
if (const QStyleOptionMenuItem *mopt = qstyleoption_cast<const QStyleOptionMenuItem *>(option)) {
|
|
QSize menuBarItemSize = QProxyStyle::sizeFromContents(type, option, size, widget);
|
|
menuBarItemSize.setHeight(widget->height());
|
|
if ((!mopt->icon.isNull()) && !mopt->text.isEmpty()) {
|
|
menuBarItemSize.setWidth(menuBarItemSize.width() + mopt->fontMetrics.horizontalAdvance(mopt->text) + 2 * _menuBarItemMargin);
|
|
}
|
|
if (!mopt->text.contains("&")) {
|
|
menuBarItemSize.setWidth(menuBarItemSize.width() + 5);
|
|
}
|
|
return menuBarItemSize;
|
|
}
|
|
}
|
|
default: {
|
|
break;
|
|
}
|
|
}
|
|
return QProxyStyle::sizeFromContents(type, option, size, widget);
|
|
}
|
|
|
|
int ElaMenuBarStyle::pixelMetric(PixelMetric metric, const QStyleOption *option, const QWidget *widget) const {
|
|
switch (metric) {
|
|
case QStyle::PM_MenuBarHMargin: {
|
|
return 0;
|
|
}
|
|
case QStyle::PM_MenuBarItemSpacing: {
|
|
return 6;
|
|
}
|
|
case QStyle::PM_ToolBarExtensionExtent: {
|
|
return 26;
|
|
}
|
|
default: {
|
|
break;
|
|
}
|
|
}
|
|
return QProxyStyle::pixelMetric(metric, option, widget);
|
|
}
|