support column reordering using drag and drop when using wxHeaderCtrl
git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@57301 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
@@ -2133,7 +2133,6 @@ protected:
|
||||
|
||||
//Column positions
|
||||
wxArrayInt m_colAt;
|
||||
int m_moveToCol;
|
||||
|
||||
bool m_canDragRowSize;
|
||||
bool m_canDragColSize;
|
||||
@@ -2293,10 +2292,11 @@ private:
|
||||
void DoStartResizeCol(int col);
|
||||
void DoUpdateResizeCol(int x);
|
||||
void DoUpdateResizeColWidth(int w);
|
||||
void DoStartMoveCol(int col);
|
||||
|
||||
void DoEndDragResizeRow();
|
||||
void DoEndDragResizeCol(wxMouseEvent *event = NULL);
|
||||
void DoEndDragMoveCol();
|
||||
void DoEndMoveCol(int pos);
|
||||
|
||||
|
||||
// common implementations of methods defined for both rows and columns
|
||||
|
@@ -3161,6 +3161,18 @@ public:
|
||||
@event{EVT_GRID_SELECT_CELL(func)}
|
||||
The user moved to, and selected a cell. Processes a
|
||||
@c wxEVT_GRID_SELECT_CELL event type.
|
||||
@event{EVT_GRID_COL_MOVE(func)}
|
||||
The user tries to change the order of the columns in the grid by
|
||||
dragging the column specified by GetCol(). This event can be vetoed to
|
||||
either prevent the user from reordering the column change completely
|
||||
(but notice that if you don't want to allow it at all, you simply
|
||||
shouldn't call wxGrid::EnableDragColMove() in the first place), vetoed
|
||||
but handled in some way in the handler, e.g. by really moving the
|
||||
column to the new position at the associated table level, or allowed to
|
||||
proceed in which case wxGrid::SetColPos() is used to reorder the
|
||||
columns display order without affecting the use of the column indices
|
||||
otherwise.
|
||||
This event macro corresponds to @c wxEVT_GRID_COL_MOVE event type.
|
||||
@event{EVT_GRID_CMD_CELL_CHANGE(id, func)}
|
||||
The user changed the data in a cell; variant taking a window
|
||||
identifier. Processes a @c wxEVT_GRID_CELL_CHANGE event type.
|
||||
|
@@ -1641,7 +1641,9 @@ public:
|
||||
private:
|
||||
enum // control ids
|
||||
{
|
||||
Id_Check_UseNative,
|
||||
Id_Check_UseNativeHeader,
|
||||
Id_Check_DrawNativeLabels,
|
||||
Id_Check_ShowRowLabels,
|
||||
Id_Check_EnableColMove
|
||||
};
|
||||
|
||||
@@ -1649,7 +1651,26 @@ private:
|
||||
|
||||
void OnToggleUseNativeHeader(wxCommandEvent&)
|
||||
{
|
||||
m_grid->SetUseNativeColLabels(m_chkUseNative->IsChecked());
|
||||
m_grid->UseNativeColHeader(m_chkUseNative->IsChecked());
|
||||
}
|
||||
|
||||
void OnUpdateDrawNativeLabelsUI(wxUpdateUIEvent& event)
|
||||
{
|
||||
// we don't draw labels at all, native or otherwise, if we use the
|
||||
// native header control
|
||||
event.Enable( !m_chkUseNative->GetValue() );
|
||||
}
|
||||
|
||||
void OnToggleDrawNativeLabels(wxCommandEvent&)
|
||||
{
|
||||
m_grid->SetUseNativeColLabels(m_chkDrawNative->IsChecked());
|
||||
}
|
||||
|
||||
void OnToggleShowRowLabels(wxCommandEvent&)
|
||||
{
|
||||
m_grid->SetRowLabelSize(m_chkShowRowLabels->IsChecked()
|
||||
? wxGRID_AUTOSIZE
|
||||
: 0);
|
||||
}
|
||||
|
||||
void OnToggleColMove(wxCommandEvent&)
|
||||
@@ -1671,7 +1692,20 @@ private:
|
||||
|
||||
void OnGridColMove(wxGridEvent& event)
|
||||
{
|
||||
// can't update it yet as the order hasn't been changed, so do it a bit
|
||||
// later
|
||||
m_shouldUpdateOrder = true;
|
||||
|
||||
event.Skip();
|
||||
}
|
||||
|
||||
void OnIdle(wxIdleEvent& event)
|
||||
{
|
||||
if ( m_shouldUpdateOrder )
|
||||
{
|
||||
m_shouldUpdateOrder = false;
|
||||
UpdateOrder();
|
||||
}
|
||||
|
||||
event.Skip();
|
||||
}
|
||||
@@ -1688,6 +1722,8 @@ private:
|
||||
// controls
|
||||
wxGrid *m_grid;
|
||||
wxCheckBox *m_chkUseNative,
|
||||
*m_chkDrawNative,
|
||||
*m_chkShowRowLabels,
|
||||
*m_chkEnableColMove;
|
||||
|
||||
ColIndexEntry *m_txtColIndex,
|
||||
@@ -1695,28 +1731,49 @@ private:
|
||||
|
||||
wxStaticText *m_statOrder;
|
||||
|
||||
// fla for EVT_IDLE handler
|
||||
bool m_shouldUpdateOrder;
|
||||
|
||||
DECLARE_NO_COPY_CLASS(TabularGridFrame)
|
||||
DECLARE_EVENT_TABLE()
|
||||
};
|
||||
|
||||
BEGIN_EVENT_TABLE(TabularGridFrame, wxFrame)
|
||||
EVT_CHECKBOX(Id_Check_UseNative, TabularGridFrame::OnToggleUseNativeHeader)
|
||||
EVT_CHECKBOX(Id_Check_EnableColMove, TabularGridFrame::OnToggleColMove)
|
||||
EVT_CHECKBOX(Id_Check_UseNativeHeader,
|
||||
TabularGridFrame::OnToggleUseNativeHeader)
|
||||
EVT_CHECKBOX(Id_Check_DrawNativeLabels,
|
||||
TabularGridFrame::OnToggleDrawNativeLabels)
|
||||
EVT_CHECKBOX(Id_Check_ShowRowLabels,
|
||||
TabularGridFrame::OnToggleShowRowLabels)
|
||||
EVT_CHECKBOX(Id_Check_EnableColMove,
|
||||
TabularGridFrame::OnToggleColMove)
|
||||
|
||||
EVT_UPDATE_UI(Id_Check_DrawNativeLabels,
|
||||
TabularGridFrame::OnUpdateDrawNativeLabelsUI)
|
||||
|
||||
EVT_BUTTON(wxID_APPLY, TabularGridFrame::OnMoveColumn)
|
||||
|
||||
EVT_GRID_COL_MOVE(TabularGridFrame::OnGridColMove)
|
||||
|
||||
EVT_IDLE(TabularGridFrame::OnIdle)
|
||||
END_EVENT_TABLE()
|
||||
|
||||
TabularGridFrame::TabularGridFrame()
|
||||
: wxFrame(NULL, wxID_ANY, "Tabular table")
|
||||
{
|
||||
m_shouldUpdateOrder = false;
|
||||
|
||||
wxPanel * const panel = new wxPanel(this);
|
||||
|
||||
// create and initialize the grid with the specified data
|
||||
m_grid = new wxGrid(this, wxID_ANY);
|
||||
m_grid = new wxGrid(panel, wxID_ANY,
|
||||
wxDefaultPosition, wxDefaultSize,
|
||||
wxBORDER_STATIC | wxWANTS_CHARS);
|
||||
m_grid->SetTable(new TabularGridTable, true, wxGrid::wxGridSelectRows);
|
||||
|
||||
m_grid->SetUseNativeColLabels();
|
||||
m_grid->EnableDragColMove();
|
||||
m_grid->UseNativeColHeader();
|
||||
m_grid->HideRowLabels();
|
||||
|
||||
// add it and the other controls to the frame
|
||||
wxSizer * const sizerTop = new wxBoxSizer(wxVERTICAL);
|
||||
@@ -1725,12 +1782,20 @@ TabularGridFrame::TabularGridFrame()
|
||||
wxSizer * const sizerControls = new wxBoxSizer(wxHORIZONTAL);
|
||||
|
||||
wxSizer * const sizerStyles = new wxBoxSizer(wxVERTICAL);
|
||||
m_chkUseNative = new wxCheckBox(this, Id_Check_UseNative,
|
||||
m_chkUseNative = new wxCheckBox(panel, Id_Check_UseNativeHeader,
|
||||
"&Use native header");
|
||||
m_chkUseNative->SetValue(true);
|
||||
sizerStyles->Add(m_chkUseNative, wxSizerFlags().Border());
|
||||
|
||||
m_chkEnableColMove = new wxCheckBox(this, Id_Check_EnableColMove,
|
||||
m_chkDrawNative = new wxCheckBox(panel, Id_Check_DrawNativeLabels,
|
||||
"&Draw native column labels");
|
||||
sizerStyles->Add(m_chkDrawNative, wxSizerFlags().Border());
|
||||
|
||||
m_chkShowRowLabels = new wxCheckBox(panel, Id_Check_ShowRowLabels,
|
||||
"Show &row labels");
|
||||
sizerStyles->Add(m_chkShowRowLabels, wxSizerFlags().Border());
|
||||
|
||||
m_chkEnableColMove = new wxCheckBox(panel, Id_Check_EnableColMove,
|
||||
"Allow column re&ordering");
|
||||
m_chkEnableColMove->SetValue(true);
|
||||
sizerStyles->Add(m_chkEnableColMove, wxSizerFlags().Border());
|
||||
@@ -1742,21 +1807,21 @@ TabularGridFrame::TabularGridFrame()
|
||||
wxSizer * const sizerMoveCols = new wxBoxSizer(wxHORIZONTAL);
|
||||
const wxSizerFlags
|
||||
flagsHorz(wxSizerFlags().Border(wxLEFT | wxRIGHT).Centre());
|
||||
sizerMoveCols->Add(new wxStaticText(this, wxID_ANY, "&Move column"),
|
||||
sizerMoveCols->Add(new wxStaticText(panel, wxID_ANY, "&Move column"),
|
||||
flagsHorz);
|
||||
m_txtColIndex = new ColIndexEntry(this);
|
||||
m_txtColIndex = new ColIndexEntry(panel);
|
||||
sizerMoveCols->Add(m_txtColIndex, flagsHorz);
|
||||
sizerMoveCols->Add(new wxStaticText(this, wxID_ANY, "&to"), flagsHorz);
|
||||
m_txtColPos = new ColIndexEntry(this);
|
||||
sizerMoveCols->Add(new wxStaticText(panel, wxID_ANY, "&to"), flagsHorz);
|
||||
m_txtColPos = new ColIndexEntry(panel);
|
||||
sizerMoveCols->Add(m_txtColPos, flagsHorz);
|
||||
sizerMoveCols->Add(new wxButton(this, wxID_APPLY), flagsHorz);
|
||||
sizerMoveCols->Add(new wxButton(panel, wxID_APPLY), flagsHorz);
|
||||
|
||||
sizerColumns->Add(sizerMoveCols, wxSizerFlags().Expand().Border(wxBOTTOM));
|
||||
|
||||
wxSizer * const sizerShowCols = new wxBoxSizer(wxHORIZONTAL);
|
||||
sizerShowCols->Add(new wxStaticText(this, wxID_ANY, "Current order:"),
|
||||
sizerShowCols->Add(new wxStaticText(panel, wxID_ANY, "Current order:"),
|
||||
flagsHorz);
|
||||
m_statOrder = new wxStaticText(this, wxID_ANY, "<default>");
|
||||
m_statOrder = new wxStaticText(panel, wxID_ANY, "<default>");
|
||||
sizerShowCols->Add(m_statOrder, flagsHorz);
|
||||
sizerColumns->Add(sizerShowCols, wxSizerFlags().Expand().Border(wxTOP));
|
||||
|
||||
@@ -1764,8 +1829,11 @@ TabularGridFrame::TabularGridFrame()
|
||||
|
||||
sizerTop->Add(sizerControls, wxSizerFlags().Expand().Border());
|
||||
|
||||
SetSizerAndFit(sizerTop);
|
||||
SetBackgroundColour(*wxWHITE);
|
||||
panel->SetSizer(sizerTop);
|
||||
|
||||
SetClientSize(panel->GetBestSize());
|
||||
SetSizeHints(GetSize());
|
||||
|
||||
Show();
|
||||
}
|
||||
|
||||
@@ -1773,4 +1841,3 @@ void GridFrame::OnTabularTable(wxCommandEvent&)
|
||||
{
|
||||
new TabularGridFrame;
|
||||
}
|
||||
|
||||
|
@@ -275,9 +275,14 @@ private:
|
||||
event.Skip();
|
||||
}
|
||||
|
||||
void OnBeginReorder(wxHeaderCtrlEvent& event)
|
||||
{
|
||||
GetOwner()->DoStartMoveCol(event.GetColumn());
|
||||
}
|
||||
|
||||
void OnEndReorder(wxHeaderCtrlEvent& event)
|
||||
{
|
||||
event.Skip(); // TODO: position it at event.GetNewOrder()
|
||||
GetOwner()->DoEndMoveCol(event.GetNewOrder());
|
||||
}
|
||||
|
||||
wxVector<wxGridHeaderColumn> m_columns;
|
||||
@@ -291,6 +296,7 @@ BEGIN_EVENT_TABLE(wxGridHeaderCtrl, wxHeaderCtrl)
|
||||
EVT_HEADER_RESIZING(wxID_ANY, wxGridHeaderCtrl::OnResizing)
|
||||
EVT_HEADER_END_RESIZE(wxID_ANY, wxGridHeaderCtrl::OnEndResize)
|
||||
|
||||
EVT_HEADER_BEGIN_REORDER(wxID_ANY, wxGridHeaderCtrl::OnBeginReorder)
|
||||
EVT_HEADER_END_REORDER(wxID_ANY, wxGridHeaderCtrl::OnEndReorder)
|
||||
END_EVENT_TABLE()
|
||||
|
||||
@@ -5888,7 +5894,7 @@ void wxGrid::ProcessColLabelMouseEvent( wxMouseEvent& event )
|
||||
GetColLabelWindow()->CaptureMouse();
|
||||
|
||||
if ( m_cursorMode == WXGRID_CURSOR_MOVE_COL )
|
||||
m_dragRowOrCol = XToCol( x );
|
||||
DoStartMoveCol(XToCol(x));
|
||||
}
|
||||
|
||||
if ( event.LeftIsDown() )
|
||||
@@ -5911,25 +5917,15 @@ void wxGrid::ProcessColLabelMouseEvent( wxMouseEvent& event )
|
||||
|
||||
case WXGRID_CURSOR_MOVE_COL:
|
||||
{
|
||||
if ( x < 0 )
|
||||
m_moveToCol = GetColAt( 0 );
|
||||
else
|
||||
m_moveToCol = XToCol( x );
|
||||
int posNew = XToPos(x);
|
||||
int colNew = GetColAt(posNew);
|
||||
|
||||
// determine the position of the drop marker
|
||||
int markerX;
|
||||
|
||||
if ( m_moveToCol < 0 )
|
||||
markerX = GetColRight( GetColAt( m_numCols - 1 ) );
|
||||
else if ( x >= (GetColLeft( m_moveToCol ) + (GetColWidth(m_moveToCol) / 2)) )
|
||||
{
|
||||
m_moveToCol = GetColAt( GetColPos( m_moveToCol ) + 1 );
|
||||
if ( m_moveToCol < 0 )
|
||||
markerX = GetColRight( GetColAt( m_numCols - 1 ) );
|
||||
if ( x >= GetColLeft(colNew) + (GetColWidth(colNew) / 2) )
|
||||
markerX = GetColRight(colNew);
|
||||
else
|
||||
markerX = GetColLeft( m_moveToCol );
|
||||
}
|
||||
else
|
||||
markerX = GetColLeft( m_moveToCol );
|
||||
markerX = GetColLeft(colNew);
|
||||
|
||||
if ( markerX != m_dragLastPos )
|
||||
{
|
||||
@@ -5955,9 +5951,7 @@ void wxGrid::ProcessColLabelMouseEvent( wxMouseEvent& event )
|
||||
|
||||
const wxColour *color;
|
||||
//Moving to the same place? Don't draw a marker
|
||||
if ( (m_moveToCol == m_dragRowOrCol)
|
||||
|| (GetColPos( m_moveToCol ) == GetColPos( m_dragRowOrCol ) + 1)
|
||||
|| (m_moveToCol < 0 && m_dragRowOrCol == GetColAt( m_numCols - 1 )))
|
||||
if ( colNew == m_dragRowOrCol )
|
||||
color = wxLIGHT_GREY;
|
||||
else
|
||||
color = wxBLUE;
|
||||
@@ -6096,9 +6090,15 @@ void wxGrid::ProcessColLabelMouseEvent( wxMouseEvent& event )
|
||||
break;
|
||||
|
||||
case WXGRID_CURSOR_MOVE_COL:
|
||||
DoEndDragMoveCol();
|
||||
|
||||
SendEvent( wxEVT_GRID_COL_MOVE, -1, m_dragRowOrCol, event );
|
||||
if ( m_dragLastPos == -1 )
|
||||
{
|
||||
// The user clicked on the column but didn't actually drag
|
||||
m_colWindow->Refresh(); // "unpress" the column
|
||||
}
|
||||
else
|
||||
{
|
||||
DoEndMoveCol(XToPos(x));
|
||||
}
|
||||
break;
|
||||
|
||||
case WXGRID_CURSOR_SELECT_COL:
|
||||
@@ -6763,26 +6763,20 @@ void wxGrid::DoEndDragResizeCol(wxMouseEvent *event)
|
||||
SendEvent( wxEVT_GRID_COL_SIZE, -1, m_dragRowOrCol );
|
||||
}
|
||||
|
||||
void wxGrid::DoEndDragMoveCol()
|
||||
void wxGrid::DoStartMoveCol(int col)
|
||||
{
|
||||
//The user clicked on the column but didn't actually drag
|
||||
if ( m_dragLastPos < 0 )
|
||||
{
|
||||
m_colWindow->Refresh(); //Do this to "unpress" the column
|
||||
return;
|
||||
}
|
||||
m_dragRowOrCol = col;
|
||||
}
|
||||
|
||||
int newPos;
|
||||
if ( m_moveToCol == -1 )
|
||||
newPos = m_numCols - 1;
|
||||
else
|
||||
{
|
||||
newPos = GetColPos( m_moveToCol );
|
||||
if ( newPos > GetColPos( m_dragRowOrCol ) )
|
||||
newPos--;
|
||||
}
|
||||
void wxGrid::DoEndMoveCol(int pos)
|
||||
{
|
||||
wxASSERT_MSG( m_dragRowOrCol != -1, "no matching DoStartMoveCol?" );
|
||||
|
||||
SetColPos( m_dragRowOrCol, newPos );
|
||||
if ( SendEvent(wxEVT_GRID_COL_MOVE, -1, m_dragRowOrCol) != -1 )
|
||||
SetColPos(m_dragRowOrCol, pos);
|
||||
//else: vetoed by user
|
||||
|
||||
m_dragRowOrCol = -1;
|
||||
}
|
||||
|
||||
void wxGrid::SetColPos(int idx, int pos)
|
||||
|
Reference in New Issue
Block a user