]> git.saurik.com Git - wxWidgets.git/blame - contrib/src/fl/rowdragpl.cpp
switch back to non appearance fonts until problems are solved
[wxWidgets.git] / contrib / src / fl / rowdragpl.cpp
CommitLineData
8e08b761 1/////////////////////////////////////////////////////////////////////////////
4cbc57f0
JS
2// Name: rowdragpl.cpp
3// Purpose: cbRowDragPlugin implementation.
8e08b761
JS
4// Author: Aleksandras Gluchovas
5// Modified by:
6// Created: 06/10/98
7// RCS-ID: $Id$
8// Copyright: (c) Aleksandras Gluchovas
4cbc57f0 9// Licence: wxWindows licence
8e08b761
JS
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
44IMPLEMENT_DYNAMIC_CLASS( cbHiddenBarInfo, wxObject )
45
46/***** Implementation for class cbRowDragPlugin *****/
47
48IMPLEMENT_DYNAMIC_CLASS( cbRowDragPlugin, cbPluginBase )
49
50BEGIN_EVENT_TABLE( cbRowDragPlugin, cbPluginBase )
51
4cbc57f0
JS
52 EVT_PL_LEFT_DOWN ( cbRowDragPlugin::OnLButtonDown )
53 EVT_PL_LEFT_UP ( cbRowDragPlugin::OnLButtonUp )
54 EVT_PL_MOTION ( cbRowDragPlugin::OnMouseMove )
8e08b761 55
4cbc57f0 56 EVT_PL_DRAW_PANE_DECOR ( cbRowDragPlugin::OnDrawPaneBackground )
8e08b761
JS
57
58END_EVENT_TABLE()
59
4cbc57f0 60// FIXME:: how to eliminated these cut and pasted constructors?
8e08b761
JS
61
62cbRowDragPlugin::cbRowDragPlugin(void)
63
4cbc57f0
JS
64 : mHightColor ( 192, 192, 255 ),
65 mLowColor ( 192, 192, 192 ),
8e08b761 66 mTrianInnerColor ( 0,0,255 ),
4cbc57f0 67 mTrianInnerPen ( mTrianInnerColor, 1, wxSOLID ),
8e08b761
JS
68
69 mDragStarted ( FALSE ),
4cbc57f0
JS
70 mDecisionMode ( FALSE ),
71 mCurDragOfs ( 0 ),
72 mCaptureIsOn ( FALSE ),
8e08b761 73 mSvTopMargin ( -1 ),
4cbc57f0
JS
74 mSvBottomMargin ( -1 ),
75 mSvLeftMargin ( -1 ),
76 mSvRightMargin ( -1 ),
8e08b761
JS
77
78 mpPaneImage ( NULL ),
4cbc57f0
JS
79 mpRowImage ( NULL ),
80 mpCombinedImage ( NULL ),
8e08b761 81
4cbc57f0
JS
82 mpRowInFocus ( NULL ),
83 mCollapsedIconInFocus( -1 ),
84
85 mpPane ( NULL )
8e08b761
JS
86{
87}
88
89cbRowDragPlugin::cbRowDragPlugin( wxFrameLayout* pLayout, int paneMask )
90
4cbc57f0
JS
91 : cbPluginBase( pLayout, paneMask ),
92
93 mHightColor ( 192, 192, 255 ),
94 mLowColor ( 192, 192, 192 ),
8e08b761 95 mTrianInnerColor ( 0,0,255 ),
4cbc57f0 96 mTrianInnerPen ( mTrianInnerColor, 1, wxSOLID ),
8e08b761
JS
97
98 mDragStarted ( FALSE ),
4cbc57f0
JS
99 mDecisionMode ( FALSE ),
100 mCurDragOfs ( 0 ),
101 mCaptureIsOn ( FALSE ),
102 mSvTopMargin ( -1 ),
103 mSvBottomMargin ( -1 ),
104 mSvLeftMargin ( -1 ),
105 mSvRightMargin ( -1 ),
8e08b761
JS
106
107 mpPaneImage ( NULL ),
108 mpRowImage ( NULL ),
4cbc57f0 109 mpCombinedImage ( NULL ),
8e08b761 110
4cbc57f0
JS
111 mpRowInFocus ( NULL ),
112 mCollapsedIconInFocus( -1 ),
113
114 mpPane ( NULL )
8e08b761
JS
115{
116}
117
118cbRowDragPlugin::~cbRowDragPlugin()
119{
120}
121
122// handlers for plugin events
123void cbRowDragPlugin::OnMouseMove( cbMotionEvent& event )
124{
4cbc57f0
JS
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 }
8e08b761
JS
250}
251
252void cbRowDragPlugin::OnLButtonDown( cbLeftDownEvent& event )
253{
4cbc57f0 254 mpPane = event.mpPane;
8e08b761 255
4cbc57f0
JS
256 // DBG::
257 wxASSERT( !mDragStarted && !mDecisionMode );
8e08b761 258
4cbc57f0
JS
259 if ( ItemIsInFocus() )
260 {
261 mDecisionMode = TRUE;
8e08b761 262
4cbc57f0
JS
263 wxPoint pos = event.mPos;
264 mpPane->PaneToFrame( &pos.x, &pos.y );
8e08b761 265
4cbc57f0 266 mDragOrigin = pos;
8e08b761 267
4cbc57f0
JS
268 SetMouseCapture( TRUE );
269 }
270 else
271 // propagate event to other plugins
272 event.Skip();
8e08b761
JS
273}
274
275void cbRowDragPlugin::OnLButtonUp ( cbLeftUpEvent& event )
276{
4cbc57f0
JS
277 if ( !mDragStarted && !mDecisionMode )
278 {
279 event.Skip();
280 return;
281 }
8e08b761 282
4cbc57f0 283 mpPane = event.mpPane;
8e08b761 284
4cbc57f0
JS
285 if ( mDecisionMode )
286 {
287 cbDockPane* pPane = mpPane;
8e08b761 288
4cbc57f0 289 SetMouseCapture( FALSE );
8e08b761 290
4cbc57f0
JS
291 mDecisionMode = FALSE;
292 mDragStarted = FALSE;
8e08b761 293
4cbc57f0
JS
294 wxPoint frmPos = event.mPos;
295 pPane->PaneToFrame( &frmPos.x, &frmPos.y );
8e08b761 296
4cbc57f0
JS
297 if ( mpRowInFocus )
298 {
299 CollapseRow( mpRowInFocus );
300 mpRowInFocus = 0;
301 }
302 else
303 {
304 ExpandRow( mCollapsedIconInFocus );
305 mCollapsedIconInFocus = -1;
306 }
8e08b761 307
4cbc57f0
JS
308 mpRowInFocus = NULL;
309 mpPane = pPane;
8e08b761 310
4cbc57f0 311 pPane->FrameToPane( &frmPos.x, &frmPos.y );
8e08b761 312
4cbc57f0 313 // give it another try after relayouting bars
8e08b761 314
4cbc57f0
JS
315 cbMotionEvent moveEvt( frmPos, pPane );
316 this->OnMouseMove( moveEvt );
8e08b761 317
4cbc57f0 318 // this plugin has "eaten" the mouse-up event
8e08b761 319
4cbc57f0
JS
320 return;
321 }
322 else
323 {
324 // otherwise, the dragged row was dropped, determine
325 // where to insert it
8e08b761 326
4cbc57f0
JS
327 // restore initial pane appearence
328 ShowPaneImage();
329 FinishOnScreenDraw();
8e08b761 330
4cbc57f0 331 cbRowInfo* pRow = GetFirstRow();
8e08b761 332
4cbc57f0 333 mpLayout->GetUpdatesManager().OnStartChanges();
8e08b761 334
4cbc57f0 335 pRow->mUMgrData.SetDirty(TRUE);
8e08b761 336
4cbc57f0 337 cbBarInfo* pBar = mpRowInFocus->mBars[0];
8e08b761 338
4cbc57f0
JS
339 while ( pBar )
340 {
341 pBar->mUMgrData.SetDirty(TRUE);
8e08b761 342
4cbc57f0
JS
343 if ( pBar->mpBarWnd )
344 {
345 // do complete refresh
346 pBar->mpBarWnd->Show(FALSE);
347 pBar->mpBarWnd->Show(TRUE);
348 }
8e08b761 349
4cbc57f0
JS
350 pBar = pBar->mpNext;
351 }
8e08b761 352
4cbc57f0
JS
353 while( pRow )
354 {
355 if ( mCurDragOfs < pRow->mRowY )
356 {
357 InsertDraggedRowBefore( pRow );
358 break;
359 }
8e08b761 360
4cbc57f0
JS
361 pRow = pRow->mpNext;
362 }
8e08b761 363
4cbc57f0 364 if ( pRow == NULL ) InsertDraggedRowBefore( NULL );
8e08b761 365
4cbc57f0 366 mpRowInFocus = NULL;
8e08b761 367
4cbc57f0 368 mpLayout->RecalcLayout(FALSE);
8e08b761 369
4cbc57f0
JS
370 // finish change "transaction"
371 mpLayout->GetUpdatesManager().OnFinishChanges();
372 mpLayout->GetUpdatesManager().UpdateNow();
8e08b761 373
4cbc57f0
JS
374 // finish drag action
375 SetMouseCapture( FALSE );
376 mDragStarted = FALSE;
377 }
8e08b761
JS
378}
379
380void cbRowDragPlugin::OnDrawPaneBackground ( cbDrawPaneDecorEvent& event )
381{
4cbc57f0 382 mpPane = event.mpPane;
8e08b761 383
4cbc57f0 384 // FIXME:: this may harm operation of other plugins
8e08b761 385
4cbc57f0
JS
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 }
8e08b761 393
4cbc57f0 394 wxClientDC dc( &mpLayout->GetParentFrame() );
8e08b761 395
4cbc57f0
JS
396 dc.SetClippingRegion( mpPane->mBoundsInParent.x,
397 mpPane->mBoundsInParent.y,
398 mpPane->mBoundsInParent.width,
399 mpPane->mBoundsInParent.height );
8e08b761 400
4cbc57f0 401 int cnt = GetHRowsCountForPane( event.mpPane );
8e08b761 402
4cbc57f0 403 if ( cnt > 0 )
8e08b761 404
4cbc57f0 405 DrawCollapsedRowsBorder( dc );
8e08b761 406
4cbc57f0
JS
407 if ( mpPane->GetRowList().GetCount() )
408
409 DrawRowsDragHintsBorder( dc );
8e08b761 410
4cbc57f0 411 cbRowInfo* pRow = GetFirstRow();
8e08b761 412
4cbc57f0
JS
413 while( pRow )
414 {
415 DrawRowDragHint( pRow, dc, FALSE );
416 pRow = pRow->mpNext;
417 }
8e08b761 418
4cbc57f0 419 for( int i = 0; i != cnt; ++i )
8e08b761 420
4cbc57f0 421 DrawCollapsedRowIcon(i, dc, FALSE );
8e08b761
JS
422}
423
424int cbRowDragPlugin::GetHRowsCountForPane( cbDockPane* pPane )
425{
4cbc57f0 426 wxNode* pNode = mHiddenBars.First();
8e08b761 427
4cbc57f0 428 int maxIconNo = -1;
8e08b761 429
4cbc57f0
JS
430 while( pNode )
431 {
432 cbHiddenBarInfo* pHBInfo = (cbHiddenBarInfo*)pNode->Data();
8e08b761 433
4cbc57f0 434 if ( pHBInfo->mAlignment == pPane->mAlignment )
8e08b761 435
4cbc57f0 436 maxIconNo = wxMax( maxIconNo, pHBInfo->mIconNo );
8e08b761 437
4cbc57f0
JS
438 pNode = pNode->Next();
439 }
8e08b761 440
4cbc57f0 441 return ( maxIconNo + 1 );
8e08b761
JS
442}
443
444int cbRowDragPlugin::GetCollapsedRowIconHeight()
445{
4cbc57f0 446 return COLLAPSED_ICON_HEIGHT;
8e08b761
JS
447}
448
449int cbRowDragPlugin::GetRowDragHintWidth()
450{
4cbc57f0 451 return ROW_DRAG_HINT_WIDTH;
8e08b761
JS
452}
453
454void cbRowDragPlugin::SetPaneMargins()
455{
4cbc57f0
JS
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 }
8e08b761
JS
485}
486
487void cbRowDragPlugin::OnInitPlugin()
488{
4cbc57f0 489 cbDockPane** panes = mpLayout->GetPanesArray();
8e08b761 490
4cbc57f0 491 for( int i = 0; i != MAX_PANES; ++i )
8e08b761 492
4cbc57f0
JS
493 if ( panes[i]->MatchesMask( mPaneMask ) )
494 {
495 mpPane = panes[i];
8e08b761 496
4cbc57f0
JS
497 SetPaneMargins();
498 }
8e08b761
JS
499}
500
501/*** helpers for drag&drop ***/
502
503void cbRowDragPlugin::SetMouseCapture( bool captureOn )
504{
4cbc57f0
JS
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;
8e08b761
JS
519}
520
4cbc57f0 521void cbRowDragPlugin::UnhighlightItemInFocus()
8e08b761 522{
4cbc57f0 523 wxClientDC dc( &mpLayout->GetParentFrame() );
8e08b761 524
4cbc57f0 525 if ( mpRowInFocus )
8e08b761 526
4cbc57f0
JS
527 DrawRowDragHint( mpRowInFocus, dc, FALSE );
528 else
529 if ( mCollapsedIconInFocus != - 1 )
8e08b761 530
4cbc57f0 531 DrawCollapsedRowIcon( mCollapsedIconInFocus, dc, FALSE );
8e08b761
JS
532}
533
534void cbRowDragPlugin::ShowDraggedRow( int offset )
535{
4cbc57f0
JS
536 // create combined image of pane and dragged
537 // row on it, in the mpCombinedImage bitmap
8e08b761 538
4cbc57f0
JS
539 if ( mpPane->IsHorizontal() )
540 {
541 if ( mInitialRowOfs + offset + mRowImgDim.y > mCombRect.y + mCombRect.height )
8e08b761 542
4cbc57f0 543 offset = mCombRect.y + mCombRect.height - mRowImgDim.y - mInitialRowOfs;
8e08b761 544
4cbc57f0 545 if ( mInitialRowOfs + offset < mCombRect.y )
8e08b761 546
4cbc57f0 547 offset = mCombRect.y - mInitialRowOfs;
8e08b761 548
4cbc57f0
JS
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 )
8e08b761 556
4cbc57f0 557 offset = mCombRect.x + mCombRect.width - mRowImgDim.x - mInitialRowOfs;
8e08b761 558
4cbc57f0 559 if ( mInitialRowOfs + offset < mCombRect.x )
8e08b761 560
4cbc57f0 561 offset = mCombRect.x - mInitialRowOfs;
8e08b761 562
4cbc57f0
JS
563 int x = mInitialRowOfs + offset, y;
564 mpPane->FrameToPane( &x, &y );
565 mCurDragOfs = x;
566 }
8e08b761 567
4cbc57f0
JS
568 wxMemoryDC rowImgDc;
569 rowImgDc.SelectObject ( *mpRowImage );
8e08b761 570
4cbc57f0
JS
571 wxMemoryDC paneImgDc;
572 paneImgDc.SelectObject( *mpPaneImage );
8e08b761 573
4cbc57f0
JS
574 wxMemoryDC combImgDc;
575 combImgDc.SelectObject( *mpCombinedImage );
8e08b761 576
4cbc57f0
JS
577 combImgDc.Blit( 0,0, mCombRect.width, mCombRect.height,
578 &paneImgDc, 0,0, wxCOPY );
8e08b761 579
4cbc57f0
JS
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 }
8e08b761 593
4cbc57f0
JS
594 int scrX = mCombRect.x,
595 scrY = mCombRect.y;
8e08b761 596
4cbc57f0 597 mpLayout->GetParentFrame().ClientToScreen( &scrX, &scrY );
8e08b761 598
4cbc57f0
JS
599 mpScrDc->Blit( scrX, scrY, mCombRect.width, mCombRect.height,
600 &combImgDc, 0,0, wxCOPY );
8e08b761 601
4cbc57f0
JS
602 rowImgDc .SelectObject( wxNullBitmap );
603 paneImgDc.SelectObject( wxNullBitmap );
604 combImgDc.SelectObject( wxNullBitmap );
8e08b761
JS
605}
606
607wxBitmap* cbRowDragPlugin::CaptureDCArea( wxDC& dc, wxRect& area )
608{
4cbc57f0 609 wxBitmap* pBmp = new wxBitmap( int(area.width), int(area.height) );
8e08b761 610
4cbc57f0
JS
611 wxMemoryDC mdc;
612 mdc.SelectObject( *pBmp );
8e08b761 613
4cbc57f0
JS
614 mdc.Blit( 0,0, area.width, area.height, &dc, area.x, area.y, wxCOPY );
615 mdc.SelectObject( wxNullBitmap );
8e08b761 616
4cbc57f0 617 return pBmp;
8e08b761
JS
618}
619
620void cbRowDragPlugin::PrepareForRowDrag()
621{
4cbc57f0 622 wxRect rowBounds = mpRowInFocus->mBoundsInParent;
8e08b761 623
4cbc57f0
JS
624 if ( mpPane->IsHorizontal() )
625 {
626 mCombRect = mpPane->mBoundsInParent;
8e08b761 627
4cbc57f0
JS
628 mCombRect.x += mpPane->mLeftMargin - ROW_DRAG_HINT_WIDTH - 1;
629 mCombRect.y += mpPane->mTopMargin;
8e08b761 630
4cbc57f0
JS
631 mCombRect.width -= mpPane->mLeftMargin + mpPane->mRightMargin - ROW_DRAG_HINT_WIDTH - 1 - 1;
632 mCombRect.height -= mpPane->mTopMargin + mpPane->mBottomMargin;
8e08b761 633
4cbc57f0
JS
634 mCombRect.height += 2*rowBounds.height;
635 mCombRect.y -= rowBounds.height;
636 mInitialRowOfs = rowBounds.y;
8e08b761 637
4cbc57f0
JS
638 rowBounds.y -= 1;
639 rowBounds.height += 2;
640 rowBounds.x = mCombRect.x;
641 rowBounds.width = mCombRect.width;
8e08b761 642
4cbc57f0
JS
643 mRowImgDim.y = rowBounds.height;
644 }
645 else
646 {
647 mCombRect = mpPane->mBoundsInParent;
8e08b761 648
4cbc57f0
JS
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;
8e08b761 654
4cbc57f0
JS
655 mCombRect.width += 2*rowBounds.width;
656 mCombRect.x -= rowBounds.width;
657 mInitialRowOfs = rowBounds.x;
8e08b761 658
4cbc57f0
JS
659 rowBounds.x -= 1;
660 rowBounds.width += 2;
661 rowBounds.y = mCombRect.y;
662 rowBounds.height = mCombRect.height;
8e08b761 663
4cbc57f0
JS
664 mRowImgDim.x = rowBounds.width;
665 }
666 // output cobination results onto frame's client area
667 wxScreenDC::StartDrawingOnTop(&mpLayout->GetParentFrame());
668 mpScrDc = new wxScreenDC();
8e08b761 669
4cbc57f0
JS
670 int x = mCombRect.x, y = mCombRect.y;
671 mpLayout->GetParentFrame().ClientToScreen( &x, &y );
8e08b761 672
4cbc57f0
JS
673 wxRect scrRect = mCombRect;
674 scrRect.x = x;
675 scrRect.y = y;
8e08b761 676
4cbc57f0 677 mpPaneImage = CaptureDCArea( *mpScrDc, scrRect );
8e08b761 678
4cbc57f0
JS
679 wxMemoryDC mdc;
680 mdc.SelectObject( *mpPaneImage );
681 mdc.SetDeviceOrigin( -mCombRect.x, -mCombRect.y );
8e08b761 682
4cbc57f0
JS
683 DrawRectShade( rowBounds, mdc, -1, mpLayout->mGrayPen, mpLayout->mDarkPen );
684 DrawRectShade( rowBounds, mdc, 0, mpLayout->mLightPen, mpLayout->mBlackPen );
8e08b761 685
4cbc57f0 686 mpRowImage = CaptureDCArea( mdc, rowBounds );
8e08b761 687
4cbc57f0
JS
688 // draw dark empty-row placeholder
689 DrawEmptyRow( mdc, rowBounds );
8e08b761 690
4cbc57f0
JS
691 //DrawRectShade( rowBounds, mdc, 0, mpLayout->mGrayPen, mpLayout->mDarkPen );
692 DrawRectShade( rowBounds, mdc, -1, mpLayout->mGrayPen, mpLayout->mGrayPen );
8e08b761 693
4cbc57f0 694 mdc.SelectObject( wxNullBitmap );
8e08b761 695
4cbc57f0 696 mpCombinedImage = new wxBitmap( int(mCombRect.width), int(mCombRect.height) );
8e08b761 697
4cbc57f0
JS
698 // show it for the first time
699 ShowDraggedRow( 0 );
8e08b761
JS
700}
701
702void cbRowDragPlugin::DrawEmptyRow( wxDC& dc, wxRect& rowBounds )
703{
4cbc57f0 704 wxBrush bkBrush( mpLayout->mDarkPen.GetColour(), wxSOLID );
8e08b761 705
4cbc57f0 706 // paint the "dark" empty-row placeholder
8e08b761 707
4cbc57f0
JS
708 dc.SetBrush( bkBrush );
709 dc.SetPen ( mpLayout->mNullPen );
8e08b761 710
4cbc57f0
JS
711 dc.DrawRectangle( rowBounds.x, rowBounds.y,
712 rowBounds.width+1, rowBounds.height+1 );
8e08b761 713
4cbc57f0 714 dc.SetBrush( wxNullBrush );
8e08b761
JS
715}
716
717void cbRowDragPlugin::ShowPaneImage()
718{
4cbc57f0 719 int scrX = 0, scrY = 0;
8e08b761 720
4cbc57f0 721 mpLayout->GetParentFrame().ClientToScreen( &scrX, &scrY );
8e08b761 722
4cbc57f0
JS
723 wxMemoryDC mdc;
724 mdc.SelectObject( *mpPaneImage );
8e08b761 725
4cbc57f0
JS
726 mpScrDc->Blit( mCombRect.x + scrX, mCombRect.y + scrY,
727 mCombRect.width, mCombRect.height,
728 &mdc, 0,0, wxCOPY );
8e08b761 729
4cbc57f0 730 mdc.SelectObject( wxNullBitmap );
8e08b761
JS
731}
732
733void cbRowDragPlugin::FinishOnScreenDraw()
734{
4cbc57f0 735 wxScreenDC::EndDrawingOnTop();
8e08b761 736
4cbc57f0
JS
737 delete mpScrDc;
738 delete mpCombinedImage;
739 delete mpPaneImage;
740 delete mpRowImage;
8e08b761 741
4cbc57f0
JS
742 mpScrDc = NULL;
743
744 mpCombinedImage = mpPaneImage = mpRowImage = NULL;
8e08b761
JS
745}
746
747void cbRowDragPlugin::CollapseRow( cbRowInfo* pRow )
748{
4cbc57f0 749 int iconCnt = GetHRowsCountForPane( mpPane );
8e08b761 750
4cbc57f0 751 mpLayout->GetUpdatesManager().OnStartChanges();
8e08b761 752
4cbc57f0 753 cbBarInfo* pBar = pRow->mBars[0];
8e08b761 754
4cbc57f0 755 int rowNo = 0;
8e08b761 756
4cbc57f0
JS
757 cbRowInfo* pCur = pRow;
758 while( pCur->mpPrev ) { ++rowNo; pCur = pCur->mpPrev; }
8e08b761 759
4cbc57f0
JS
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;
8e08b761 768
4cbc57f0 769 mHiddenBars.Append( (wxObject*) pHBInfo );
8e08b761 770
4cbc57f0
JS
771 // hide it
772 if ( pBar->mpBarWnd )
8e08b761 773
4cbc57f0 774 pBar->mpBarWnd->Show( FALSE );
8e08b761 775
4cbc57f0 776 pBar->mState = wxCBAR_HIDDEN;
8e08b761 777
4cbc57f0 778 cbBarInfo* pNext = pBar->mpNext;
8e08b761 779
4cbc57f0
JS
780 pBar->mpRow = NULL;
781 pBar->mpNext = NULL;
782 pBar->mpPrev = NULL;
8e08b761 783
4cbc57f0
JS
784 pBar = pNext;
785 }
8e08b761 786
4cbc57f0
JS
787 mpPane->GetRowList().Remove( pRow );
788 mpPane->InitLinksForRows();
8e08b761 789
4cbc57f0 790 delete pRow;
8e08b761 791
4cbc57f0 792 SetPaneMargins();
8e08b761 793
4cbc57f0 794 mpLayout->RecalcLayout(FALSE);
8e08b761 795
4cbc57f0 796 mpRowInFocus = NULL;
8e08b761 797
4cbc57f0
JS
798 mpLayout->GetUpdatesManager().OnFinishChanges();
799 mpLayout->GetUpdatesManager().UpdateNow();
8e08b761
JS
800}
801
802void cbRowDragPlugin::ExpandRow( int collapsedIconIdx )
803{
4cbc57f0 804 mpLayout->GetUpdatesManager().OnStartChanges();
8e08b761 805
4cbc57f0 806 cbRowInfo* pNewRow = new cbRowInfo();
8e08b761 807
4cbc57f0 808 wxNode* pNode = mHiddenBars.First();
8e08b761 809
4cbc57f0 810 int rowNo = 0;
8e08b761 811
4cbc57f0 812 // move bars from internal list to the newly expanded row
8e08b761 813
4cbc57f0
JS
814 while( pNode )
815 {
816 cbHiddenBarInfo* pHBInfo = (cbHiddenBarInfo*)pNode->Data();
8e08b761 817
4cbc57f0
JS
818 if ( pHBInfo->mAlignment == mpPane->mAlignment &&
819 pHBInfo->mIconNo == collapsedIconIdx )
820 {
821 rowNo = pHBInfo->mRowNo;
8e08b761 822
4cbc57f0
JS
823 if ( pHBInfo->mpBar->mState == wxCBAR_HIDDEN )
824 {
825 pNewRow->mBars.Add( pHBInfo->mpBar );
8e08b761 826
4cbc57f0
JS
827 pHBInfo->mpBar->mState = ( mpPane->IsHorizontal() )
828 ? wxCBAR_DOCKED_HORIZONTALLY
829 : wxCBAR_DOCKED_VERTICALLY;
830 }
8e08b761 831
4cbc57f0 832 // remove bar info from internal list
8e08b761 833
4cbc57f0 834 wxNode* pNext = pNode->Next();
8e08b761 835
4cbc57f0
JS
836 delete pHBInfo;
837 mHiddenBars.DeleteNode( pNode );
8e08b761 838
4cbc57f0
JS
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
8e08b761 845
4cbc57f0
JS
846 if ( pHBInfo->mIconNo > collapsedIconIdx &&
847 pHBInfo->mAlignment == mpPane->mAlignment )
8e08b761 848
4cbc57f0 849 --pHBInfo->mIconNo;
8e08b761 850
4cbc57f0
JS
851 pNode = pNode->Next();
852 }
853 }
8e08b761 854
4cbc57f0 855 mpPane->InitLinksForRow( pNewRow );
8e08b761 856
4cbc57f0 857 // insert row into pane at it's original position
8e08b761 858
4cbc57f0
JS
859 if ( pNewRow->mBars.GetCount() )
860 {
861 cbRowInfo* beforeRowNode = mpPane->GetRow( rowNo );
8e08b761 862
4cbc57f0
JS
863 mpPane->InsertRow( pNewRow, beforeRowNode );
864 }
865 else
866 delete pNewRow;
8e08b761 867
4cbc57f0 868 SetPaneMargins();
8e08b761 869
4cbc57f0 870 mpLayout->RecalcLayout(FALSE);
8e08b761 871
4cbc57f0 872 mCollapsedIconInFocus = -1;
8e08b761 873
4cbc57f0
JS
874 mpLayout->GetUpdatesManager().OnFinishChanges();
875 mpLayout->GetUpdatesManager().UpdateNow();
8e08b761
JS
876
877
4cbc57f0
JS
878 /*
879 wxNode* pRowNode = mHiddenRows.Nth( collapsedIconIdx );
8e08b761 880
4cbc57f0 881 mpLayout->GetUpdatesManager().OnStartChanges();
8e08b761 882
4cbc57f0
JS
883 // insert at the end of rows list
884 mpPane->InsertRow( pRowNode, NULL );
8e08b761 885
4cbc57f0
JS
886 int success = mHiddenRows.DeleteNode( pRowNode );
887 // DBG::
888 wxASSERT( success );
8e08b761 889
4cbc57f0 890 SetPaneMargins();
8e08b761 891
4cbc57f0 892 mpLayout->RecalcLayout(FALSE);
8e08b761 893
4cbc57f0 894 mCollapsedIconInFocus = -1;
8e08b761 895
4cbc57f0
JS
896 mpLayout->GetUpdatesManager().OnFinishChanges();
897 mpLayout->GetUpdatesManager().UpdateNow();
898 */
8e08b761
JS
899}
900
901void cbRowDragPlugin::InsertDraggedRowBefore( cbRowInfo* pBeforeRow )
902{
4cbc57f0
JS
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 }
8e08b761
JS
920}
921
922bool cbRowDragPlugin::ItemIsInFocus()
923{
4cbc57f0 924 return ( mpRowInFocus || mCollapsedIconInFocus != - 1 );
8e08b761
JS
925}
926
927void cbRowDragPlugin::CheckPrevItemInFocus( cbRowInfo* pRow, int iconIdx )
928{
4cbc57f0 929 wxClientDC dc( &mpLayout->GetParentFrame() );
8e08b761 930
4cbc57f0
JS
931 if ( pRow != NULL && mpRowInFocus == pRow ) return;
932 if ( iconIdx != -1 && mCollapsedIconInFocus == iconIdx ) return;
8e08b761 933
4cbc57f0 934 UnhighlightItemInFocus();
8e08b761 935
4cbc57f0
JS
936 if ( iconIdx != - 1 )
937
938 DrawCollapsedRowIcon( iconIdx, dc, TRUE );
8e08b761 939
4cbc57f0
JS
940 else
941 if ( pRow != NULL )
8e08b761 942
4cbc57f0 943 DrawRowDragHint( pRow, dc, TRUE );
8e08b761
JS
944}
945
946cbRowInfo* cbRowDragPlugin::GetFirstRow()
947{
4cbc57f0
JS
948 return ( mpPane->GetRowList().GetCount() )
949 ? mpPane->GetRowList()[0]
950 : NULL;
8e08b761
JS
951}
952
953/*** "hard-coded" metafile for NN-look ***/
954
955void cbRowDragPlugin::DrawTrianUp( wxRect& inRect, wxDC& dc )
956{
4cbc57f0 957 int xOfs = (inRect.width - ICON_TRIAN_WIDTH)/2;
8e08b761 958
4cbc57f0 959 wxBrush br( mTrianInnerColor, wxSOLID );
8e08b761 960
4cbc57f0
JS
961 dc.SetBrush( br );
962 dc.SetPen( mpLayout->mBlackPen );
8e08b761 963
4cbc57f0
JS
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;
8e08b761 971
4cbc57f0 972 dc.DrawPolygon( 3, points );
8e08b761 973
4cbc57f0
JS
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 );
8e08b761 978
4cbc57f0 979 dc.SetBrush( wxNullBrush );
8e08b761
JS
980}
981
982void cbRowDragPlugin::DrawTrianDown( wxRect& inRect, wxDC& dc )
983{
4cbc57f0 984 int xOfs = (inRect.width - ICON_TRIAN_WIDTH)/2;
8e08b761 985
4cbc57f0 986 wxBrush br( mTrianInnerColor, wxSOLID );
8e08b761 987
4cbc57f0
JS
988 dc.SetBrush( br );
989 dc.SetPen( mpLayout->mBlackPen );
8e08b761 990
4cbc57f0
JS
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;
8e08b761 998
4cbc57f0 999 dc.DrawPolygon( 3, points );
8e08b761 1000
4cbc57f0
JS
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 );
8e08b761 1005
4cbc57f0 1006 dc.SetBrush( wxNullBrush );
8e08b761
JS
1007}
1008
1009void cbRowDragPlugin::DrawTrianRight( wxRect& inRect, wxDC& dc )
1010{
4cbc57f0 1011 int yOfs = (inRect.height - ICON_TRIAN_WIDTH)/2;
8e08b761 1012
4cbc57f0 1013 wxBrush br( mTrianInnerColor, wxSOLID );
8e08b761 1014
4cbc57f0
JS
1015 dc.SetBrush( br );
1016 dc.SetPen( mpLayout->mBlackPen );
8e08b761 1017
4cbc57f0
JS
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;
8e08b761 1025
4cbc57f0 1026 dc.DrawPolygon( 3, points );
8e08b761 1027
4cbc57f0
JS
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 );
8e08b761 1032
4cbc57f0 1033 dc.SetBrush( wxNullBrush );
8e08b761
JS
1034}
1035
1036void cbRowDragPlugin::Draw3DPattern( wxRect& inRect, wxDC& dc )
1037{
4cbc57f0
JS
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 }
8e08b761
JS
1047}
1048
1049void cbRowDragPlugin::DrawRombShades( wxPoint& p1, wxPoint& p2,
4cbc57f0
JS
1050 wxPoint& p3, wxPoint& p4,
1051 wxDC& dc )
8e08b761 1052{
4cbc57f0
JS
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 );
8e08b761
JS
1059}
1060
1061void cbRowDragPlugin::DrawOrtoRomb( wxRect& inRect, wxDC& dc, wxBrush& bkBrush )
1062{
4cbc57f0
JS
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 );
8e08b761
JS
1120}
1121
1122void cbRowDragPlugin::DrawRomb( wxRect& inRect, wxDC& dc, wxBrush& bkBrush )
1123{
4cbc57f0
JS
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 );
8e08b761
JS
1181}
1182
1183void cbRowDragPlugin::DrawRectShade( wxRect& inRect, wxDC& dc,
4cbc57f0 1184 int level, wxPen& upperPen, wxPen& lowerPen )
8e08b761 1185{
4cbc57f0
JS
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 );
8e08b761
JS
1207}
1208
1209void cbRowDragPlugin::Draw3DRect( wxRect& inRect, wxDC& dc, wxBrush& bkBrush )
1210{
4cbc57f0
JS
1211 dc.SetPen( mpLayout->mNullPen );
1212 dc.SetBrush( bkBrush );
8e08b761 1213
4cbc57f0
JS
1214 dc.DrawRectangle( inRect.x, inRect.y,
1215 inRect.width, inRect.height );
8e08b761 1216
4cbc57f0 1217 DrawRectShade( inRect, dc, 0, mpLayout->mLightPen, mpLayout->mDarkPen );
8e08b761
JS
1218}
1219
1220int cbRowDragPlugin::GetCollapsedIconsPos()
1221{
4cbc57f0 1222 RowArrayT& rows = mpPane->GetRowList();
8e08b761 1223
4cbc57f0
JS
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 }
8e08b761 1232
4cbc57f0 1233 wxRect& bounds = rows[ rows.GetCount() - 1 ]->mBoundsInParent;
8e08b761 1234
4cbc57f0 1235 if ( mpPane->IsHorizontal() )
8e08b761 1236
4cbc57f0
JS
1237 return bounds.y + bounds.height + 1;
1238 else
1239 return bounds.x + bounds.width + 1;
8e08b761
JS
1240
1241}
1242
1243void cbRowDragPlugin::GetRowHintRect( cbRowInfo* pRow, wxRect& rect )
1244{
4cbc57f0
JS
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 }
8e08b761
JS
1261}
1262
1263void cbRowDragPlugin::GetCollapsedInconRect( int iconIdx, wxRect& rect )
1264{
4cbc57f0
JS
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 }
8e08b761
JS
1289}
1290
1291/*** overridables ***/
1292
1293void cbRowDragPlugin::DrawCollapsedRowIcon( int index, wxDC& dc, bool isHighlighted )
1294{
4cbc57f0
JS
1295 wxRect rect;
1296 GetCollapsedInconRect( index, rect );
8e08b761 1297
4cbc57f0
JS
1298 wxBrush hiBrush ( mHightColor, wxSOLID );
1299 wxBrush lowBrush( mLowColor, wxSOLID );
1300 wxBrush& curBrush = ( isHighlighted ) ? hiBrush : lowBrush;
8e08b761 1301
4cbc57f0
JS
1302 if ( mpPane->IsHorizontal() )
1303 {
1304 if ( index == 0 )
8e08b761 1305
4cbc57f0
JS
1306 DrawOrtoRomb( rect, dc, curBrush );
1307 else
1308 DrawRomb( rect, dc, curBrush );
8e08b761 1309
4cbc57f0 1310 int triOfs = (index == 0) ? TRIANGLE_OFFSET : TRIANGLE_OFFSET + COLLAPSED_ICON_HEIGHT;
8e08b761 1311
4cbc57f0
JS
1312 wxRect triRect;
1313 triRect.x = triOfs + rect.x;
8e08b761 1314
4cbc57f0
JS
1315 triRect.width = ICON_TRIAN_HEIGHT;
1316 triRect.y = rect.y;
1317 triRect.height = rect.height;
8e08b761 1318
4cbc57f0 1319 DrawTrianRight( triRect, dc );
8e08b761 1320
4cbc57f0
JS
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;
8e08b761 1326
4cbc57f0
JS
1327 Draw3DPattern( patRect, dc );
1328 }
1329 else
1330 {
1331 if ( index == 0 )
8e08b761 1332
4cbc57f0
JS
1333 DrawOrtoRomb( rect, dc, curBrush );
1334 else
1335 DrawRomb( rect, dc, curBrush );
8e08b761 1336
4cbc57f0
JS
1337 int triOfs = (index == 0)
1338 ? TRIANGLE_OFFSET + ICON_TRIAN_HEIGHT
1339 : TRIANGLE_OFFSET + COLLAPSED_ICON_HEIGHT + ICON_TRIAN_HEIGHT;
8e08b761 1340
4cbc57f0
JS
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;
8e08b761 1346
4cbc57f0 1347 DrawTrianUp( triRect, dc );
8e08b761 1348
4cbc57f0
JS
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;
8e08b761 1354
4cbc57f0
JS
1355 Draw3DPattern( patRect, dc );
1356 }
8e08b761
JS
1357}
1358
1359void cbRowDragPlugin::DrawRowDragHint( cbRowInfo* pRow , wxDC& dc, bool isHighlighted )
1360{
4cbc57f0
JS
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 }
8e08b761
JS
1410}
1411
1412void cbRowDragPlugin::DrawRowsDragHintsBorder( wxDC& dc )
1413{
4cbc57f0 1414 // FIXME:: what was that?
8e08b761
JS
1415}
1416
1417void cbRowDragPlugin::DrawCollapsedRowsBorder( wxDC& dc )
1418{
4cbc57f0
JS
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 );
8e08b761
JS
1440}
1441
1442static inline bool rect_contains_point( const wxRect& rect, int x, int y )
1443{
4cbc57f0
JS
1444 return ( x >= rect.x &&
1445 y >= rect.y &&
1446 x < rect.x + rect.width &&
1447 y < rect.y + rect.height );
8e08b761
JS
1448}
1449
1450bool cbRowDragPlugin::HitTestCollapsedRowIcon( int iconIdx, const wxPoint& pos )
1451{
4cbc57f0
JS
1452 wxRect bounds;
1453 GetCollapsedInconRect( iconIdx, bounds );
8e08b761 1454
4cbc57f0 1455 return rect_contains_point( bounds, pos.x, pos.y );
8e08b761
JS
1456}
1457
1458bool cbRowDragPlugin::HitTestRowDragHint( cbRowInfo* pRow, const wxPoint& pos )
1459{
4cbc57f0
JS
1460 wxRect bounds;
1461 GetRowHintRect( pRow, bounds );
8e08b761 1462
4cbc57f0 1463 return rect_contains_point( bounds, pos.x, pos.y );
8e08b761
JS
1464}
1465