1、前言
在Qt中,导航按钮通常用于界面切换或功能引导,可以通过多种方式实现。以下是常见的实现方案:
使用QPushButton和信号槽机制
导航按钮的视觉样式可以通过QSS进行自定义
cpp
QPushButton *navButton = new QPushButton("导航");
connect(navButton, &QPushButton::clicked, this, &MainWindow::navigateToPage);
使用QToolButton实现图标导航
导航按钮的视觉样式可以通过QSS进行自定义
cpp
QPushButton {
background-color: #3498db;
color: white;
border-radius: 5px;
padding: 8px 16px;
}
QPushButton:hover {
background-color: #2980b9;
}
导航按钮组实现
对于需要多个导航按钮的情况,可以使用QButtonGroup:
cpp
QButtonGroup *navGroup = new QButtonGroup(this);
navGroup->addButton(homeButton, 0);
navGroup->addButton(settingsButton, 1);
connect(navGroup, QOverload<QAbstractButton *>::of(&QButtonGroup::buttonClicked),
[](QAbstractButton *button) {
// 处理导航逻辑
});
2、马上干
1、创建自定义控件
在Qt中,创建自定义控件是一个非常灵活和强大的方式,可以让你根据具体需求扩展现有的控件或完全从头开始设计控件,自定义控件继承自QWidget或现有控件类(如QPushButton、QLabel等),重写关键方法实现自定义功能。通过重写paintEvent实现视觉效果定制,使用Q_PROPERTY宏定义可在Qt Designer中编辑的属性,为控件添加自定义信号,通过QSS定制外观,需确保控件正确处理样式。
自定义控件的步骤
-
继承
QWidget或其他控件类 : 创建一个新的类,继承自QWidget或其他你希望扩展的控件类。 -
重写绘制事件 : 在自定义控件类中,重写
paintEvent方法来定义控件的绘制逻辑。使用QPainter类来进行绘制操作。 -
处理其他事件 : 根据需要重写其他事件处理函数,如
mousePressEvent、keyPressEvent等,以实现控件的交互逻辑。 -
添加属性和槽函数 : 使用 Qt 的属性系统(通过
Q_PROPERTY宏)为控件添加自定义属性,并通过槽函数来响应外部信号或内部状态变化。 -
注册控件 (可选): 如果你希望将自定义控件集成到 Qt Designer 中,可以通过
Q_PLUGIN_METADATA宏和QDesignerCustomWidgetInterface类来注册控件。


2、添加有关的属性,变量,槽函数,事件

cpp
#ifndef NAVBUTTON_H
#define NAVBUTTON_H
#include <QPaintEvent>
#include <QWidget>
class NavButton : public QWidget
{
Q_OBJECT
Q_PROPERTY(int icon READ icon WRITE setIcon);
Q_PROPERTY(QString text READ text WRITE setText);
Q_PROPERTY(bool isChecked READ isChecked WRITE setIsChecked);
public:
explicit NavButton(QWidget *parent = nullptr);
int icon() const{
return m_icon;
}
QString text() const
{
return m_text;
}
bool isChecked() const
{
return m_isChecked;
}
public slots:
void setIcon(int icon)
{
if(m_icon==icon) return;
m_icon = icon;
// 涉及到控件的重绘
update();
}
void setText(QString text)
{
m_text = text;
}
void setIsChecked(bool isChecked)
{
m_isChecked = isChecked;
}
private:
bool isMouseOver=false;
int m_icon;
QString m_text;
bool m_isChecked;
protected:
void paintEvent(QPaintEvent *event) override;//窗体重绘事件
signals:
};
#endif // NAVBUTTON_H
3、绘制有关图形
paintEvent 基本概念
在 Qt 中,paintEvent 是 QWidget 及其子类的一个关键虚函数,用于处理控件的绘制逻辑。当控件需要重绘时(如窗口首次显示、尺寸变化、调用 update() 或 repaint()),系统会自动调用此函数。
重写 paintEvent 方法
自定义绘制需要重写 paintEvent,并通过 QPainter 进行绘图操作。以下是一个基本示例:
cpp
void MyWidget::paintEvent(QPaintEvent *event) {
QPainter painter(this); // 创建 QPainter 对象,绑定当前控件
painter.setPen(Qt::red); // 设置画笔颜色
painter.drawLine(0, 0, width(), height()); // 绘制对角线
painter.drawText(rect(), Qt::AlignCenter, "Hello Qt!"); // 绘制文本
}
关键注意事项
- 避免直接调用
paintEvent:应通过update()(异步,合并多次调用)或repaint()(同步,立即重绘)触发重绘。 - 性能优化 :通过
event->rect()获取需要重绘的区域,仅绘制该区域以减少计算量。 - 双缓冲技术 :复杂绘图可使用
QPixmap作为缓冲,避免闪烁:

常用绘图操作
- 几何图形 :
drawLine、drawRect、drawEllipse、drawPolygon。 - 文本 :
drawText,配合QFont设置字体。 - 图像 :
drawPixmap或drawImage显示图片。 - 路径 :
QPainterPath绘制复杂路径。
QPainter 基本概念
QPainter 是 Qt 框架中用于二维图形绘制的核心类,支持在多种绘图设备(如 QWidget、QPixmap、QImage)上绘制形状、文本和图像。其功能涵盖路径绘制、坐标变换、混合模式等高级特性。
初始化与基本用法
创建 QPainter 对象需绑定绘图设备。例如,在 QWidget 的 paintEvent 方法中使用:
cpp
void MyWidget::paintEvent(QPaintEvent *event) {
QPainter painter(this);
painter.setPen(Qt::blue);
painter.drawLine(0, 0, width(), height());
}
常用绘制操作
绘制形状
绘制文本
绘制图像
坐标变换与状态管理
路径绘制(QPainterPath),复杂路径可通过 QPainterPath 定义后绘制
常见问题
绘图不显示
检查是否在 paintEvent 外创建 QPainter,或未调用 end() 方法。
坐标系统问题
默认坐标系原点在左上角,Y轴向下为正方向。可通过 setViewport 和 setWindow 调整映射范围。
资源释放
QPainter 通常无需手动释放,但绑定 QPixmap 等设备时需确保设备生命周期覆盖绘图过程。
通过结合上述方法,QPainter 可实现从简单图形到复杂界面的高效绘制。
完整代码
cpp
#include "navbutton.h"
#include <QPaintEvent>
#include <QPainter>
NavButton::NavButton(QWidget *parent): QWidget{parent}
{
}
//窗体重绘事件
void NavButton::paintEvent(QPaintEvent *event)
{
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
//1、绘制按钮的背景
if(m_isChecked){//如果选中,则设置线性渐变
//创建渐变对象
QLinearGradient gradient(0,0,this->rect().width(),this->rect().height());//从哪开始进行渐变,0,0是起点,终点是矩形的宽度和高度
gradient.setColorAt(0,QColor(62,155,253));//起点颜色
gradient.setColorAt(1,QColor(33,97,216));//终点颜色
painter.setBrush(gradient); //设置笔刷
}
else{
}
painter.drawRoundedRect(this->rect(),10,10);//绘制带有圆角的矩形,10是圆角半径
//2、绘制图标
painter.setPen(QColor(255,255,255));//设置笔的颜色
QFont iconFont=QFont("zx_icons",22);//创建字体对象
painter.setFont(iconFont);//设置字体
//参数1表示位置 ,参数2表示对齐方式,参数3表示文字内容
painter.drawText(QRect(0,10,this->rect().width(),this->rect().height()),
Qt::AlignHCenter,
QChar(this->icon()));
//3、绘制标题
QFont font=QFont("Microsoft YaHei",9);
painter.setFont(font);
painter.drawText(QRect(0,10,this->rect().width(),this->rect().height()-22),
Qt::AlignHCenter|Qt::AlignBottom,
this->text());
//4、绘制线边框
if(m_isChecked){
QPen pen(QColor(255,150,0),3);
painter.setPen(pen);
painter.drawLine(2,10,2,this->rect().height()-10);
}
}
4、转到界面,提升控件
Qt中的提升概念
在Qt框架中,"提升"(Promotion)通常指将某个基础控件转换为自定义控件的过程。这一功能主要用于Qt Designer中,允许开发者将界面中的标准Qt控件替换为自行编写的派生类控件。
提升的主要用途
通过控件提升可以实现界面设计与代码逻辑的分离。标准控件如QWidget、QPushButton等可以在设计时布局,运行时替换为功能更丰富的自定义控件。
提升操作保留了原始控件的所有属性,同时添加了派生类的新功能。这种方式避免了手动修改UI文件,使得可视化设计与代码扩展能够协同工作。
实现提升的步骤
在Qt Designer中选择需要提升的控件,右键点击选择"Promote to..."。在弹出的对话框中填写提升后的类名和头文件路径。确认后该控件即被标记为自定义类型,实际运行时会实例化指定的派生类。
提升后的类必须满足:是原控件类的直接或间接子类;具有相同的构造函数签名;头文件路径在项目编译时可达。
提升与继承的区别
提升是Qt特有的设计时概念,而继承是面向对象的通用特性。提升侧重于可视化设计工具中的控件替换,继承关注代码层面的类关系。通过提升可以快速将设计器中的标准控件转换为自定义类实例。
实际应用示例
例如将QWidget提升为自定义的ChartWidget类:
- 在Qt Designer中放置QWidget
- 设置提升信息:基类QWidget,提升类名ChartWidget
- 指定头文件"chartwidget.h"
- 生成的UI文件将自动包含提升信息
- 运行时该部件会实例化为ChartWidget对象
这种方法常用于创建复合控件、定制绘制控件或添加特殊行为的界面元素,同时保持设计器的可视化编辑能力。


5、设置新添加的属性



6、运行测试


3、小结
Qt框架提供了多种方式来实现自定义导航功能,可以通过QML或C++结合Qt Widgets来完成。使用Qt Widgets实现自定义导航,对于传统的桌面应用,可以使用QWidget和QHBoxLayout来创建自定义导航栏。为了提升用户体验,可以为导航添加平滑的过渡动画。对于不同屏幕尺寸,可以调整导航栏的布局,这些方法提供了在Qt应用中实现自定义导航的基础,可以根据具体需求进行扩展和组合。
原创不易,打字不易,截图不易,撸码不易,整理不易,走过路过,不要错过,欢迎点赞,收藏,转载,复制,抄袭,留言,灌水,请动动你的金手指,祝您早日实现财务自由。
