wxWidgets/samples/xti/classlist.cpp
Dimitri Schoolwerth 3fdcd5d5ab Changed licence references to "wxWindows licence".
Use "wxWindows licence" and not "wxWidgets licence" and also use British spelling for licence. Updated new occurrences in recently added files and a couple of previously (r64940) missed ones.

See #12165.

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@67387 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
2011-04-04 09:21:52 +00:00

561 lines
18 KiB
C++

/////////////////////////////////////////////////////////////////////////////
// Name: classlist.cpp
// Purpose: ClassListDialog implementation
// Author: Francesco Montorsi
// Modified by:
// Created: 03/06/2007 14:49:55
// RCS-ID: $Id$
// Copyright: (c) 2007 Francesco Montorsi
// Licence: wxWindows licence
/////////////////////////////////////////////////////////////////////////////
// ----------------------------------------------------------------------------
// headers
// ----------------------------------------------------------------------------
// For compilers that support precompilation, includes "wx/wx.h".
#include "wx/wxprec.h"
#ifdef __BORLANDC__
#pragma hdrstop
#endif
#ifndef WX_PRECOMP
#include "wx/wx.h"
#endif
#include "classlist.h"
#if !wxUSE_EXTENDED_RTTI
#error This sample requires XTI (eXtended RTTI) enabled
#endif
// IMPLEMENT_DYNAMIC_CLASS( ClassListDialog, wxDialog ) -- see the header
BEGIN_EVENT_TABLE( ClassListDialog, wxDialog )
EVT_LISTBOX( ID_LISTBOX, ClassListDialog::OnListboxSelected )
EVT_TREE_SEL_CHANGED( ID_TREECTRL, ClassListDialog::OnTreectrlSelChanged )
EVT_CHOICEBOOK_PAGE_CHANGED( ID_LISTMODE, ClassListDialog::OnChoiceBookPageChange )
EVT_CHECKBOX( ID_SHOW_ONLY_XTI, ClassListDialog::OnShowOnlyXTICheckbox )
EVT_CHECKBOX( ID_SHOW_PROPERTIES_RECURSIVELY, ClassListDialog::OnShowRecursiveInfoCheckbox )
END_EVENT_TABLE()
// defined later
wxString DumpClassInfo(const wxClassInfo*, bool recursive);
// ----------------------------------------------------------------------------
// ClassListDialog
// ----------------------------------------------------------------------------
ClassListDialog::ClassListDialog()
{
Init();
}
ClassListDialog::ClassListDialog( wxWindow* parent, wxWindowID id,
const wxString& caption, const wxPoint& pos,
const wxSize& size, long style )
{
Init();
Create(parent, id, caption, pos, size, style);
}
bool ClassListDialog::Create( wxWindow* parent, wxWindowID id, const wxString& caption,
const wxPoint& pos, const wxSize& size, long style )
{
SetExtraStyle(wxWS_EX_BLOCK_EVENTS);
wxDialog::Create( parent, id, caption, pos, size, style );
CreateControls();
if (GetSizer())
{
GetSizer()->SetSizeHints(this);
}
Centre();
return true;
}
ClassListDialog::~ClassListDialog()
{
}
void ClassListDialog::Init()
{
m_pClassCountText = NULL;
m_pRawListBox = NULL;
m_pParentTreeCtrl = NULL;
m_pSizeListBox = NULL;
m_pTextCtrl = NULL;
}
void ClassListDialog::CreateControls()
{
wxBoxSizer* itemBoxSizer2 = new wxBoxSizer(wxVERTICAL);
this->SetSizer(itemBoxSizer2);
wxStaticText* itemStaticText3 = new wxStaticText( this, wxID_STATIC, _("This is the list of wxWidgets classes registered in the XTI system.\nNote that not all wxWidgets classes are registered nor all registered classes are completely _described_ using XTI metadata."), wxDefaultPosition, wxDefaultSize, 0 );
itemBoxSizer2->Add(itemStaticText3, 0, wxALIGN_LEFT|wxALL, 5);
// filters
wxBoxSizer* filters = new wxBoxSizer(wxHORIZONTAL);
itemBoxSizer2->Add(filters, 0, wxGROW|wxLEFT|wxRIGHT|wxBOTTOM, 5);
filters->Add(new wxCheckBox(this, ID_SHOW_ONLY_XTI,
wxT("Show only classes with eXtended infos")));
filters->AddSpacer(10);
filters->Add(new wxCheckBox(this, ID_SHOW_PROPERTIES_RECURSIVELY,
wxT("Show properties of parent classes")));
// show how many have we filtered out
m_pClassCountText = new wxStaticText( this, wxID_STATIC,
wxT("xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"),
wxDefaultPosition, wxDefaultSize, 0 );
m_pClassCountText->SetFont(wxFont(8, wxSWISS, wxNORMAL, wxBOLD, false, wxT("Tahoma")));
itemBoxSizer2->Add(m_pClassCountText, 0, wxALIGN_LEFT|wxLEFT|wxRIGHT|wxBOTTOM, 5);
wxBoxSizer* itemBoxSizer5 = new wxBoxSizer(wxHORIZONTAL);
itemBoxSizer2->Add(itemBoxSizer5, 1, wxGROW, 5);
m_pChoiceBook = new wxChoicebook( this, ID_LISTMODE, wxDefaultPosition, wxDefaultSize, wxCHB_DEFAULT );
// raw-list page
wxPanel* itemPanel7 = new wxPanel( m_pChoiceBook, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxTAB_TRAVERSAL );
wxBoxSizer* itemBoxSizer8 = new wxBoxSizer(wxHORIZONTAL);
itemPanel7->SetSizer(itemBoxSizer8);
wxArrayString m_pRawListBoxStrings;
m_pRawListBox = new wxListBox( itemPanel7, ID_LISTBOX, wxDefaultPosition, wxDefaultSize, m_pRawListBoxStrings, wxLB_SINGLE );
itemBoxSizer8->Add(m_pRawListBox, 1, wxGROW, 5);
m_pChoiceBook->AddPage(itemPanel7, _("Raw list"));
// by-size page
wxPanel* itemPanel13 = new wxPanel( m_pChoiceBook, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxSUNKEN_BORDER|wxTAB_TRAVERSAL );
wxBoxSizer* itemBoxSizer14 = new wxBoxSizer(wxHORIZONTAL);
itemPanel13->SetSizer(itemBoxSizer14);
wxArrayString m_pSizeListBoxStrings;
m_pSizeListBox = new wxListBox( itemPanel13, ID_LISTBOX, wxDefaultPosition, wxDefaultSize, m_pSizeListBoxStrings, wxLB_SINGLE );
itemBoxSizer14->Add(m_pSizeListBox, 1, wxGROW, 5);
m_pChoiceBook->AddPage(itemPanel13, _("Classes by size"));
// tree page
wxPanel* itemPanel10 = new wxPanel( m_pChoiceBook, ID_PANEL, wxDefaultPosition, wxDefaultSize, wxTAB_TRAVERSAL );
wxBoxSizer* itemBoxSizer11 = new wxBoxSizer(wxVERTICAL);
itemPanel10->SetSizer(itemBoxSizer11);
m_pParentTreeCtrl = new wxTreeCtrl( itemPanel10, ID_TREECTRL, wxDefaultPosition, wxSize(100, 100), wxTR_HAS_BUTTONS |wxTR_SINGLE );
itemBoxSizer11->Add(m_pParentTreeCtrl, 1, wxGROW, 5);
m_pChoiceBook->AddPage(itemPanel10, _("Classes by parent"));
itemBoxSizer5->Add(m_pChoiceBook, 0, wxGROW|wxALL, 5);
m_pTextCtrl = new wxTextCtrl( this, ID_TEXTCTRL, _T(""), wxDefaultPosition, wxSize(500, -1), wxTE_MULTILINE|wxTE_READONLY );
itemBoxSizer5->Add(m_pTextCtrl, 3, wxGROW|wxALL, 5);
wxStdDialogButtonSizer* itemStdDialogButtonSizer17 = new wxStdDialogButtonSizer;
itemBoxSizer2->Add(itemStdDialogButtonSizer17, 0, wxGROW|wxALL, 5);
wxButton* itemButton18 = new wxButton( this, wxID_OK, _("&OK"), wxDefaultPosition, wxDefaultSize, 0 );
itemStdDialogButtonSizer17->AddButton(itemButton18);
wxButton* itemButton19 = new wxButton( this, wxID_CANCEL, _("&Cancel"), wxDefaultPosition, wxDefaultSize, 0 );
itemStdDialogButtonSizer17->AddButton(itemButton19);
itemStdDialogButtonSizer17->Realize();
InitControls();
}
int ClassListDialog::AddClassesWithParent(const wxClassInfo *parent, const wxTreeItemId &id)
{
const wxClassInfo *ci = wxClassInfo::GetFirst();
int count = 0;
while (ci)
{
// is this class derived from the given parent?
if (wxString(ci->GetBaseClassName1()) == parent->GetClassName() ||
wxString(ci->GetBaseClassName2()) == parent->GetClassName())
{
wxTreeItemId child = m_pParentTreeCtrl->AppendItem(id, ci->GetClassName());
// update the name of this child with the count of the children classes
int ret = AddClassesWithParent(ci, child);
m_pParentTreeCtrl->SetItemText(child,
m_pParentTreeCtrl->GetItemText(child) +
wxString::Format(wxT(" [%d]"), ret));
count += ret+1;
}
ci = ci->GetNext();
}
// reorder all the children we've just added
m_pParentTreeCtrl->SortChildren(id);
return count;
}
int GetSizeOfClass(const wxString &cn)
{
const wxClassInfo *ci = wxClassInfo::FindClass(cn);
if (ci)
return ci->GetSize();
return 0;
}
int CompareClassSizes(const wxString &class1, const wxString &class2)
{
return GetSizeOfClass(class1) - GetSizeOfClass(class2);
}
void ClassListDialog::InitControls()
{
// create a wxArrayString with the names of all classes:
const wxClassInfo *ci = wxClassInfo::GetFirst();
wxArrayString arr;
while (ci)
{
arr.Add(ci->GetClassName());
ci = ci->GetNext();
}
arr.Sort(); // sort alphabetically
// now add it to the raw-mode listbox
for (unsigned int i=0; i<arr.GetCount(); i++)
if (!IsToDiscard(arr[i]))
m_pRawListBox->Append(arr[i]);
m_nCount = m_pRawListBox->GetCount();
// sort again using size as sortkey
arr.Sort((wxArrayString::CompareFunction)CompareClassSizes);
// now add it to the size-mode listbox
for (unsigned int i=0; i<arr.GetCount(); i++)
if (!IsToDiscard(arr[i]))
m_pSizeListBox->Append(arr[i]);
// add root item to parent-mode treectrl
wxTreeItemId id = m_pParentTreeCtrl->AddRoot(_T("wxObject"));
// recursively add all leaves to the treectrl
int count = AddClassesWithParent(CLASSINFO(wxObject), id);
m_pParentTreeCtrl->SetItemText(id, m_pParentTreeCtrl->GetItemText(id) +
wxString::Format(wxT(" [%d]"), count));
// initially expand the root item
m_pParentTreeCtrl->Expand(id);
m_nTotalCount = arr.GetCount();
UpdateFilterText();
// don't leave blank the XTI info display
m_pChoiceBook->ChangeSelection(0);
m_pRawListBox->Select(0);
UpdateClassInfo(m_pRawListBox->GetStringSelection());
}
bool ClassListDialog::IsToDiscard(const wxString &classname) const
{
wxCheckBox *cb = wx_static_cast(wxCheckBox*, FindWindow(ID_SHOW_ONLY_XTI));
if (!cb || !cb->IsChecked())
return false;
// check if this class has XTI infos
wxClassInfo *info = wxClassInfo::FindClass(classname);
if (!info)
return false;
if (info->GetFirstProperty() != NULL || info->GetFirstHandler() != NULL)
return false; // has XTI info
return true; // no XTI info
}
void ClassListDialog::UpdateFilterText()
{
// tell the user how many registered classes are present and
// how many are we showing
m_pClassCountText->SetLabel(
wxString::Format(
wxT("Showing %d classes on a total of %d registered classes in wxXTI."),
m_nCount, m_nTotalCount));
}
void ClassListDialog::UpdateClassInfo(const wxString &itemName)
{
wxString classname = itemName.BeforeFirst(_T(' '));
wxCheckBox *cb = wx_static_cast(wxCheckBox*, FindWindow(ID_SHOW_PROPERTIES_RECURSIVELY));
m_pTextCtrl->SetValue(
DumpClassInfo(wxClassInfo::FindClass(classname), cb->IsChecked()));
}
// ----------------------------------------------------------------------------
// ClassListDialog - event handlers
// ----------------------------------------------------------------------------
void ClassListDialog::OnShowOnlyXTICheckbox( wxCommandEvent& WXUNUSED(event) )
{
m_pRawListBox->Clear();
m_pParentTreeCtrl->DeleteAllItems();
m_pSizeListBox->Clear();
InitControls();
}
void ClassListDialog::OnShowRecursiveInfoCheckbox( wxCommandEvent& WXUNUSED(event) )
{
m_pRawListBox->Clear();
m_pParentTreeCtrl->DeleteAllItems();
m_pSizeListBox->Clear();
InitControls();
}
void ClassListDialog::OnListboxSelected( wxCommandEvent& event )
{
UpdateClassInfo(event.GetString());
}
void ClassListDialog::OnTreectrlSelChanged( wxTreeEvent& event )
{
UpdateClassInfo(m_pParentTreeCtrl->GetItemText(event.GetItem()));
}
void ClassListDialog::OnChoiceBookPageChange( wxChoicebookEvent& event )
{
switch (event.GetSelection())
{
case 0:
if (m_pRawListBox->GetCount())
{
m_pRawListBox->Select(0);
UpdateClassInfo(m_pRawListBox->GetStringSelection());
}
break;
case 1:
if (m_pSizeListBox->GetCount())
{
m_pSizeListBox->Select(0);
UpdateClassInfo(m_pSizeListBox->GetStringSelection());
}
break;
case 2:
{
wxTreeItemId root = m_pParentTreeCtrl->GetRootItem();
if (root.IsOk())
{
m_pParentTreeCtrl->SelectItem(root);
UpdateClassInfo(m_pParentTreeCtrl->GetItemText(root));
}
}
break;
}
}
// ----------------------------------------------------------------------------
// dump functions
// ----------------------------------------------------------------------------
wxString DumpStr(const wxString &str)
{
if (str.empty())
return wxT("none");
return str;
}
wxString DumpTypeInfo(const wxTypeInfo *ti)
{
if (!ti)
return _T("none");
return DumpStr(ti->GetTypeName());
}
wxString DumpPropertyAccessor(const wxPropertyAccessor *acc, int indent)
{
wxString ind = _T("\n") + wxString(indent, wxT(' '));
wxString infostr;
if (!acc)
return ind + _T("no property accessors");
if (acc->HasSetter())
infostr << ind << _T("setter name: ") << acc->GetSetterName();
if (acc->HasCollectionGetter())
infostr << ind << _T("collection getter name: ") << acc->GetCollectionGetterName();
if (acc->HasGetter())
infostr << ind << _T("getter name: ") << acc->GetGetterName();
if (acc->HasAdder())
infostr << ind << _T("adder name: ") << acc->GetAdderName();
return infostr;
}
wxString DumpPropertyInfo(const wxPropertyInfo *prop, int indent)
{
wxString ind = _T("\n") + wxString(indent, wxT(' '));
wxString infostr;
if (!prop)
return ind + _T("none");
infostr << ind << _T("flags: ");
if (prop->GetFlags() & wxPROP_DEPRECATED)
infostr << _T("wxPROP_DEPRECATED,");
if (prop->GetFlags() & wxPROP_OBJECT_GRAPH)
infostr << _T("wxPROP_OBJECT_GRAPH,");
if (prop->GetFlags() & wxPROP_ENUM_STORE_LONG)
infostr << _T("wxPROP_ENUM_STORE_LONG,");
if (prop->GetFlags() & wxPROP_DONT_STREAM)
infostr << _T("wxPROP_DONT_STREAM,");
if (prop->GetFlags() == 0)
infostr << _T("none");
else
infostr.RemoveLast(); // remove last comma
infostr << ind << _T("help string: ") << DumpStr(prop->GetHelpString());
infostr << ind << _T("group string: ") << DumpStr(prop->GetGroupString());
infostr << ind << _T("collection element type: ") << DumpTypeInfo(prop->GetCollectionElementTypeInfo());
infostr << ind << _T("type: ") << DumpTypeInfo(prop->GetTypeInfo());
infostr << ind << _T("default value: ") << DumpStr(wxAnyGetAsString(prop->GetDefaultValue()));
infostr << DumpPropertyAccessor(prop->GetAccessor(), indent+1);
return infostr;
}
wxString DumpHandlerInfo(const wxHandlerInfo *phdlr, int indent)
{
wxString ind = _T("\n") + wxString(indent, wxT(' '));
wxString infostr;
if (!phdlr)
return ind + _T("none");
infostr << ind << _T("event class: ") <<
(phdlr->GetEventClassInfo() ? phdlr->GetEventClassInfo()->GetClassName() : wxT("none"));
return infostr;
}
int DumpProperties(const wxClassInfo *info, wxString& infostr, bool recursive)
{
const wxPropertyInfo *prop;
int pcount;
for (prop = info->GetFirstProperty(), pcount = 0;
prop;
prop = prop->GetNext(), pcount++)
{
infostr << _T("\n\n [") << pcount+1 << _T("] Property: ") << prop->GetName();
infostr << DumpPropertyInfo(prop, 4);
}
if (pcount == 0)
infostr << _T("\n None");
if (recursive)
{
const wxClassInfo **parent = info->GetParents();
wxString str;
for (int i=0; parent[i] != NULL; i++)
{
int ppcount = DumpProperties(parent[i], str, recursive);
if (ppcount)
{
pcount += ppcount;
infostr << _T("\n\n ") << parent[i]->GetClassName() << _T(" PARENT'S PROPERTIES:");
infostr << str;
}
}
}
return pcount;
}
int DumpHandlers(const wxClassInfo *info, wxString& infostr, bool recursive)
{
const wxHandlerInfo *h;
int hcount;
for (h = info->GetFirstHandler(), hcount = 0;
h;
h = h->GetNext(), hcount++)
{
infostr << _T("\n\n [") << hcount+1 << _T("] Handler: ") << h->GetName();
infostr << DumpHandlerInfo(h, 4);
}
if (hcount == 0)
infostr << _T("\n None");
if (recursive)
{
const wxClassInfo **parent = info->GetParents();
wxString str;
for (int i=0; parent[i] != NULL; i++)
{
int hhcount = DumpHandlers(parent[i], str, recursive);
if (hhcount)
{
hcount += hhcount;
infostr << _T("\n\n ") << parent[i]->GetClassName() << _T(" PARENT'S HANDLERS:");
infostr << str;
}
}
}
return hcount;
}
wxString DumpClassInfo(const wxClassInfo *info, bool recursive)
{
wxString infostr;
if (!info)
return wxEmptyString;
// basic stuff:
infostr << _T("\n BASIC RTTI INFO ABOUT ") << info->GetClassName();
infostr << _T("\n =================================================");
infostr << _T("\n Base class #1: ") << DumpStr(info->GetBaseClassName1());
infostr << _T("\n Base class #2: ") << DumpStr(info->GetBaseClassName2());
infostr << _T("\n Include file: ") << DumpStr(info->GetIncludeName());
infostr << _T("\n Size: ") << info->GetSize();
infostr << _T("\n Dynamic: ") << (info->IsDynamic() ? _T("true") : _T("false"));
// advanced stuff:
infostr << _T("\n\n\n ADVANCED RTTI INFO ABOUT ") << info->GetClassName();
infostr << _T("\n =================================================\n");
infostr << _T("\n PROPERTIES");
infostr << _T("\n -----------------------------------------");
int pcount = DumpProperties(info, infostr, recursive);
infostr << _T("\n\n HANDLERS");
infostr << _T("\n -----------------------------------------");
int hcount = DumpHandlers(info, infostr, recursive);
if (pcount+hcount == 0)
infostr << _T("\n\n no advanced info\n");
else
{
infostr << _T("\n\n Total count of properties: ") << pcount;
infostr << _T("\n Total count of handlers: ") << hcount << _T("\n");
}
return infostr;
}