+ ChangeCurrentRow( newCurrent );
+
+ if ( !event.ControlDown() )
+ {
+ SelectRow( m_currentRow, true );
+ SendSelectionChangedEvent(GetItemByRow(m_currentRow));
+ }
+ else
+ RefreshRow( m_currentRow );
+ }
+
+ GetOwner()->EnsureVisible( m_currentRow, -1 );
+}
+
+void wxDataViewMainWindow::OnLeftKey()
+{
+ if ( IsList() )
+ {
+ TryAdvanceCurrentColumn(NULL, /*forward=*/false);
+ }
+ else
+ {
+ wxDataViewTreeNode* node = GetTreeNodeByRow(m_currentRow);
+ if ( !node )
+ return;
+
+ if ( TryAdvanceCurrentColumn(node, /*forward=*/false) )
+ return;
+
+ // Because TryAdvanceCurrentColumn() return false, we are at the first
+ // column or using whole-row selection. In this situation, we can use
+ // the standard TreeView handling of the left key.
+ if (node->HasChildren() && node->IsOpen())
+ {
+ Collapse(m_currentRow);
+ }
+ else
+ {
+ // if the node is already closed, we move the selection to its parent
+ wxDataViewTreeNode *parent_node = node->GetParent();
+
+ if (parent_node)
+ {
+ int parent = GetRowByItem( parent_node->GetItem() );
+ if ( parent >= 0 )
+ {
+ unsigned int row = m_currentRow;
+ SelectRow( row, false);
+ SelectRow( parent, true );
+ ChangeCurrentRow( parent );
+ GetOwner()->EnsureVisible( parent, -1 );
+ SendSelectionChangedEvent( parent_node->GetItem() );
+ }
+ }
+ }
+ }
+}
+
+void wxDataViewMainWindow::OnRightKey()
+{
+ if ( IsList() )
+ {
+ TryAdvanceCurrentColumn(NULL, /*forward=*/true);
+ }
+ else
+ {
+ wxDataViewTreeNode* node = GetTreeNodeByRow(m_currentRow);
+ if ( !node )
+ return;
+
+ if ( node->HasChildren() )
+ {
+ if ( !node->IsOpen() )
+ {
+ Expand( m_currentRow );
+ }
+ else
+ {
+ // if the node is already open, we move the selection to the first child
+ unsigned int row = m_currentRow;
+ SelectRow( row, false );
+ SelectRow( row + 1, true );
+ ChangeCurrentRow( row + 1 );
+ GetOwner()->EnsureVisible( row + 1, -1 );
+ SendSelectionChangedEvent( GetItemByRow(row+1) );
+ }
+ }
+ else
+ {
+ TryAdvanceCurrentColumn(node, /*forward=*/true);
+ }
+ }
+}
+
+bool wxDataViewMainWindow::TryAdvanceCurrentColumn(wxDataViewTreeNode *node, bool forward)
+{
+ if ( GetOwner()->GetColumnCount() == 0 )
+ return false;
+
+ if ( !m_useCellFocus )
+ return false;
+
+ if ( node )
+ {
+ // navigation shouldn't work in branch nodes without other columns:
+ if ( node->HasChildren() && !GetModel()->HasContainerColumns(node->GetItem()) )
+ return false;
+ }
+
+ if ( m_currentCol == NULL || !m_currentColSetByKeyboard )
+ {
+ if ( forward )
+ {
+ m_currentCol = GetOwner()->GetColumnAt(1);
+ m_currentColSetByKeyboard = true;
+ RefreshRow(m_currentRow);
+ return true;
+ }
+ else
+ return false;
+ }
+
+ int idx = GetOwner()->GetColumnIndex(m_currentCol) + (forward ? +1 : -1);
+
+ if ( idx >= (int)GetOwner()->GetColumnCount() )
+ return false;
+
+ GetOwner()->EnsureVisible(m_currentRow, idx);
+
+ if ( idx < 1 )
+ {
+ // We are going to the left of the second column. Reset to whole-row
+ // focus (which means first column would be edited).
+ m_currentCol = NULL;
+ RefreshRow(m_currentRow);
+ return true;
+ }
+
+ m_currentCol = GetOwner()->GetColumnAt(idx);
+ m_currentColSetByKeyboard = true;
+ RefreshRow(m_currentRow);
+ return true;
+}
+
+void wxDataViewMainWindow::OnMouse( wxMouseEvent &event )
+{
+ if (event.GetEventType() == wxEVT_MOUSEWHEEL)
+ {
+ // let the base handle mouse wheel events.
+ event.Skip();
+ return;
+ }
+
+ if(event.ButtonDown())
+ {
+ // Not skipping button down events would prevent the system from
+ // setting focus to this window as most (all?) of them do by default,
+ // so skip it to enable default handling.
+ event.Skip();
+ }