// Purpose: wxDataViewCtrl base classes and common parts
// Author: Robert Roebling
// Created: 2006/02/20
-// RCS-ID: $Id$
// Copyright: (c) 2006, Robert Roebling
// Licence: wxWindows licence
/////////////////////////////////////////////////////////////////////////////
int wxDataViewModel::Compare( const wxDataViewItem &item1, const wxDataViewItem &item2,
unsigned int column, bool ascending ) const
{
- // sort branches before leaves
- bool item1_is_container = IsContainer(item1);
- bool item2_is_container = IsContainer(item2);
-
- if (item1_is_container && !item2_is_container)
- return 1;
- if (item2_is_container && !item1_is_container)
- return -1;
-
wxVariant value1,value2;
GetValue( value1, item1, column );
GetValue( value2, item2, column );
return wxDataViewItem( m_hash[row] );
}
-bool wxDataViewIndexListModel::HasDefaultCompare() const
-{
- return !m_ordered;
-}
-
-int wxDataViewIndexListModel::Compare(const wxDataViewItem& item1,
- const wxDataViewItem& item2,
- unsigned int WXUNUSED(column),
- bool ascending) const
-{
- if (m_ordered)
- {
- unsigned int pos1 = wxPtrToUInt(item1.GetID()); // -1 not needed here
- unsigned int pos2 = wxPtrToUInt(item2.GetID()); // -1 not needed here
-
- if (ascending)
- return pos1 - pos2;
- else
- return pos2 - pos1;
- }
-
- if (ascending)
- return GetRow(item1) - GetRow(item2);
-
- return GetRow(item2) - GetRow(item1);
-}
-
unsigned int wxDataViewIndexListModel::GetChildren( const wxDataViewItem &item, wxDataViewItemArray &children ) const
{
if (item.IsOk())
wxDataViewCtrl* dv_ctrl = GetOwner()->GetOwner();
// Before doing anything we send an event asking if editing of this item is really wanted.
- wxDataViewEvent start_event( wxEVT_COMMAND_DATAVIEW_ITEM_START_EDITING, dv_ctrl->GetId() );
+ wxDataViewEvent start_event( wxEVT_DATAVIEW_ITEM_START_EDITING, dv_ctrl->GetId() );
start_event.SetDataViewColumn( GetOwner() );
start_event.SetModel( dv_ctrl->GetModel() );
start_event.SetItem( item );
#endif
// Now we should send Editing Started event
- wxDataViewEvent event( wxEVT_COMMAND_DATAVIEW_ITEM_EDITING_STARTED, dv_ctrl->GetId() );
+ wxDataViewEvent event( wxEVT_DATAVIEW_ITEM_EDITING_STARTED, dv_ctrl->GetId() );
event.SetDataViewColumn( GetOwner() );
event.SetModel( dv_ctrl->GetModel() );
event.SetItem( item );
wxPendingDelete.Append(handler);
wxPendingDelete.Append(m_editorCtrl);
- m_editorCtrl = NULL;
+ // Ensure that DestroyEditControl() is not called again for this control.
+ m_editorCtrl.Release();
}
void wxDataViewRendererBase::CancelEditing()
unsigned int col = GetOwner()->GetModelColumn();
// Now we should send Editing Done event
- wxDataViewEvent event( wxEVT_COMMAND_DATAVIEW_ITEM_EDITING_DONE, dv_ctrl->GetId() );
+ wxDataViewEvent event( wxEVT_DATAVIEW_ITEM_EDITING_DONE, dv_ctrl->GetId() );
event.SetDataViewColumn( GetOwner() );
event.SetModel( dv_ctrl->GetModel() );
event.SetItem( m_item );
}
+int wxDataViewRendererBase::GetEffectiveAlignment() const
+{
+ int alignment = GetAlignment();
+
+ if ( alignment == wxDVR_DEFAULT_ALIGNMENT )
+ {
+ // if we don't have an explicit alignment ourselves, use that of the
+ // column in horizontal direction and default vertical alignment
+ alignment = GetOwner()->GetAlignment() | wxALIGN_CENTRE_VERTICAL;
+ }
+
+ return alignment;
+}
+
// ----------------------------------------------------------------------------
// wxDataViewCustomRendererBase
// ----------------------------------------------------------------------------
return Activate(cell, model, item, col);
}
+void wxDataViewCustomRendererBase::RenderBackground(wxDC* dc, const wxRect& rect)
+{
+ if ( !m_attr.HasBackgroundColour() )
+ return;
+
+ const wxColour& colour = m_attr.GetBackgroundColour();
+ wxDCPenChanger changePen(*dc, colour);
+ wxDCBrushChanger changeBrush(*dc, colour);
+
+ dc->DrawRectangle(rect);
+}
+
void
wxDataViewCustomRendererBase::WXCallRender(wxRect rectCell, wxDC *dc, int state)
{
// adjust the rectangle ourselves to account for the alignment
wxRect rectItem = rectCell;
- const int align = GetAlignment();
- if ( align != wxDVR_DEFAULT_ALIGNMENT )
- {
- const wxSize size = GetSize();
+ const int align = GetEffectiveAlignment();
- // take alignment into account only if there is enough space, otherwise
- // show as much contents as possible
- //
- // notice that many existing renderers (e.g. wxDataViewSpinRenderer)
- // return hard-coded size which can be more than they need and if we
- // trusted their GetSize() we'd draw the text out of cell bounds
- // entirely
+ const wxSize size = GetSize();
- if ( size.x >= 0 && size.x < rectCell.width )
- {
- if ( align & wxALIGN_CENTER_HORIZONTAL )
- rectItem.x += (rectCell.width - size.x)/2;
- else if ( align & wxALIGN_RIGHT )
- rectItem.x += rectCell.width - size.x;
- // else: wxALIGN_LEFT is the default
+ // take alignment into account only if there is enough space, otherwise
+ // show as much contents as possible
+ //
+ // notice that many existing renderers (e.g. wxDataViewSpinRenderer)
+ // return hard-coded size which can be more than they need and if we
+ // trusted their GetSize() we'd draw the text out of cell bounds
+ // entirely
- rectItem.width = size.x;
- }
+ if ( size.x >= 0 && size.x < rectCell.width )
+ {
+ if ( align & wxALIGN_CENTER_HORIZONTAL )
+ rectItem.x += (rectCell.width - size.x)/2;
+ else if ( align & wxALIGN_RIGHT )
+ rectItem.x += rectCell.width - size.x;
+ // else: wxALIGN_LEFT is the default
- if ( size.y >= 0 && size.y < rectCell.height )
- {
- if ( align & wxALIGN_CENTER_VERTICAL )
- rectItem.y += (rectCell.height - size.y)/2;
- else if ( align & wxALIGN_BOTTOM )
- rectItem.y += rectCell.height - size.y;
- // else: wxALIGN_TOP is the default
+ rectItem.width = size.x;
+ }
- rectItem.height = size.y;
- }
+ if ( size.y >= 0 && size.y < rectCell.height )
+ {
+ if ( align & wxALIGN_CENTER_VERTICAL )
+ rectItem.y += (rectCell.height - size.y)/2;
+ else if ( align & wxALIGN_BOTTOM )
+ rectItem.y += rectCell.height - size.y;
+ // else: wxALIGN_TOP is the default
+
+ rectItem.height = size.y;
}
}
// get the alignment to use
- int align = GetAlignment();
- if ( align == wxDVR_DEFAULT_ALIGNMENT )
- {
- // if we don't have an explicit alignment ourselves, use that of the
- // column in horizontal direction and default vertical alignment
- align = GetOwner()->GetAlignment() | wxALIGN_CENTRE_VERTICAL;
- }
-
dc->DrawLabel(ellipsizedText.empty() ? text : ellipsizedText,
- rectText, align);
+ rectText, GetEffectiveAlignment());
}
//-----------------------------------------------------------------------------
return true;
}
+void wxDataViewCtrlBase::StartEditor(const wxDataViewItem& item, unsigned int column)
+{
+ EditItem(item, GetColumn(column));
+}
+
// ---------------------------------------------------------
// wxDataViewEvent
// ---------------------------------------------------------
IMPLEMENT_DYNAMIC_CLASS(wxDataViewEvent,wxNotifyEvent)
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_SELECTION_CHANGED, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_SELECTION_CHANGED, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_ACTIVATED, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_COLLAPSING, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_COLLAPSED, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_EXPANDING, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_EXPANDED, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_EDITING_STARTED, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_START_EDITING, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_EDITING_DONE, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_VALUE_CHANGED, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_ACTIVATED, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_COLLAPSING, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_COLLAPSED, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_EXPANDING, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_EXPANDED, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_EDITING_STARTED, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_START_EDITING, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_EDITING_DONE, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_VALUE_CHANGED, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_CONTEXT_MENU, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_CONTEXT_MENU, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_COLUMN_HEADER_CLICK, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_COLUMN_HEADER_RIGHT_CLICK, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_COLUMN_SORTED, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_COLUMN_REORDERED, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_COLUMN_HEADER_CLICK, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_COLUMN_HEADER_RIGHT_CLICK, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_COLUMN_SORTED, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_COLUMN_REORDERED, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_CACHE_HINT, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_CACHE_HINT, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_BEGIN_DRAG, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_DROP_POSSIBLE, wxDataViewEvent );
-wxDEFINE_EVENT( wxEVT_COMMAND_DATAVIEW_ITEM_DROP, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_BEGIN_DRAG, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_DROP_POSSIBLE, wxDataViewEvent );
+wxDEFINE_EVENT( wxEVT_DATAVIEW_ITEM_DROP, wxDataViewEvent );
return m_cols.GetCount();
}
+unsigned int wxDataViewListStore::GetItemCount() const
+{
+ return m_data.size();
+}
+
wxString wxDataViewListStore::GetColumnType( unsigned int pos ) const
{
return m_cols[pos];
}
-void wxDataViewListStore::AppendItem( const wxVector<wxVariant> &values, wxClientData *data )
+void wxDataViewListStore::AppendItem( const wxVector<wxVariant> &values, wxUIntPtr data )
{
wxDataViewListStoreLine *line = new wxDataViewListStoreLine( data );
line->m_values = values;
RowAppended();
}
-void wxDataViewListStore::PrependItem( const wxVector<wxVariant> &values, wxClientData *data )
+void wxDataViewListStore::PrependItem( const wxVector<wxVariant> &values, wxUIntPtr data )
{
wxDataViewListStoreLine *line = new wxDataViewListStoreLine( data );
line->m_values = values;
}
void wxDataViewListStore::InsertItem( unsigned int row, const wxVector<wxVariant> &values,
- wxClientData *data )
+ wxUIntPtr data )
{
wxDataViewListStoreLine *line = new wxDataViewListStoreLine( data );
line->m_values = values;
Reset( 0 );
}
+void wxDataViewListStore::SetItemData( const wxDataViewItem& item, wxUIntPtr data )
+{
+ wxDataViewListStoreLine* line = m_data[GetRow(item)];
+ if (!line) return;
+
+ line->SetData( data );
+}
+
+wxUIntPtr wxDataViewListStore::GetItemData( const wxDataViewItem& item ) const
+{
+ wxDataViewListStoreLine* line = m_data[GetRow(item)];
+ if (!line) return static_cast<wxUIntPtr>(NULL);
+
+ return line->GetData();
+}
+
void wxDataViewListStore::GetValueByRow( wxVariant &value, unsigned int row, unsigned int col ) const
{
wxDataViewListStoreLine *line = m_data[row];
wxDataViewTreeStoreContainerNode *parent_node = FindContainerNode( parent_item );
if (!parent_node) return;
- wxDataViewTreeStoreContainerNode *node = FindContainerNode( item );
- if (!node) return;
-
- parent_node->GetChildren().DeleteObject( node );
+ parent_node->GetChildren().DeleteObject( FindNode(item) );
}
void wxDataViewTreeStore::DeleteChildren( const wxDataViewItem& item )