C++/Qt 方向实训 · 第 3 / 4 个讲授日
今天的主线:把昨天的计算器升级成"正经软件"——主窗口骨架 + 对话框交互 + 布局讲透 + 美化。
上午 · 讲授 08:30–11:00
setCentralWidget()
显式安放;菜单项和工具栏按钮的统一抽象是 QAction(一个动作,
多处复用)。QAction 显示出来 ≠ 生效:忘了 connect 到槽,
就是"菜单点了没反应"。exec():阻塞等用户给结果,返回值就是用户的选择
(Accepted/Rejected);非模态 show():立即返回,窗口独立存活
——所以对话框对象必须活过当前函数作用域(堆 + parent,或
WA_DeleteOnClose 自清理)。QMessageBox(提示/确认)、QFileDialog(选文件)。show() 完函数一返回就析构——窗口一闪而过。
p03/ch06 的三个 modeless 版本(栈/堆/DeleteOnClose)就是这个坑的对照教材。出处:p03/ch06/modal_dialog.cpp · modeless_dialog_stack.cpp · modeless_dialog_heap.cpp · modeless_dialog_deleteonclose.cpp
auto ret = QMessageBox::question(this, "确认", "真的要删除吗?");
if (ret == QMessageBox::Yes) { /* ... */ }
QString path = QFileDialog::getOpenFileName(this, "选择文件", "", "*.json");
if (!path.isEmpty()) { /* ... */ } // 用户可能点取消:必须处理空返回
出处:p03/ch06/message_box_question.cpp · message_box_custom.cpp · file_dialog.cpp
上午 · 课堂练习 11:00–12:00(工程师指导、答疑)
QMessageBox;加一个「历史」停靠窗(可先放空 QLabel)下午 · 讲授 13:30–16:00
QGridLayout 今天讲透:QHBox/QVBox/QGrid 三兄弟 + 嵌套组合 + 伸缩因子
addStretch();布局对象同样遵循 QObject 父子所有权。setGeometry()/move() 手动改位置——
会被下次布局刷新覆盖,看起来"设置没生效"。QPixmap)/
动图(QMovie);输入靠 QLineEdit,按钮族 QPushButton/QRadioButton/QCheckBox。:/... 路径是 Qt 资源系统:资源编译期打包进可执行文件,运行时不依赖
外部文件——发布不用带一堆散图。.qrc 里的路径与代码引用不一致:运行时静默失败(图不显示),
不报编译错误;忘接 CMake 的 AUTORCC/qt5_add_resources 资源系统不生效。出处:p03/ch08/label_text_html.cpp · label_pixmap.cpp · label_movie.cpp
QPushButton#okButton { background-color: #2f855a; border-radius: 6px; }
QPushButton#okButton:hover { background-color: #276749; }
#objectName)/ 伪状态
(:hover :pressed)+ 层叠继承——作用对象是 QWidget 树而非 DOM;
"长什么样"与"做什么"分离,改样式不碰逻辑。setObjectName();setStyleSheet() 会级联影响所有子控件——范围失控是最容易踩的坑,
样式尽量写窄(带选择器),不要裸写属性。下午 · 课堂作业 16:00–17:00(工程师答疑)
background-color;至少 1 个按钮有
:hover 或 :pressed 效果;拉伸窗口按钮跟着重排现场演示升级后的计算器:主窗口(菜单/停靠窗)+ QSS 配色 + 缩放自适应,功能不回退。
钩子 · QSS 与前端 CSS 是同源思想;Qt Designer/QML 是另一条 UI
路线(拖拽/声明式),本课程走纯代码路线,知道它们存在即可。
明天 Day4:事件机制 / 绘图 / 表格 + 文件系统——数据要开始落盘了。