0

我正在使用qt的 FlowLayout 示例。

我为 FlowLayout 中的所有项目添加了一个上下文菜单,以启用重命名和删除。重命名有效,但每当我调用 Remove 时,我都会收到分段错误。

这是removeSlot电话:

  QAction *removeAction = new QAction(tr("Remove"), this);
  connect(removeAction, SIGNAL(triggered()), this, SLOT(removeSlot()));
  Menu->addAction(removeAction);

并发出信号:

void FlowLayoutWidget::removeSlot()
{
  emit removeMe(m_ownId);
}

FlowWindow.cpp 捕获信号并执行以下代码:

void FlowWindow::removeItemAt(int _index)
{

  while(QLayoutItem* item = flowLayout->itemAt(_index))
  {
      QWidget* widget = item->widget();
      flowLayout->removeWidget(widget);
      delete widget;
      break;

  }
}

每当调用此函数时,我都会收到分段错误。我该如何解决这个问题?

4

1 回答 1

1

您正在delete从该对象触发的插槽中调用一个对象。这有时可能是有问题的,其方式并不总是显而易见的。我怀疑在这种情况下它可能会导致您的问题。Qt 提供了一种方法QObject::deleteLater()来处理这个问题,方法是在控制返回事件循环后安排删除对象。

void FlowWindow::removeItemAt(int _index)
{

  while(QLayoutItem* item = flowLayout->itemAt(_index))
  {
      QWidget* widget = item->widget();
      flowLayout->removeWidget(widget);
      //delete widget; avoid this
      widget.deleteLater(); //try this instead
      break;

  }
}

有关更多信息,请参阅此问题/答案。

另外,我会注意到,由于您正在删除(或计划删除)对象,因此您不需要显式调用flowLayout->removeWidget(widget)- 当对象被销毁时会自动处理它。

于 2013-07-30T09:57:11.480 回答