重置QMenu以接受新的QActions集

时间:2018-02-20 14:12:09

标签: c++ qt qmenu

我希望重置/重新创建自定义上下文菜单。我正在使用QMenu和QAction(成员变量)来实现这一目标。

@@ -84,11 +84,11 @@
               end if
               TotalParticleMass = &
                 TotalParticleMass + &
-                Particles(I)%Mass
+                MassArray(I)
               if (IsVirtualParticle(I)) then
                 TotalVirtualParticleMass =  &
                   TotalVirtualParticleMass + &
-                  Particles(I)%Mass
+                  MassArray(I)
               end if
             end do
             write(TVMunit, '(I12, G12.4, G12.4, I12, I12, I12)')  &

我的插槽连接如下:

 QMenu* m_menu;
 QAction* m_actionTitle;

工作部分:

在我的构造函数中,我设置了类似的东西:

connect(m_ui->actionLoad_Definition_File, &QAction::triggered, m_Item.get(),
        &Item::loadDefinitionFilesFromMenu);

我想要的是什么:

我想重置其所有操作的 Item::Item(QWidget* parent) { // Connect context menu this->setContextMenuPolicy(Qt::CustomContextMenu); connect(this, SIGNAL(customContextMenuRequested(const QPoint&)), this, SLOT(showContextMenu(const QPoint&))); } /* virtual */ void Item::showContextMenu(const QPoint& pos) { // Obtain global position QPoint globalPos = mapToGlobal(pos); // Change the first menu entry to show the range m_actionTitle->setText(QString::number(m_from) + " - " + QString::number(m_to)); //Access Violation error QAction* action = m_menu->exec(globalPos); if (action != NULL) { if (action->text() == "something") { // Remove the item m_view->removeItem(this); } else { // Display the text setText(action->text()); setColor(action->text()); setToolTip(action->text()); m_edit.setText(action->text()); m_view->arrange(); } } } 并将新动作推入其中。因此,每当我右键单击时,都会显示新的上下文菜单。

问题:

创建QToolButton后,如果我右键单击它,我会得到"访问违规错误"。调试它,m_menu和m_actionTitle都超出了范围或被简单地销毁。不知道为什么会这样。

到目前为止我做了什么:

m_menu

我想在整个程序中重用void Item::loadDefinitionFilesFromMenu() { //Clear the vector of existing values m_defaults.clear(); //Clear the menu of actions m_menu->clear(); QString file = QFileDialog::getOpenFileName(nullptr, "Choose a definition file", QString(), QString("(*.ad)")); if (!file.isNull()) { MLParser ml; std::map<std::string, std::string> base = ml.readDefinitions(file.toStdString()); for (auto const& gestureValues : base) { m_defaults.push_back(gestureValues.first); // string (key) } m_menu = new QMenu(this); m_actionTitle = new QAction("Note", m_menu); m_actionTitle->setEnabled(false); m_menu->addAction(m_actionTitle); m_menu->addSeparator(); for (std::vector<std::string>::iterator it = m_defaults.begin(); it != m_defaults.end(); ++it) { m_menu->addAction(QString::fromStdString(*it)); //works ok } m_menu->addSeparator(); } } ,但我无法让它重置并接受新的操作集。我在这里错过了什么吗?

编辑1:

在构造函数中删除了m_menuQMenu。仅在QAction

1 个答案:

答案 0 :(得分:0)

在所有Item个实例之间共享菜单。

在Item类标题中:

private:
    static QMenu* m_menu;
    static QAction * m_actionTitle;
    static std::vector<std::string> m_defaults;

在Item类cpp中,在定义之后和方法定义之前:

QMenu* Item::m_menu = 0;
QAction * Item::m_actionTitle = 0;
std::vector<std::string> Item::m_defaults;

菜单仅在Item构造函数中实例化一次:

if(m_menu == 0)
{
    m_menu = new QMenu();
    // load defaults here
}

无需再次实例化菜单:从loadDefinitionFilesFromMenu

中删除此行
m_menu = new QMenu(this);

关于您的m_actionTitle指针:不要为其指定新的QAction,让其保留addAction方法的返回值:

    m_actionTitle = m_menu->addAction("Note");
    m_actionTitle->setEnabled(false);
    m_menu->addSeparator();

最后,有一个静态方法来删除(唯一的)菜单实例。在头文件中:

static void dismissMenu();

在cpp:

void Item::dismissMenu()
{
  delete m_menu;
}

您可以在QApplication::exec返回后退出前调用此方法:

Item::dismissMenu();