]> git.saurik.com Git - wxWidgets.git/blob - contrib/src/fl/rowdragpl.cpp
better cleanup
[wxWidgets.git] / contrib / src / fl / rowdragpl.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: rowdragpl.cpp
3 // Purpose: cbRowDragPlugin implementation.
4 // Author: Aleksandras Gluchovas
5 // Modified by:
6 // Created: 06/10/98
7 // RCS-ID: $Id$
8 // Copyright: (c) Aleksandras Gluchovas
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
11
12 #ifdef __GNUG__
13 #pragma implementation "rowdragpl.h"
14 #endif
15
16 // For compilers that support precompilation, includes "wx.h".
17 #include "wx/wxprec.h"
18
19 #ifdef __BORLANDC__
20 #pragma hdrstop
21 #endif
22
23 #ifndef WX_PRECOMP
24 #include "wx/wx.h"
25 #endif
26
27 #include "wx/fl/rowdragpl.h"
28
29 #define MINIMAL_ROW_DRAG_OFS 5
30
31 // parameters for row-hints of NC-look
32
33 #define TRIANGLE_OFFSET 2
34 #define TRIANGLE_TO_PAT_GAP 2
35 #define PAT_OFFSET 2
36 #define COLLAPSED_ICON_WIDTH 45
37 #define COLLAPSED_ICON_HEIGHT 9
38 #define ROW_DRAG_HINT_WIDTH 10
39 #define ICON_TRIAN_WIDTH 6
40 #define ICON_TRIAN_HEIGHT 3
41
42 /***** Implementation for class cbHiddenBarInfo *****/
43
44 IMPLEMENT_DYNAMIC_CLASS( cbHiddenBarInfo, wxObject )
45
46 /***** Implementation for class cbRowDragPlugin *****/
47
48 IMPLEMENT_DYNAMIC_CLASS( cbRowDragPlugin, cbPluginBase )
49
50 BEGIN_EVENT_TABLE( cbRowDragPlugin, cbPluginBase )
51
52 EVT_PL_LEFT_DOWN ( cbRowDragPlugin::OnLButtonDown )
53 EVT_PL_LEFT_UP ( cbRowDragPlugin::OnLButtonUp )
54 EVT_PL_MOTION ( cbRowDragPlugin::OnMouseMove )
55
56 EVT_PL_DRAW_PANE_DECOR ( cbRowDragPlugin::OnDrawPaneBackground )
57
58 END_EVENT_TABLE()
59
60 // FIXME:: how to eliminated these cut and pasted constructors?
61
62 cbRowDragPlugin::cbRowDragPlugin(void)
63
64 : mHightColor ( 192, 192, 255 ),
65 mLowColor ( 192, 192, 192 ),
66 mTrianInnerColor ( 0,0,255 ),
67 mTrianInnerPen ( mTrianInnerColor, 1, wxSOLID ),
68
69 mDragStarted ( FALSE ),
70 mDecisionMode ( FALSE ),
71 mCurDragOfs ( 0 ),
72 mCaptureIsOn ( FALSE ),
73 mSvTopMargin ( -1 ),
74 mSvBottomMargin ( -1 ),
75 mSvLeftMargin ( -1 ),
76 mSvRightMargin ( -1 ),
77
78 mpPaneImage ( NULL ),
79 mpRowImage ( NULL ),
80 mpCombinedImage ( NULL ),
81
82 mpRowInFocus ( NULL ),
83 mCollapsedIconInFocus( -1 ),
84
85 mpPane ( NULL )
86 {
87 }
88
89 cbRowDragPlugin::cbRowDragPlugin( wxFrameLayout* pLayout, int paneMask )
90
91 : cbPluginBase( pLayout, paneMask ),
92
93 mHightColor ( 192, 192, 255 ),
94 mLowColor ( 192, 192, 192 ),
95 mTrianInnerColor ( 0,0,255 ),
96 mTrianInnerPen ( mTrianInnerColor, 1, wxSOLID ),
97
98 mDragStarted ( FALSE ),
99 mDecisionMode ( FALSE ),
100 mCurDragOfs ( 0 ),
101 mCaptureIsOn ( FALSE ),
102 mSvTopMargin ( -1 ),
103 mSvBottomMargin ( -1 ),
104 mSvLeftMargin ( -1 ),
105 mSvRightMargin ( -1 ),
106
107 mpPaneImage ( NULL ),
108 mpRowImage ( NULL ),
109 mpCombinedImage ( NULL ),
110
111 mpRowInFocus ( NULL ),
112 mCollapsedIconInFocus( -1 ),
113
114 mpPane ( NULL )
115 {
116 }
117
118 cbRowDragPlugin::~cbRowDragPlugin()
119 {
120 }
121
122 // handlers for plugin events
123 void cbRowDragPlugin::OnMouseMove( cbMotionEvent& event )
124 {
125 // short-cuts
126 wxPoint pos = event.mPos;
127 mpPane = event.mpPane;
128
129 mpPane->PaneToFrame( &pos.x, &pos.y );
130
131 if ( !mDragStarted )
132 {
133 if ( mDecisionMode && mpRowInFocus )
134 {
135 int ofs;
136
137 if ( mpPane->IsHorizontal() )
138
139 ofs = pos.y - mDragOrigin.y;
140 else
141 ofs = pos.x - mDragOrigin.x;
142
143 // check if the item was dragged sufficeintly
144 // far, enough to consider that user really intends
145 // to drag it
146
147 if ( ofs >= MINIMAL_ROW_DRAG_OFS ||
148 ofs <= -MINIMAL_ROW_DRAG_OFS )
149 {
150 // DBG::
151 //.wxPoint pos = event.mPos;
152 //wxPoint drg = mDragOrigin;
153 //int dif = event.mPos.x - mDragOrigin.x;
154
155 mDragStarted = TRUE;
156 mDecisionMode = FALSE;
157 mDragOrigin = pos;
158
159 PrepareForRowDrag();
160 return;
161 }
162
163 // this plugin "eats" all mouse input while item is dragged,
164 return;
165 }
166
167 cbRowInfo* pRow = GetFirstRow();
168
169 bool focusFound = FALSE;
170
171 while( pRow )
172 {
173 if ( HitTestRowDragHint( pRow, pos ) )
174 {
175 CheckPrevItemInFocus( pRow, -1 );
176 SetMouseCapture( TRUE );
177
178 focusFound = TRUE;
179
180 mpRowInFocus = pRow;
181 mCollapsedIconInFocus = -1;
182 break;
183 }
184
185 pRow = pRow->mpNext;
186 }
187
188 if ( !focusFound )
189 {
190 int hrCnt = GetHRowsCountForPane( event.mpPane );
191
192 for( int i = 0; i != hrCnt; ++i )
193 {
194 if ( HitTestCollapsedRowIcon( i, pos ) )
195 {
196 CheckPrevItemInFocus( NULL, i );
197 SetMouseCapture( TRUE );
198
199 focusFound = TRUE;
200
201 mCollapsedIconInFocus = i;
202 mpRowInFocus = NULL;
203 break;
204 }
205 }
206 }
207
208 if ( !focusFound && ItemIsInFocus() )
209 {
210 // kill focus from item previously been in focus
211 UnhighlightItemInFocus();
212
213 mpRowInFocus = NULL;
214 mCollapsedIconInFocus = -1;
215 SetMouseCapture( FALSE );
216 }
217
218 if ( !ItemIsInFocus() )
219
220 // delegate it to other plugins
221 event.Skip();
222 }
223 else
224 {
225 // otherwise mouse pointer moves, when dragging is started
226
227 if ( mpPane->IsHorizontal() )
228 {
229 // DBG::
230 wxPoint p = event.mPos;
231 wxPoint d = mDragOrigin;
232 // int dif = event.mPos.x - mDragOrigin.x;
233
234 // row is dragged up or down;
235 ShowDraggedRow( pos.y - mDragOrigin.y );
236 }
237 else
238 {
239 // DBG::
240 wxPoint p = event.mPos;
241 wxPoint d = mDragOrigin;
242 // int dif = event.mPos.x - mDragOrigin.x;
243
244 // row is dragged left or right
245 ShowDraggedRow( pos.x - mDragOrigin.x );
246 }
247
248 // this plugin "eats" all mouse input while item is dragged,
249 }
250 }
251
252 void cbRowDragPlugin::OnLButtonDown( cbLeftDownEvent& event )
253 {
254 mpPane = event.mpPane;
255
256 // DBG::
257 wxASSERT( !mDragStarted && !mDecisionMode );
258
259 if ( ItemIsInFocus() )
260 {
261 mDecisionMode = TRUE;
262
263 wxPoint pos = event.mPos;
264 mpPane->PaneToFrame( &pos.x, &pos.y );
265
266 mDragOrigin = pos;
267
268 SetMouseCapture( TRUE );
269 }
270 else
271 // propagate event to other plugins
272 event.Skip();
273 }
274
275 void cbRowDragPlugin::OnLButtonUp ( cbLeftUpEvent& event )
276 {
277 if ( !mDragStarted && !mDecisionMode )
278 {
279 event.Skip();
280 return;
281 }
282
283 mpPane = event.mpPane;
284
285 if ( mDecisionMode )
286 {
287 cbDockPane* pPane = mpPane;
288
289 SetMouseCapture( FALSE );
290
291 mDecisionMode = FALSE;
292 mDragStarted = FALSE;
293
294 wxPoint frmPos = event.mPos;
295 pPane->PaneToFrame( &frmPos.x, &frmPos.y );
296
297 if ( mpRowInFocus )
298 {
299 CollapseRow( mpRowInFocus );
300 mpRowInFocus = 0;
301 }
302 else
303 {
304 ExpandRow( mCollapsedIconInFocus );
305 mCollapsedIconInFocus = -1;
306 }
307
308 mpRowInFocus = NULL;
309 mpPane = pPane;
310
311 pPane->FrameToPane( &frmPos.x, &frmPos.y );
312
313 // give it another try after relayouting bars
314
315 cbMotionEvent moveEvt( frmPos, pPane );
316 this->OnMouseMove( moveEvt );
317
318 // this plugin has "eaten" the mouse-up event
319
320 return;
321 }
322 else
323 {
324 // otherwise, the dragged row was dropped, determine
325 // where to insert it
326
327 // restore initial pane appearence
328 ShowPaneImage();
329 FinishOnScreenDraw();
330
331 cbRowInfo* pRow = GetFirstRow();
332
333 mpLayout->GetUpdatesManager().OnStartChanges();
334
335 pRow->mUMgrData.SetDirty(TRUE);
336
337 cbBarInfo* pBar = mpRowInFocus->mBars[0];
338
339 while ( pBar )
340 {
341 pBar->mUMgrData.SetDirty(TRUE);
342
343 if ( pBar->mpBarWnd )
344 {
345 // do complete refresh
346 pBar->mpBarWnd->Show(FALSE);
347 pBar->mpBarWnd->Show(TRUE);
348 }
349
350 pBar = pBar->mpNext;
351 }
352
353 while( pRow )
354 {
355 if ( mCurDragOfs < pRow->mRowY )
356 {
357 InsertDraggedRowBefore( pRow );
358 break;
359 }
360
361 pRow = pRow->mpNext;
362 }
363
364 if ( pRow == NULL ) InsertDraggedRowBefore( NULL );
365
366 mpRowInFocus = NULL;
367
368 mpLayout->RecalcLayout(FALSE);
369
370 // finish change "transaction"
371 mpLayout->GetUpdatesManager().OnFinishChanges();
372 mpLayout->GetUpdatesManager().UpdateNow();
373
374 // finish drag action
375 SetMouseCapture( FALSE );
376 mDragStarted = FALSE;
377 }
378 }
379
380 void cbRowDragPlugin::OnDrawPaneBackground ( cbDrawPaneDecorEvent& event )
381 {
382 mpPane = event.mpPane;
383
384 // FIXME:: this may harm operation of other plugins
385
386 if ( GetNextHandler() && mpPane->GetRowList().GetCount() )
387 {
388 // first, let other plugins add their decorations now
389
390 GetNextHandler()->ProcessEvent( event );
391 event.Skip(FALSE);
392 }
393
394 wxClientDC dc( &mpLayout->GetParentFrame() );
395
396 dc.SetClippingRegion( mpPane->mBoundsInParent.x,
397 mpPane->mBoundsInParent.y,
398 mpPane->mBoundsInParent.width,
399 mpPane->mBoundsInParent.height );
400
401 int cnt = GetHRowsCountForPane( event.mpPane );
402
403 if ( cnt > 0 )
404
405 DrawCollapsedRowsBorder( dc );
406
407 if ( mpPane->GetRowList().GetCount() )
408
409 DrawRowsDragHintsBorder( dc );
410
411 cbRowInfo* pRow = GetFirstRow();
412
413 while( pRow )
414 {
415 DrawRowDragHint( pRow, dc, FALSE );
416 pRow = pRow->mpNext;
417 }
418
419 for( int i = 0; i != cnt; ++i )
420
421 DrawCollapsedRowIcon(i, dc, FALSE );
422 }
423
424 int cbRowDragPlugin::GetHRowsCountForPane( cbDockPane* pPane )
425 {
426 wxNode* pNode = mHiddenBars.First();
427
428 int maxIconNo = -1;
429
430 while( pNode )
431 {
432 cbHiddenBarInfo* pHBInfo = (cbHiddenBarInfo*)pNode->Data();
433
434 if ( pHBInfo->mAlignment == pPane->mAlignment )
435
436 maxIconNo = wxMax( maxIconNo, pHBInfo->mIconNo );
437
438 pNode = pNode->Next();
439 }
440
441 return ( maxIconNo + 1 );
442 }
443
444 int cbRowDragPlugin::GetCollapsedRowIconHeight()
445 {
446 return COLLAPSED_ICON_HEIGHT;
447 }
448
449 int cbRowDragPlugin::GetRowDragHintWidth()
450 {
451 return ROW_DRAG_HINT_WIDTH;
452 }
453
454 void cbRowDragPlugin::SetPaneMargins()
455 {
456 int hiddenRowsCnt = GetHRowsCountForPane( mpPane );
457
458 if ( mSvTopMargin == -1 )
459 {
460 mSvTopMargin = mpPane->mTopMargin;
461 mSvBottomMargin = mpPane->mBottomMargin;
462 mSvLeftMargin = mpPane->mLeftMargin;
463 mSvRightMargin = mpPane->mRightMargin;
464 }
465
466 if ( mpPane->IsHorizontal() )
467 {
468 mpPane->mTopMargin = mSvTopMargin;
469 mpPane->mBottomMargin = ( hiddenRowsCnt == 0 )
470 ? mSvBottomMargin
471 : mSvBottomMargin + GetCollapsedRowIconHeight();
472
473 mpPane->mLeftMargin = mSvLeftMargin + GetRowDragHintWidth();
474 mpPane->mRightMargin = mSvRightMargin;
475 }
476 else
477 {
478 mpPane->mTopMargin = mSvTopMargin;
479 mpPane->mBottomMargin = mSvBottomMargin + GetRowDragHintWidth();
480
481 mpPane->mLeftMargin = mSvLeftMargin;
482 mpPane->mRightMargin = ( hiddenRowsCnt == 0 ) ?
483 mSvRightMargin : mSvRightMargin + GetCollapsedRowIconHeight();
484 }
485 }
486
487 void cbRowDragPlugin::OnInitPlugin()
488 {
489 cbDockPane** panes = mpLayout->GetPanesArray();
490
491 for( int i = 0; i != MAX_PANES; ++i )
492
493 if ( panes[i]->MatchesMask( mPaneMask ) )
494 {
495 mpPane = panes[i];
496
497 SetPaneMargins();
498 }
499 }
500
501 /*** helpers for drag&drop ***/
502
503 void cbRowDragPlugin::SetMouseCapture( bool captureOn )
504 {
505 if ( mCaptureIsOn == captureOn ) return;
506
507 if ( captureOn )
508 {
509 mpLayout->CaptureEventsForPane( mpPane );
510 mpLayout->CaptureEventsForPlugin( this );
511 }
512 else
513 {
514 mpLayout->ReleaseEventsFromPane( mpPane );
515 mpLayout->ReleaseEventsFromPlugin( this );
516 }
517
518 mCaptureIsOn = captureOn;
519 }
520
521 void cbRowDragPlugin::UnhighlightItemInFocus()
522 {
523 wxClientDC dc( &mpLayout->GetParentFrame() );
524
525 if ( mpRowInFocus )
526
527 DrawRowDragHint( mpRowInFocus, dc, FALSE );
528 else
529 if ( mCollapsedIconInFocus != - 1 )
530
531 DrawCollapsedRowIcon( mCollapsedIconInFocus, dc, FALSE );
532 }
533
534 void cbRowDragPlugin::ShowDraggedRow( int offset )
535 {
536 // create combined image of pane and dragged
537 // row on it, in the mpCombinedImage bitmap
538
539 if ( mpPane->IsHorizontal() )
540 {
541 if ( mInitialRowOfs + offset + mRowImgDim.y > mCombRect.y + mCombRect.height )
542
543 offset = mCombRect.y + mCombRect.height - mRowImgDim.y - mInitialRowOfs;
544
545 if ( mInitialRowOfs + offset < mCombRect.y )
546
547 offset = mCombRect.y - mInitialRowOfs;
548
549 int x, y = mInitialRowOfs + offset;
550 mpPane->FrameToPane( &x, &y );
551 mCurDragOfs = y;
552 }
553 else
554 {
555 if ( mInitialRowOfs + offset + mRowImgDim.x > mCombRect.x + mCombRect.width )
556
557 offset = mCombRect.x + mCombRect.width - mRowImgDim.x - mInitialRowOfs;
558
559 if ( mInitialRowOfs + offset < mCombRect.x )
560
561 offset = mCombRect.x - mInitialRowOfs;
562
563 int x = mInitialRowOfs + offset, y;
564 mpPane->FrameToPane( &x, &y );
565 mCurDragOfs = x;
566 }
567
568 wxMemoryDC rowImgDc;
569 rowImgDc.SelectObject ( *mpRowImage );
570
571 wxMemoryDC paneImgDc;
572 paneImgDc.SelectObject( *mpPaneImage );
573
574 wxMemoryDC combImgDc;
575 combImgDc.SelectObject( *mpCombinedImage );
576
577 combImgDc.Blit( 0,0, mCombRect.width, mCombRect.height,
578 &paneImgDc, 0,0, wxCOPY );
579
580 if ( mpPane->IsHorizontal() )
581 {
582 combImgDc.Blit( 0, mInitialRowOfs + offset - mCombRect.y,
583 mCombRect.width, mRowImgDim.y,
584 &rowImgDc, 0,0, wxCOPY );
585 }
586 else
587 {
588 combImgDc.Blit( mInitialRowOfs + offset - mCombRect.x,
589 0,
590 mRowImgDim.x, mCombRect.height,
591 &rowImgDc, 0,0, wxCOPY );
592 }
593
594 int scrX = mCombRect.x,
595 scrY = mCombRect.y;
596
597 mpLayout->GetParentFrame().ClientToScreen( &scrX, &scrY );
598
599 mpScrDc->Blit( scrX, scrY, mCombRect.width, mCombRect.height,
600 &combImgDc, 0,0, wxCOPY );
601
602 rowImgDc .SelectObject( wxNullBitmap );
603 paneImgDc.SelectObject( wxNullBitmap );
604 combImgDc.SelectObject( wxNullBitmap );
605 }
606
607 wxBitmap* cbRowDragPlugin::CaptureDCArea( wxDC& dc, wxRect& area )
608 {
609 wxBitmap* pBmp = new wxBitmap( int(area.width), int(area.height) );
610
611 wxMemoryDC mdc;
612 mdc.SelectObject( *pBmp );
613
614 mdc.Blit( 0,0, area.width, area.height, &dc, area.x, area.y, wxCOPY );
615 mdc.SelectObject( wxNullBitmap );
616
617 return pBmp;
618 }
619
620 void cbRowDragPlugin::PrepareForRowDrag()
621 {
622 wxRect rowBounds = mpRowInFocus->mBoundsInParent;
623
624 if ( mpPane->IsHorizontal() )
625 {
626 mCombRect = mpPane->mBoundsInParent;
627
628 mCombRect.x += mpPane->mLeftMargin - ROW_DRAG_HINT_WIDTH - 1;
629 mCombRect.y += mpPane->mTopMargin;
630
631 mCombRect.width -= mpPane->mLeftMargin + mpPane->mRightMargin - ROW_DRAG_HINT_WIDTH - 1 - 1;
632 mCombRect.height -= mpPane->mTopMargin + mpPane->mBottomMargin;
633
634 mCombRect.height += 2*rowBounds.height;
635 mCombRect.y -= rowBounds.height;
636 mInitialRowOfs = rowBounds.y;
637
638 rowBounds.y -= 1;
639 rowBounds.height += 2;
640 rowBounds.x = mCombRect.x;
641 rowBounds.width = mCombRect.width;
642
643 mRowImgDim.y = rowBounds.height;
644 }
645 else
646 {
647 mCombRect = mpPane->mBoundsInParent;
648
649 mCombRect.y += mpPane->mTopMargin - 1;
650 mCombRect.x += mpPane->mLeftMargin - 1;
651 ;
652 mCombRect.height -= mpPane->mTopMargin + mpPane->mBottomMargin - ROW_DRAG_HINT_WIDTH - 1 - 1;
653 mCombRect.width -= mpPane->mLeftMargin + mpPane->mRightMargin;
654
655 mCombRect.width += 2*rowBounds.width;
656 mCombRect.x -= rowBounds.width;
657 mInitialRowOfs = rowBounds.x;
658
659 rowBounds.x -= 1;
660 rowBounds.width += 2;
661 rowBounds.y = mCombRect.y;
662 rowBounds.height = mCombRect.height;
663
664 mRowImgDim.x = rowBounds.width;
665 }
666 // output cobination results onto frame's client area
667 wxScreenDC::StartDrawingOnTop(&mpLayout->GetParentFrame());
668 mpScrDc = new wxScreenDC();
669
670 int x = mCombRect.x, y = mCombRect.y;
671 mpLayout->GetParentFrame().ClientToScreen( &x, &y );
672
673 wxRect scrRect = mCombRect;
674 scrRect.x = x;
675 scrRect.y = y;
676
677 mpPaneImage = CaptureDCArea( *mpScrDc, scrRect );
678
679 wxMemoryDC mdc;
680 mdc.SelectObject( *mpPaneImage );
681 mdc.SetDeviceOrigin( -mCombRect.x, -mCombRect.y );
682
683 DrawRectShade( rowBounds, mdc, -1, mpLayout->mGrayPen, mpLayout->mDarkPen );
684 DrawRectShade( rowBounds, mdc, 0, mpLayout->mLightPen, mpLayout->mBlackPen );
685
686 mpRowImage = CaptureDCArea( mdc, rowBounds );
687
688 // draw dark empty-row placeholder
689 DrawEmptyRow( mdc, rowBounds );
690
691 //DrawRectShade( rowBounds, mdc, 0, mpLayout->mGrayPen, mpLayout->mDarkPen );
692 DrawRectShade( rowBounds, mdc, -1, mpLayout->mGrayPen, mpLayout->mGrayPen );
693
694 mdc.SelectObject( wxNullBitmap );
695
696 mpCombinedImage = new wxBitmap( int(mCombRect.width), int(mCombRect.height) );
697
698 // show it for the first time
699 ShowDraggedRow( 0 );
700 }
701
702 void cbRowDragPlugin::DrawEmptyRow( wxDC& dc, wxRect& rowBounds )
703 {
704 wxBrush bkBrush( mpLayout->mDarkPen.GetColour(), wxSOLID );
705
706 // paint the "dark" empty-row placeholder
707
708 dc.SetBrush( bkBrush );
709 dc.SetPen ( mpLayout->mNullPen );
710
711 dc.DrawRectangle( rowBounds.x, rowBounds.y,
712 rowBounds.width+1, rowBounds.height+1 );
713
714 dc.SetBrush( wxNullBrush );
715 }
716
717 void cbRowDragPlugin::ShowPaneImage()
718 {
719 int scrX = 0, scrY = 0;
720
721 mpLayout->GetParentFrame().ClientToScreen( &scrX, &scrY );
722
723 wxMemoryDC mdc;
724 mdc.SelectObject( *mpPaneImage );
725
726 mpScrDc->Blit( mCombRect.x + scrX, mCombRect.y + scrY,
727 mCombRect.width, mCombRect.height,
728 &mdc, 0,0, wxCOPY );
729
730 mdc.SelectObject( wxNullBitmap );
731 }
732
733 void cbRowDragPlugin::FinishOnScreenDraw()
734 {
735 wxScreenDC::EndDrawingOnTop();
736
737 delete mpScrDc;
738 delete mpCombinedImage;
739 delete mpPaneImage;
740 delete mpRowImage;
741
742 mpScrDc = NULL;
743
744 mpCombinedImage = mpPaneImage = mpRowImage = NULL;
745 }
746
747 void cbRowDragPlugin::CollapseRow( cbRowInfo* pRow )
748 {
749 int iconCnt = GetHRowsCountForPane( mpPane );
750
751 mpLayout->GetUpdatesManager().OnStartChanges();
752
753 cbBarInfo* pBar = pRow->mBars[0];
754
755 int rowNo = 0;
756
757 cbRowInfo* pCur = pRow;
758 while( pCur->mpPrev ) { ++rowNo; pCur = pCur->mpPrev; }
759
760 while( pBar )
761 {
762 cbHiddenBarInfo* pHBInfo = new cbHiddenBarInfo();
763
764 pHBInfo->mpBar = pBar;
765 pHBInfo->mRowNo = rowNo;
766 pHBInfo->mIconNo = iconCnt;
767 pHBInfo->mAlignment = mpPane->mAlignment;
768
769 mHiddenBars.Append( (wxObject*) pHBInfo );
770
771 // hide it
772 if ( pBar->mpBarWnd )
773
774 pBar->mpBarWnd->Show( FALSE );
775
776 pBar->mState = wxCBAR_HIDDEN;
777
778 cbBarInfo* pNext = pBar->mpNext;
779
780 pBar->mpRow = NULL;
781 pBar->mpNext = NULL;
782 pBar->mpPrev = NULL;
783
784 pBar = pNext;
785 }
786
787 mpPane->GetRowList().Remove( pRow );
788 mpPane->InitLinksForRows();
789
790 delete pRow;
791
792 SetPaneMargins();
793
794 mpLayout->RecalcLayout(FALSE);
795
796 mpRowInFocus = NULL;
797
798 mpLayout->GetUpdatesManager().OnFinishChanges();
799 mpLayout->GetUpdatesManager().UpdateNow();
800 }
801
802 void cbRowDragPlugin::ExpandRow( int collapsedIconIdx )
803 {
804 mpLayout->GetUpdatesManager().OnStartChanges();
805
806 cbRowInfo* pNewRow = new cbRowInfo();
807
808 wxNode* pNode = mHiddenBars.First();
809
810 int rowNo = 0;
811
812 // move bars from internal list to the newly expanded row
813
814 while( pNode )
815 {
816 cbHiddenBarInfo* pHBInfo = (cbHiddenBarInfo*)pNode->Data();
817
818 if ( pHBInfo->mAlignment == mpPane->mAlignment &&
819 pHBInfo->mIconNo == collapsedIconIdx )
820 {
821 rowNo = pHBInfo->mRowNo;
822
823 if ( pHBInfo->mpBar->mState == wxCBAR_HIDDEN )
824 {
825 pNewRow->mBars.Add( pHBInfo->mpBar );
826
827 pHBInfo->mpBar->mState = ( mpPane->IsHorizontal() )
828 ? wxCBAR_DOCKED_HORIZONTALLY
829 : wxCBAR_DOCKED_VERTICALLY;
830 }
831
832 // remove bar info from internal list
833
834 wxNode* pNext = pNode->Next();
835
836 delete pHBInfo;
837 mHiddenBars.DeleteNode( pNode );
838
839 pNode = pNext;
840 }
841 else
842 {
843 // decrease incon numbers with higher indicies, since this
844 // row is now removed from the hidden-rows list
845
846 if ( pHBInfo->mIconNo > collapsedIconIdx &&
847 pHBInfo->mAlignment == mpPane->mAlignment )
848
849 --pHBInfo->mIconNo;
850
851 pNode = pNode->Next();
852 }
853 }
854
855 mpPane->InitLinksForRow( pNewRow );
856
857 // insert row into pane at it's original position
858
859 if ( pNewRow->mBars.GetCount() )
860 {
861 cbRowInfo* beforeRowNode = mpPane->GetRow( rowNo );
862
863 mpPane->InsertRow( pNewRow, beforeRowNode );
864 }
865 else
866 delete pNewRow;
867
868 SetPaneMargins();
869
870 mpLayout->RecalcLayout(FALSE);
871
872 mCollapsedIconInFocus = -1;
873
874 mpLayout->GetUpdatesManager().OnFinishChanges();
875 mpLayout->GetUpdatesManager().UpdateNow();
876
877
878 /*
879 wxNode* pRowNode = mHiddenRows.Nth( collapsedIconIdx );
880
881 mpLayout->GetUpdatesManager().OnStartChanges();
882
883 // insert at the end of rows list
884 mpPane->InsertRow( pRowNode, NULL );
885
886 int success = mHiddenRows.DeleteNode( pRowNode );
887 // DBG::
888 wxASSERT( success );
889
890 SetPaneMargins();
891
892 mpLayout->RecalcLayout(FALSE);
893
894 mCollapsedIconInFocus = -1;
895
896 mpLayout->GetUpdatesManager().OnFinishChanges();
897 mpLayout->GetUpdatesManager().UpdateNow();
898 */
899 }
900
901 void cbRowDragPlugin::InsertDraggedRowBefore( cbRowInfo* pBeforeRow )
902 {
903 if ( mpRowInFocus != pBeforeRow &&
904 mpRowInFocus->mpNext != pBeforeRow
905 )
906 {
907 mpPane->GetRowList().Remove( mpRowInFocus );
908
909 mpPane->InsertRow( mpRowInFocus, pBeforeRow );
910 }
911 else
912 {
913 // otherwise, nothing has happned (row positions do not change)
914
915 //wxClientDC dc( &mpLayout->GetParentFrame() );
916
917 //mpPane->PaintRow( mpRowInFocus, dc );
918 //DrawRowDragHint( mpRowInFocus, dc, FALSE );
919 }
920 }
921
922 bool cbRowDragPlugin::ItemIsInFocus()
923 {
924 return ( mpRowInFocus || mCollapsedIconInFocus != - 1 );
925 }
926
927 void cbRowDragPlugin::CheckPrevItemInFocus( cbRowInfo* pRow, int iconIdx )
928 {
929 wxClientDC dc( &mpLayout->GetParentFrame() );
930
931 if ( pRow != NULL && mpRowInFocus == pRow ) return;
932 if ( iconIdx != -1 && mCollapsedIconInFocus == iconIdx ) return;
933
934 UnhighlightItemInFocus();
935
936 if ( iconIdx != - 1 )
937
938 DrawCollapsedRowIcon( iconIdx, dc, TRUE );
939
940 else
941 if ( pRow != NULL )
942
943 DrawRowDragHint( pRow, dc, TRUE );
944 }
945
946 cbRowInfo* cbRowDragPlugin::GetFirstRow()
947 {
948 return ( mpPane->GetRowList().GetCount() )
949 ? mpPane->GetRowList()[0]
950 : NULL;
951 }
952
953 /*** "hard-coded" metafile for NN-look ***/
954
955 void cbRowDragPlugin::DrawTrianUp( wxRect& inRect, wxDC& dc )
956 {
957 int xOfs = (inRect.width - ICON_TRIAN_WIDTH)/2;
958
959 wxBrush br( mTrianInnerColor, wxSOLID );
960
961 dc.SetBrush( br );
962 dc.SetPen( mpLayout->mBlackPen );
963
964 wxPoint points[3];
965 points[0].x = inRect.x + xOfs;
966 points[0].y = inRect.y + inRect.height - 1;
967 points[1].x = inRect.x + xOfs + ICON_TRIAN_WIDTH/2 + 1;
968 points[1].y = inRect.y + inRect.height - 2 - ICON_TRIAN_HEIGHT;
969 points[2].x = inRect.x + xOfs + ICON_TRIAN_WIDTH+1;
970 points[2].y = inRect.y + inRect.height - 1;
971
972 dc.DrawPolygon( 3, points );
973
974 // higlight upper-right edge of triangle
975 dc.SetPen( mpLayout->mLightPen );
976 dc.DrawLine( points[2].x, points[2].y,
977 points[0].x, points[0].y );
978
979 dc.SetBrush( wxNullBrush );
980 }
981
982 void cbRowDragPlugin::DrawTrianDown( wxRect& inRect, wxDC& dc )
983 {
984 int xOfs = (inRect.width - ICON_TRIAN_WIDTH)/2;
985
986 wxBrush br( mTrianInnerColor, wxSOLID );
987
988 dc.SetBrush( br );
989 dc.SetPen( mpLayout->mBlackPen );
990
991 wxPoint points[3];
992 points[0].x = inRect.x + xOfs;
993 points[0].y = inRect.y;
994 points[1].x = inRect.x + xOfs + ICON_TRIAN_WIDTH;
995 points[1].y = inRect.y;
996 points[2].x = inRect.x + xOfs + ICON_TRIAN_WIDTH/2;
997 points[2].y = inRect.y + ICON_TRIAN_HEIGHT;
998
999 dc.DrawPolygon( 3, points );
1000
1001 // higlight upper-right edge of triangle
1002 dc.SetPen( mpLayout->mLightPen );
1003 dc.DrawLine( points[2].x, points[2].y,
1004 points[1].x, points[1].y );
1005
1006 dc.SetBrush( wxNullBrush );
1007 }
1008
1009 void cbRowDragPlugin::DrawTrianRight( wxRect& inRect, wxDC& dc )
1010 {
1011 int yOfs = (inRect.height - ICON_TRIAN_WIDTH)/2;
1012
1013 wxBrush br( mTrianInnerColor, wxSOLID );
1014
1015 dc.SetBrush( br );
1016 dc.SetPen( mpLayout->mBlackPen );
1017
1018 wxPoint points[3];
1019 points[0].x = inRect.x;
1020 points[0].y = inRect.y + yOfs + ICON_TRIAN_WIDTH;
1021 points[1].x = inRect.x;
1022 points[1].y = inRect.y + yOfs;
1023 points[2].x = inRect.x + ICON_TRIAN_HEIGHT;
1024 points[2].y = inRect.y + yOfs + ICON_TRIAN_WIDTH/2;
1025
1026 dc.DrawPolygon( 3, points );
1027
1028 // higlight upper-right edge of triangle
1029 dc.SetPen( mpLayout->mLightPen );
1030 dc.DrawLine( points[0].x, points[0].y,
1031 points[2].x, points[2].y );
1032
1033 dc.SetBrush( wxNullBrush );
1034 }
1035
1036 void cbRowDragPlugin::Draw3DPattern( wxRect& inRect, wxDC& dc )
1037 {
1038 for( int y = inRect.y; y < inRect.y + inRect.height; y+=3 )
1039
1040 for( int x = inRect.x; x < inRect.x + inRect.width; x+=3 )
1041 {
1042 dc.SetPen( mpLayout->mLightPen );
1043 dc.DrawPoint( x,y );
1044 dc.SetPen( mpLayout->mBlackPen );
1045 dc.DrawPoint( x+1, y+1 );
1046 }
1047 }
1048
1049 void cbRowDragPlugin::DrawRombShades( wxPoint& p1, wxPoint& p2,
1050 wxPoint& p3, wxPoint& p4,
1051 wxDC& dc )
1052 {
1053 dc.SetPen( mpLayout->mLightPen );
1054 dc.DrawLine( p1.x, p1.y, p2.x, p2.y );
1055 dc.DrawLine( p2.x, p2.y, p3.x, p3.y );
1056 dc.SetPen( mpLayout->mDarkPen );
1057 dc.DrawLine( p3.x, p3.y, p4.x, p4.y );
1058 dc.DrawLine( p4.x, p4.y, p1.x, p1.y );
1059 }
1060
1061 void cbRowDragPlugin::DrawOrtoRomb( wxRect& inRect, wxDC& dc, wxBrush& bkBrush )
1062 {
1063 dc.SetBrush( bkBrush );
1064 dc.SetPen( mpLayout->mBlackPen );
1065
1066 wxPoint points[4];
1067
1068 if ( inRect.width > inRect.height )
1069 {
1070 // horizontal orienation
1071 points[0].x = inRect.x;
1072 points[0].y = inRect.y + inRect.height;
1073 points[1].x = inRect.x;
1074 points[1].y = inRect.y;
1075 points[2].x = inRect.x + inRect.width;
1076 points[2].y = inRect.y;
1077 points[3].x = inRect.x + inRect.width - COLLAPSED_ICON_HEIGHT;
1078 points[3].y = inRect.y + inRect.height;
1079
1080 dc.DrawPolygon( 4, points );
1081
1082 // squeeze romb's bounds to create an inner-shade shape
1083 ++points[0].x;
1084 --points[0].y;
1085 ++points[1].x;
1086 ++points[1].y;
1087 --points[2].x; --points[2].x;
1088 ++points[2].y;
1089 --points[3].y;
1090
1091 DrawRombShades( points[0], points[1], points[2], points[3], dc );
1092 }
1093 else
1094 {
1095 // vertical orientation
1096 points[0].x = inRect.x + inRect.width;
1097 points[0].y = inRect.y + inRect.height;
1098 points[1].x = inRect.x;
1099 points[1].y = inRect.y + inRect.height;
1100 points[2].x = inRect.x;
1101 points[2].y = inRect.y;
1102 points[3].x = inRect.x + inRect.width;
1103 points[3].y = inRect.y + COLLAPSED_ICON_HEIGHT;
1104
1105 dc.DrawPolygon( 4, points );
1106
1107 // squeeze romb's bounds to create an inner-shade shape
1108 --points[0].y ;
1109 --points[0].x;
1110 ++points[1].x;
1111 --points[1].y;
1112 ++points[2].y; ++points[2].y;
1113 ++points[2].x;
1114 --points[3].x;
1115
1116 DrawRombShades( points[1], points[2], points[3], points[0], dc );
1117 }
1118
1119 dc.SetBrush( wxNullBrush );
1120 }
1121
1122 void cbRowDragPlugin::DrawRomb( wxRect& inRect, wxDC& dc, wxBrush& bkBrush )
1123 {
1124 wxPoint points[4];
1125
1126 dc.SetBrush( bkBrush );
1127 dc.SetPen( mpLayout->mBlackPen );
1128
1129 if ( inRect.width > inRect.height )
1130 {
1131 // horizontal orientation
1132 points[0].x = inRect.x;
1133 points[0].y = inRect.y + inRect.height;
1134 points[1].x = inRect.x + COLLAPSED_ICON_HEIGHT;
1135 points[1].y = inRect.y;
1136 points[2].x = inRect.x + inRect.width;
1137 points[2].y = inRect.y;
1138 points[3].x = inRect.x + inRect.width - COLLAPSED_ICON_HEIGHT;
1139 points[3].y = inRect.y + inRect.height;
1140
1141 dc.DrawPolygon( 4, points );
1142
1143 // squeeze romb's bounds to create an inner-shade shape
1144 ++points[0].x ;++points[0].x ;
1145 --points[0].y;
1146 ++points[1].y;
1147 --points[2].x; --points[2].x;
1148 ++points[2].y;
1149 //--points[3].x ;
1150 --points[3].y;
1151
1152 DrawRombShades( points[0], points[1], points[2], points[3], dc );
1153
1154 }
1155 else
1156 {
1157 // vertical orientation
1158 points[0].x = inRect.x + inRect.width;
1159 points[0].y = inRect.y + inRect.height;
1160 points[1].x = inRect.x;
1161 points[1].y = inRect.y + inRect.height - COLLAPSED_ICON_HEIGHT;
1162 points[2].x = inRect.x;
1163 points[2].y = inRect.y;
1164 points[3].x = inRect.x + inRect.width;
1165 points[3].y = inRect.y + COLLAPSED_ICON_HEIGHT;
1166
1167 dc.DrawPolygon( 4, points );
1168
1169 // squeeze romb's bounds to create an inner-shade shape
1170 --points[0].y ;--points[0].y ;
1171 --points[0].x;
1172 ++points[1].x;
1173 ++points[2].y; ++points[2].y;
1174 ++points[2].x;
1175 --points[3].x;
1176
1177 DrawRombShades( points[1], points[2], points[3], points[0], dc );
1178 }
1179
1180 dc.SetBrush( wxNullBrush );
1181 }
1182
1183 void cbRowDragPlugin::DrawRectShade( wxRect& inRect, wxDC& dc,
1184 int level, wxPen& upperPen, wxPen& lowerPen )
1185 {
1186 // upper shade
1187 dc.SetPen( upperPen );
1188 dc.DrawLine( inRect.x - level,
1189 inRect.y - level,
1190 inRect.x + inRect.width - 1 + level,
1191 inRect.y - level);
1192 dc.DrawLine( inRect.x - level, inRect.y - level,
1193 inRect.x - level, inRect.y + inRect.height - 1 + level );
1194
1195 // lower shade
1196 dc.SetPen( lowerPen );
1197 dc.DrawLine( inRect.x - level,
1198 inRect.y + inRect.height - 1 + level,
1199 inRect.x + inRect.width + level,
1200 inRect.y + inRect.height - 1 + level);
1201 dc.DrawLine( inRect.x + inRect.width - 1 + level,
1202 inRect.y - level,
1203 inRect.x + inRect.width - 1 + level,
1204 inRect.y + inRect.height + level);
1205
1206 dc.SetBrush( wxNullBrush );
1207 }
1208
1209 void cbRowDragPlugin::Draw3DRect( wxRect& inRect, wxDC& dc, wxBrush& bkBrush )
1210 {
1211 dc.SetPen( mpLayout->mNullPen );
1212 dc.SetBrush( bkBrush );
1213
1214 dc.DrawRectangle( inRect.x, inRect.y,
1215 inRect.width, inRect.height );
1216
1217 DrawRectShade( inRect, dc, 0, mpLayout->mLightPen, mpLayout->mDarkPen );
1218 }
1219
1220 int cbRowDragPlugin::GetCollapsedIconsPos()
1221 {
1222 RowArrayT& rows = mpPane->GetRowList();
1223
1224 if ( rows.GetCount() == 0 )
1225 {
1226 if ( mpPane->IsHorizontal() )
1227
1228 return mpPane->mBoundsInParent.y + mpPane->mTopMargin;
1229 else
1230 return mpPane->mBoundsInParent.x + mpPane->mLeftMargin;
1231 }
1232
1233 wxRect& bounds = rows[ rows.GetCount() - 1 ]->mBoundsInParent;
1234
1235 if ( mpPane->IsHorizontal() )
1236
1237 return bounds.y + bounds.height + 1;
1238 else
1239 return bounds.x + bounds.width + 1;
1240
1241 }
1242
1243 void cbRowDragPlugin::GetRowHintRect( cbRowInfo* pRow, wxRect& rect )
1244 {
1245 wxRect& bounds = pRow->mBoundsInParent;
1246
1247 if ( mpPane->IsHorizontal() )
1248 {
1249 rect.x = bounds.x - ROW_DRAG_HINT_WIDTH - 1;
1250 rect.y = bounds.y;
1251 rect.width = ROW_DRAG_HINT_WIDTH;
1252 rect.height = bounds.height;
1253 }
1254 else
1255 {
1256 rect.x = bounds.x;
1257 rect.y = bounds.y + bounds.height + 1;
1258 rect.width = bounds.width;
1259 rect.height = ROW_DRAG_HINT_WIDTH;
1260 }
1261 }
1262
1263 void cbRowDragPlugin::GetCollapsedInconRect( int iconIdx, wxRect& rect )
1264 {
1265 int upper = GetCollapsedIconsPos();
1266
1267 int right = (iconIdx == 0 )
1268 ? 0 : iconIdx * (COLLAPSED_ICON_WIDTH - COLLAPSED_ICON_HEIGHT);
1269
1270 if ( mpPane->IsHorizontal() )
1271 {
1272 rect.x = mpPane->mBoundsInParent.x + mpPane->mLeftMargin - ROW_DRAG_HINT_WIDTH - 1
1273 + right;
1274
1275 rect.y = upper;
1276 rect.width = COLLAPSED_ICON_WIDTH;
1277 rect.height = COLLAPSED_ICON_HEIGHT;
1278 }
1279 else
1280 {
1281 rect.x = upper;
1282 rect.y = mpPane->mBoundsInParent.y + mpPane->mBoundsInParent.height
1283 - mpPane->mBottomMargin + ROW_DRAG_HINT_WIDTH + 1
1284 - right - COLLAPSED_ICON_WIDTH;
1285
1286 rect.height = COLLAPSED_ICON_WIDTH;
1287 rect.width = COLLAPSED_ICON_HEIGHT;
1288 }
1289 }
1290
1291 /*** overridables ***/
1292
1293 void cbRowDragPlugin::DrawCollapsedRowIcon( int index, wxDC& dc, bool isHighlighted )
1294 {
1295 wxRect rect;
1296 GetCollapsedInconRect( index, rect );
1297
1298 wxBrush hiBrush ( mHightColor, wxSOLID );
1299 wxBrush lowBrush( mLowColor, wxSOLID );
1300 wxBrush& curBrush = ( isHighlighted ) ? hiBrush : lowBrush;
1301
1302 if ( mpPane->IsHorizontal() )
1303 {
1304 if ( index == 0 )
1305
1306 DrawOrtoRomb( rect, dc, curBrush );
1307 else
1308 DrawRomb( rect, dc, curBrush );
1309
1310 int triOfs = (index == 0) ? TRIANGLE_OFFSET : TRIANGLE_OFFSET + COLLAPSED_ICON_HEIGHT;
1311
1312 wxRect triRect;
1313 triRect.x = triOfs + rect.x;
1314
1315 triRect.width = ICON_TRIAN_HEIGHT;
1316 triRect.y = rect.y;
1317 triRect.height = rect.height;
1318
1319 DrawTrianRight( triRect, dc );
1320
1321 wxRect patRect;
1322 patRect.x = triOfs + ICON_TRIAN_HEIGHT + TRIANGLE_TO_PAT_GAP + rect.x;
1323 patRect.y = rect.y + PAT_OFFSET;
1324 patRect.width = rect.width - (patRect.x - rect.x) - COLLAPSED_ICON_HEIGHT - PAT_OFFSET;
1325 patRect.height = rect.height - PAT_OFFSET*2;
1326
1327 Draw3DPattern( patRect, dc );
1328 }
1329 else
1330 {
1331 if ( index == 0 )
1332
1333 DrawOrtoRomb( rect, dc, curBrush );
1334 else
1335 DrawRomb( rect, dc, curBrush );
1336
1337 int triOfs = (index == 0)
1338 ? TRIANGLE_OFFSET + ICON_TRIAN_HEIGHT
1339 : TRIANGLE_OFFSET + COLLAPSED_ICON_HEIGHT + ICON_TRIAN_HEIGHT;
1340
1341 wxRect triRect;
1342 triRect.y = rect.y + rect.height - triOfs;
1343 triRect.x = rect.x;
1344 triRect.width = rect.width;
1345 triRect.height = ICON_TRIAN_HEIGHT;
1346
1347 DrawTrianUp( triRect, dc );
1348
1349 wxRect patRect;
1350 patRect.y = rect.y + COLLAPSED_ICON_HEIGHT + PAT_OFFSET;
1351 patRect.x = rect.x + PAT_OFFSET;
1352 patRect.width = rect.width - 2*PAT_OFFSET ;
1353 patRect.height = rect.height - triOfs - 2*PAT_OFFSET - COLLAPSED_ICON_HEIGHT;
1354
1355 Draw3DPattern( patRect, dc );
1356 }
1357 }
1358
1359 void cbRowDragPlugin::DrawRowDragHint( cbRowInfo* pRow , wxDC& dc, bool isHighlighted )
1360 {
1361 wxRect rect;
1362 GetRowHintRect( pRow, rect );
1363
1364 wxBrush hiBrush ( mHightColor, wxSOLID );
1365 wxBrush lowBrush( mLowColor, wxSOLID );
1366 wxBrush& curBrush = ( isHighlighted ) ? hiBrush : lowBrush;
1367
1368 Draw3DRect( rect, dc, curBrush );
1369
1370 if ( mpPane->IsHorizontal() )
1371 {
1372 wxRect triRect;
1373 triRect.y = rect.y + TRIANGLE_OFFSET;
1374 triRect.x = rect.x;
1375 triRect.width = rect.width;
1376 triRect.height = ICON_TRIAN_HEIGHT;
1377
1378 DrawTrianDown( triRect, dc );
1379
1380 wxRect patRect;
1381 patRect.x = rect.x + PAT_OFFSET;
1382 patRect.y = rect.y + TRIANGLE_OFFSET + ICON_TRIAN_HEIGHT + TRIANGLE_TO_PAT_GAP;
1383 patRect.width = rect.width - 2*PAT_OFFSET;
1384 patRect.height = rect.height - ( patRect.y - rect.y ) - PAT_OFFSET;
1385 Draw3DPattern( patRect, dc );
1386
1387 dc.SetPen( mpLayout->mLightPen );
1388 dc.DrawLine( rect.x, rect.y + rect.height, rect.x + rect.width, rect.y + rect.height );
1389 }
1390 else
1391 {
1392 wxRect triRect;
1393 triRect.x = rect.x + TRIANGLE_OFFSET;
1394 triRect.y = rect.y;
1395 triRect.height = rect.height;
1396 triRect.width = ICON_TRIAN_HEIGHT;
1397
1398 DrawTrianRight( triRect, dc );
1399
1400 wxRect patRect;
1401 patRect.y = rect.y + PAT_OFFSET;
1402 patRect.x = rect.x + TRIANGLE_OFFSET + ICON_TRIAN_HEIGHT + TRIANGLE_TO_PAT_GAP;
1403 patRect.height = rect.height - 2*PAT_OFFSET;
1404 patRect.width = rect.width - ( patRect.x - rect.x ) - PAT_OFFSET;
1405 Draw3DPattern( patRect, dc );
1406
1407 dc.SetPen( mpLayout->mLightPen );
1408 dc.DrawLine( rect.x + rect.width, rect.y, rect.x + rect.width, rect.y + rect.height );
1409 }
1410 }
1411
1412 void cbRowDragPlugin::DrawRowsDragHintsBorder( wxDC& dc )
1413 {
1414 // FIXME:: what was that?
1415 }
1416
1417 void cbRowDragPlugin::DrawCollapsedRowsBorder( wxDC& dc )
1418 {
1419 int colRowOfs = GetCollapsedIconsPos();
1420 wxRect& bounds = mpPane->mBoundsInParent;
1421
1422 wxBrush bkBrush( mpLayout->mGrayPen.GetColour(), wxSOLID );
1423 dc.SetBrush( bkBrush );
1424 dc.SetPen( mpLayout->mDarkPen );
1425
1426 if ( mpPane->IsHorizontal() )
1427
1428 dc.DrawRectangle( bounds.x + mpPane->mLeftMargin - ROW_DRAG_HINT_WIDTH - 1,
1429 colRowOfs,
1430 bounds.width - mpPane->mLeftMargin - mpPane->mRightMargin + 2 + ROW_DRAG_HINT_WIDTH,
1431 COLLAPSED_ICON_HEIGHT + 1);
1432 else
1433 dc.DrawRectangle( colRowOfs,
1434 bounds.y + mpPane->mTopMargin - 1,
1435 COLLAPSED_ICON_HEIGHT + 1,
1436 bounds.height - mpPane->mTopMargin - mpPane->mBottomMargin
1437 - ROW_DRAG_HINT_WIDTH - 2 );
1438
1439 dc.SetBrush( wxNullBrush );
1440 }
1441
1442 static inline bool rect_contains_point( const wxRect& rect, int x, int y )
1443 {
1444 return ( x >= rect.x &&
1445 y >= rect.y &&
1446 x < rect.x + rect.width &&
1447 y < rect.y + rect.height );
1448 }
1449
1450 bool cbRowDragPlugin::HitTestCollapsedRowIcon( int iconIdx, const wxPoint& pos )
1451 {
1452 wxRect bounds;
1453 GetCollapsedInconRect( iconIdx, bounds );
1454
1455 return rect_contains_point( bounds, pos.x, pos.y );
1456 }
1457
1458 bool cbRowDragPlugin::HitTestRowDragHint( cbRowInfo* pRow, const wxPoint& pos )
1459 {
1460 wxRect bounds;
1461 GetRowHintRect( pRow, bounds );
1462
1463 return rect_contains_point( bounds, pos.x, pos.y );
1464 }
1465