在 wxWidgets 的事件中包含我自己的数据的最佳方法是什么?

What is the best way to include my own data in an event in wxWidgets?

我正在尝试实现类文件结构。文件和文件夹名称显示在列表框中。

我想向 ListBox 条目添加额外的数据 - 现在它只有它的字符串,我希望它有一个 bool 来区分文件夹和文件,所以当我双击和 OnDoubleClick(wxCommandEvent&) 方法时,我已绑定到此事件调用我可以访问其他数据。

我知道我可以创建自定义事件或对现有事件进行子类化,但如何自定义 ListBox 以保存更多数据?

wxListBox 派生自wxItemContainer,这意味着它允许每个项目保存一个额外的数据。例如,您可以这样定义客户端数据 class:

class MyClientData:public wxClientData
{
public:
    enum ItemType
    {
        ItemTypeInvalid,
        File,
        Folder
    };

    MyClientData(ItemType it):m_itemType(it){}
    ItemType GetItemType() const{return m_itemType;}

private:
    ItemType m_itemType;
};

然后,当您将客户端数据附加到控件时,您可以将它们附加到列表框项目,如下所示:

listbox->Append("Folder 1", new MyClientData(MyClientData::Folder));
listbox->Append("Folder 2", new MyClientData(MyClientData::Folder));
listbox->Append("File 1", new MyClientData(MyClientData::File));
listbox->Append("File 2", new MyClientData(MyClientData::File));
listbox->Append("File 3", new MyClientData(MyClientData::File));
listbox->Append("File 4", new MyClientData(MyClientData::File));
listbox->Append("No Client Data 1");

由于 MyClientData 派生自 wxClientData,列表框将取得客户端数据对象的所有权,并在其析构函数中或在从控件中删除项目时将其删除。

您可以在 OnDoubleClick 方法中恢复客户端数据(假设该方法正在为您的列表框处理 wxEVT_LISTBOX_DCLICK 事件),如下所示:

void xxx::OnDoubleClick(wxCommandEvent& event)
{
    int itemNo = event.GetSelection();
    wxListBox* listBox = wxDynamicCast(event.GetEventObject(), wxListBox);
    MyClientData* clientData = NULL;

    if ( listBox != NULL && itemNo != wxNOT_FOUND )
    {
        clientData=static_cast<MyClientData*>(listBox->GetClientObject(itemNo));
    }

    ... do something with clientData here ...
}

最后,正如 Igor 所说,我不确定 wxListBox 是否是此处使用的最佳控件。 wxListCtrl or wxDataViewListCtrl 可能会更好看。这些控件有点复杂,并且不是从 wxItemContainer 派生的。但是,您仍然可以附加额外的数据,例如 wxListCtrl::SetItemPtrData,但是您必须自己清理任何动态创建的对象。