【Qt开发】按钮类控件(二)-> QRadioButton

发布于:2025-09-03 ⋅ 阅读:(11) ⋅ 点赞:(0)

目录

1 -> 概念

1.1 -> 核心概念:互斥性选择

1.2 -> 视觉呈现与状态

1.3 -> 分组机制

2 -> 相关属性

3 -> 代码示例

3.1 -> 选择性别

3.2 -> click,press,release,toggled 的区别

3.3 -> 单选框分组

4 -> 总结


1 -> 概念

在构建图形用户界面(GUI)时,提供清晰、直观的选项选择机制是提升用户体验的关键。Qt 框架中的 QRadioButton(单选按钮)控件,正是为满足 “多选一” 的精确场景而设计的核心元素。它源于其物理世界原型——老式汽车收音机上的机械按钮,按下其中一个则会弹出之前被按下的那个,确保了任何时候都只有一个选项处于激活状态。

1.1 -> 核心概念:互斥性选择

QRadioButton 最根本、最重要的特性是 互斥性。这意味着在一组单选按钮中,用户只能且必须选择其中的一个选项。当一个选项被选中时,之前选中的选项会自动变为未选中状态。这种设计天然地适用于那些所有选项相互排斥、不可兼得的场景。

例如:

  • 性别选择:男 / 女 / 其他
  • 评分等级:优 / 良 / 差
  • 支付方式:信用卡 / 支付宝 / 微信支付
  • 分辨率设置:1920*1080 / 1280*720 / 800*600

这种 “非此即彼” 的交互模式,能够清晰地引导用户做出唯一选择,避免了歧义。

1.2 -> 视觉呈现与状态

一个典型的 QRadioButton 由两部分组成:

  1. 圆形指示器:一个空心的圆形,当被选中时,内部会填充一个实心圆点。

  2. 文本标签:紧邻指示器显示的描述性文字,用于明确告知用户该选项代表的意义。

它拥有两种主要状态:

  • 选中状态:圆形指示器内有一个实心点。这是该选项被激活的视觉反馈。

  • 未选中状态:圆形指示器为空心的。

此外,为了满足更复杂的需求,QRadioButton 还支持第三种状态:

  • 部分选中状态:在某些特殊情况下(例如通过 setAutoExclusive(false) 暂时关闭自动互斥),它可以被设置为一种 “未决” 或 “三态” 模式。但这是一种非典型用法,绝大多数情况下使用的是标准的选中 / 未选中两种状态。

1.3 -> 分组机制

单个 QRadioButton 本身并不具备互斥性。互斥的行为并非由按钮自身实现,而是由它们所处的 分组 所强制规定的。

Qt 提供了两种主要的分组方式:

  1. 父容器自动分组:这是最常见和简便的方法。将多个 QRadioButton 放置在同一个父控件内(例如同一个 QGroupBoxQWidget 或 QFrame),Qt 会自动识别它们属于同一逻辑组,并为其建立互斥关系。这种方式布局直观,管理方便。

  2. 使用 QButtonGroup 抽象分组:对于更复杂的界面,当单选按钮分散在不同的布局或容器中,但又属于同一个逻辑选择集时,QButtonGroup 类就变得至关重要。它是一个不可见的逻辑容器,可以将任何地方的 QRadioButton 添加进去,从而在逻辑上将它们编为一组,实现互斥选择,而不受其物理布局的限制。这提供了极大的灵活性。

2 -> 相关属性

QRadioButton 是单选按钮。可以让我们在多个选项中选择一个。

作为 QAbstractButton 和 QWidget 的子类,对于 QRadioButton 同样适用。

QAbstractButton 中和 QRadioButton 关系比较大的属性:

属性 说明
checkable 是否能选中
checked 是否已经被选中。checkable 是 checked 的前提条件
autoExclusive

是否排他

选中一个按钮之后是否会取消其他按钮的选中

对于 QRadioButton 来说默认就是排他的

3 -> 代码示例

3.1 -> 选择性别

1. 在界面上创建一个 label,和 3个 单选按钮

设置的文本如下。3个 单选按钮的 objectName 分别为 radioButton_male、radioButton_female 和 

radioButton_other

2. 修改 widget.cpp,编辑 3个 QRadioButton 的 slot 函数

void Widget::on_radioButton_male_clicked()
{
    // 把界面上的 label 的内容进行更新
    ui->label->setText("您选择的性别为: 男");
}

void Widget::on_radioButton_female_clicked()
{
    // 把界面上的 label 的内容进行更新
    ui->label->setText("您选择的性别为: 女");
}

void Widget::on_radioButton_other_clicked()
{
    // 把界面上的 label 的内容进行更新
    ui->label->setText("您选择的性别为: 其他");
}

3. 运行程序,可以看到随着选择不同的单选按钮,label 中的提示文字就会随之变化

4. 当前代码中,如果程序启动,则不会选择任何选项

可以修改代码,让程序启动默认选中性别男

#include "widget.h"
#include "ui_widget.h"

Widget::Widget(QWidget *parent)
    : QWidget(parent)
    , ui(new Ui::Widget)
{
    ui->setupUi(this);

    // 设置默认选项
    ui->radioButton_male->setChecked(true);
    ui->label->setText("您选择的性别为: 男");

}

Widget::~Widget()
{
    delete ui;
}


void Widget::on_radioButton_male_clicked()
{
    // 把界面上的 label 的内容进行更新
    ui->label->setText("您选择的性别为: 男");
}

void Widget::on_radioButton_female_clicked()
{
    // 把界面上的 label 的内容进行更新
    ui->label->setText("您选择的性别为: 女");
}

void Widget::on_radioButton_other_clicked()
{
    // 把界面上的 label 的内容进行更新
    ui->label->setText("您选择的性别为: 其他");
}

此时运行程序,即可以看到性别男已经被选中了。

5. 当前代码中,也可以禁用 “其他” 被选中

修改 widget.cpp 的构造函数

ui->radioButton_other->setCheckable(false);

运行程序,可以看到,点击 “其他” 按钮时,虽然不会被选中,但是可以触发点击事件,使上面的 label 显示性别为其他。

使用 setEnabled 是更加彻底的禁用按钮的方式。此时该按钮无法被选中,也无法响应任何输入。

ui->radioButton_other->setEnabled(false);

3.2 -> click,press,release,toggled 的区别

  • clicked 表示一次 “点击”
  • pressed 表示鼠标 “按下”
  • released 表示鼠标 “释放”
  • toggled 表示按钮状态切换

1. 在界面上创建四个单选按钮

objectName 分别为 radioButton、radioButton_2、radioButton_3 和 radioButton_4。

2. 依次给四个单选按钮创建 clicked槽函数、pressed槽函数、released槽函数 和 toggled槽函数

#include "widget.h"
#include "ui_widget.h"

#include <QDebug>

Widget::Widget(QWidget *parent)
    : QWidget(parent)
    , ui(new Ui::Widget)
{
    ui->setupUi(this);
}

Widget::~Widget()
{
    delete ui;
}


void Widget::on_radioButton_clicked(bool checked)
{
    // 此处从 checked 就表示了当前 radioButton 的选中状态.
    qDebug() << "cliched: " << checked;
}

void Widget::on_radioButton_2_pressed()
{
    qDebug() << "pressed";
}

void Widget::on_radioButton_3_released()
{
    qDebug() << "released";
}

void Widget::on_radioButton_4_toggled(bool checked)
{
    // checked 状态发生改变, 就会触发这个信号.
    qDebug() << "toggled: " << checked;
}

3. 运行程序,可以看到

  • clicked 是一次鼠标按下 + 鼠标释放触发的
  • pressed 是鼠标按下触发的
  • released 是鼠标释放触发的
  • toggled 是 checked 属性改变时触发的

总的来说,toggled 是最适合 QRadioButton 的。

3.3 -> 单选框分组

1. 在界面上创建 9个 单选框,用来模拟麦麦点餐界面

objectName 分别为 radioButton ~ radioButton_9

此时直接运行程序,可以看到,这 9个 QRadioButton 之间是排他的。

我们希望的是每一组的内部来控制排他,但是组和组之间不能排他。

2. 引入 QButtonGroup 进行分组

修改 widget.cpp

#include "widget.h"
#include "ui_widget.h"

#include <QButtonGroup>

Widget::Widget(QWidget *parent)
    : QWidget(parent)
    , ui(new Ui::Widget)
{
    ui->setupUi(this);

    QButtonGroup* group1 = new QButtonGroup(this);
    QButtonGroup* group2 = new QButtonGroup(this);
    QButtonGroup* group3 = new QButtonGroup(this);

    group1->addButton(ui->radioButton);
    group1->addButton(ui->radioButton_2);
    group1->addButton(ui->radioButton_3);

    group2->addButton(ui->radioButton_4);
    group2->addButton(ui->radioButton_5);
    group2->addButton(ui->radioButton_6);

    group3->addButton(ui->radioButton_7);
    group3->addButton(ui->radioButton_8);
    group3->addButton(ui->radioButton_9);

}

Widget::~Widget()
{
    delete ui;
}

再次执行程序,可以看到可以按照正确的分组方式来完成排他了。

4 -> 总结

QRadioButton 是 Qt 控件库中一个功能专一而强大的组件。它通过其固有的互斥性,完美解决了需要用户进行单一选择的交互需求。其有效性不仅依赖于控件本身,更在于通过父容器或 QButtonGroup 进行合理分组的机制。在与 QCheckBox 的对比中,其应用场景的区别变得尤为清晰。最终,遵循良好的UI/UX设计原则来使用它,是构建出清晰、高效、用户友好的桌面应用程序界面的重要一环。


感谢各位大佬支持!!!

互三啦!!!


网站公告

今日签到

点亮在社区的每一天
去签到