1 ///////////////////////////////////////////////////////////////////////////
2 // Name: generic/gridsel.cpp
3 // Purpose: wxGridSelection
8 // Copyright: (c) Stefan Neis (Stefan.Neis@t-online.de)
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
12 // ============================================================================
14 // ============================================================================
16 // ----------------------------------------------------------------------------
18 // ----------------------------------------------------------------------------
20 // For compilers that support precompilation, includes "wx/wx.h".
21 #include "wx/wxprec.h"
31 #include "wx/generic/gridsel.h"
34 // Some explanation for the members of the class:
35 // m_cellSelection stores individual selected cells
36 // -- this is only used if m_selectionMode == wxGridSelectCells
37 // m_blockSelectionTopLeft and m_blockSelectionBottomRight
38 // store the upper left and lower right corner of selected Blocks
39 // m_rowSelection and m_colSelection store individual selected
40 // rows and columns; maybe those are superfluous and should be
43 wxGridSelection::wxGridSelection( wxGrid
* grid
,
44 wxGrid::wxGridSelectionModes sel
)
47 m_selectionMode
= sel
;
50 bool wxGridSelection::IsSelection()
52 return ( m_cellSelection
.GetCount() || m_blockSelectionTopLeft
.GetCount() ||
53 m_rowSelection
.GetCount() || m_colSelection
.GetCount() );
56 bool wxGridSelection::IsInSelection( int row
, int col
)
60 // First check whether the given cell is individually selected
61 // (if m_selectionMode is wxGridSelectCells).
62 if ( m_selectionMode
== wxGrid::wxGridSelectCells
)
64 count
= m_cellSelection
.GetCount();
65 for ( size_t n
= 0; n
< count
; n
++ )
67 wxGridCellCoords
& coords
= m_cellSelection
[n
];
68 if ( row
== coords
.GetRow() && col
== coords
.GetCol() )
73 // Now check whether the given cell is
74 // contained in one of the selected blocks.
75 count
= m_blockSelectionTopLeft
.GetCount();
76 for ( size_t n
= 0; n
< count
; n
++ )
78 wxGridCellCoords
& coords1
= m_blockSelectionTopLeft
[n
];
79 wxGridCellCoords
& coords2
= m_blockSelectionBottomRight
[n
];
80 if ( BlockContainsCell(coords1
.GetRow(), coords1
.GetCol(),
81 coords2
.GetRow(), coords2
.GetCol(),
86 // Now check whether the given cell is
87 // contained in one of the selected rows
88 // (unless we are in column selection mode).
89 if ( m_selectionMode
!= wxGrid::wxGridSelectColumns
)
91 count
= m_rowSelection
.GetCount();
92 for ( size_t n
= 0; n
< count
; n
++ )
94 if ( row
== m_rowSelection
[n
] )
99 // Now check whether the given cell is
100 // contained in one of the selected columns
101 // (unless we are in row selection mode).
102 if ( m_selectionMode
!= wxGrid::wxGridSelectRows
)
104 count
= m_colSelection
.GetCount();
105 for ( size_t n
= 0; n
< count
; n
++ )
107 if ( col
== m_colSelection
[n
] )
115 // Change the selection mode
116 void wxGridSelection::SetSelectionMode( wxGrid::wxGridSelectionModes selmode
)
118 // if selection mode is unchanged return immediately
119 if (selmode
== m_selectionMode
)
122 if ( m_selectionMode
!= wxGrid::wxGridSelectCells
)
124 // if changing form row to column selection
125 // or vice versa, clear the selection.
126 if ( selmode
!= wxGrid::wxGridSelectCells
)
129 m_selectionMode
= selmode
;
133 // if changing from cell selection to something else,
134 // promote selected cells/blocks to whole rows/columns.
136 while ( ( n
= m_cellSelection
.GetCount() ) > 0 )
139 wxGridCellCoords
& coords
= m_cellSelection
[n
];
140 int row
= coords
.GetRow();
141 int col
= coords
.GetCol();
142 m_cellSelection
.RemoveAt(n
);
143 if (selmode
== wxGrid::wxGridSelectRows
)
145 else // selmode == wxGridSelectColumns)
149 // Note that m_blockSelectionTopLeft's size may be changing!
150 for (n
= 0; n
< m_blockSelectionTopLeft
.GetCount(); n
++)
152 wxGridCellCoords
& coords
= m_blockSelectionTopLeft
[n
];
153 int topRow
= coords
.GetRow();
154 int leftCol
= coords
.GetCol();
155 coords
= m_blockSelectionBottomRight
[n
];
156 int bottomRow
= coords
.GetRow();
157 int rightCol
= coords
.GetCol();
159 if (selmode
== wxGrid::wxGridSelectRows
)
161 if (leftCol
!= 0 || rightCol
!= m_grid
->GetNumberCols() - 1 )
163 m_blockSelectionTopLeft
.RemoveAt(n
);
164 m_blockSelectionBottomRight
.RemoveAt(n
);
165 SelectBlock( topRow
, 0,
166 bottomRow
, m_grid
->GetNumberCols() - 1,
167 false, false, false, false, false );
170 else // selmode == wxGridSelectColumns)
172 if (topRow
!= 0 || bottomRow
!= m_grid
->GetNumberRows() - 1 )
174 m_blockSelectionTopLeft
.RemoveAt(n
);
175 m_blockSelectionBottomRight
.RemoveAt(n
);
176 SelectBlock( 0, leftCol
,
177 m_grid
->GetNumberRows() - 1, rightCol
,
178 false, false, false, false, false );
183 m_selectionMode
= selmode
;
187 void wxGridSelection::SelectRow( int row
,
188 bool ControlDown
, bool ShiftDown
,
189 bool AltDown
, bool MetaDown
)
191 if ( m_selectionMode
== wxGrid::wxGridSelectColumns
)
196 // Remove single cells contained in newly selected block.
197 if ( m_selectionMode
== wxGrid::wxGridSelectCells
)
199 count
= m_cellSelection
.GetCount();
200 for ( n
= 0; n
< count
; n
++ )
202 wxGridCellCoords
& coords
= m_cellSelection
[n
];
203 if ( BlockContainsCell( row
, 0, row
, m_grid
->GetNumberCols() - 1,
204 coords
.GetRow(), coords
.GetCol() ) )
206 m_cellSelection
.RemoveAt(n
);
213 // Simplify list of selected blocks (if possible)
214 count
= m_blockSelectionTopLeft
.GetCount();
217 for ( n
= 0; n
< count
; n
++ )
219 wxGridCellCoords
& coords1
= m_blockSelectionTopLeft
[n
];
220 wxGridCellCoords
& coords2
= m_blockSelectionBottomRight
[n
];
222 // Remove block if it is a subset of the row
223 if ( coords1
.GetRow() == row
&& row
== coords2
.GetRow() )
225 m_blockSelectionTopLeft
.RemoveAt(n
);
226 m_blockSelectionBottomRight
.RemoveAt(n
);
230 else if ( coords1
.GetCol() == 0 &&
231 coords2
.GetCol() == m_grid
->GetNumberCols() - 1 )
233 // silently return, if row is contained in block
234 if ( coords1
.GetRow() <= row
&& row
<= coords2
.GetRow() )
236 // expand block, if it touched row
237 else if ( coords1
.GetRow() == row
+ 1)
242 else if ( coords2
.GetRow() == row
- 1)
250 // Unless we successfully handled the row,
251 // check whether row is already selected.
254 count
= m_rowSelection
.GetCount();
255 for ( n
= 0; n
< count
; n
++ )
257 if ( row
== m_rowSelection
[n
] )
261 // Add row to selection
262 m_rowSelection
.Add(row
);
266 if ( !m_grid
->GetBatchCount() )
268 wxRect r
= m_grid
->BlockToDeviceRect( wxGridCellCoords( row
, 0 ),
269 wxGridCellCoords( row
, m_grid
->GetNumberCols() - 1 ) );
270 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
274 wxGridRangeSelectEvent
gridEvt( m_grid
->GetId(),
275 wxEVT_GRID_RANGE_SELECT
,
277 wxGridCellCoords( row
, 0 ),
278 wxGridCellCoords( row
, m_grid
->GetNumberCols() - 1 ),
280 ControlDown
, ShiftDown
,
283 m_grid
->GetEventHandler()->ProcessEvent( gridEvt
);
286 void wxGridSelection::SelectCol( int col
,
287 bool ControlDown
, bool ShiftDown
,
288 bool AltDown
, bool MetaDown
)
290 if ( m_selectionMode
== wxGrid::wxGridSelectRows
)
294 // Remove single cells contained in newly selected block.
295 if ( m_selectionMode
== wxGrid::wxGridSelectCells
)
297 count
= m_cellSelection
.GetCount();
298 for ( n
= 0; n
< count
; n
++ )
300 wxGridCellCoords
& coords
= m_cellSelection
[n
];
301 if ( BlockContainsCell( 0, col
, m_grid
->GetNumberRows() - 1, col
,
302 coords
.GetRow(), coords
.GetCol() ) )
304 m_cellSelection
.RemoveAt(n
);
311 // Simplify list of selected blocks (if possible)
312 count
= m_blockSelectionTopLeft
.GetCount();
314 for ( n
= 0; n
< count
; n
++ )
316 wxGridCellCoords
& coords1
= m_blockSelectionTopLeft
[n
];
317 wxGridCellCoords
& coords2
= m_blockSelectionBottomRight
[n
];
319 // Remove block if it is a subset of the column
320 if ( coords1
.GetCol() == col
&& col
== coords2
.GetCol() )
322 m_blockSelectionTopLeft
.RemoveAt(n
);
323 m_blockSelectionBottomRight
.RemoveAt(n
);
327 else if ( coords1
.GetRow() == 0 &&
328 coords2
.GetRow() == m_grid
->GetNumberRows() - 1 )
330 // silently return, if row is contained in block
331 if ( coords1
.GetCol() <= col
&& col
<= coords2
.GetCol() )
333 // expand block, if it touched col
334 else if ( coords1
.GetCol() == col
+ 1)
339 else if ( coords2
.GetCol() == col
- 1)
347 // Unless we successfully handled the column,
348 // Check whether col is already selected.
351 count
= m_colSelection
.GetCount();
352 for ( n
= 0; n
< count
; n
++ )
354 if ( col
== m_colSelection
[n
] )
358 // Add col to selection
359 m_colSelection
.Add(col
);
363 if ( !m_grid
->GetBatchCount() )
365 wxRect r
= m_grid
->BlockToDeviceRect( wxGridCellCoords( 0, col
),
366 wxGridCellCoords( m_grid
->GetNumberRows() - 1, col
) );
367 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
371 wxGridRangeSelectEvent
gridEvt( m_grid
->GetId(),
372 wxEVT_GRID_RANGE_SELECT
,
374 wxGridCellCoords( 0, col
),
375 wxGridCellCoords( m_grid
->GetNumberRows() - 1, col
),
377 ControlDown
, ShiftDown
,
380 m_grid
->GetEventHandler()->ProcessEvent( gridEvt
);
383 void wxGridSelection::SelectBlock( int topRow
, int leftCol
,
384 int bottomRow
, int rightCol
,
385 bool ControlDown
, bool ShiftDown
,
386 bool AltDown
, bool MetaDown
,
389 // Fix the coordinates of the block if needed.
390 if ( m_selectionMode
== wxGrid::wxGridSelectRows
)
393 rightCol
= m_grid
->GetNumberCols() - 1;
395 else if ( m_selectionMode
== wxGrid::wxGridSelectColumns
)
398 bottomRow
= m_grid
->GetNumberRows() - 1;
401 if ( topRow
> bottomRow
)
408 if ( leftCol
> rightCol
)
415 // Handle single cell selection in SelectCell.
416 // (MB: added check for selection mode here to prevent
417 // crashes if, for example, we are select rows and the
418 // grid only has 1 col)
419 if ( m_selectionMode
== wxGrid::wxGridSelectCells
&&
420 topRow
== bottomRow
&& leftCol
== rightCol
)
422 SelectCell( topRow
, leftCol
, ControlDown
, ShiftDown
,
423 AltDown
, MetaDown
, sendEvent
);
428 // Remove single cells contained in newly selected block.
429 if ( m_selectionMode
== wxGrid::wxGridSelectCells
)
431 count
= m_cellSelection
.GetCount();
432 for ( n
= 0; n
< count
; n
++ )
434 wxGridCellCoords
& coords
= m_cellSelection
[n
];
435 if ( BlockContainsCell( topRow
, leftCol
, bottomRow
, rightCol
,
436 coords
.GetRow(), coords
.GetCol() ) )
438 m_cellSelection
.RemoveAt(n
);
445 // If a block containing the selection is already selected, return,
446 // if a block contained in the selection is found, remove it.
448 count
= m_blockSelectionTopLeft
.GetCount();
449 for ( n
= 0; n
< count
; n
++ )
451 wxGridCellCoords
& coords1
= m_blockSelectionTopLeft
[n
];
452 wxGridCellCoords
& coords2
= m_blockSelectionBottomRight
[n
];
454 switch ( BlockContain( coords1
.GetRow(), coords1
.GetCol(),
455 coords2
.GetRow(), coords2
.GetCol(),
456 topRow
, leftCol
, bottomRow
, rightCol
) )
462 m_blockSelectionTopLeft
.RemoveAt(n
);
463 m_blockSelectionBottomRight
.RemoveAt(n
);
473 // If a row containing the selection is already selected, return,
474 // if a row contained in newly selected block is found, remove it.
475 if ( m_selectionMode
!= wxGrid::wxGridSelectColumns
)
477 count
= m_rowSelection
.GetCount();
478 for ( n
= 0; n
< count
; n
++ )
480 switch ( BlockContain( m_rowSelection
[n
], 0,
481 m_rowSelection
[n
], m_grid
->GetNumberCols() - 1,
482 topRow
, leftCol
, bottomRow
, rightCol
) )
488 m_rowSelection
.RemoveAt(n
);
499 if ( m_selectionMode
!= wxGrid::wxGridSelectRows
)
501 count
= m_colSelection
.GetCount();
502 for ( n
= 0; n
< count
; n
++ )
504 switch ( BlockContain( 0, m_colSelection
[n
],
505 m_grid
->GetNumberRows() - 1, m_colSelection
[n
],
506 topRow
, leftCol
, bottomRow
, rightCol
) )
512 m_colSelection
.RemoveAt(n
);
523 m_blockSelectionTopLeft
.Add( wxGridCellCoords( topRow
, leftCol
) );
524 m_blockSelectionBottomRight
.Add( wxGridCellCoords( bottomRow
, rightCol
) );
527 if ( !m_grid
->GetBatchCount() )
529 wxRect r
= m_grid
->BlockToDeviceRect( wxGridCellCoords( topRow
, leftCol
),
530 wxGridCellCoords( bottomRow
, rightCol
) );
531 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
534 // Send Event, if not disabled.
537 wxGridRangeSelectEvent
gridEvt( m_grid
->GetId(),
538 wxEVT_GRID_RANGE_SELECT
,
540 wxGridCellCoords( topRow
, leftCol
),
541 wxGridCellCoords( bottomRow
, rightCol
),
543 ControlDown
, ShiftDown
,
545 m_grid
->GetEventHandler()->ProcessEvent( gridEvt
);
549 void wxGridSelection::SelectCell( int row
, int col
,
550 bool ControlDown
, bool ShiftDown
,
551 bool AltDown
, bool MetaDown
,
554 if ( m_selectionMode
== wxGrid::wxGridSelectRows
)
556 SelectBlock(row
, 0, row
, m_grid
->GetNumberCols() - 1,
557 ControlDown
, ShiftDown
, AltDown
, MetaDown
, sendEvent
);
561 else if ( m_selectionMode
== wxGrid::wxGridSelectColumns
)
563 SelectBlock(0, col
, m_grid
->GetNumberRows() - 1, col
,
564 ControlDown
, ShiftDown
, AltDown
, MetaDown
, sendEvent
);
568 else if ( IsInSelection ( row
, col
) )
571 m_cellSelection
.Add( wxGridCellCoords( row
, col
) );
574 if ( !m_grid
->GetBatchCount() )
576 wxRect r
= m_grid
->BlockToDeviceRect(
577 wxGridCellCoords( row
, col
),
578 wxGridCellCoords( row
, col
) );
579 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
585 wxGridRangeSelectEvent
gridEvt( m_grid
->GetId(),
586 wxEVT_GRID_RANGE_SELECT
,
588 wxGridCellCoords( row
, col
),
589 wxGridCellCoords( row
, col
),
591 ControlDown
, ShiftDown
,
593 m_grid
->GetEventHandler()->ProcessEvent( gridEvt
);
597 void wxGridSelection::ToggleCellSelection( int row
, int col
,
598 bool ControlDown
, bool ShiftDown
,
599 bool AltDown
, bool MetaDown
)
601 // if the cell is not selected, select it
602 if ( !IsInSelection ( row
, col
) )
604 SelectCell( row
, col
, ControlDown
, ShiftDown
, AltDown
, MetaDown
);
609 // otherwise deselect it. This can be simple or more or
610 // less difficult, depending on how the cell is selected.
613 // The simplest case: The cell is contained in m_cellSelection
614 // Then it can't be contained in rows/cols/block (since those
615 // would remove the cell from m_cellSelection on creation), so
616 // we just have to remove it from m_cellSelection.
618 if ( m_selectionMode
== wxGrid::wxGridSelectCells
)
620 count
= m_cellSelection
.GetCount();
621 for ( n
= 0; n
< count
; n
++ )
623 const wxGridCellCoords
& sel
= m_cellSelection
[n
];
624 if ( row
== sel
.GetRow() && col
== sel
.GetCol() )
626 wxGridCellCoords coords
= m_cellSelection
[n
];
627 m_cellSelection
.RemoveAt(n
);
628 if ( !m_grid
->GetBatchCount() )
630 wxRect r
= m_grid
->BlockToDeviceRect( coords
, coords
);
631 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
635 wxGridRangeSelectEvent
gridEvt( m_grid
->GetId(),
636 wxEVT_GRID_RANGE_SELECT
,
638 wxGridCellCoords( row
, col
),
639 wxGridCellCoords( row
, col
),
641 ControlDown
, ShiftDown
,
643 m_grid
->GetEventHandler()->ProcessEvent( gridEvt
);
650 // The most difficult case: The cell is member of one or even several
651 // blocks. Split each such block in up to 4 new parts, that don't
652 // contain the cell to be selected, like this:
653 // |---------------------------|
657 // |---------------------------|
658 // | part 3 |x| part 4 |
659 // |---------------------------|
663 // |---------------------------|
664 // (The x marks the newly deselected cell).
665 // Note: in row selection mode, we only need part1 and part2;
666 // in column selection mode, we only need part 3 and part4,
667 // which are expanded to whole columns automatically!
669 count
= m_blockSelectionTopLeft
.GetCount();
670 for ( n
= 0; n
< count
; n
++ )
672 wxGridCellCoords
& coords1
= m_blockSelectionTopLeft
[n
];
673 wxGridCellCoords
& coords2
= m_blockSelectionBottomRight
[n
];
674 int topRow
= coords1
.GetRow();
675 int leftCol
= coords1
.GetCol();
676 int bottomRow
= coords2
.GetRow();
677 int rightCol
= coords2
.GetCol();
679 if ( BlockContainsCell( topRow
, leftCol
, bottomRow
, rightCol
, row
, col
) )
682 m_blockSelectionTopLeft
.RemoveAt(n
);
683 m_blockSelectionBottomRight
.RemoveAt(n
);
687 // add up to 4 smaller blocks and set update region
688 if ( m_selectionMode
!= wxGrid::wxGridSelectColumns
)
691 SelectBlock( topRow
, leftCol
, row
- 1, rightCol
,
692 false, false, false, false, false );
693 if ( bottomRow
> row
)
694 SelectBlock( row
+ 1, leftCol
, bottomRow
, rightCol
,
695 false, false, false, false, false );
698 if ( m_selectionMode
!= wxGrid::wxGridSelectRows
)
701 SelectBlock( row
, leftCol
, row
, col
- 1,
702 false, false, false, false, false );
703 if ( rightCol
> col
)
704 SelectBlock( row
, col
+ 1, row
, rightCol
,
705 false, false, false, false, false );
710 // remove a cell from a row, adding up to two new blocks
711 if ( m_selectionMode
!= wxGrid::wxGridSelectColumns
)
713 count
= m_rowSelection
.GetCount();
714 for ( n
= 0; n
< count
; n
++ )
716 if ( m_rowSelection
[n
] == row
)
718 m_rowSelection
.RemoveAt(n
);
722 if (m_selectionMode
== wxGrid::wxGridSelectCells
)
725 SelectBlock( row
, 0, row
, col
- 1,
726 false, false, false, false, false );
727 if ( col
< m_grid
->GetNumberCols() - 1 )
728 SelectBlock( row
, col
+ 1,
729 row
, m_grid
->GetNumberCols() - 1,
730 false, false, false, false, false );
736 // remove a cell from a column, adding up to two new blocks
737 if ( m_selectionMode
!= wxGrid::wxGridSelectRows
)
739 count
= m_colSelection
.GetCount();
740 for ( n
= 0; n
< count
; n
++ )
742 if ( m_colSelection
[n
] == col
)
744 m_colSelection
.RemoveAt(n
);
748 if (m_selectionMode
== wxGrid::wxGridSelectCells
)
751 SelectBlock( 0, col
, row
- 1, col
,
752 false, false, false, false, false );
753 if ( row
< m_grid
->GetNumberRows() - 1 )
754 SelectBlock( row
+ 1, col
,
755 m_grid
->GetNumberRows() - 1, col
,
756 false, false, false, false, false );
762 // Refresh the screen and send the event; according to m_selectionMode,
763 // we need to either update only the cell, or the whole row/column.
765 switch (m_selectionMode
)
767 case wxGrid::wxGridSelectCells
:
769 if ( !m_grid
->GetBatchCount() )
771 r
= m_grid
->BlockToDeviceRect(
772 wxGridCellCoords( row
, col
),
773 wxGridCellCoords( row
, col
) );
774 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
777 wxGridRangeSelectEvent
gridEvt( m_grid
->GetId(),
778 wxEVT_GRID_RANGE_SELECT
,
780 wxGridCellCoords( row
, col
),
781 wxGridCellCoords( row
, col
),
783 ControlDown
, ShiftDown
,
785 m_grid
->GetEventHandler()->ProcessEvent( gridEvt
);
789 case wxGrid::wxGridSelectRows
:
791 if ( !m_grid
->GetBatchCount() )
793 r
= m_grid
->BlockToDeviceRect(
794 wxGridCellCoords( row
, 0 ),
795 wxGridCellCoords( row
, m_grid
->GetNumberCols() - 1 ) );
796 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
799 wxGridRangeSelectEvent
gridEvt( m_grid
->GetId(),
800 wxEVT_GRID_RANGE_SELECT
,
802 wxGridCellCoords( row
, 0 ),
803 wxGridCellCoords( row
, m_grid
->GetNumberCols() - 1 ),
805 ControlDown
, ShiftDown
,
807 m_grid
->GetEventHandler()->ProcessEvent( gridEvt
);
811 case wxGrid::wxGridSelectColumns
:
813 if ( !m_grid
->GetBatchCount() )
815 r
= m_grid
->BlockToDeviceRect(
816 wxGridCellCoords( 0, col
),
817 wxGridCellCoords( m_grid
->GetNumberRows() - 1, col
) );
818 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
821 wxGridRangeSelectEvent
gridEvt( m_grid
->GetId(),
822 wxEVT_GRID_RANGE_SELECT
,
824 wxGridCellCoords( 0, col
),
825 wxGridCellCoords( m_grid
->GetNumberRows() - 1, col
),
827 ControlDown
, ShiftDown
,
829 m_grid
->GetEventHandler()->ProcessEvent( gridEvt
);
838 void wxGridSelection::ClearSelection()
842 wxGridCellCoords coords1
, coords2
;
844 // deselect all individual cells and update the screen
845 if ( m_selectionMode
== wxGrid::wxGridSelectCells
)
847 while ( ( n
= m_cellSelection
.GetCount() ) > 0)
850 coords1
= m_cellSelection
[n
];
851 m_cellSelection
.RemoveAt(n
);
852 if ( !m_grid
->GetBatchCount() )
854 r
= m_grid
->BlockToDeviceRect( coords1
, coords1
);
855 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
858 ((wxWindow
*)m_grid
->m_gridWin
)->Update();
864 // deselect all blocks and update the screen
865 while ( ( n
= m_blockSelectionTopLeft
.GetCount() ) > 0)
868 coords1
= m_blockSelectionTopLeft
[n
];
869 coords2
= m_blockSelectionBottomRight
[n
];
870 m_blockSelectionTopLeft
.RemoveAt(n
);
871 m_blockSelectionBottomRight
.RemoveAt(n
);
872 if ( !m_grid
->GetBatchCount() )
874 r
= m_grid
->BlockToDeviceRect( coords1
, coords2
);
875 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
878 ((wxWindow
*)m_grid
->m_gridWin
)->Update();
883 // deselect all rows and update the screen
884 if ( m_selectionMode
!= wxGrid::wxGridSelectColumns
)
886 while ( ( n
= m_rowSelection
.GetCount() ) > 0)
889 int row
= m_rowSelection
[n
];
890 m_rowSelection
.RemoveAt(n
);
891 if ( !m_grid
->GetBatchCount() )
893 r
= m_grid
->BlockToDeviceRect( wxGridCellCoords( row
, 0 ),
894 wxGridCellCoords( row
, m_grid
->GetNumberCols() - 1 ) );
895 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
898 ((wxWindow
*)m_grid
->m_gridWin
)->Update();
904 // deselect all columns and update the screen
905 if ( m_selectionMode
!= wxGrid::wxGridSelectRows
)
907 while ( ( n
= m_colSelection
.GetCount() ) > 0)
910 int col
= m_colSelection
[n
];
911 m_colSelection
.RemoveAt(n
);
912 if ( !m_grid
->GetBatchCount() )
914 r
= m_grid
->BlockToDeviceRect( wxGridCellCoords( 0, col
),
915 wxGridCellCoords( m_grid
->GetNumberRows() - 1, col
) );
916 ((wxWindow
*)m_grid
->m_gridWin
)->Refresh( false, &r
);
919 ((wxWindow
*)m_grid
->m_gridWin
)->Update();
925 // One deselection event, indicating deselection of _all_ cells.
926 // (No finer grained events for each of the smaller regions
927 // deselected above!)
928 wxGridRangeSelectEvent
gridEvt( m_grid
->GetId(),
929 wxEVT_GRID_RANGE_SELECT
,
931 wxGridCellCoords( 0, 0 ),
933 m_grid
->GetNumberRows() - 1,
934 m_grid
->GetNumberCols() - 1 ),
937 m_grid
->GetEventHandler()->ProcessEvent(gridEvt
);
941 void wxGridSelection::UpdateRows( size_t pos
, int numRows
)
943 size_t count
= m_cellSelection
.GetCount();
945 for ( n
= 0; n
< count
; n
++ )
947 wxGridCellCoords
& coords
= m_cellSelection
[n
];
948 wxCoord row
= coords
.GetRow();
949 if ((size_t)row
>= pos
)
953 // If rows inserted, increase row counter where necessary
954 coords
.SetRow(row
+ numRows
);
956 else if (numRows
< 0)
958 // If rows deleted ...
959 if ((size_t)row
>= pos
- numRows
)
961 // ...either decrement row counter (if row still exists)...
962 coords
.SetRow(row
+ numRows
);
966 // ...or remove the attribute
967 m_cellSelection
.RemoveAt(n
);
975 count
= m_blockSelectionTopLeft
.GetCount();
976 for ( n
= 0; n
< count
; n
++ )
978 wxGridCellCoords
& coords1
= m_blockSelectionTopLeft
[n
];
979 wxGridCellCoords
& coords2
= m_blockSelectionBottomRight
[n
];
980 wxCoord row1
= coords1
.GetRow();
981 wxCoord row2
= coords2
.GetRow();
983 if ((size_t)row2
>= pos
)
987 // If rows inserted, increase row counter where necessary
988 coords2
.SetRow( row2
+ numRows
);
989 if ((size_t)row1
>= pos
)
990 coords1
.SetRow( row1
+ numRows
);
992 else if (numRows
< 0)
994 // If rows deleted ...
995 if ((size_t)row2
>= pos
- numRows
)
997 // ...either decrement row counter (if row still exists)...
998 coords2
.SetRow( row2
+ numRows
);
999 if ((size_t)row1
>= pos
)
1000 coords1
.SetRow( wxMax(row1
+ numRows
, (int)pos
) );
1005 if ((size_t)row1
>= pos
)
1007 // ...or remove the attribute
1008 m_blockSelectionTopLeft
.RemoveAt(n
);
1009 m_blockSelectionBottomRight
.RemoveAt(n
);
1014 coords2
.SetRow( pos
);
1020 count
= m_rowSelection
.GetCount();
1021 for ( n
= 0; n
< count
; n
++ )
1023 int rowOrCol_
= m_rowSelection
[n
];
1025 if ((size_t) rowOrCol_
>= pos
)
1029 m_rowSelection
[n
] += numRows
;
1031 else if ( numRows
< 0 )
1033 if ((size_t)rowOrCol_
>= (pos
- numRows
))
1034 m_rowSelection
[n
] += numRows
;
1037 m_rowSelection
.RemoveAt( n
);
1044 // No need to touch selected columns, unless we removed _all_
1045 // rows, in this case, we remove all columns from the selection.
1047 if ( !m_grid
->GetNumberRows() )
1048 m_colSelection
.Clear();
1052 void wxGridSelection::UpdateCols( size_t pos
, int numCols
)
1054 size_t count
= m_cellSelection
.GetCount();
1057 for ( n
= 0; n
< count
; n
++ )
1059 wxGridCellCoords
& coords
= m_cellSelection
[n
];
1060 wxCoord col
= coords
.GetCol();
1061 if ((size_t)col
>= pos
)
1065 // If rows inserted, increase row counter where necessary
1066 coords
.SetCol(col
+ numCols
);
1068 else if (numCols
< 0)
1070 // If rows deleted ...
1071 if ((size_t)col
>= pos
- numCols
)
1073 // ...either decrement row counter (if row still exists)...
1074 coords
.SetCol(col
+ numCols
);
1078 // ...or remove the attribute
1079 m_cellSelection
.RemoveAt(n
);
1087 count
= m_blockSelectionTopLeft
.GetCount();
1088 for ( n
= 0; n
< count
; n
++ )
1090 wxGridCellCoords
& coords1
= m_blockSelectionTopLeft
[n
];
1091 wxGridCellCoords
& coords2
= m_blockSelectionBottomRight
[n
];
1092 wxCoord col1
= coords1
.GetCol();
1093 wxCoord col2
= coords2
.GetCol();
1095 if ((size_t)col2
>= pos
)
1099 // If rows inserted, increase row counter where necessary
1100 coords2
.SetCol(col2
+ numCols
);
1101 if ((size_t)col1
>= pos
)
1102 coords1
.SetCol(col1
+ numCols
);
1104 else if (numCols
< 0)
1106 // If cols deleted ...
1107 if ((size_t)col2
>= pos
- numCols
)
1109 // ...either decrement col counter (if col still exists)...
1110 coords2
.SetCol(col2
+ numCols
);
1111 if ( (size_t) col1
>= pos
)
1112 coords1
.SetCol( wxMax(col1
+ numCols
, (int)pos
) );
1117 if ((size_t)col1
>= pos
)
1119 // ...or remove the attribute
1120 m_blockSelectionTopLeft
.RemoveAt(n
);
1121 m_blockSelectionBottomRight
.RemoveAt(n
);
1126 coords2
.SetCol(pos
);
1132 count
= m_colSelection
.GetCount();
1133 for ( n
= 0; n
< count
; n
++ )
1135 int rowOrCol
= m_colSelection
[n
];
1137 if ((size_t)rowOrCol
>= pos
)
1140 m_colSelection
[n
] += numCols
;
1141 else if ( numCols
< 0 )
1143 if ((size_t)rowOrCol
>= (pos
- numCols
))
1144 m_colSelection
[n
] += numCols
;
1147 m_colSelection
.RemoveAt( n
);
1155 // No need to touch selected rows, unless we removed _all_
1156 // columns, in this case, we remove all rows from the selection.
1157 if ( !m_grid
->GetNumberCols() )
1158 m_rowSelection
.Clear();
1161 int wxGridSelection::BlockContain( int topRow1
, int leftCol1
,
1162 int bottomRow1
, int rightCol1
,
1163 int topRow2
, int leftCol2
,
1164 int bottomRow2
, int rightCol2
)
1165 // returns 1, if Block1 contains Block2,
1166 // -1, if Block2 contains Block1,
1169 if ( topRow1
<= topRow2
&& bottomRow2
<= bottomRow1
&&
1170 leftCol1
<= leftCol2
&& rightCol2
<= rightCol1
)
1172 else if ( topRow2
<= topRow1
&& bottomRow1
<= bottomRow2
&&
1173 leftCol2
<= leftCol1
&& rightCol1
<= rightCol2
)