繁体   English   中英

C ++ Qt:是否可以创建一种模板插槽?

[英]C++ Qt: is it possible to create a sort of template slot?

我是Qt的新手而不是C ++专家所以请耐心等待。 我正在开发一个具有12种不同QPushButtons的应用程序,但它们都执行非常类似的操作:它们从地图中获取一些值,然后使用它来设置该按钮的样式:

void MainWindow::on_btn01_clicked(){
    QString img=images["btn01"];
    ui->btn01->setStyleSheet("#btn01{ background-image: url(://" + img + ") }");
}

对于12个按钮中的每一个,我必须创建一个仅在使用的按钮上有所不同的插槽。 因此,创建几乎完全相同的12个函数看起来有点奇怪。

有一个更好的方法吗?

一般来说,我见过几种方法:

  1. 首选方法:lambda表达式。

    如果您使用的是现代C ++(C ++ 11或更高版本),则可以使用lambda函数来获得所描述的精确效果。

    我希望结果代码看起来像这样:

     foreach( QPushButton * button : buttons ) { connect( button, &QPushButton::clicked, [button, &images]() { button->setStyleSheet( QString( "{ background-image: url(://%1) }" ) .arg( images[button->objectName()] ) ); }); } 

    有关如何使用Qt编写lambda函数的更多指导,请参阅“ Qt Slots和C ++ 11 lambda ”。

  2. 更脏的方式:QObject :: sender()。

    Qt允许您在插槽中使用QObject :: sender()来获取指向调用它的对象的指针。 这已经是一种广泛使用的方法多年,但有一些限制,如Qt文档中所述:

    警告:如上所述,当通过Qt :: DirectConnection从与该对象的线程不同的线程调用插槽时,此函数的返回值无效。 请勿在此类场景中使用此功能。

    有关详细信息,请参阅“ 如何使用信号/插槽机制获取发件人窗口小部件? ”。

  3. 过时的代码:QSignalMapper。

    有一个QSignalMapper类,它允许您将信号与一些数据(如字符串)相关联,然后连接到使用此参数的插槽。 这曾经作为Qt中的一个便利类存在,但正逐步淘汰,因为lambda方法使它毫无意义。

    如果您需要更新使用QSignalMapper删除它的代码, 本教程是一个合理的起点。

您可以尝试一种更简单的方法,即分别设置QPushButton的对象名称,并检查插槽中的对象名称并使用该字符串。 这为您节省了大量代码。

例如:
QPushButton 1对象名设置为button->setObjectName("btn01"); 并且你可以分别设置按钮的其他名称,在你的插槽中你可以做这样的事情

void MainWindow::on_button_clicked(){
     QPushButton* btn=qobject_cast<QPushButton*>(sender()); 
     QString name=btn->objectName(); 
     QString img=images[name]; btn->setStyleSheet("#" + name + "{ background-image: url(://" + img + ");
}

然后将所有QPushButtons连接到此插槽

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM