X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/472137baebae6c011ad7d70285de454b9ce7796d..74a3342702bf3a76a845f65f4510fd8612d3d802:/src/propgrid/propgridpagestate.cpp?ds=sidebyside diff --git a/src/propgrid/propgridpagestate.cpp b/src/propgrid/propgridpagestate.cpp index a425b12d6a..a2ce40e1ed 100644 --- a/src/propgrid/propgridpagestate.cpp +++ b/src/propgrid/propgridpagestate.cpp @@ -4,7 +4,7 @@ // Author: Jaakko Salli // Modified by: // Created: 2008-08-24 -// RCS-ID: $Id: +// RCS-ID: $Id$ // Copyright: (c) Jaakko Salli // Licence: wxWindows license ///////////////////////////////////////////////////////////////////////////// @@ -29,33 +29,18 @@ #include "wx/panel.h" #include "wx/dc.h" #include "wx/dcmemory.h" - #include "wx/button.h" #include "wx/pen.h" #include "wx/brush.h" - #include "wx/cursor.h" - #include "wx/dialog.h" - #include "wx/settings.h" - #include "wx/msgdlg.h" - #include "wx/choice.h" - #include "wx/stattext.h" - #include "wx/scrolwin.h" - #include "wx/dirdlg.h" - #include "wx/layout.h" - #include "wx/sizer.h" - #include "wx/textdlg.h" - #include "wx/filedlg.h" - #include "wx/statusbr.h" #include "wx/intl.h" - #include "wx/frame.h" #include "wx/stopwatch.h" #endif // This define is necessary to prevent macro clearing #define __wxPG_SOURCE_FILE__ -#include -#include -#include +#include "wx/propgrid/propgridpagestate.h" +#include "wx/propgrid/propgrid.h" +#include "wx/propgrid/editors.h" #define wxPG_DEFAULT_SPLITTERX 110 @@ -89,11 +74,10 @@ void wxPropertyGridIteratorBase::Init( wxPropertyGridPageState* state, int flags void wxPropertyGridIteratorBase::Init( wxPropertyGridPageState* state, int flags, int startPos, int dir ) { - wxPGProperty* property; + wxPGProperty* property = NULL; if ( startPos == wxTOP ) { - property = NULL; if ( dir == 0 ) dir = 1; } @@ -105,8 +89,7 @@ void wxPropertyGridIteratorBase::Init( wxPropertyGridPageState* state, int flags } else { - wxASSERT_MSG( false, wxT("Only supported stating positions are wxTOP and wxBOTTOM") ); - property = NULL; + wxFAIL_MSG("Only supported starting positions are wxTOP and wxBOTTOM"); } Init( state, flags, property, dir ); @@ -262,17 +245,17 @@ void wxPropertyGridPageState::InitNonCatMode() if ( m_properties->GetChildCount() ) { - // Copy items. - wxPropertyGridIterator it( this, wxPG_ITERATE_DEFAULT|wxPG_ITERATE_CATEGORIES ); + // + // Prepare m_abcArray + wxPropertyGridIterator it( this, wxPG_ITERATE_PROPERTIES ); for ( ; !it.AtEnd(); it.Next() ) { wxPGProperty* p = it.GetProperty(); wxPGProperty* parent = p->GetParent(); - if ( p->HasFlag(wxPG_PROP_MISC_PARENT) && - ( parent == m_properties || (parent->IsCategory() || parent->IsRoot()) ) ) + if ( parent->IsCategory() || parent->IsRoot() ) { - m_abcArray->AddChild2( p ); + m_abcArray->AddChild2(p); p->m_parent = &m_regularArray; } } @@ -463,6 +446,26 @@ wxPGProperty* wxPropertyGridPageState::BaseGetPropertyByName( const wxString& na return (wxPGProperty*) NULL; } +// ----------------------------------------------------------------------- + +void wxPropertyGridPageState::DoSetPropertyName( wxPGProperty* p, + const wxString& newName ) +{ + wxCHECK_RET( p, wxT("invalid property id") ); + + wxPGProperty* parent = p->GetParent(); + + if ( parent->IsCategory() || parent->IsRoot() ) + { + if ( p->GetBaseName().length() ) + m_dictName.erase( p->GetBaseName() ); + if ( newName.length() ) + m_dictName[newName] = (void*) p; + } + + p->DoSetName(newName); +} + // ----------------------------------------------------------------------- // wxPropertyGridPageState global operations // ----------------------------------------------------------------------- @@ -472,7 +475,7 @@ wxPGProperty* wxPropertyGridPageState::BaseGetPropertyByName( const wxString& na // NB: Nowadays only needed for alphabetic/categoric mode switching. // ----------------------------------------------------------------------- -#define II_INVALID_I 0x00FFFFFF +//#define II_INVALID_I 0x00FFFFFF #define ITEM_ITERATION_VARIABLES \ wxPGProperty* parent; \ @@ -483,6 +486,7 @@ wxPGProperty* wxPropertyGridPageState::BaseGetPropertyByName( const wxString& na parent = m_properties; \ i = 0; +#if 0 #define ITEM_ITERATION_INIT(startparent, startindex, state) \ parent = startparent; \ i = (unsigned int)startindex; \ @@ -491,6 +495,7 @@ wxPGProperty* wxPropertyGridPageState::BaseGetPropertyByName( const wxString& na parent = state->m_properties; \ i = 0; \ } +#endif #define ITEM_ITERATION_LOOP_BEGIN \ do \ @@ -594,13 +599,25 @@ bool wxPropertyGridPageState::EnableCategories( bool enable ) // ----------------------------------------------------------------------- -static int wxPG_SortFunc(void **p1, void **p2) +#if wxUSE_STL +#include + +static bool wxPG_SortFunc(wxPGProperty *p1, wxPGProperty *p2) { - wxPGProperty *pp1 = *((wxPGProperty**)p1); - wxPGProperty *pp2 = *((wxPGProperty**)p2); + return p1->GetLabel() < p2->GetLabel(); +} + +#else + +static int wxPG_SortFunc(wxPGProperty **p1, wxPGProperty **p2) +{ + wxPGProperty *pp1 = *p1; + wxPGProperty *pp2 = *p2; return pp1->GetLabel().compare( pp2->GetLabel() ); } +#endif + void wxPropertyGridPageState::SortChildren( wxPGProperty* p ) { if ( !p ) @@ -615,10 +632,14 @@ void wxPropertyGridPageState::SortChildren( wxPGProperty* p ) if ( pwc->GetChildCount() < 1 ) return; +#if wxUSE_STL + std::sort(pwc->m_children.begin(), pwc->m_children.end(), wxPG_SortFunc); +#else pwc->m_children.Sort( wxPG_SortFunc ); +#endif // Fix indexes - pwc->FixIndexesOfChildren(); + pwc->FixIndicesOfChildren(); } @@ -683,7 +704,10 @@ int wxPropertyGridPageState::GetColumnFitWidth(wxClientDC& dc, wxPGProperty* p = pwc->Item(i); if ( !p->IsCategory() ) { - dc.GetTextExtent( p->GetColumnText(col), &w, &h ); + const wxPGCell* cell = NULL; + wxString text; + p->GetDisplayInfo(col, -1, 0, &text, &cell); + dc.GetTextExtent(text, &w, &h); if ( col == 0 ) w += ( ((int)p->m_depth-1) * pg->m_subgroup_extramargin ); @@ -878,8 +902,6 @@ void wxPropertyGridPageState::CheckColumnWidths( int widthChange ) int reduceCol = -1; int highestColWidth = 0; - bool minimizedCols = false; - #ifdef __WXDEBUG__ if ( debug ) wxLogDebug(wxT("ColumnWidthCheck (virtualWidth: %i, clientWidth: %i)"), width, clientWidth); @@ -893,7 +915,6 @@ void wxPropertyGridPageState::CheckColumnWidths( int widthChange ) if ( m_colWidths[i] <= min ) { m_colWidths[i] = min; - minimizedCols = true; } else { @@ -930,10 +951,10 @@ void wxPropertyGridPageState::CheckColumnWidths( int widthChange ) if ( colsWidth < width ) { // Increase column - #ifdef __WXDEBUG__ - if ( debug ) - wxLogDebug(wxT(" Adjust last column to %i"), m_colWidths[lastColumn] + widthHigher); - #endif +#ifdef __WXDEBUG__ + if ( debug ) + wxLogDebug(wxT(" Adjust last column to %i"), m_colWidths[lastColumn] + widthHigher); +#endif m_colWidths[lastColumn] = m_colWidths[lastColumn] + widthHigher; } else if ( colsWidth > width ) @@ -1086,7 +1107,7 @@ bool wxPropertyGridPageState::DoSetPropertyValueString( wxPGProperty* p, const w { if ( p ) { - int flags = wxPG_REPORT_ERROR|wxPG_FULL_VALUE; + int flags = wxPG_REPORT_ERROR|wxPG_FULL_VALUE|wxPG_PROGRAMMATIC_VALUE; wxVariant variant = p->GetValueRef(); bool res; @@ -1359,7 +1380,7 @@ void wxPropertyGridPageState::DoSetPropertyValues( const wxVariantList& list, wx // // Second pass for special entries - for ( node = list.begin(); node != list.end(); node++ ) + for ( node = list.begin(); node != list.end(); ++node ) { wxVariant *current = (wxVariant*)*node; @@ -1423,7 +1444,7 @@ void wxPropertyGridPageState::DoSetPropertyValues( const wxVariantList& list, wx if ( numSpecialEntries ) { - for ( node = list.begin(); node != list.end(); node++ ) + for ( node = list.begin(); node != list.end(); ++node ) { wxVariant *current = (wxVariant*)*node; @@ -1454,7 +1475,7 @@ void wxPropertyGridPageState::DoSetPropertyValues( const wxVariantList& list, wx wxVariantList& list2 = current->GetList(); wxVariantList::const_iterator node2; - for ( node2 = list2.begin(); node2 != list2.end(); node2++ ) + for ( node2 = list2.begin(); node2 != list2.end(); ++node2 ) { wxVariant *attr = (wxVariant*)*node2; foundProp->SetAttribute( attr->GetName(), *attr ); @@ -1494,8 +1515,8 @@ void wxPropertyGridPageState::DoSetPropertyValues( const wxVariantList& list, wx // wxPropertyGridPageState property adding and removal // ----------------------------------------------------------------------- -int wxPropertyGridPageState::PrepareToAddItem( wxPGProperty* property, - wxPGProperty* scheduledParent ) +bool wxPropertyGridPageState::PrepareToAddItem( wxPGProperty* property, + wxPGProperty* scheduledParent ) { wxPropertyGrid* propGrid = m_pPropGrid; @@ -1531,7 +1552,7 @@ int wxPropertyGridPageState::PrepareToAddItem( wxPGProperty* property, { delete property; m_currentCategory = pwc; - return 2; // Tells the caller what we did. + return false; } } } @@ -1548,123 +1569,29 @@ int wxPropertyGridPageState::PrepareToAddItem( wxPGProperty* property, #endif // Make sure nothing is selected. - if ( propGrid && propGrid->m_selected ) - { - bool selRes = propGrid->ClearSelection(); - wxPG_CHECK_MSG_DBG( selRes, - -1, - wxT("failed to deselect a property (editor probably had invalid value)") ); - } - - if ( scheduledParent ) - { - // Use parent's colours. - property->m_bgColIndex = scheduledParent->m_bgColIndex; - property->m_fgColIndex = scheduledParent->m_fgColIndex; - - // Fix no parent does not yet have parenting flag yet, set one now - if ( !scheduledParent->HasFlag(wxPG_PROP_PARENTAL_FLAGS) ) - scheduledParent->SetParentalType(wxPG_PROP_MISC_PARENT); - //scheduledParent->SetFlag(wxPG_PROP_MISC_PARENT); - } - - // If in hideable adding mode, or if assigned parent is hideable, then - // make this one hideable. - if ( - ( scheduledParent && (scheduledParent->m_flags & wxPG_PROP_HIDDEN) ) || - ( propGrid && (propGrid->m_iFlags & wxPG_FL_ADDING_HIDEABLES) ) - ) - property->SetFlag( wxPG_PROP_HIDDEN ); - - // Set custom image flag. - int custImgHeight = property->OnMeasureImage().y; - if ( custImgHeight < 0 /*|| custImgHeight > 1*/ ) - { - property->m_flags |= wxPG_PROP_CUSTOMIMAGE; - } - - if ( propGrid && (propGrid->GetWindowStyleFlag() & wxPG_LIMITED_EDITING) ) - property->m_flags |= wxPG_PROP_NOEDITOR; - - if ( !property->IsCategory() ) - { - // This is not a category. - - //wxASSERT_MSG( property->GetEditorClass(), wxT("Editor class not initialized!") ); + if ( propGrid ) + propGrid->ClearSelection(false); - // Depth. - // - unsigned char depth = 1; - if ( scheduledParent ) - { - depth = scheduledParent->m_depth; - if ( !scheduledParent->IsCategory() ) - depth++; - } - property->m_depth = depth; - unsigned char greyDepth = depth; - - if ( scheduledParent ) - { - wxPropertyCategory* pc; + // NULL parent == root parent + if ( !scheduledParent ) + scheduledParent = DoGetRoot(); - if ( scheduledParent->IsCategory() || scheduledParent->IsRoot() ) - pc = (wxPropertyCategory*)scheduledParent; - else - // This conditional compile is necessary to - // bypass some compiler bug. - pc = GetPropertyCategory(scheduledParent); + property->m_parent = scheduledParent; - if ( pc ) - greyDepth = pc->GetDepth(); - else - greyDepth = scheduledParent->m_depthBgCol; - } + property->InitAfterAdded(this, propGrid); - property->m_depthBgCol = greyDepth; - - // Prepare children pre-added children - if ( property->GetChildCount() ) - { - property->SetParentalType(wxPG_PROP_AGGREGATE); - - property->SetExpanded(false); // Properties with children are not expanded by default. - if ( propGrid && propGrid->GetWindowStyleFlag() & wxPG_HIDE_MARGIN ) - property->SetExpanded(true); // ...unless it cannot be expanded. - - property->PrepareSubProperties(); - - return -1; - } - - if ( propGrid && (propGrid->GetExtraStyle() & wxPG_EX_AUTO_UNSPECIFIED_VALUES) ) - property->SetFlagRecursively(wxPG_PROP_AUTO_UNSPECIFIED, true); - - return 0; - } - else + if ( property->IsCategory() ) { - // This is a category. + wxPropertyCategory* pc = wxStaticCast(property, wxPropertyCategory); - // depth - unsigned char depth = 1; - if ( scheduledParent ) - { - depth = scheduledParent->m_depth + 1; - } - property->m_depth = depth; - property->m_depthBgCol = depth; - - m_currentCategory = (wxPropertyCategory*)property; + m_currentCategory = pc; - wxPropertyCategory* pc = (wxPropertyCategory*)property; - - // Calculate text extent for caption item. + // Calculate text extent for category caption if ( propGrid ) pc->CalculateTextExtent(propGrid, propGrid->GetCaptionFont()); - - return 1; } + + return true; } // ----------------------------------------------------------------------- @@ -1689,11 +1616,11 @@ wxPGProperty* wxPropertyGridPageState::DoInsert( wxPGProperty* parent, int index wxNullProperty, wxT("when adding properties to fixed parents, use BeginAddChildren and EndAddChildren.") ); - int parenting = PrepareToAddItem( property, (wxPropertyCategory*)parent ); + bool res = PrepareToAddItem( property, (wxPropertyCategory*)parent ); - // This type of invalid parenting value indicates we should exit now, returning - // id of most recent category. - if ( parenting > 1 ) + // PrepareToAddItem() may just decide to use use current category + // instead of adding new one. + if ( !res ) return m_currentCategory; // Note that item must be added into current mode later. @@ -1722,7 +1649,7 @@ wxPGProperty* wxPropertyGridPageState::DoInsert( wxPGProperty* parent, int index // Categorized mode // Only add non-categories to m_abcArray. - if ( m_abcArray && parenting <= 0 ) + if ( m_abcArray && !property->IsCategory() ) m_abcArray->AddChild2( property, -1, false ); // Add to current mode. @@ -1741,7 +1668,7 @@ wxPGProperty* wxPropertyGridPageState::DoInsert( wxPGProperty* parent, int index m_regularArray.AddChild2( property, -1, false ); // Add to current mode (no categories). - if ( parenting <= 0 ) + if ( !property->IsCategory() ) m_abcArray->AddChild2( property, index ); } } @@ -1756,7 +1683,8 @@ wxPGProperty* wxPropertyGridPageState::DoInsert( wxPGProperty* parent, int index } // Only add name to hashmap if parent is root or category - if ( (parent->IsCategory() || parent->IsRoot()) && property->m_name.length() ) + if ( property->m_name.length() && + (parent->IsCategory() || parent->IsRoot()) ) m_dictName[property->m_name] = (void*) property; VirtualHeightChanged(); @@ -1770,7 +1698,7 @@ wxPGProperty* wxPropertyGridPageState::DoInsert( wxPGProperty* parent, int index // ----------------------------------------------------------------------- -void wxPropertyGridPageState::DoDelete( wxPGProperty* item ) +void wxPropertyGridPageState::DoDelete( wxPGProperty* item, bool doDelete ) { wxCHECK_RET( item->GetParent(), wxT("this property was already deleted") ); @@ -1778,60 +1706,43 @@ void wxPropertyGridPageState::DoDelete( wxPGProperty* item ) wxCHECK_RET( item != &m_regularArray && item != m_abcArray, wxT("wxPropertyGrid: Do not attempt to remove the root item.") ); - size_t i; unsigned int indinparent = item->GetIndexInParent(); wxPGProperty* pwc = (wxPGProperty*)item; + wxPGProperty* parent = item->GetParent(); - wxCHECK_RET( !item->GetParent()->HasFlag(wxPG_PROP_AGGREGATE), + wxCHECK_RET( !parent->HasFlag(wxPG_PROP_AGGREGATE), wxT("wxPropertyGrid: Do not attempt to remove sub-properties.") ); - if ( item->IsCategory() ) + // Delete children + if ( item->GetChildCount() && !item->HasFlag(wxPG_PROP_AGGREGATE) ) { // deleting a category - - // erase category entries from the hash table - for ( i=0; iGetChildCount(); i++ ) + if ( item->IsCategory() ) { - wxPGProperty* sp = pwc->Item( i ); - if ( sp->GetBaseName().Len() ) m_dictName.erase(sp->GetBaseName()); + if ( pwc == m_currentCategory ) + m_currentCategory = (wxPropertyCategory*) NULL; } - if ( pwc == m_currentCategory ) - m_currentCategory = (wxPropertyCategory*) NULL; - - if ( m_abcArray ) - { - // Remove children from non-categorized array. - for ( i=0; iGetChildCount(); i++ ) - { - wxPGProperty * p = pwc->Item( i ); - wxASSERT( p != NULL ); - if ( !p->IsCategory() ) - m_abcArray->m_children.Remove( p ); - } - - if ( IsInNonCatMode() ) - m_abcArray->FixIndexesOfChildren(); - } + item->DeleteChildren(); } if ( !IsInNonCatMode() ) { // categorized mode - non-categorized array - // Remove from non-cat array, but only if parent is in it - if ( !item->IsCategory() && item->GetParent()->IsCategory() ) + // Remove from non-cat array + if ( !item->IsCategory() && + (parent->IsCategory() || parent->IsRoot()) ) { if ( m_abcArray ) - { - m_abcArray->m_children.Remove( item ); - } + m_abcArray->RemoveChild(item); } // categorized mode - categorized array - item->m_parent->m_children.RemoveAt(indinparent); - item->m_parent->FixIndexesOfChildren(/*indinparent*/); + wxArrayPGProperty& parentsChildren = parent->m_children; + parentsChildren.erase( parentsChildren.begin() + indinparent ); + item->m_parent->FixIndicesOfChildren(); } else { @@ -1856,21 +1767,25 @@ void wxPropertyGridPageState::DoDelete( wxPGProperty* item ) } } } - cat_parent->m_children.RemoveAt(cat_index); + cat_parent->m_children.erase(cat_parent->m_children.begin()+cat_index); // non-categorized mode - non-categorized array if ( !item->IsCategory() ) { wxASSERT( item->m_parent == m_abcArray ); - item->m_parent->m_children.RemoveAt(indinparent); - item->m_parent->FixIndexesOfChildren(indinparent); + wxArrayPGProperty& parentsChildren = item->m_parent->m_children; + parentsChildren.erase(parentsChildren.begin() + indinparent); + item->m_parent->FixIndicesOfChildren(indinparent); } } - if ( item->GetBaseName().Len() ) m_dictName.erase(item->GetBaseName()); + if ( item->GetBaseName().length() && + (parent->IsCategory() || parent->IsRoot()) ) + m_dictName.erase(item->GetBaseName()); // We can actually delete it now - delete item; + if ( doDelete ) + delete item; m_itemsAdded = 1; // Not a logical assignment (but required nonetheless).