C++ wxWidgets:关闭自定义模式对话框时出现内存错误

C++ wxWidgets:关闭自定义模式对话框时出现内存错误,c++,exception,memory,wxwidgets,C++,Exception,Memory,Wxwidgets,我已经读过了,但是我仍然不明白我在代码上犯了什么错误 下面是bmnewfromagedialog.h,该类扩展了wxDialog #ifndef BMNEWFROMIMAGEDIALOG_H #define BMNEWFROMIMAGEDIALOG_H #include "./../utils/includer.h" // includes a bunch of wx-related files class bmNewFromImageDialog : public wxDialog { pu

我已经读过了,但是我仍然不明白我在代码上犯了什么错误

下面是
bmnewfromagedialog.h
,该类扩展了
wxDialog

#ifndef BMNEWFROMIMAGEDIALOG_H
#define BMNEWFROMIMAGEDIALOG_H

#include "./../utils/includer.h" // includes a bunch of wx-related files
class bmNewFromImageDialog : public wxDialog {
public:
    wxBoxSizer *mainVBox, *flagHBox, *OKCancelHBox;
    wxStaticBox *flagsSBox;
    wxButton *OKButton, *cancelButton;
    wxRadioButton *GT0RadioButton;

    bmNewFromImageDialog() {}
    bmNewFromImageDialog(wxWindow *parent);

    void init();
};

#endif
这是
bmnewfromagedialog.cpp

#include "./bmNewFromImageDialog.h"
#include "./../utils/includer.h"

bmNewFromImageDialog::bmNewFromImageDialog(wxWindow *parent) : wxDialog(parent, -1, wxT("new image..."), wxDefaultPosition, wxDefaultSize) {
    init();
}

void bmNewFromImageDialog::init() {
    mainVBox = new wxBoxSizer(wxVERTICAL);
    flagHBox = new wxBoxSizer(wxHORIZONTAL);
    OKCancelHBox = new wxBoxSizer(wxHORIZONTAL);

    flagsSBox = new wxStaticBox(this, -1, wxT("Color flags"), wxPoint(0, 0), wxDefaultSize);
    GT0RadioButton = new wxRadioButton(this, -1, wxT(">0: 3 channels"), wxPoint(0, 0));
    flagsSBox->AddChild(GT0RadioButton);
    flagHBox->Add(flagsSBox, 0, wxALIGN_CENTER | wxTOP | wxBOTTOM, 10);

    OKButton = new wxButton(this, wxID_OK, wxT("OK"), wxDefaultPosition, wxSize(100, 40));
    cancelButton = new wxButton(this, wxID_CANCEL, wxT("cancel"), wxDefaultPosition, wxSize(100, 40));
    OKCancelHBox->Add(OKButton, 1);
    OKCancelHBox->Add(cancelButton, 1, wxLEFT, 5);

    mainVBox->Add(flagHBox, 0, wxALIGN_CENTER | wxTOP | wxBOTTOM, 10);
    mainVBox->Add(OKCancelHBox, 0, wxALIGN_CENTER | wxBOTTOM, 10);
    SetSizer(mainVBox);
    Center();
}
下面是我在代码中使用对话框的方式:

bmNewFromImageDialog *newDialog = new bmNewFromImageDialog(this);
newDialog->ShowModal();
delete newDialog;
当我在
bmnewfrommagedialog
上关闭/单击OK/单击Cancel时,我经常在运行时收到一个未处理的内存异常错误。我该如何解决这个问题

编辑

@digby chicken caesar爵士我尝试了
.Destroy()
和堆栈解决方案,但仍然存在相同的错误:

此块:

bmNewFromImageDialog *newDialog = new bmNewFromImageDialog(this);
newDialog->ShowModal();
delete newDialog;
应改为:

bmNewFromImageDialog *newDialog = new bmNewFromImageDialog(nullptr);
newDialog->ShowModal();
newDialog->Destroy();
切勿在wx小部件类上调用
delete
。如果需要取消分配小部件,请将其从父层次结构中删除,将其与使用它的任何大小调整器分离,然后调用
Destroy()

编辑:

正如用户VZ和所指出的,模态对话框是少数不需要在堆上创建的wx小部件类之一。因此,只要在堆栈上创建对话框,并让析构函数在对象超出范围时为您处理清理:

bmNewFromImageDialog newDialog = bmNewFromImageDialog(nullptr);
newDialog.ShowModal();
该调用没有文档记录,并且在头文件中标记为“主要实现”。除非你真的知道自己在做什么,否则不要使用它

如果您仅创建
GT0RadioButton
,并将
flagsSBox
作为其父项(删除
AddChild
调用),则代码应该可以工作


查看一下
wxStaticBoxSizer

正确,但是在堆栈上而不是堆上创建对话框会更简单、更好。正确。我总是忘记模态对话框是少数不需要在堆上创建的wxWidgets窗口之一。谢谢!这只不过是注释了那句话就行了。
flagsSBox = new wxStaticBox(this, -1, wxT("Color flags"), wxPoint(0, 0), wxDefaultSize);
GT0RadioButton = new wxRadioButton(this, -1, wxT(">0: 3 channels"), wxPoint(0, 0));
flagsSBox->AddChild(GT0RadioButton);
//         ^^^^^^^^ this looks very wrong