From c232dfe592d5f766c33ef91ac38fda44b10b1236 Mon Sep 17 00:00:00 2001 From: Robert Roebling Date: Fri, 11 Apr 2008 10:40:58 +0000 Subject: [PATCH] Add test for context menu, fixed mem leak, fixed focus problem when re-editing same item git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@53126 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775 --- include/wx/dataview.h | 4 +++- samples/dataview/dataview.cpp | 12 +++++++++--- src/common/datavcmn.cpp | 36 +++++++++++++++++++++++------------ src/gtk/dataview.cpp | 6 ++++++ 4 files changed, 42 insertions(+), 16 deletions(-) diff --git a/include/wx/dataview.h b/include/wx/dataview.h index c2db8eef48..dca249147a 100644 --- a/include/wx/dataview.h +++ b/include/wx/dataview.h @@ -23,6 +23,7 @@ #include "wx/dynarray.h" #include "wx/icon.h" #include "wx/imaglist.h" +#include "wx/weakref.h" class WXDLLIMPEXP_FWD_CORE wxDataFormat; @@ -413,6 +414,7 @@ public: wxDataViewRendererBase( const wxString &varianttype, wxDataViewCellMode mode = wxDATAVIEW_CELL_INERT, int alignment = wxDVR_DEFAULT_ALIGNMENT ); + ~wxDataViewRendererBase(); virtual bool Validate( wxVariant& WXUNUSED(value) ) { return true; } @@ -456,7 +458,7 @@ public: protected: wxString m_variantType; wxDataViewColumn *m_owner; - wxControl *m_editorCtrl; + wxWeakRef m_editorCtrl; wxDataViewItem m_item; // for m_editorCtrl // internal utility: diff --git a/samples/dataview/dataview.cpp b/samples/dataview/dataview.cpp index 8e216d8ea6..14d66161b2 100644 --- a/samples/dataview/dataview.cpp +++ b/samples/dataview/dataview.cpp @@ -27,9 +27,7 @@ #include "wx/numdlg.h" #include "wx/dataview.h" #include "wx/spinctrl.h" - -#include "wx/ptr_shrd.h" -#include "wx/vector.h" +#include "wx/menu.h" #ifndef __WXMSW__ #include "../sample.xpm" @@ -1039,6 +1037,14 @@ void MyFrame::OnContextMenu( wxDataViewEvent &event ) wxString title = m_music_model->GetTitle( event.GetItem() ); wxLogMessage(wxT("wxEVT_COMMAND_DATAVIEW_ITEM_CONTEXT_MENU, Item: %s"),title.GetData()); + + wxMenu *menu = new wxMenu; + menu->Append( 1, wxT("entry 1") ); + menu->Append( 2, wxT("entry 2") ); + menu->Append( 3, wxT("entry 3") ); + + m_musicCtrl->PopupMenu( menu ); + // wxLogMessage(wxT("wxEVT_COMMAND_DATAVIEW_ITEM_CONTEXT_MENU, Item: %s Value: %s"),title.GetData(), event.GetValue().GetString()); } diff --git a/src/common/datavcmn.cpp b/src/common/datavcmn.cpp index 645aa4ed0e..7f85194b9b 100644 --- a/src/common/datavcmn.cpp +++ b/src/common/datavcmn.cpp @@ -18,9 +18,10 @@ #if wxUSE_DATAVIEWCTRL #include "wx/dataview.h" - #include "wx/spinctrl.h" +#include "wx/weakref.h" + #ifndef WX_PRECOMP #include "wx/dc.h" #include "wx/settings.h" @@ -658,15 +659,29 @@ wxDataViewRendererBase::wxDataViewRendererBase( const wxString &varianttype, int WXUNUSED(align) ) { m_variantType = varianttype; - m_editorCtrl = NULL; m_owner = NULL; } +wxDataViewRendererBase::~wxDataViewRendererBase() +{ +} + const wxDataViewCtrl* wxDataViewRendererBase::GetView() const { return wx_const_cast(wxDataViewRendererBase*, this)->GetOwner()->GetOwner(); } +class wxKillRef: public wxWindowRef +{ +public: + wxKillRef( wxWindow *win ) : wxWindowRef( win ) { } + virtual void OnObjectDestroy() + { + get()->PopEventHandler( true ); + delete this; + } +}; + bool wxDataViewRendererBase::StartEditing( const wxDataViewItem &item, wxRect labelRect ) { m_item = item; // remember for later @@ -676,6 +691,7 @@ bool wxDataViewRendererBase::StartEditing( const wxDataViewItem &item, wxRect la GetOwner()->GetOwner()->GetModel()->GetValue( value, item, col ); m_editorCtrl = CreateEditorCtrl( GetOwner()->GetOwner()->GetMainWindow(), labelRect, value ); + (void) new wxKillRef( m_editorCtrl.get() ); wxDataViewEditorCtrlEvtHandler *handler = new wxDataViewEditorCtrlEvtHandler( m_editorCtrl, (wxDataViewRenderer*) this ); @@ -700,11 +716,10 @@ bool wxDataViewRendererBase::StartEditing( const wxDataViewItem &item, wxRect la void wxDataViewRendererBase::CancelEditing() { - wxPendingDelete.Append( m_editorCtrl ); - GetOwner()->GetOwner()->GetMainWindow()->SetFocus(); - - // m_editorCtrl->PopEventHandler( true ); + + m_editorCtrl->Hide(); + wxPendingDelete.Append( m_editorCtrl ); } bool wxDataViewRendererBase::FinishEditing() @@ -712,10 +727,11 @@ bool wxDataViewRendererBase::FinishEditing() wxVariant value; GetValueFromEditorCtrl( m_editorCtrl, value ); - wxPendingDelete.Append( m_editorCtrl ); - GetOwner()->GetOwner()->GetMainWindow()->SetFocus(); + m_editorCtrl->Hide(); + wxPendingDelete.Append( m_editorCtrl ); + if (!Validate(value)) return false; @@ -723,8 +739,6 @@ bool wxDataViewRendererBase::FinishEditing() GetOwner()->GetOwner()->GetModel()->SetValue( value, m_item, col ); GetOwner()->GetOwner()->GetModel()->ValueChanged( m_item, col ); - // m_editorCtrl->PopEventHandler( true ); - // Now we should send Editing Done event wxDataViewEvent event( wxEVT_COMMAND_DATAVIEW_ITEM_EDITING_DONE, GetOwner()->GetOwner()->GetId() ); event.SetDataViewColumn( GetOwner() ); @@ -772,7 +786,6 @@ void wxDataViewEditorCtrlEvtHandler::OnChar( wxKeyEvent &event ) switch ( event.m_keyCode ) { case WXK_RETURN: - wxPrintf( "OnChar RETURN\n" ); m_finished = true; m_owner->FinishEditing(); break; @@ -791,7 +804,6 @@ void wxDataViewEditorCtrlEvtHandler::OnKillFocus( wxFocusEvent &event ) { if (!m_finished) { - wxPrintf( "OnKillFocus\n" ); m_finished = true; m_owner->FinishEditing(); } diff --git a/src/gtk/dataview.cpp b/src/gtk/dataview.cpp index 0ecca2c7f1..518590545f 100644 --- a/src/gtk/dataview.cpp +++ b/src/gtk/dataview.cpp @@ -975,8 +975,14 @@ static GtkCellEditable *gtk_wx_cell_renderer_start_editing( { GtkWxCellRenderer *wxrenderer = (GtkWxCellRenderer *) renderer; wxDataViewCustomRenderer *cell = wxrenderer->cell; + + // Renderer doesn't support in-place editing if (!cell->HasEditorCtrl()) return NULL; + + // An in-place editing control is still around + if (cell->GetEditorCtrl()) + return NULL; GdkRectangle rect; gtk_wx_cell_renderer_get_size (renderer, widget, cell_area, -- 2.45.2