【问题标题】:Open a new Qt window with a slot打开一个带有插槽的新 Qt 窗口
【发布时间】:2017-01-21 02:51:39
【问题描述】:

在我的 Qt 程序中,有一个菜单栏,其中一个菜单选项是设置。当用户点击设置窗口时,它应该打开一个设置窗口。设置窗口使用openSettingsWindow() 函数打开。这就是我在主窗口中制作“设置”菜单的方式:

QMenu settingsMenu("&Settings");
QAction *settings = toolsMenu.addAction("&Settings");
Window::connect(settings,&QAction::triggered,&mainWindow,[&mainWindow](){
    openSettingsWindow();
});
menuBar.addMenu(&toolsMenu);

mainWindow 是主窗口,Window 是用于创建窗口的类,它继承自 QWidget。它的构造函数有两个参数:窗口的标题和窗口的图标。这是openSettingsWindow() 函数:

void openSettingsWindow(){
    Window settingsWindow("Settings","icon.png");
    settingsWindow.show();
}

问题是,当我单击“设置”菜单中的“设置”选项时,“设置”窗口会按原样打开,但不到一秒钟后它会直接关闭。我应该怎么做才能使“设置”窗口保持打开状态?

【问题讨论】:

  • 但不到一秒后它直接关闭。openSettingsWindow() 结束时,窗口超出范围。

标签: c++ qt


【解决方案1】:

当您的函数openSettingsWindow 超出范围时,局部变量settingsWindow 会被破坏,只要您想显示您的settingsWindow,就需要保持该对象有效。

一种解决方案是在堆上分配Window 对象,并使用Qt::WA_DeleteOnClose 使Qt 在关闭时为您删除Window 对象,这是您的openSettingsWindow 的样子:

void openSettingsWindow(){
    Window* settingsWindow = new Window("Settings","icon.png");
    settingsWindow->setAttribute(Qt::WA_DeleteOnClose);
    settingsWindow->show();
}

【讨论】:

    【解决方案2】:

    您需要返回对该Window 的引用并保留它,直到您不再使用它为止。

    Window *openSettingsWindow() {
        Window *settingsWindow = new Window("Settings, "icon.png");
        settingsWindow.show();
        return settingsWindow;
    }
    
    QMenu settingsMenu("&Settings");
    QAction *settings = toolsMenu.addAction("&Settings");
    Window *settingsWindow = null;
    Window::connect(settings,&QAction::triggered,&mainWindow,[&mainWindow, &settingsWindow](){
        settingsWindow = openSettingsWindow();
    });
    menuBar.addMenu(&toolsMenu);
    

    如果您要打开许多可能的窗口,您可能希望找到一种更好的方法将 settingsWindow 指针存储在主函数中,但这会奏效。

    当您完成设置窗口(可能在窗口关闭事件中)时,记得在该指针上调用delete()

    【讨论】:

    • 编辑后,您正在泄漏Window 对象,settingsWindow 永远不会被破坏。
    • OP 可以随意处理返回的 Window 指针,并将其存储在适当的时候可以释放它的地方。我没有足够的代码来判断何时是这样做的好时机。
    • 我试过了,得到了错误error: C3493: 'settingsWindow' cannot be implicitly captured because no default capture mode has been specified
    • 我的错,忘记在那个 lambda 中捕获 settingsWindow,现在应该可以工作了
    • 你可以使用Qt::WA_DeleteOnClose让Qt在Window对象关闭时自动为你删除它,不需要从openSettingsWindow返回指针。
    猜你喜欢
    • 1970-01-01
    • 2013-08-02
    • 2011-04-17
    • 1970-01-01
    • 2016-09-03
    • 2011-05-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多