1 ///////////////////////////////////////////////////////////////////////////// 
   2 // Name:        src/common/xti.cpp 
   3 // Purpose:     runtime metadata information (extended class info 
   4 // Author:      Stefan Csomor 
   8 // Copyright:   (c) 1997 Julian Smart 
   9 //              (c) 2003 Stefan Csomor 
  10 // Licence:     wxWindows licence 
  11 ///////////////////////////////////////////////////////////////////////////// 
  13 // For compilers that support precompilation, includes "wx.h". 
  14 #include "wx/wxprec.h" 
  22 #include "wx/object.h" 
  25 #if wxUSE_EXTENDED_RTTI 
  28 #include "wx/xml/xml.h" 
  29 #include "wx/tokenzr.h" 
  33 #include "wx/beforestd.h" 
  37 #include "wx/afterstd.h" 
  41 // ---------------------------------------------------------------------------- 
  43 // ---------------------------------------------------------------------------- 
  45 wxEnumData::wxEnumData( wxEnumMemberData
* data 
) 
  48     for ( m_count 
= 0; m_members
[m_count
].m_name 
; m_count
++) 
  52 bool wxEnumData::HasEnumMemberValue(const wxChar 
*name
, int *value
) const 
  55     for (i 
= 0; m_members
[i
].m_name 
; i
++ ) 
  57         if (!wxStrcmp(name
, m_members
[i
].m_name
)) 
  60                 *value 
= m_members
[i
].m_value
; 
  67 int wxEnumData::GetEnumMemberValue(const wxChar 
*name
) const 
  70     for (i 
= 0; m_members
[i
].m_name 
; i
++ ) 
  72         if (!wxStrcmp(name
, m_members
[i
].m_name
)) 
  74             return m_members
[i
].m_value
; 
  80 const wxChar 
*wxEnumData::GetEnumMemberName(int value
) const 
  83     for (i 
= 0; m_members
[i
].m_name 
; i
++) 
  84         if (value 
== m_members
[i
].m_value
) 
  85             return m_members
[i
].m_name
; 
  87     return wxEmptyString 
; 
  90 int wxEnumData::GetEnumMemberValueByIndex( int idx 
) const 
  92     // we should cache the count in order to avoid out-of-bounds errors 
  93     return m_members
[idx
].m_value 
; 
  96 const wxChar 
* wxEnumData::GetEnumMemberNameByIndex( int idx 
) const 
  98     // we should cache the count in order to avoid out-of-bounds errors 
  99     return m_members
[idx
].m_name 
; 
 102 // ---------------------------------------------------------------------------- 
 104 // ---------------------------------------------------------------------------- 
 105 // ---------------------------------------------------------------------------- 
 107 // ---------------------------------------------------------------------------- 
 109 // streamer specializations 
 110 // for all built-in types 
 114 template<> void wxStringReadValue(const wxString 
&s 
, bool &data 
) 
 117     wxSscanf(s
, _T("%d"), &intdata 
) ; 
 118     data 
= (bool)intdata 
; 
 121 template<> void wxStringWriteValue(wxString 
&s 
, const bool &data 
) 
 123     s 
= wxString::Format(_T("%d"), data 
) ; 
 128 template<> void wxStringReadValue(const wxString 
&s 
, char &data 
) 
 131     wxSscanf(s
, _T("%d"), &intdata 
) ; 
 132     data 
= char(intdata
) ; 
 135 template<> void wxStringWriteValue(wxString 
&s 
, const char &data 
) 
 137     s 
= wxString::Format(_T("%d"), data 
) ; 
 142 template<> void wxStringReadValue(const wxString 
&s 
, unsigned char &data 
) 
 145     wxSscanf(s
, _T("%d"), &intdata 
) ; 
 146     data 
= (unsigned char)(intdata
) ; 
 149 template<> void wxStringWriteValue(wxString 
&s 
, const unsigned char &data 
) 
 151     s 
= wxString::Format(_T("%d"), data 
) ; 
 156 template<> void wxStringReadValue(const wxString 
&s 
, int &data 
) 
 158     wxSscanf(s
, _T("%d"), &data 
) ; 
 161 template<> void wxStringWriteValue(wxString 
&s 
, const int &data 
) 
 163     s 
= wxString::Format(_T("%d"), data 
) ; 
 168 template<> void wxStringReadValue(const wxString 
&s 
, unsigned int &data 
) 
 170     wxSscanf(s
, _T("%d"), &data 
) ; 
 173 template<> void wxStringWriteValue(wxString 
&s 
, const unsigned int &data 
) 
 175     s 
= wxString::Format(_T("%d"), data 
) ; 
 180 template<> void wxStringReadValue(const wxString 
&s 
, long &data 
) 
 182     wxSscanf(s
, _T("%ld"), &data 
) ; 
 185 template<> void wxStringWriteValue(wxString 
&s 
, const long &data 
) 
 187     s 
= wxString::Format(_T("%ld"), data 
) ; 
 192 template<> void wxStringReadValue(const wxString 
&s 
, unsigned long &data 
) 
 194     wxSscanf(s
, _T("%ld"), &data 
) ; 
 197 template<> void wxStringWriteValue(wxString 
&s 
, const unsigned long &data 
) 
 199     s 
= wxString::Format(_T("%ld"), data 
) ; 
 204 template<> void wxStringReadValue(const wxString 
&s 
, float &data 
) 
 206     wxSscanf(s
, _T("%f"), &data 
) ; 
 209 template<> void wxStringWriteValue(wxString 
&s 
, const float &data 
) 
 211     s 
= wxString::Format(_T("%f"), data 
) ; 
 216 template<> void wxStringReadValue(const wxString 
&s 
, double &data 
) 
 218     wxSscanf(s
, _T("%lf"), &data 
) ; 
 221 template<> void wxStringWriteValue(wxString 
&s 
, const double &data 
) 
 223     s 
= wxString::Format(_T("%lf"), data 
) ; 
 228 template<> void wxStringReadValue(const wxString 
&s 
, wxString 
&data 
) 
 233 template<> void wxStringWriteValue(wxString 
&s 
, const wxString 
&data 
) 
 241 #if wxUSE_FUNC_TEMPLATE_POINTER 
 242 #define wxBUILTIN_TYPE_INFO( element , type ) \ 
 243     wxBuiltInTypeInfo s_typeInfo##type(element , &wxToStringConverter<type> , &wxFromStringConverter<type> , typeid(type).name()) ; 
 245 #define wxBUILTIN_TYPE_INFO( element , type ) \ 
 246     void _toString##element( const wxxVariant& data , wxString &result ) { wxToStringConverter<type>(data, result); } \ 
 247     void _fromString##element( const wxString& data , wxxVariant &result ) { wxFromStringConverter<type>(data, result); } \ 
 248     wxBuiltInTypeInfo s_typeInfo##type(element , &_toString##element , &_fromString##element , typeid(type).name()) ; 
 251 typedef unsigned char unsigned_char
; 
 252 typedef unsigned int unsigned_int
; 
 253 typedef unsigned long unsigned_long
; 
 255 wxBuiltInTypeInfo 
s_typeInfovoid( wxT_VOID 
, NULL 
, NULL 
, typeid(void).name()); 
 256 wxBUILTIN_TYPE_INFO( wxT_BOOL 
,  bool); 
 257 wxBUILTIN_TYPE_INFO( wxT_CHAR 
,  char); 
 258 wxBUILTIN_TYPE_INFO( wxT_UCHAR 
, unsigned_char
); 
 259 wxBUILTIN_TYPE_INFO( wxT_INT 
, int); 
 260 wxBUILTIN_TYPE_INFO( wxT_UINT 
, unsigned_int
); 
 261 wxBUILTIN_TYPE_INFO( wxT_LONG 
, long); 
 262 wxBUILTIN_TYPE_INFO( wxT_ULONG 
, unsigned_long
); 
 263 wxBUILTIN_TYPE_INFO( wxT_FLOAT 
, float); 
 264 wxBUILTIN_TYPE_INFO( wxT_DOUBLE 
, double); 
 265 wxBUILTIN_TYPE_INFO( wxT_STRING 
, wxString
); 
 268 // this are compiler induced specialization which are never used anywhere 
 270 wxILLEGAL_TYPE_SPECIALIZATION( char const * ) 
 271 wxILLEGAL_TYPE_SPECIALIZATION( char * ) 
 272 wxILLEGAL_TYPE_SPECIALIZATION( unsigned char * ) 
 273 wxILLEGAL_TYPE_SPECIALIZATION( int * ) 
 274 wxILLEGAL_TYPE_SPECIALIZATION( bool * ) 
 275 wxILLEGAL_TYPE_SPECIALIZATION( long * ) 
 276 wxILLEGAL_TYPE_SPECIALIZATION( wxString 
* ) 
 278 wxCOLLECTION_TYPE_INFO( wxString 
, wxArrayString 
) ; 
 280 template<> void wxCollectionToVariantArray( wxArrayString 
const &theArray
, wxxVariantArray 
&value
) 
 282     wxArrayCollectionToVariantArray( theArray 
, value 
) ; 
 285 wxTypeInfoMap 
*wxTypeInfo::ms_typeTable 
= NULL 
; 
 287 wxTypeInfo 
*wxTypeInfo::FindType(const wxChar 
*typeName
) 
 289     wxTypeInfoMap::iterator iter 
= ms_typeTable
->find(typeName
) ; 
 290     wxASSERT_MSG( iter 
!= ms_typeTable
->end() , wxT("lookup for a non-existent type-info") ) ; 
 291     return (wxTypeInfo 
*)iter
->second
; 
 295 wxClassTypeInfo::wxClassTypeInfo( wxTypeKind kind 
, wxClassInfo
* classInfo 
, converterToString_t to 
, converterFromString_t from 
, const char *name
) : 
 296 wxTypeInfo( kind 
, to 
, from 
, name
) 
 297 { wxASSERT_MSG( kind 
== wxT_OBJECT_PTR 
|| kind 
== wxT_OBJECT 
, wxT("Illegal Kind for Enum Type")) ; m_classInfo 
= classInfo 
;} 
 300 wxClassTypeInfo::wxClassTypeInfo( wxTypeKind kind 
, wxClassInfo
* classInfo 
, converterToString_t to 
, converterFromString_t from 
, const wxString 
&name
) : 
 301 wxTypeInfo( kind 
, to 
, from 
, name
) 
 302 { wxASSERT_MSG( kind 
== wxT_OBJECT_PTR 
|| kind 
== wxT_OBJECT 
, wxT("Illegal Kind for Enum Type")) ; m_classInfo 
= classInfo 
;} 
 304 wxDelegateTypeInfo::wxDelegateTypeInfo( int eventType 
, wxClassInfo
* eventClass 
, converterToString_t to 
, converterFromString_t from 
) : 
 305 wxTypeInfo ( wxT_DELEGATE 
, to 
, from 
, wxEmptyString 
) 
 306 { m_eventClass 
= eventClass 
; m_eventType 
= eventType 
; m_lastEventType 
= -1 ;} 
 308 wxDelegateTypeInfo::wxDelegateTypeInfo( int eventType 
, int lastEventType 
, wxClassInfo
* eventClass 
, converterToString_t to 
, converterFromString_t from 
) : 
 309 wxTypeInfo ( wxT_DELEGATE 
, to 
, from 
, wxEmptyString 
) 
 310 { m_eventClass 
= eventClass 
; m_eventType 
= eventType 
; m_lastEventType 
= lastEventType
; } 
 312 void wxTypeInfo::Register() 
 314     if ( ms_typeTable 
== NULL 
) 
 315         ms_typeTable 
= new wxTypeInfoMap() ; 
 317     if( !m_name
.empty() ) 
 318         (*ms_typeTable
)[m_name
] = this ; 
 321 void wxTypeInfo::Unregister() 
 323     if( !m_name
.empty() ) 
 324         ms_typeTable
->erase(m_name
); 
 327 // removing header dependancy on string tokenizer 
 329 void wxSetStringToArray( const wxString 
&s 
, wxArrayString 
&array 
) 
 331     wxStringTokenizer 
tokenizer(s
, wxT("| \t\n"), wxTOKEN_STRTOK
); 
 334     while (tokenizer
.HasMoreTokens()) 
 336         array
.Add(tokenizer
.GetNextToken()) ; 
 340 // ---------------------------------------------------------------------------- 
 342 // ---------------------------------------------------------------------------- 
 344 wxPropertyInfo::~wxPropertyInfo() 
 346     if ( this == m_itsClass
->m_firstProperty 
) 
 348         m_itsClass
->m_firstProperty 
= m_next
; 
 352         wxPropertyInfo 
*info 
= m_itsClass
->m_firstProperty
; 
 355             if ( info
->m_next 
== this ) 
 357                 info
->m_next 
= m_next
; 
 366 wxHandlerInfo::~wxHandlerInfo() 
 368     if ( this == m_itsClass
->m_firstHandler 
) 
 370         m_itsClass
->m_firstHandler 
= m_next
; 
 374         wxHandlerInfo 
*info 
= m_itsClass
->m_firstHandler
; 
 377             if ( info
->m_next 
== this ) 
 379                 info
->m_next 
= m_next
; 
 388 const wxPropertyAccessor 
*wxClassInfo::FindAccessor(const wxChar 
*PropertyName
) const 
 390     const wxPropertyInfo
* info 
= FindPropertyInfo( PropertyName 
) ; 
 393         return info
->GetAccessor() ; 
 398 wxPropertyInfo 
*wxClassInfo::FindPropertyInfoInThisClass (const wxChar 
*PropertyName
) const 
 400     wxPropertyInfo
* info 
= m_firstProperty 
; 
 404         if ( wxStrcmp( info
->GetName() , PropertyName 
) == 0 ) 
 406         info 
= info
->GetNext() ; 
 412 const wxPropertyInfo 
*wxClassInfo::FindPropertyInfo (const wxChar 
*PropertyName
) const 
 414     const wxPropertyInfo
* info 
= FindPropertyInfoInThisClass( PropertyName 
) ; 
 418     const wxClassInfo
** parents 
= GetParents() ; 
 419     for ( int i 
= 0 ; parents
[i
] ; ++ i 
) 
 421         if ( ( info 
= parents
[i
]->FindPropertyInfo( PropertyName 
) ) != NULL 
) 
 428 wxHandlerInfo 
*wxClassInfo::FindHandlerInfoInThisClass (const wxChar 
*PropertyName
) const 
 430     wxHandlerInfo
* info 
= m_firstHandler 
; 
 434         if ( wxStrcmp( info
->GetName() , PropertyName 
) == 0 ) 
 436         info 
= info
->GetNext() ; 
 442 const wxHandlerInfo 
*wxClassInfo::FindHandlerInfo (const wxChar 
*PropertyName
) const 
 444     const wxHandlerInfo
* info 
= FindHandlerInfoInThisClass( PropertyName 
) ; 
 449     const wxClassInfo
** parents 
= GetParents() ; 
 450     for ( int i 
= 0 ; parents
[i
] ; ++ i 
) 
 452         if ( ( info 
= parents
[i
]->FindHandlerInfo( PropertyName 
) ) != NULL 
) 
 459 wxObjectStreamingCallback 
wxClassInfo::GetStreamingCallback() const 
 461     if ( m_streamingCallback 
) 
 462         return m_streamingCallback 
; 
 464     wxObjectStreamingCallback retval 
= NULL 
; 
 465     const wxClassInfo
** parents 
= GetParents() ; 
 466     for ( int i 
= 0 ; parents
[i
] && retval 
== NULL 
; ++ i 
) 
 468         retval 
= parents
[i
]->GetStreamingCallback() ; 
 473 bool wxClassInfo::BeforeWriteObject( const wxObject 
*obj
, wxWriter 
*streamer 
, wxPersister 
*persister 
, wxxVariantArray 
&metadata
) const 
 475     wxObjectStreamingCallback sb 
= GetStreamingCallback() ; 
 477         return (*sb
)(obj 
, streamer 
, persister 
, metadata 
) ; 
 482 void wxClassInfo::SetProperty(wxObject 
*object
, const wxChar 
*propertyName
, const wxxVariant 
&value
) const 
 484     const wxPropertyAccessor 
*accessor
; 
 486     accessor 
= FindAccessor(propertyName
); 
 487     wxASSERT(accessor
->HasSetter()); 
 488     accessor
->SetProperty( object 
, value 
) ; 
 491 wxxVariant 
wxClassInfo::GetProperty(wxObject 
*object
, const wxChar 
*propertyName
) const 
 493     const wxPropertyAccessor 
*accessor
; 
 495     accessor 
= FindAccessor(propertyName
); 
 496     wxASSERT(accessor
->HasGetter()); 
 498     accessor
->GetProperty(object
,result
); 
 502 wxxVariantArray 
wxClassInfo::GetPropertyCollection(wxObject 
*object
, const wxChar 
*propertyName
) const 
 504     const wxPropertyAccessor 
*accessor
; 
 506     accessor 
= FindAccessor(propertyName
); 
 507     wxASSERT(accessor
->HasGetter()); 
 508     wxxVariantArray result 
; 
 509     accessor
->GetPropertyCollection(object
,result
); 
 513 void wxClassInfo::AddToPropertyCollection(wxObject 
*object
, const wxChar 
*propertyName 
, const wxxVariant
& value
) const 
 515     const wxPropertyAccessor 
*accessor
; 
 517     accessor 
= FindAccessor(propertyName
); 
 518     wxASSERT(accessor
->HasAdder()); 
 519     accessor
->AddToPropertyCollection( object 
, value 
) ; 
 522 // void wxClassInfo::GetProperties( wxPropertyInfoMap &map ) const 
 523 // The map parameter (the name map that is) seems something special 
 524 // to MSVC and so we use a other name. 
 525 void wxClassInfo::GetProperties( wxPropertyInfoMap 
&infomap 
) const 
 527     const wxPropertyInfo 
*pi 
= GetFirstProperty() ; 
 530         if ( infomap
.find( pi
->GetName() ) == infomap
.end() ) 
 531             infomap
[pi
->GetName()] = (wxPropertyInfo
*) pi 
; 
 536     const wxClassInfo
** parents 
= GetParents() ; 
 537     for ( int i 
= 0 ; parents
[i
] ; ++ i 
) 
 539         parents
[i
]->GetProperties( infomap 
) ; 
 547 wxObject
* wxxVariant::GetAsObject() 
 549     const wxClassTypeInfo 
*ti 
= dynamic_cast<const wxClassTypeInfo
*>( m_data
->GetTypeInfo() ) ; 
 551         return ti
->GetClassInfo()->VariantToInstance(*this) ; 
 556 // ---------------------------------------------------------------------------- 
 557 // wxDynamicObject support 
 558 // ---------------------------------------------------------------------------- 
 560 // Dynamic Objects are objects that have a real superclass instance and carry their 
 561 // own attributes in a hash map. Like this it is possible to create the objects and 
 562 // stream them, as if their class information was already available from compiled data 
 564 struct wxDynamicObject::wxDynamicObjectInternal
 
 566     wxDynamicObjectInternal() {} 
 569     map
<wstring
,wxxVariant
> m_properties 
; 
 571     map
<string
,wxxVariant
> m_properties 
; 
 575 typedef list
< wxDynamicObject
* > wxDynamicObjectList 
; 
 577 struct wxDynamicClassInfo::wxDynamicClassInfoInternal
 
 579     wxDynamicObjectList m_dynamicObjects 
; 
 582 // instantiates this object with an instance of its superclass 
 583 wxDynamicObject::wxDynamicObject(wxObject
* superClassInstance
, const wxDynamicClassInfo 
*info
) 
 585     m_superClassInstance 
= superClassInstance 
; 
 587     m_data 
= new wxDynamicObjectInternal 
; 
 590 wxDynamicObject::~wxDynamicObject() 
 592     dynamic_cast<const wxDynamicClassInfo
*>(m_classInfo
)->m_data
->m_dynamicObjects
.remove( this ) ; 
 594     delete m_superClassInstance 
; 
 597 void wxDynamicObject::SetProperty (const wxChar 
*propertyName
, const wxxVariant 
&value
) 
 599     wxASSERT_MSG(m_classInfo
->FindPropertyInfoInThisClass(propertyName
),wxT("Accessing Unknown Property in a Dynamic Object") ) ; 
 600     m_data
->m_properties
[propertyName
] = value 
; 
 603 wxxVariant 
wxDynamicObject::GetProperty (const wxChar 
*propertyName
) const 
 605     wxASSERT_MSG(m_classInfo
->FindPropertyInfoInThisClass(propertyName
),wxT("Accessing Unknown Property in a Dynamic Object") ) ; 
 606     return m_data
->m_properties
[propertyName
] ; 
 609 void wxDynamicObject::RemoveProperty( const wxChar 
*propertyName 
) 
 611     wxASSERT_MSG(m_classInfo
->FindPropertyInfoInThisClass(propertyName
),wxT("Removing Unknown Property in a Dynamic Object") ) ; 
 612     m_data
->m_properties
.erase( propertyName 
) ; 
 615 void wxDynamicObject::RenameProperty( const wxChar 
*oldPropertyName 
, const wxChar 
*newPropertyName 
) 
 617     wxASSERT_MSG(m_classInfo
->FindPropertyInfoInThisClass(oldPropertyName
),wxT("Renaming Unknown Property in a Dynamic Object") ) ; 
 618     wxxVariant value 
= m_data
->m_properties
[oldPropertyName
] ; 
 619     m_data
->m_properties
.erase( oldPropertyName 
) ; 
 620     m_data
->m_properties
[newPropertyName
] = value 
; 
 624 // ---------------------------------------------------------------------------- 
 626 // ---------------------------------------------------------------------------- 
 628 wxDynamicClassInfo::wxDynamicClassInfo( const wxChar 
*unitName
, const wxChar 
*className 
, const wxClassInfo
* superClass 
) : 
 629 wxClassInfo( unitName
, className 
, new const wxClassInfo
*[2]) 
 631     GetParents()[0] = superClass 
; 
 632     GetParents()[1] = NULL 
; 
 633     m_data 
= new wxDynamicClassInfoInternal 
; 
 636 wxDynamicClassInfo::~wxDynamicClassInfo() 
 638     delete[] GetParents() ; 
 642 wxObject 
*wxDynamicClassInfo::AllocateObject() const 
 644     wxObject
* parent 
= GetParents()[0]->AllocateObject() ; 
 645     wxDynamicObject 
*obj 
= new wxDynamicObject( parent 
, this ) ; 
 646     m_data
->m_dynamicObjects
.push_back( obj 
) ; 
 650 void wxDynamicClassInfo::Create (wxObject 
*object
, int paramCount
, wxxVariant 
*params
) const 
 652     wxDynamicObject 
*dynobj 
= dynamic_cast< wxDynamicObject 
*>( object 
) ; 
 653     wxASSERT_MSG( dynobj 
, wxT("cannot call wxDynamicClassInfo::Create on an object other than wxDynamicObject") ) ; 
 654     GetParents()[0]->Create( dynobj
->GetSuperClassInstance() , paramCount 
, params 
) ; 
 657 // get number of parameters for constructor 
 658 int wxDynamicClassInfo::GetCreateParamCount() const 
 660     return GetParents()[0]->GetCreateParamCount() ; 
 663 // get i-th constructor parameter 
 664 const wxChar
* wxDynamicClassInfo::GetCreateParamName(int i
) const 
 666     return GetParents()[0]->GetCreateParamName( i 
) ; 
 669 void wxDynamicClassInfo::SetProperty(wxObject 
*object
, const wxChar 
*propertyName
, const wxxVariant 
&value
) const 
 671     wxDynamicObject
* dynobj 
= dynamic_cast< wxDynamicObject 
* >( object 
) ; 
 672     wxASSERT_MSG( dynobj 
, wxT("cannot call wxDynamicClassInfo::SetProperty on an object other than wxDynamicObject") ) ; 
 673     if ( FindPropertyInfoInThisClass(propertyName
) ) 
 674         dynobj
->SetProperty( propertyName 
, value 
) ; 
 676         GetParents()[0]->SetProperty( dynobj
->GetSuperClassInstance() , propertyName 
, value 
) ; 
 679 wxxVariant 
wxDynamicClassInfo::GetProperty(wxObject 
*object
, const wxChar 
*propertyName
) const 
 681     wxDynamicObject
* dynobj 
= dynamic_cast< wxDynamicObject 
* >( object 
) ; 
 682     wxASSERT_MSG( dynobj 
, wxT("cannot call wxDynamicClassInfo::SetProperty on an object other than wxDynamicObject") ) ; 
 683     if ( FindPropertyInfoInThisClass(propertyName
) ) 
 684         return dynobj
->GetProperty( propertyName 
) ; 
 686         return GetParents()[0]->GetProperty( dynobj
->GetSuperClassInstance() , propertyName 
) ; 
 689 void wxDynamicClassInfo::AddProperty( const wxChar 
*propertyName 
, const wxTypeInfo
* typeInfo 
) 
 691     new wxPropertyInfo( m_firstProperty 
, this , propertyName 
, typeInfo
->GetTypeName() , new wxGenericPropertyAccessor( propertyName 
) , wxxVariant() ) ; 
 694 void wxDynamicClassInfo::AddHandler( const wxChar 
*handlerName 
, wxObjectEventFunction address 
, const wxClassInfo
* eventClassInfo 
) 
 696     new wxHandlerInfo( m_firstHandler 
, this , handlerName 
, address 
, eventClassInfo 
) ; 
 699 // removes an existing runtime-property 
 700 void wxDynamicClassInfo::RemoveProperty( const wxChar 
*propertyName 
) 
 702     for ( wxDynamicObjectList::iterator iter 
= m_data
->m_dynamicObjects
.begin() ; iter 
!= m_data
->m_dynamicObjects
.end() ; ++iter 
) 
 703         (*iter
)->RemoveProperty( propertyName 
) ; 
 704     delete FindPropertyInfoInThisClass(propertyName
) ; 
 707 // removes an existing runtime-handler 
 708 void wxDynamicClassInfo::RemoveHandler( const wxChar 
*handlerName 
) 
 710     delete FindHandlerInfoInThisClass(handlerName
) ; 
 713 // renames an existing runtime-property 
 714 void wxDynamicClassInfo::RenameProperty( const wxChar 
*oldPropertyName 
, const wxChar 
*newPropertyName 
) 
 716     wxPropertyInfo
* pi 
= FindPropertyInfoInThisClass(oldPropertyName
) ; 
 717     wxASSERT_MSG( pi 
,wxT("not existing property") ) ; 
 718     pi
->m_name 
= newPropertyName 
; 
 719     dynamic_cast<wxGenericPropertyAccessor
*>(pi
->GetAccessor())->RenameProperty( oldPropertyName 
, newPropertyName 
) ; 
 720     for ( wxDynamicObjectList::iterator iter 
= m_data
->m_dynamicObjects
.begin() ; iter 
!= m_data
->m_dynamicObjects
.end() ; ++iter 
) 
 721         (*iter
)->RenameProperty( oldPropertyName 
, newPropertyName 
) ; 
 724 // renames an existing runtime-handler 
 725 void wxDynamicClassInfo::RenameHandler( const wxChar 
*oldHandlerName 
, const wxChar 
*newHandlerName 
) 
 727     wxASSERT_MSG(FindHandlerInfoInThisClass(oldHandlerName
),wxT("not existing handler") ) ; 
 728     FindHandlerInfoInThisClass(oldHandlerName
)->m_name 
= newHandlerName 
; 
 731 // ---------------------------------------------------------------------------- 
 732 // wxGenericPropertyAccessor 
 733 // ---------------------------------------------------------------------------- 
 735 struct wxGenericPropertyAccessor::wxGenericPropertyAccessorInternal
 
 740 wxGenericPropertyAccessor::wxGenericPropertyAccessor( const wxString
& propertyName 
) 
 741 : wxPropertyAccessor( NULL 
, NULL 
, NULL 
, NULL 
) 
 743     m_data 
= new wxGenericPropertyAccessorInternal 
; 
 744     m_propertyName 
= propertyName 
; 
 745     m_getterName 
= wxT("Get")+propertyName 
; 
 746     m_setterName 
= wxT("Set")+propertyName 
; 
 749 wxGenericPropertyAccessor::~wxGenericPropertyAccessor() 
 753 void wxGenericPropertyAccessor::SetProperty(wxObject 
*object
, const wxxVariant 
&value
) const 
 755     wxDynamicObject
* dynobj 
= dynamic_cast< wxDynamicObject 
* >( object 
) ; 
 756     wxASSERT_MSG( dynobj 
, wxT("cannot call wxDynamicClassInfo::SetProperty on an object other than wxDynamicObject") ) ; 
 757     dynobj
->SetProperty(m_propertyName 
, value 
) ; 
 760 void wxGenericPropertyAccessor::GetProperty(const wxObject 
*object
, wxxVariant
& value
) const 
 762     const wxDynamicObject
* dynobj 
= dynamic_cast< const wxDynamicObject 
* >( object 
) ; 
 763     wxASSERT_MSG( dynobj 
, wxT("cannot call wxDynamicClassInfo::SetProperty on an object other than wxDynamicObject") ) ; 
 764     value 
= dynobj
->GetProperty( m_propertyName 
) ;