【问题标题】:Qt QSignalMapper is emitting a signal for every item in the mapQt QSignalMapper 正在为地图中的每个项目发出信号
【发布时间】:2016-02-04 01:31:40
【问题描述】:

我有一个接收我创建的类的 QList 的函数。让我们称这个假设的类为“Stuff”。所以,这个函数接收一个 QList of Stuff

我遍历 QList,根据“Stuff”对象的属性,我将生成以下内容之一:

1) QLineEdit

2) QCheckBox

3) QComboBox

这不是实际的代码,但这是我本质上在做的事情:

void MyProgram::update(QList<Stuff> myStuffs)
{
  this->mSignalMapper = new QSignalMapper();

  foreach (Stuff stuff, myStuffs)
  {
    if (stuff.isInt())
    {
      QLineEdit* input = new QLineEdit();
      //There is code here to setup the QLineEdit and fill an initial value
      verticalLayout->addWidget(input); //verticalLayout is QVBoxLayout
      QObject::connect(input, SIGNAL(editingFinished()), this->mSignalMapper, SLOT(map()));
      this->mSignalMapper->setMapping(input, stuff.getMappingId());
      /*
       * NOTE: the stuff.getMappingId() function returns an int that is unique
       * to that stuff object.  I'm 100% sure each stuff object is getting
       * a unique mapping ID */
      QObject::connect(this->mSignalMapper, SIGNAL(mapped(int)), this, SLOT(onStuffChanged(int)));
    }
    else if (stuff.isBool())
    {
      QCheckBox* input = new QCheckBox();
      //There is code here to setup the QCheckBox and set an initial value
      verticalLayout->addWidget(input);
      QObject::connect(input, SIGNAL(stateChanged(int)), this->mSignalMapper, SLOT(map()));
      this->mSignalMapper->setMapping(input, stuff.getMappingId());
      QObject::connect(this->mSignalMapper, SIGNAL(mapped(int)), this, SLOT(onStuffChanged(int)));
    }
    else if (stuff.isStringList())
    {
      QComboBox* input = new QComboBox();
      //There is code here to setup the QComboBox and fill in values for the combo box
      verticalLayout->addWidget(input);
      QObject::connect(input, SIGNAL(activated(int)), this->mSignalMapper, SLOT(map()));
      this->mSignalMapper->setMapping(input, stuff.getMappingId());
      QObject::connect(this->mSignalMapper, SIGNAL(mapped(int)), this, SLOT(onStuffChanged(int)));
    }
  }
}

问题在于,如果我通过编辑 QLineEdit、选中复选框或更改组合框值仅触发 Widget 的一个信号,则 onStuffChanged(int) 函数将被调用 N 次,其中 N = mSignalMapper 的映射数。

这里发生了什么?如果我循环并创建 10 个小部件,则仅单击 10 个小部件中的 1 个会调用该函数 10 次,而这 10 次中的每一次都会传递与仅与我交互的 1 个对象相关联的唯一 int。因此,如果 10 个小部件中的第一个是唯一 int ID 为 27 的复选框,则 onStuffChanged(int) 函数将被调用 10 次,每次参数为 27。

【问题讨论】:

    标签: qt qcombobox qlineedit qcheckbox qsignalmapper


    【解决方案1】:

    问题出在这一行:

    QObject::connect(this->mSignalMapper, SIGNAL(mapped(int)), this, SLOT(onStuffChanged(int)));
    

    您正在建立相同的连接 N 次(N = 您的“东西”计数),因此每个 mapped() 信号都会触发 onStuffChanged(int) 插槽 N 次。

    解决方案: 将此行移到循环外,只调用一次。

    【讨论】:

    • 就是这样。其中一个“我怎么会错过这个明显的事情”的错误。我在这个问题上坐了一整天。有时你需要一双清新的眼睛。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-02-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多