LCOV - code coverage report
Current view: top level - libreoffice/svtools/source/contnr - imivctl1.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 0 2147 0.0 %
Date: 2012-12-27 Functions: 0 151 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : 
      21             : #include <limits.h>
      22             : #include <tools/debug.hxx>
      23             : #include <vcl/wall.hxx>
      24             : #include <vcl/help.hxx>
      25             : #include <vcl/decoview.hxx>
      26             : #include <vcl/svapp.hxx>
      27             : #include <tools/poly.hxx>
      28             : #include <vcl/lineinfo.hxx>
      29             : #include <vcl/i18nhelp.hxx>
      30             : #include <vcl/mnemonic.hxx>
      31             : #include <vcl/controllayout.hxx>
      32             : 
      33             : #include <svtools/ivctrl.hxx>
      34             : #include "imivctl.hxx"
      35             : #include <svtools/svmedit.hxx>
      36             : 
      37             : #include <algorithm>
      38             : #include <memory>
      39             : 
      40             : #define IMPICNVIEW_ACC_RETURN 1
      41             : #define IMPICNVIEW_ACC_ESCAPE 2
      42             : 
      43             : #define DRAWTEXT_FLAGS_ICON \
      44             :     ( TEXT_DRAW_CENTER | TEXT_DRAW_TOP | TEXT_DRAW_ENDELLIPSIS | \
      45             :       TEXT_DRAW_CLIP | TEXT_DRAW_MULTILINE | TEXT_DRAW_WORDBREAK | TEXT_DRAW_MNEMONIC )
      46             : 
      47             : #define DRAWTEXT_FLAGS_SMALLICON (TEXT_DRAW_LEFT|TEXT_DRAW_ENDELLIPSIS|TEXT_DRAW_CLIP)
      48             : 
      49             : #define EVENTID_SHOW_CURSOR             ((void*)1)
      50             : #define EVENTID_ADJUST_SCROLLBARS       ((void*)2)
      51             : 
      52             : struct SvxIconChoiceCtrlEntry_Impl
      53             : {
      54             :     SvxIconChoiceCtrlEntry* _pEntry;
      55             :     Point           _aPos;
      56             :                     SvxIconChoiceCtrlEntry_Impl( SvxIconChoiceCtrlEntry* pEntry, const Rectangle& rBoundRect )
      57             :                     : _pEntry( pEntry), _aPos( rBoundRect.TopLeft()) {}
      58             : };
      59             : 
      60             : static sal_Bool bEndScrollInvalidate = sal_True;
      61             : 
      62             : class IcnViewEdit_Impl : public MultiLineEdit
      63             : {
      64             :     Link            aCallBackHdl;
      65             :     Accelerator     aAccReturn;
      66             :     Accelerator     aAccEscape;
      67             :     Timer           aTimer;
      68             :     sal_Bool            bCanceled;
      69             :     sal_Bool            bAlreadyInCallback;
      70             :     sal_Bool            bGrabFocus;
      71             : 
      72             :     void            CallCallBackHdl_Impl();
      73             :                     DECL_LINK(Timeout_Impl, void *);
      74             :                     DECL_LINK( ReturnHdl_Impl, Accelerator * );
      75             :                     DECL_LINK( EscapeHdl_Impl, Accelerator * );
      76             : 
      77             : public:
      78             : 
      79             :                     IcnViewEdit_Impl(
      80             :                         SvtIconChoiceCtrl* pParent,
      81             :                         const Point& rPos,
      82             :                         const Size& rSize,
      83             :                         const XubString& rData,
      84             :                         const Link& rNotifyEditEnd );
      85             : 
      86             :                     ~IcnViewEdit_Impl();
      87             :     virtual void    KeyInput( const KeyEvent& rKEvt );
      88             :     virtual long    PreNotify( NotifyEvent& rNEvt );
      89           0 :     sal_Bool            EditingCanceled() const { return bCanceled; }
      90             :     void            StopEditing( sal_Bool bCancel = sal_False );
      91           0 :     sal_Bool            IsGrabFocus() const { return bGrabFocus; }
      92             : };
      93             : 
      94           0 : SvxIconChoiceCtrl_Impl::SvxIconChoiceCtrl_Impl(
      95             :     SvtIconChoiceCtrl* pCurView,
      96             :     WinBits nWinStyle
      97             : ) :
      98             :     aEntries( this ),
      99             :     aVerSBar( pCurView, WB_DRAG | WB_VSCROLL ),
     100             :     aHorSBar( pCurView, WB_DRAG | WB_HSCROLL ),
     101             :     aScrBarBox( pCurView ),
     102             :     aImageSize( 32, 32 ),
     103           0 :     pColumns( 0 )
     104             : {
     105           0 :     bChooseWithCursor=sal_False;
     106           0 :     pEntryPaintDev = 0;
     107           0 :     pCurEditedEntry = 0;
     108           0 :     pCurHighlightFrame = 0;
     109           0 :     pEdit = 0;
     110           0 :     pAnchor = 0;
     111           0 :     pPrevDropTarget = 0;
     112           0 :     pHdlEntry = 0;
     113           0 :     pHead = NULL;
     114           0 :     pCursor = NULL;
     115           0 :     bUpdateMode = sal_True;
     116           0 :     bEntryEditingEnabled = sal_False;
     117           0 :     bHighlightFramePressed = sal_False;
     118           0 :     eSelectionMode = MULTIPLE_SELECTION;
     119           0 :     pView = pCurView;
     120           0 :     pZOrderList = new SvxIconChoiceCtrlEntryList_impl();
     121           0 :     ePositionMode = IcnViewPositionModeFree;
     122           0 :     SetStyle( nWinStyle );
     123           0 :     nFlags = 0;
     124           0 :     nUserEventAdjustScrBars = 0;
     125           0 :     nUserEventShowCursor = 0;
     126           0 :     nMaxVirtWidth = DEFAULT_MAX_VIRT_WIDTH;
     127           0 :     nMaxVirtHeight = DEFAULT_MAX_VIRT_HEIGHT;
     128           0 :     pDDRefEntry = 0;
     129           0 :     pDDDev = 0;
     130           0 :     pDDBufDev = 0;
     131           0 :     pDDTempDev = 0;
     132           0 :     eTextMode = IcnShowTextShort;
     133           0 :     pImpCursor = new IcnCursor_Impl( this );
     134           0 :     pGridMap = new IcnGridMap_Impl( this );
     135             : 
     136           0 :     aVerSBar.SetScrollHdl( LINK( this, SvxIconChoiceCtrl_Impl, ScrollUpDownHdl ) );
     137           0 :     aHorSBar.SetScrollHdl( LINK( this, SvxIconChoiceCtrl_Impl, ScrollLeftRightHdl ) );
     138           0 :     Link aEndScrollHdl( LINK( this, SvxIconChoiceCtrl_Impl, EndScrollHdl ) );
     139           0 :     aVerSBar.SetEndScrollHdl( aEndScrollHdl );
     140           0 :     aHorSBar.SetEndScrollHdl( aEndScrollHdl );
     141             : 
     142           0 :     nHorSBarHeight = aHorSBar.GetSizePixel().Height();
     143           0 :     nVerSBarWidth = aVerSBar.GetSizePixel().Width();
     144             : 
     145           0 :     aEditTimer.SetTimeout( 800 );
     146           0 :     aEditTimer.SetTimeoutHdl(LINK(this,SvxIconChoiceCtrl_Impl,EditTimeoutHdl));
     147           0 :     aAutoArrangeTimer.SetTimeout( 100 );
     148           0 :     aAutoArrangeTimer.SetTimeoutHdl(LINK(this,SvxIconChoiceCtrl_Impl,AutoArrangeHdl));
     149           0 :     aCallSelectHdlTimer.SetTimeout( 500 );
     150           0 :     aCallSelectHdlTimer.SetTimeoutHdl( LINK(this,SvxIconChoiceCtrl_Impl,CallSelectHdlHdl));
     151             : 
     152           0 :     aDocRectChangedTimer.SetTimeout( 50 );
     153           0 :     aDocRectChangedTimer.SetTimeoutHdl(LINK(this,SvxIconChoiceCtrl_Impl,DocRectChangedHdl));
     154           0 :     aVisRectChangedTimer.SetTimeout( 50 );
     155           0 :     aVisRectChangedTimer.SetTimeoutHdl(LINK(this,SvxIconChoiceCtrl_Impl,VisRectChangedHdl));
     156             : 
     157           0 :     Clear( sal_True );
     158             : 
     159           0 :     SetGrid( Size(100, 70) );
     160           0 : }
     161             : 
     162           0 : SvxIconChoiceCtrl_Impl::~SvxIconChoiceCtrl_Impl()
     163             : {
     164           0 :     pCurEditedEntry = 0;
     165           0 :     DELETEZ(pEdit);
     166           0 :     Clear();
     167           0 :     StopEditTimer();
     168           0 :     CancelUserEvents();
     169           0 :     delete pZOrderList;
     170           0 :     delete pImpCursor;
     171           0 :     delete pGridMap;
     172           0 :     delete pDDDev;
     173           0 :     delete pDDBufDev;
     174           0 :     delete pDDTempDev;
     175           0 :     delete pEntryPaintDev;
     176           0 :     ClearSelectedRectList();
     177           0 :     ClearColumnList();
     178           0 : }
     179             : 
     180           0 : void SvxIconChoiceCtrl_Impl::Clear( sal_Bool bInCtor )
     181             : {
     182           0 :     StopEntryEditing( sal_True );
     183           0 :     nSelectionCount = 0;
     184           0 :     pCurHighlightFrame = 0;
     185           0 :     StopEditTimer();
     186           0 :     CancelUserEvents();
     187           0 :     ShowCursor( sal_False );
     188           0 :     bBoundRectsDirty = sal_False;
     189           0 :     nMaxBoundHeight = 0;
     190             : 
     191           0 :     nFlags &= ~(F_PAINTED | F_MOVED_ENTRIES);
     192           0 :     pCursor = 0;
     193           0 :     if( !bInCtor )
     194             :     {
     195           0 :         pImpCursor->Clear();
     196           0 :         pGridMap->Clear();
     197           0 :         aVirtOutputSize.Width() = 0;
     198           0 :         aVirtOutputSize.Height() = 0;
     199           0 :         Size aSize( pView->GetOutputSizePixel() );
     200           0 :         nMaxVirtWidth = aSize.Width() - nVerSBarWidth;
     201           0 :         if( nMaxVirtWidth <= 0 )
     202           0 :             nMaxVirtWidth = DEFAULT_MAX_VIRT_WIDTH;
     203           0 :         nMaxVirtHeight = aSize.Height() - nHorSBarHeight;
     204           0 :         if( nMaxVirtHeight <= 0 )
     205           0 :             nMaxVirtHeight = DEFAULT_MAX_VIRT_HEIGHT;
     206           0 :         pZOrderList->clear();
     207           0 :         SetOrigin( Point() );
     208           0 :         if( bUpdateMode )
     209           0 :             pView->Invalidate(INVALIDATE_NOCHILDREN);
     210             :     }
     211           0 :     AdjustScrollBars();
     212           0 :     size_t nCount = aEntries.size();
     213           0 :     for( size_t nCur = 0; nCur < nCount; nCur++ )
     214             :     {
     215           0 :         SvxIconChoiceCtrlEntry* pCur = aEntries[ nCur ];
     216           0 :         delete pCur;
     217             :     }
     218           0 :     aEntries.clear();
     219           0 :     DocRectChanged();
     220           0 :     VisRectChanged();
     221           0 : }
     222             : 
     223           0 : void SvxIconChoiceCtrl_Impl::SetStyle( WinBits nWinStyle )
     224             : {
     225           0 :     nWinBits = nWinStyle;
     226           0 :     nCurTextDrawFlags = DRAWTEXT_FLAGS_ICON;
     227           0 :     if( nWinBits & (WB_SMALLICON | WB_DETAILS) )
     228           0 :         nCurTextDrawFlags = DRAWTEXT_FLAGS_SMALLICON;
     229           0 :     if( nWinBits & WB_NOSELECTION )
     230           0 :         eSelectionMode = NO_SELECTION;
     231           0 :     if( !(nWinStyle & (WB_ALIGN_TOP | WB_ALIGN_LEFT)))
     232           0 :         nWinBits |= WB_ALIGN_LEFT;
     233           0 :     if( (nWinStyle & WB_DETAILS))
     234             :     {
     235           0 :         if( !pColumns  )
     236           0 :             SetColumn( 0, SvxIconChoiceCtrlColumnInfo( 0, 100, IcnViewAlignLeft ));
     237             :     }
     238           0 : }
     239             : 
     240           0 : IMPL_LINK( SvxIconChoiceCtrl_Impl, ScrollUpDownHdl, ScrollBar*, pScrollBar )
     241             : {
     242           0 :     StopEntryEditing( sal_True );
     243             :     // arrow up: delta=-1; arrow down: delta=+1
     244           0 :     Scroll( 0, pScrollBar->GetDelta(), sal_True );
     245           0 :     bEndScrollInvalidate = sal_True;
     246           0 :     return 0;
     247             : }
     248             : 
     249           0 : IMPL_LINK( SvxIconChoiceCtrl_Impl, ScrollLeftRightHdl, ScrollBar*, pScrollBar )
     250             : {
     251           0 :     StopEntryEditing( sal_True );
     252             :     // arrow left: delta=-1; arrow right: delta=+1
     253           0 :     Scroll( pScrollBar->GetDelta(), 0, sal_True );
     254           0 :     bEndScrollInvalidate = sal_True;
     255           0 :     return 0;
     256             : }
     257             : 
     258           0 : IMPL_LINK_NOARG(SvxIconChoiceCtrl_Impl, EndScrollHdl)
     259             : {
     260           0 :     if( pView->HasBackground() && !pView->GetBackground().IsScrollable() &&
     261             :         bEndScrollInvalidate )
     262             :     {
     263           0 :         pView->Invalidate(INVALIDATE_NOCHILDREN);
     264             :     }
     265           0 :     return 0;
     266             : }
     267             : 
     268           0 : void SvxIconChoiceCtrl_Impl::FontModified()
     269             : {
     270           0 :     StopEditTimer();
     271           0 :     DELETEZ(pDDDev);
     272           0 :     DELETEZ(pDDBufDev);
     273           0 :     DELETEZ(pDDTempDev);
     274           0 :     DELETEZ(pEntryPaintDev);
     275           0 :     SetDefaultTextSize();
     276           0 :     ShowCursor( sal_False );
     277           0 :     ShowCursor( sal_True );
     278           0 : }
     279             : 
     280           0 : void SvxIconChoiceCtrl_Impl::InsertEntry( SvxIconChoiceCtrlEntry* pEntry, size_t nPos,
     281             :     const Point* pPos )
     282             : {
     283           0 :     StopEditTimer();
     284           0 :     aEntries.insert( nPos, pEntry );
     285           0 :     if( (nFlags & F_ENTRYLISTPOS_VALID) && nPos >= aEntries.size() - 1 )
     286           0 :         pEntry->nPos = aEntries.size() - 1;
     287             :     else
     288           0 :         nFlags &= ~F_ENTRYLISTPOS_VALID;
     289             : 
     290           0 :     pZOrderList->push_back( pEntry );
     291           0 :     pImpCursor->Clear();
     292           0 :     if( pPos )
     293             :     {
     294           0 :         Size aSize( CalcBoundingSize( pEntry ) );
     295           0 :         SetBoundingRect_Impl( pEntry, *pPos, aSize );
     296           0 :         SetEntryPos( pEntry, *pPos, sal_False, sal_True, sal_True /*keep grid map*/ );
     297           0 :         pEntry->nFlags |= ICNVIEW_FLAG_POS_MOVED;
     298           0 :         SetEntriesMoved( sal_True );
     299             :     }
     300             :     else
     301             :     {
     302             :         // If the UpdateMode is sal_True, don't set all bounding rectangles to
     303             :         // 'to be checked', but only the bounding rectangle of the new entry.
     304             :         // Thus, don't call InvalidateBoundingRect!
     305           0 :         pEntry->aRect.Right() = LONG_MAX;
     306           0 :         if( bUpdateMode )
     307             :         {
     308           0 :             FindBoundingRect( pEntry );
     309           0 :             Rectangle aOutputArea( GetOutputRect() );
     310           0 :             pGridMap->OccupyGrids( pEntry );
     311           0 :             if( !aOutputArea.IsOver( pEntry->aRect ) )
     312           0 :                 return; // is invisible
     313           0 :             pView->Invalidate( pEntry->aRect );
     314             :         }
     315             :         else
     316           0 :             InvalidateBoundingRect( pEntry->aRect );
     317             :     }
     318             : }
     319             : 
     320           0 : void SvxIconChoiceCtrl_Impl::CreateAutoMnemonics( MnemonicGenerator* _pGenerator )
     321             : {
     322           0 :     ::std::auto_ptr< MnemonicGenerator > pAutoDeleteOwnGenerator;
     323           0 :     if ( !_pGenerator )
     324             :     {
     325           0 :         _pGenerator = new MnemonicGenerator;
     326           0 :         pAutoDeleteOwnGenerator.reset( _pGenerator );
     327             :     }
     328             : 
     329           0 :     sal_uLong   nEntryCount = GetEntryCount();
     330             :     sal_uLong   i;
     331             : 
     332             :     // insert texts in generator
     333           0 :     for( i = 0; i < nEntryCount; ++i )
     334             :     {
     335             :         DBG_ASSERT( GetEntry( i ), "-SvxIconChoiceCtrl_Impl::CreateAutoMnemonics(): more expected than provided!" );
     336             : 
     337           0 :         _pGenerator->RegisterMnemonic( GetEntry( i )->GetText() );
     338             :     }
     339             : 
     340             :     // exchange texts with generated mnemonics
     341           0 :     for( i = 0; i < nEntryCount; ++i )
     342             :     {
     343           0 :         SvxIconChoiceCtrlEntry* pEntry = GetEntry( i );
     344           0 :         String                  aTxt = pEntry->GetText();
     345             : 
     346           0 :         if( _pGenerator->CreateMnemonic( aTxt ) )
     347           0 :             pEntry->SetText( aTxt );
     348           0 :     }
     349           0 : }
     350             : 
     351           0 : Rectangle SvxIconChoiceCtrl_Impl::GetOutputRect() const
     352             : {
     353           0 :     Point aOrigin( pView->GetMapMode().GetOrigin() );
     354           0 :     aOrigin *= -1;
     355           0 :     return Rectangle( aOrigin, aOutputSize );
     356             : }
     357             : 
     358           0 : void SvxIconChoiceCtrl_Impl::SetListPositions()
     359             : {
     360           0 :     if( nFlags & F_ENTRYLISTPOS_VALID )
     361           0 :         return;
     362             : 
     363           0 :     size_t nCount = aEntries.size();
     364           0 :     for( size_t nCur = 0; nCur < nCount; nCur++ )
     365             :     {
     366           0 :         SvxIconChoiceCtrlEntry* pEntry = aEntries[ nCur ];
     367           0 :         pEntry->nPos = nCur;
     368             :     }
     369           0 :     nFlags |= F_ENTRYLISTPOS_VALID;
     370             : }
     371             : 
     372           0 : void SvxIconChoiceCtrl_Impl::SelectEntry( SvxIconChoiceCtrlEntry* pEntry, sal_Bool bSelect,
     373             :     sal_Bool bCallHdl, sal_Bool bAdd, sal_Bool bSyncPaint )
     374             : {
     375           0 :     if( eSelectionMode == NO_SELECTION )
     376           0 :         return;
     377             : 
     378           0 :     if( !bAdd )
     379             :     {
     380           0 :         if ( 0 == ( nFlags & F_CLEARING_SELECTION ) )
     381             :         {
     382           0 :             nFlags |= F_CLEARING_SELECTION;
     383           0 :             DeselectAllBut( pEntry, sal_True );
     384           0 :             nFlags &= ~F_CLEARING_SELECTION;
     385             :         }
     386             :     }
     387           0 :     if( pEntry->IsSelected() != bSelect )
     388             :     {
     389           0 :         pHdlEntry = pEntry;
     390           0 :         sal_uInt16 nEntryFlags = pEntry->GetFlags();
     391           0 :         if( bSelect )
     392             :         {
     393           0 :             nEntryFlags |= ICNVIEW_FLAG_SELECTED;
     394           0 :             pEntry->AssignFlags( nEntryFlags );
     395           0 :             nSelectionCount++;
     396           0 :             if( bCallHdl )
     397           0 :                 CallSelectHandler( pEntry );
     398             :         }
     399             :         else
     400             :         {
     401           0 :             nEntryFlags &= ~( ICNVIEW_FLAG_SELECTED);
     402           0 :             pEntry->AssignFlags( nEntryFlags );
     403           0 :             nSelectionCount--;
     404           0 :             if( bCallHdl )
     405           0 :                 CallSelectHandler( 0 );
     406             :         }
     407           0 :         EntrySelected( pEntry, bSelect, bSyncPaint );
     408             :     }
     409             : }
     410             : 
     411           0 : void SvxIconChoiceCtrl_Impl::EntrySelected( SvxIconChoiceCtrlEntry* pEntry, sal_Bool bSelect,
     412             :     sal_Bool bSyncPaint )
     413             : {
     414             :     // When using SingleSelection, make sure that the cursor is always placed
     415             :     // over the (only) selected entry. (But only if a cursor exists.)
     416           0 :     if( bSelect && pCursor &&
     417             :         eSelectionMode == SINGLE_SELECTION &&
     418             :         pEntry != pCursor )
     419             :     {
     420           0 :         SetCursor( pEntry );
     421             :         //DBG_ASSERT(pView->GetSelectionCount()==1,"selection count?")
     422             :     }
     423             : 
     424             :     // Not when dragging though, else the loop in SelectRect doesn't work
     425             :     // correctly!
     426           0 :     if( !(nFlags & F_SELECTING_RECT) )
     427           0 :         ToTop( pEntry );
     428           0 :     if( bUpdateMode )
     429             :     {
     430           0 :         if( pEntry == pCursor )
     431           0 :             ShowCursor( sal_False );
     432           0 :         if( pView->IsTracking() && (bSelect || !pView->HasBackground()) ) // always synchronous when tracking
     433           0 :             PaintEntry( pEntry );
     434           0 :         else if( bSyncPaint ) // synchronous & with a virtual OutDev!
     435           0 :             PaintEntryVirtOutDev( pEntry );
     436             :         else
     437             :         {
     438           0 :             pView->Invalidate( CalcFocusRect( pEntry ) );
     439             :         }
     440           0 :         if( pEntry == pCursor )
     441           0 :             ShowCursor( sal_True );
     442             :     }
     443             : 
     444             :     // #i101012# emit vcl event LISTBOX_SELECT only in case that the given entry is selected.
     445           0 :     if ( bSelect )
     446             :     {
     447           0 :         CallEventListeners( VCLEVENT_LISTBOX_SELECT, pEntry );
     448             :     }
     449           0 : }
     450             : 
     451           0 : void SvxIconChoiceCtrl_Impl::ResetVirtSize()
     452             : {
     453           0 :     StopEditTimer();
     454           0 :     aVirtOutputSize.Width() = 0;
     455           0 :     aVirtOutputSize.Height() = 0;
     456           0 :     const size_t nCount = aEntries.size();
     457           0 :     for( size_t nCur = 0; nCur < nCount; nCur++ )
     458             :     {
     459           0 :         SvxIconChoiceCtrlEntry* pCur = aEntries[ nCur ];
     460           0 :         pCur->ClearFlags( ICNVIEW_FLAG_POS_MOVED );
     461           0 :         if( pCur->IsPosLocked() )
     462             :         {
     463             :             // adapt (among others) VirtSize
     464           0 :             if( !IsBoundingRectValid( pCur->aRect ) )
     465           0 :                 FindBoundingRect( pCur );
     466             :             else
     467           0 :                 AdjustVirtSize( pCur->aRect );
     468             :         }
     469             :         else
     470           0 :             InvalidateBoundingRect( pCur->aRect );
     471             :     }
     472             : 
     473           0 :     if( !(nWinBits & (WB_NOVSCROLL | WB_NOHSCROLL)) )
     474             :     {
     475           0 :         Size aRealOutputSize( pView->GetOutputSizePixel() );
     476           0 :         if( aVirtOutputSize.Width() < aRealOutputSize.Width() ||
     477           0 :             aVirtOutputSize.Height() < aRealOutputSize.Height() )
     478             :         {
     479             :             sal_uLong nGridCount = IcnGridMap_Impl::GetGridCount(
     480           0 :                 aRealOutputSize, (sal_uInt16)nGridDX, (sal_uInt16)nGridDY );
     481           0 :             if( nGridCount < nCount )
     482             :             {
     483           0 :                 if( nWinBits & WB_ALIGN_TOP )
     484           0 :                     nMaxVirtWidth = aRealOutputSize.Width() - nVerSBarWidth;
     485             :                 else // WB_ALIGN_LEFT
     486           0 :                     nMaxVirtHeight = aRealOutputSize.Height() - nHorSBarHeight;
     487             :             }
     488             :         }
     489             :     }
     490             : 
     491           0 :     pImpCursor->Clear();
     492           0 :     pGridMap->Clear();
     493           0 :     VisRectChanged();
     494           0 : }
     495             : 
     496           0 : void SvxIconChoiceCtrl_Impl::AdjustVirtSize( const Rectangle& rRect )
     497             : {
     498           0 :     long nHeightOffs = 0;
     499           0 :     long nWidthOffs = 0;
     500             : 
     501           0 :     if( aVirtOutputSize.Width() < (rRect.Right()+LROFFS_WINBORDER) )
     502           0 :         nWidthOffs = (rRect.Right()+LROFFS_WINBORDER) - aVirtOutputSize.Width();
     503             : 
     504           0 :     if( aVirtOutputSize.Height() < (rRect.Bottom()+TBOFFS_WINBORDER) )
     505           0 :         nHeightOffs = (rRect.Bottom()+TBOFFS_WINBORDER) - aVirtOutputSize.Height();
     506             : 
     507           0 :     if( nWidthOffs || nHeightOffs )
     508             :     {
     509           0 :         Range aRange;
     510           0 :         aVirtOutputSize.Width() += nWidthOffs;
     511           0 :         aRange.Max() = aVirtOutputSize.Width();
     512           0 :         aHorSBar.SetRange( aRange );
     513             : 
     514           0 :         aVirtOutputSize.Height() += nHeightOffs;
     515           0 :         aRange.Max() = aVirtOutputSize.Height();
     516           0 :         aVerSBar.SetRange( aRange );
     517             : 
     518           0 :         pImpCursor->Clear();
     519           0 :         pGridMap->OutputSizeChanged();
     520           0 :         AdjustScrollBars();
     521           0 :         DocRectChanged();
     522             :     }
     523           0 : }
     524             : 
     525           0 : void SvxIconChoiceCtrl_Impl::InitPredecessors()
     526             : {
     527             :     DBG_ASSERT(!pHead,"SvxIconChoiceCtrl_Impl::InitPredecessors() >> Already initialized");
     528           0 :     size_t nCount = aEntries.size();
     529           0 :     if( nCount )
     530             :     {
     531           0 :         SvxIconChoiceCtrlEntry* pPrev = aEntries[ 0 ];
     532           0 :         for( size_t nCur = 1; nCur <= nCount; nCur++ )
     533             :         {
     534             :             pPrev->ClearFlags( ICNVIEW_FLAG_POS_LOCKED | ICNVIEW_FLAG_POS_MOVED |
     535           0 :                                 ICNVIEW_FLAG_PRED_SET);
     536             : 
     537             :             SvxIconChoiceCtrlEntry* pNext;
     538           0 :             if( nCur == nCount )
     539           0 :                 pNext = aEntries[ 0 ];
     540             :             else
     541           0 :                 pNext = aEntries[ nCur ];
     542           0 :             pPrev->pflink = pNext;
     543           0 :             pNext->pblink = pPrev;
     544           0 :             pPrev = pNext;
     545             :         }
     546           0 :         pHead = aEntries[ 0 ];
     547             :     }
     548             :     else
     549           0 :         pHead = 0;
     550           0 :     nFlags &= ~F_MOVED_ENTRIES;
     551           0 : }
     552             : 
     553           0 : void SvxIconChoiceCtrl_Impl::ClearPredecessors()
     554             : {
     555           0 :     if( pHead )
     556             :     {
     557           0 :         size_t nCount = aEntries.size();
     558           0 :         for( size_t nCur = 0; nCur < nCount; nCur++ )
     559             :         {
     560           0 :             SvxIconChoiceCtrlEntry* pCur = aEntries[ nCur ];
     561           0 :             pCur->pflink = 0;
     562           0 :             pCur->pblink = 0;
     563           0 :             pCur->ClearFlags( ICNVIEW_FLAG_PRED_SET );
     564             :         }
     565           0 :         pHead = 0;
     566             :     }
     567           0 : }
     568             : 
     569           0 : void SvxIconChoiceCtrl_Impl::Arrange( sal_Bool bKeepPredecessors, long nSetMaxVirtWidth, long nSetMaxVirtHeight )
     570             : {
     571           0 :     if ( nSetMaxVirtWidth != 0 )
     572           0 :         nMaxVirtWidth = nSetMaxVirtWidth;
     573             :     else
     574           0 :         nMaxVirtWidth = aOutputSize.Width();
     575             : 
     576           0 :     if ( nSetMaxVirtHeight != 0 )
     577           0 :         nMaxVirtHeight = nSetMaxVirtHeight;
     578             :     else
     579           0 :         nMaxVirtHeight = aOutputSize.Height();
     580             : 
     581           0 :     ImpArrange( bKeepPredecessors );
     582           0 : }
     583             : 
     584           0 : void SvxIconChoiceCtrl_Impl::ImpArrange( sal_Bool bKeepPredecessors )
     585             : {
     586           0 :     static Point aEmptyPoint;
     587             : 
     588           0 :     sal_Bool bOldUpdate = bUpdateMode;
     589           0 :     Rectangle aCurOutputArea( GetOutputRect() );
     590           0 :     if( (nWinBits & WB_SMART_ARRANGE) && aCurOutputArea.TopLeft() != aEmptyPoint )
     591           0 :         bUpdateMode = sal_False;
     592           0 :     aAutoArrangeTimer.Stop();
     593           0 :     nFlags &= ~F_MOVED_ENTRIES;
     594           0 :     nFlags |= F_ARRANGING;
     595           0 :     StopEditTimer();
     596           0 :     ShowCursor( sal_False );
     597           0 :     ResetVirtSize();
     598           0 :     if( !bKeepPredecessors )
     599           0 :         ClearPredecessors();
     600           0 :     bBoundRectsDirty = sal_False;
     601           0 :     SetOrigin( Point() );
     602           0 :     VisRectChanged();
     603           0 :     RecalcAllBoundingRectsSmart();
     604             :     // TODO: the invalidation in the detail view should be more intelligent
     605             :     //if( !(nWinBits & WB_DETAILS ))
     606           0 :         pView->Invalidate( INVALIDATE_NOCHILDREN );
     607           0 :     nFlags &= ~F_ARRANGING;
     608           0 :     if( (nWinBits & WB_SMART_ARRANGE) && aCurOutputArea.TopLeft() != aEmptyPoint )
     609             :     {
     610           0 :         MakeVisible( aCurOutputArea );
     611           0 :         SetUpdateMode( bOldUpdate );
     612             :     }
     613           0 :     ShowCursor( sal_True );
     614           0 : }
     615             : 
     616           0 : void SvxIconChoiceCtrl_Impl::Paint( const Rectangle& rRect )
     617             : {
     618           0 :     bEndScrollInvalidate = sal_False;
     619             : 
     620             : #if defined(OV_DRAWGRID)
     621             :     Color aOldColor ( pView->GetLineColor() );
     622             :     Color aColor( COL_BLACK );
     623             :     pView->SetLineColor( aColor );
     624             :     Point aOffs( pView->GetMapMode().GetOrigin());
     625             :     Size aXSize( pView->GetOutputSizePixel() );
     626             : 
     627             :     {
     628             :     Point aStart( LROFFS_WINBORDER, 0 );
     629             :     Point aEnd( LROFFS_WINBORDER, aXSize.Height());
     630             :     aStart -= aOffs;
     631             :     aEnd -= aOffs;
     632             :     pView->DrawLine( aStart, aEnd );
     633             :     }
     634             :     {
     635             :     Point aStart( 0, TBOFFS_WINBORDER );
     636             :     Point aEnd( aXSize.Width(), TBOFFS_WINBORDER );
     637             :     aStart -= aOffs;
     638             :     aEnd -= aOffs;
     639             :     pView->DrawLine( aStart, aEnd );
     640             :     }
     641             : 
     642             :     for( long nDX = nGridDX; nDX <= aXSize.Width(); nDX += nGridDX )
     643             :     {
     644             :         Point aStart( nDX+LROFFS_WINBORDER, 0 );
     645             :         Point aEnd( nDX+LROFFS_WINBORDER, aXSize.Height());
     646             :         aStart -= aOffs;
     647             :         aEnd -= aOffs;
     648             :         pView->DrawLine( aStart, aEnd );
     649             :     }
     650             :     for( long nDY = nGridDY; nDY <= aXSize.Height(); nDY += nGridDY )
     651             :     {
     652             :         Point aStart( 0, nDY+TBOFFS_WINBORDER );
     653             :         Point aEnd( aXSize.Width(), nDY+TBOFFS_WINBORDER );
     654             :         aStart -= aOffs;
     655             :         aEnd -= aOffs;
     656             :         pView->DrawLine( aStart, aEnd );
     657             :     }
     658             :     pView->SetLineColor( aOldColor );
     659             : #endif
     660           0 :     nFlags |= F_PAINTED;
     661             : 
     662           0 :     if( !aEntries.size() )
     663           0 :         return;
     664           0 :     if( !pCursor )
     665             :     {
     666             :         // set cursor to item with focus-flag
     667           0 :         sal_Bool bfound = sal_False;
     668           0 :         for ( sal_uLong i = 0; i < pView->GetEntryCount() && !bfound; i++)
     669             :         {
     670           0 :             SvxIconChoiceCtrlEntry* pEntry = pView->GetEntry ( i );
     671           0 :             if( pEntry->IsFocused() )
     672             :             {
     673           0 :                 pCursor = pEntry;
     674           0 :                 bfound=sal_True;
     675             :             }
     676             :         }
     677             : 
     678           0 :         if( !bfound )
     679           0 :             pCursor = aEntries[ 0 ];
     680             :     }
     681             : 
     682             :     // Show Focus at Init-Time
     683           0 :     if ( pView->HasFocus() )
     684           0 :         GetFocus();
     685             : 
     686           0 :     size_t nCount = pZOrderList->size();
     687           0 :     if( !nCount )
     688           0 :         return;
     689             : 
     690           0 :     sal_Bool bResetClipRegion = sal_False;
     691           0 :     if( !pView->IsClipRegion() )
     692             :     {
     693           0 :         Rectangle aOutputArea( GetOutputRect() );
     694           0 :         bResetClipRegion = sal_True;
     695           0 :         pView->SetClipRegion( aOutputArea );
     696             :     }
     697             : 
     698           0 :     SvxIconChoiceCtrlEntryList_impl* pNewZOrderList = new SvxIconChoiceCtrlEntryList_impl();
     699           0 :     SvxIconChoiceCtrlEntryList_impl* pPaintedEntries = new SvxIconChoiceCtrlEntryList_impl();
     700             : 
     701           0 :     size_t nPos = 0;
     702           0 :     while( nCount )
     703             :     {
     704           0 :         SvxIconChoiceCtrlEntry* pEntry = (*pZOrderList)[ nPos ];
     705           0 :         const Rectangle& rBoundRect = GetEntryBoundRect( pEntry );
     706           0 :         if( rRect.IsOver( rBoundRect ) )
     707             :         {
     708           0 :             PaintEntry( pEntry, rBoundRect.TopLeft(), pView, sal_True );
     709             :             // set entries to Top if they are being repainted
     710           0 :             pPaintedEntries->push_back( pEntry );
     711             :         }
     712             :         else
     713           0 :             pNewZOrderList->push_back( pEntry );
     714             : 
     715           0 :         nCount--;
     716           0 :         nPos++;
     717             :     }
     718           0 :     delete pZOrderList;
     719           0 :     pZOrderList = pNewZOrderList;
     720           0 :     nCount = pPaintedEntries->size();
     721           0 :     if( nCount )
     722             :     {
     723           0 :         for( size_t nCur = 0; nCur < nCount; nCur++ )
     724           0 :             pZOrderList->push_back( (*pPaintedEntries)[ nCur ] );
     725             :     }
     726           0 :     delete pPaintedEntries;
     727             : 
     728           0 :     if( bResetClipRegion )
     729           0 :         pView->SetClipRegion();
     730             : }
     731             : 
     732           0 : void SvxIconChoiceCtrl_Impl::RepaintEntries( sal_uInt16 nEntryFlagsMask )
     733             : {
     734           0 :     const size_t nCount = pZOrderList->size();
     735           0 :     if( !nCount )
     736           0 :         return;
     737             : 
     738           0 :     sal_Bool bResetClipRegion = sal_False;
     739           0 :     Rectangle aOutRect( GetOutputRect() );
     740           0 :     if( !pView->IsClipRegion() )
     741             :     {
     742           0 :         bResetClipRegion = sal_True;
     743           0 :         pView->SetClipRegion( aOutRect );
     744             :     }
     745           0 :     for( size_t nCur = 0; nCur < nCount; nCur++ )
     746             :     {
     747           0 :         SvxIconChoiceCtrlEntry* pEntry = (*pZOrderList)[ nCur ];
     748           0 :         if( pEntry->GetFlags() & nEntryFlagsMask )
     749             :         {
     750           0 :             const Rectangle& rBoundRect = GetEntryBoundRect( pEntry );
     751           0 :             if( aOutRect.IsOver( rBoundRect ) )
     752           0 :                 PaintEntry( pEntry, rBoundRect.TopLeft() );
     753             :         }
     754             :     }
     755           0 :     if( bResetClipRegion )
     756           0 :         pView->SetClipRegion();
     757             : }
     758             : 
     759             : 
     760           0 : void SvxIconChoiceCtrl_Impl::InitScrollBarBox()
     761             : {
     762           0 :     aScrBarBox.SetSizePixel( Size(nVerSBarWidth-1, nHorSBarHeight-1) );
     763           0 :     Size aSize( pView->GetOutputSizePixel() );
     764           0 :     aScrBarBox.SetPosPixel( Point(aSize.Width()-nVerSBarWidth+1, aSize.Height()-nHorSBarHeight+1));
     765           0 : }
     766             : 
     767           0 : sal_Bool SvxIconChoiceCtrl_Impl::MouseButtonDown( const MouseEvent& rMEvt)
     768             : {
     769           0 :     sal_Bool bHandled = sal_True;
     770           0 :     bHighlightFramePressed = sal_False;
     771           0 :     StopEditTimer();
     772           0 :     sal_Bool bGotFocus = (sal_Bool)(!pView->HasFocus() && !(nWinBits & WB_NOPOINTERFOCUS));
     773           0 :     if( !(nWinBits & WB_NOPOINTERFOCUS) )
     774           0 :         pView->GrabFocus();
     775             : 
     776           0 :     Point aDocPos( rMEvt.GetPosPixel() );
     777           0 :     if(aDocPos.X()>=aOutputSize.Width() || aDocPos.Y()>=aOutputSize.Height())
     778           0 :         return sal_False;
     779           0 :     ToDocPos( aDocPos );
     780           0 :     SvxIconChoiceCtrlEntry* pEntry = GetEntry( aDocPos, sal_True );
     781           0 :     if( pEntry )
     782           0 :         MakeEntryVisible( pEntry, sal_False );
     783             : 
     784           0 :     if( rMEvt.IsShift() && eSelectionMode != SINGLE_SELECTION )
     785             :     {
     786           0 :         if( pEntry )
     787           0 :             SetCursor_Impl( pCursor, pEntry, rMEvt.IsMod1(), rMEvt.IsShift(), sal_True);
     788           0 :         return sal_True;
     789             :     }
     790             : 
     791           0 :     if( pAnchor && (rMEvt.IsShift() || rMEvt.IsMod1())) // keyboard selection?
     792             :     {
     793             :         DBG_ASSERT(eSelectionMode != SINGLE_SELECTION,"Invalid selection mode");
     794           0 :         if( rMEvt.IsMod1() )
     795           0 :             nFlags |= F_ADD_MODE;
     796             : 
     797           0 :         if( rMEvt.IsShift() )
     798             :         {
     799           0 :             Rectangle aRect( GetEntryBoundRect( pAnchor ));
     800           0 :             if( pEntry )
     801           0 :                 aRect.Union( GetEntryBoundRect( pEntry ) );
     802             :             else
     803             :             {
     804           0 :                 Rectangle aTempRect( aDocPos, Size(1,1));
     805           0 :                 aRect.Union( aTempRect );
     806             :             }
     807           0 :             aCurSelectionRect = aRect;
     808           0 :             SelectRect( aRect, (nFlags & F_ADD_MODE)!=0, &aSelectedRectList );
     809             :         }
     810           0 :         else if( rMEvt.IsMod1() )
     811             :         {
     812           0 :             AddSelectedRect( aCurSelectionRect );
     813           0 :             pAnchor = 0;
     814           0 :             aCurSelectionRect.SetPos( aDocPos );
     815             :         }
     816             : 
     817           0 :         if( !pEntry && !(nWinBits & WB_NODRAGSELECTION))
     818           0 :             pView->StartTracking( STARTTRACK_SCROLLREPEAT );
     819           0 :         return sal_True;
     820             :     }
     821             :     else
     822             :     {
     823           0 :         if( !pEntry )
     824             :         {
     825           0 :             if( eSelectionMode == MULTIPLE_SELECTION )
     826             :             {
     827           0 :                 if( !rMEvt.IsMod1() )  // Ctrl
     828             :                 {
     829           0 :                     if( !bGotFocus )
     830             :                     {
     831           0 :                         SetNoSelection();
     832           0 :                         ClearSelectedRectList();
     833             :                     }
     834             :                 }
     835             :                 else
     836           0 :                     nFlags |= F_ADD_MODE;
     837           0 :                 aCurSelectionRect.SetPos( aDocPos );
     838           0 :                 pView->StartTracking( STARTTRACK_SCROLLREPEAT );
     839             :             }
     840             :             else
     841           0 :                 bHandled = sal_False;
     842           0 :             return bHandled;
     843             :         }
     844             :     }
     845           0 :     sal_Bool bSelected = pEntry->IsSelected();
     846           0 :     sal_Bool bEditingEnabled = IsEntryEditingEnabled();
     847             : 
     848           0 :     if( rMEvt.GetClicks() == 2 )
     849             :     {
     850           0 :         DeselectAllBut( pEntry );
     851           0 :         SelectEntry( pEntry, sal_True, sal_True, sal_False, sal_True );
     852           0 :         pHdlEntry = pEntry;
     853           0 :         pView->ClickIcon();
     854             :     }
     855             :     else
     856             :     {
     857             :         // Inplace-Editing ?
     858           0 :         if( rMEvt.IsMod2() )  // Alt?
     859             :         {
     860           0 :             if( bEntryEditingEnabled && pEntry &&
     861           0 :                 pEntry->IsSelected())
     862             :             {
     863           0 :                 if( pView->EditingEntry( pEntry ))
     864           0 :                     EditEntry( pEntry );
     865             :             }
     866             :         }
     867           0 :         else if( eSelectionMode == SINGLE_SELECTION )
     868             :         {
     869           0 :             DeselectAllBut( pEntry );
     870           0 :             SetCursor( pEntry );
     871           0 :             if( bEditingEnabled && bSelected && !rMEvt.GetModifier() &&
     872           0 :                 rMEvt.IsLeft() && IsTextHit( pEntry, aDocPos ) )
     873             :             {
     874           0 :                 nFlags |= F_START_EDITTIMER_IN_MOUSEUP;
     875             :             }
     876             :         }
     877           0 :         else if( eSelectionMode == NO_SELECTION )
     878             :         {
     879           0 :             if( rMEvt.IsLeft() && (nWinBits & WB_HIGHLIGHTFRAME) )
     880             :             {
     881           0 :                 pCurHighlightFrame = 0; // force repaint of frame
     882           0 :                 bHighlightFramePressed = sal_True;
     883           0 :                 SetEntryHighlightFrame( pEntry, sal_True );
     884             :             }
     885             :         }
     886             :         else
     887             :         {
     888           0 :             if( !rMEvt.GetModifier() && rMEvt.IsLeft() )
     889             :             {
     890           0 :                 if( !bSelected )
     891             :                 {
     892           0 :                     DeselectAllBut( pEntry, sal_True /* paint synchronously */ );
     893           0 :                     SetCursor( pEntry );
     894           0 :                     SelectEntry( pEntry, sal_True, sal_True, sal_False, sal_True );
     895             :                 }
     896             :                 else
     897             :                 {
     898             :                     // deselect only in the Up, if the Move happened via D&D!
     899           0 :                     nFlags |= F_DOWN_DESELECT;
     900           0 :                     if( bEditingEnabled && IsTextHit( pEntry, aDocPos ) &&
     901           0 :                         rMEvt.IsLeft())
     902             :                     {
     903           0 :                         nFlags |= F_START_EDITTIMER_IN_MOUSEUP;
     904             :                     }
     905             :                 }
     906             :             }
     907           0 :             else if( rMEvt.IsMod1() )
     908           0 :                 nFlags |= F_DOWN_CTRL;
     909             :         }
     910             :     }
     911           0 :     return bHandled;
     912             : }
     913             : 
     914           0 : sal_Bool SvxIconChoiceCtrl_Impl::MouseButtonUp( const MouseEvent& rMEvt )
     915             : {
     916           0 :     sal_Bool bHandled = sal_False;
     917           0 :     if( rMEvt.IsRight() && (nFlags & (F_DOWN_CTRL | F_DOWN_DESELECT) ))
     918             :     {
     919           0 :         nFlags &= ~(F_DOWN_CTRL | F_DOWN_DESELECT);
     920           0 :         bHandled = sal_True;
     921             :     }
     922             : 
     923           0 :     Point aDocPos( rMEvt.GetPosPixel() );
     924           0 :     ToDocPos( aDocPos );
     925           0 :     SvxIconChoiceCtrlEntry* pDocEntry = GetEntry( aDocPos );
     926           0 :     if( pDocEntry )
     927             :     {
     928           0 :         if( nFlags & F_DOWN_CTRL )
     929             :         {
     930             :             // Ctrl & MultiSelection
     931           0 :             ToggleSelection( pDocEntry );
     932           0 :             SetCursor( pDocEntry );
     933           0 :             bHandled = sal_True;
     934             :         }
     935           0 :         else if( nFlags & F_DOWN_DESELECT )
     936             :         {
     937           0 :             DeselectAllBut( pDocEntry );
     938           0 :             SetCursor( pDocEntry );
     939           0 :             SelectEntry( pDocEntry, sal_True, sal_True, sal_False, sal_True );
     940           0 :             bHandled = sal_True;
     941             :         }
     942             :     }
     943             : 
     944           0 :     nFlags &= ~(F_DOWN_CTRL | F_DOWN_DESELECT);
     945           0 :     if( nFlags & F_START_EDITTIMER_IN_MOUSEUP )
     946             :     {
     947           0 :         bHandled = sal_True;
     948           0 :         StartEditTimer();
     949           0 :         nFlags &= ~F_START_EDITTIMER_IN_MOUSEUP;
     950             :     }
     951             : 
     952           0 :     if((nWinBits & WB_HIGHLIGHTFRAME) && bHighlightFramePressed && pCurHighlightFrame)
     953             :     {
     954           0 :         bHandled = sal_True;
     955           0 :         SvxIconChoiceCtrlEntry* pEntry = pCurHighlightFrame;
     956           0 :         pCurHighlightFrame = 0; // force repaint of frame
     957           0 :         bHighlightFramePressed = sal_False;
     958           0 :         SetEntryHighlightFrame( pEntry, sal_True );
     959             : 
     960           0 :         pHdlEntry = pCurHighlightFrame;
     961           0 :         pView->ClickIcon();
     962             : 
     963             :         // set focus on Icon
     964           0 :         SvxIconChoiceCtrlEntry* pOldCursor = pCursor;
     965           0 :         SetCursor_Impl( pOldCursor, pHdlEntry, sal_False, sal_False, sal_True );
     966             : 
     967           0 :         pHdlEntry = 0;
     968             :     }
     969           0 :     return bHandled;
     970             : }
     971             : 
     972           0 : sal_Bool SvxIconChoiceCtrl_Impl::MouseMove( const MouseEvent& rMEvt )
     973             : {
     974           0 :     const Point aDocPos( pView->PixelToLogic(rMEvt.GetPosPixel()) );
     975             : 
     976           0 :     if( pView->IsTracking() )
     977           0 :         return sal_False;
     978           0 :     else if( nWinBits & WB_HIGHLIGHTFRAME )
     979             :     {
     980           0 :         SvxIconChoiceCtrlEntry* pEntry = GetEntry( aDocPos, sal_True );
     981           0 :         SetEntryHighlightFrame( pEntry );
     982             :     }
     983             :     else
     984           0 :         return sal_False;
     985           0 :     return sal_True;
     986             : }
     987             : 
     988           0 : void SvxIconChoiceCtrl_Impl::SetCursor_Impl( SvxIconChoiceCtrlEntry* pOldCursor,
     989             :     SvxIconChoiceCtrlEntry* pNewCursor, sal_Bool bMod1, sal_Bool bShift, sal_Bool bPaintSync )
     990             : {
     991           0 :     if( pNewCursor )
     992             :     {
     993           0 :         SvxIconChoiceCtrlEntry* pFilterEntry = 0;
     994           0 :         sal_Bool bDeselectAll = sal_False;
     995           0 :         if( eSelectionMode != SINGLE_SELECTION )
     996             :         {
     997           0 :             if( !bMod1 && !bShift )
     998           0 :                 bDeselectAll = sal_True;
     999           0 :             else if( bShift && !bMod1 && !pAnchor )
    1000             :             {
    1001           0 :                 bDeselectAll = sal_True;
    1002           0 :                 pFilterEntry = pOldCursor;
    1003             :             }
    1004             :         }
    1005           0 :         if( bDeselectAll )
    1006           0 :             DeselectAllBut( pFilterEntry, bPaintSync );
    1007           0 :         ShowCursor( sal_False );
    1008           0 :         MakeEntryVisible( pNewCursor );
    1009           0 :         SetCursor( pNewCursor );
    1010           0 :         if( bMod1 && !bShift )
    1011             :         {
    1012           0 :             if( pAnchor )
    1013             :             {
    1014           0 :                 AddSelectedRect( pAnchor, pOldCursor );
    1015           0 :                 pAnchor = 0;
    1016             :             }
    1017             :         }
    1018           0 :         else if( bShift )
    1019             :         {
    1020           0 :             if( !pAnchor )
    1021           0 :                 pAnchor = pOldCursor;
    1022           0 :             if ( nWinBits & WB_ALIGN_LEFT )
    1023           0 :                 SelectRange( pAnchor, pNewCursor, (nFlags & F_ADD_MODE)!=0 );
    1024             :             else
    1025           0 :                 SelectRect(pAnchor,pNewCursor,(nFlags & F_ADD_MODE)!=0,&aSelectedRectList);
    1026             :         }
    1027             :         else
    1028             :         {
    1029           0 :             SelectEntry( pCursor, sal_True, sal_True,  sal_False, bPaintSync );
    1030           0 :             aCurSelectionRect = GetEntryBoundRect( pCursor );
    1031             :         }
    1032             :     }
    1033           0 : }
    1034             : 
    1035           0 : sal_Bool SvxIconChoiceCtrl_Impl::KeyInput( const KeyEvent& rKEvt )
    1036             : {
    1037           0 :     StopEditTimer();
    1038             : 
    1039           0 :     sal_Bool bMod2 = rKEvt.GetKeyCode().IsMod2();
    1040           0 :     sal_Unicode cChar = rKEvt.GetCharCode();
    1041           0 :     sal_uLong nPos = (sal_uLong)-1;
    1042           0 :     if ( bMod2 && cChar && IsMnemonicChar( cChar, nPos ) )
    1043             :     {
    1044             :         // shortcut is clicked
    1045           0 :         SvxIconChoiceCtrlEntry* pNewCursor = GetEntry( nPos );
    1046           0 :         SvxIconChoiceCtrlEntry* pOldCursor = pCursor;
    1047           0 :         if ( pNewCursor != pOldCursor )
    1048           0 :             SetCursor_Impl( pOldCursor, pNewCursor, sal_False, sal_False, sal_False );
    1049           0 :         return sal_True;
    1050             :     }
    1051             : 
    1052           0 :     if ( bMod2 )
    1053             :         // no actions with <ALT>
    1054           0 :         return sal_False;
    1055             : 
    1056           0 :     sal_Bool bKeyUsed = sal_True;
    1057           0 :     sal_Bool bMod1 = rKEvt.GetKeyCode().IsMod1();
    1058           0 :     sal_Bool bShift = rKEvt.GetKeyCode().IsShift();
    1059             : 
    1060           0 :     if( eSelectionMode == SINGLE_SELECTION || eSelectionMode == NO_SELECTION)
    1061             :     {
    1062           0 :         bShift = sal_False;
    1063           0 :         bMod1 = sal_False;
    1064             :     }
    1065             : 
    1066           0 :     if( bMod1 )
    1067           0 :         nFlags |= F_ADD_MODE;
    1068             : 
    1069             :     SvxIconChoiceCtrlEntry* pNewCursor;
    1070           0 :     SvxIconChoiceCtrlEntry* pOldCursor = pCursor;
    1071             : 
    1072           0 :     sal_uInt16 nCode = rKEvt.GetKeyCode().GetCode();
    1073           0 :     switch( nCode )
    1074             :     {
    1075             :         case KEY_UP:
    1076             :         case KEY_PAGEUP:
    1077           0 :             if( pCursor )
    1078             :             {
    1079           0 :                 MakeEntryVisible( pCursor );
    1080           0 :                 if( nCode == KEY_UP )
    1081           0 :                     pNewCursor = pImpCursor->GoUpDown(pCursor,sal_False);
    1082             :                 else
    1083           0 :                     pNewCursor = pImpCursor->GoPageUpDown(pCursor,sal_False);
    1084           0 :                 SetCursor_Impl( pOldCursor, pNewCursor, bMod1, bShift, sal_True );
    1085           0 :                 if( !pNewCursor )
    1086             :                 {
    1087           0 :                     Rectangle aRect( GetEntryBoundRect( pCursor ) );
    1088           0 :                     if( aRect.Top())
    1089             :                     {
    1090           0 :                         aRect.Bottom() -= aRect.Top();
    1091           0 :                         aRect.Top() = 0;
    1092           0 :                         MakeVisible( aRect );
    1093             :                     }
    1094             :                 }
    1095             : 
    1096           0 :                 if ( bChooseWithCursor && pNewCursor != NULL )
    1097             :                 {
    1098           0 :                     pHdlEntry = pNewCursor;//GetCurEntry();
    1099           0 :                     pCurHighlightFrame = pHdlEntry;
    1100           0 :                     pView->ClickIcon();
    1101           0 :                     pCurHighlightFrame = NULL;
    1102             :                 }
    1103             :             }
    1104           0 :             break;
    1105             : 
    1106             :         case KEY_DOWN:
    1107             :         case KEY_PAGEDOWN:
    1108           0 :             if( pCursor )
    1109             :             {
    1110           0 :                 if( nCode == KEY_DOWN )
    1111           0 :                     pNewCursor=pImpCursor->GoUpDown( pCursor,sal_True );
    1112             :                 else
    1113           0 :                     pNewCursor=pImpCursor->GoPageUpDown( pCursor,sal_True );
    1114           0 :                 SetCursor_Impl( pOldCursor, pNewCursor, bMod1, bShift, sal_True );
    1115             : 
    1116           0 :                 if ( bChooseWithCursor && pNewCursor != NULL)
    1117             :                 {
    1118           0 :                     pHdlEntry = pNewCursor;//GetCurEntry();
    1119           0 :                     pCurHighlightFrame = pHdlEntry;
    1120           0 :                     pView->ClickIcon();
    1121           0 :                     pCurHighlightFrame = NULL;
    1122             :                 }
    1123             :             }
    1124           0 :             break;
    1125             : 
    1126             :         case KEY_RIGHT:
    1127           0 :             if( pCursor )
    1128             :             {
    1129           0 :                 pNewCursor=pImpCursor->GoLeftRight(pCursor,sal_True );
    1130           0 :                 SetCursor_Impl( pOldCursor, pNewCursor, bMod1, bShift, sal_True );
    1131             :             }
    1132           0 :             break;
    1133             : 
    1134             :         case KEY_LEFT:
    1135           0 :             if( pCursor )
    1136             :             {
    1137           0 :                 MakeEntryVisible( pCursor );
    1138           0 :                 pNewCursor = pImpCursor->GoLeftRight(pCursor,sal_False );
    1139           0 :                 SetCursor_Impl( pOldCursor, pNewCursor, bMod1, bShift, sal_True );
    1140           0 :                 if( !pNewCursor )
    1141             :                 {
    1142           0 :                     Rectangle aRect( GetEntryBoundRect(pCursor));
    1143           0 :                     if( aRect.Left() )
    1144             :                     {
    1145           0 :                         aRect.Right() -= aRect.Left();
    1146           0 :                         aRect.Left() = 0;
    1147           0 :                         MakeVisible( aRect );
    1148             :                     }
    1149             :                 }
    1150             :             }
    1151           0 :             break;
    1152             : 
    1153             :         case KEY_F2:
    1154           0 :             if( !bMod1 && !bShift )
    1155           0 :                 EditTimeoutHdl( 0 );
    1156             :             else
    1157           0 :                 bKeyUsed = sal_False;
    1158           0 :             break;
    1159             : 
    1160             :         case KEY_F8:
    1161           0 :             if( rKEvt.GetKeyCode().IsShift() )
    1162             :             {
    1163           0 :                 if( nFlags & F_ADD_MODE )
    1164           0 :                     nFlags &= (~F_ADD_MODE);
    1165             :                 else
    1166           0 :                     nFlags |= F_ADD_MODE;
    1167             :             }
    1168             :             else
    1169           0 :                 bKeyUsed = sal_False;
    1170           0 :             break;
    1171             : 
    1172             :         case KEY_SPACE:
    1173           0 :             if( pCursor && eSelectionMode != SINGLE_SELECTION )
    1174             :             {
    1175           0 :                 if( !bMod1 )
    1176             :                 {
    1177             :                     //SelectAll( sal_False );
    1178           0 :                     SetNoSelection();
    1179           0 :                     ClearSelectedRectList();
    1180             : 
    1181             :                     // click Icon with spacebar
    1182           0 :                     SetEntryHighlightFrame( GetCurEntry(), sal_True );
    1183           0 :                     pView->ClickIcon();
    1184           0 :                     pHdlEntry = pCurHighlightFrame;
    1185           0 :                     pCurHighlightFrame=0;
    1186             :                 }
    1187             :                 else
    1188           0 :                     ToggleSelection( pCursor );
    1189             :             }
    1190           0 :             break;
    1191             : 
    1192             : #ifdef DBG_UTIL
    1193             :         case KEY_F10:
    1194             :             if( rKEvt.GetKeyCode().IsShift() )
    1195             :             {
    1196             :                 if( pCursor )
    1197             :                     pView->SetEntryTextMode( IcnShowTextFull, pCursor );
    1198             :             }
    1199             :             if( rKEvt.GetKeyCode().IsMod1() )
    1200             :             {
    1201             :                 if( pCursor )
    1202             :                     pView->SetEntryTextMode( IcnShowTextShort, pCursor );
    1203             :             }
    1204             :             break;
    1205             : #endif
    1206             : 
    1207             :         case KEY_ADD:
    1208             :         case KEY_DIVIDE :
    1209             :         case KEY_A:
    1210           0 :             if( bMod1 && (eSelectionMode != SINGLE_SELECTION))
    1211           0 :                 SelectAll( sal_True );
    1212             :             else
    1213           0 :                 bKeyUsed = sal_False;
    1214           0 :             break;
    1215             : 
    1216             :         case KEY_SUBTRACT:
    1217             :         case KEY_COMMA :
    1218           0 :             if( bMod1 )
    1219           0 :                 SetNoSelection();
    1220             :             else
    1221           0 :                 bKeyUsed = sal_False;
    1222           0 :             break;
    1223             : 
    1224             :         case KEY_RETURN:
    1225           0 :             if( bMod1 )
    1226             :             {
    1227           0 :                 if( pCursor && bEntryEditingEnabled )
    1228           0 :                     /*pView->*/EditEntry( pCursor );
    1229             :             }
    1230             :             else
    1231           0 :                 bKeyUsed = sal_False;
    1232           0 :             break;
    1233             : 
    1234             :         case KEY_END:
    1235           0 :             if( pCursor )
    1236             :             {
    1237           0 :                 pNewCursor = aEntries[ aEntries.size() - 1 ];
    1238           0 :                 SetCursor_Impl( pOldCursor, pNewCursor, bMod1, bShift, sal_True );
    1239             :             }
    1240           0 :             break;
    1241             : 
    1242             :         case KEY_HOME:
    1243           0 :             if( pCursor )
    1244             :             {
    1245           0 :                 pNewCursor = aEntries[ 0 ];
    1246           0 :                 SetCursor_Impl( pOldCursor, pNewCursor, bMod1, bShift, sal_True );
    1247             :             }
    1248           0 :             break;
    1249             : 
    1250             :         default:
    1251           0 :             bKeyUsed = sal_False;
    1252             : 
    1253             :     }
    1254           0 :     return bKeyUsed;
    1255             : }
    1256             : 
    1257             : // recalculate TopLeft of scrollbars (but not their sizes!)
    1258           0 : void SvxIconChoiceCtrl_Impl::PositionScrollBars( long nRealWidth, long nRealHeight )
    1259             : {
    1260             :     // horizontal scrollbar
    1261           0 :     Point aPos( 0, nRealHeight );
    1262           0 :     aPos.Y() -= nHorSBarHeight;
    1263             : 
    1264           0 :     if( aHorSBar.GetPosPixel() != aPos )
    1265           0 :         aHorSBar.SetPosPixel( aPos );
    1266             : 
    1267             :     // vertical scrollbar
    1268           0 :     aPos.X() = nRealWidth; aPos.Y() = 0;
    1269           0 :     aPos.X() -= nVerSBarWidth;
    1270           0 :     aPos.X()++;
    1271           0 :     aPos.Y()--;
    1272             : 
    1273           0 :     if( aVerSBar.GetPosPixel() != aPos )
    1274           0 :         aVerSBar.SetPosPixel( aPos );
    1275           0 : }
    1276             : 
    1277           0 : void SvxIconChoiceCtrl_Impl::AdjustScrollBars( sal_Bool )
    1278             : {
    1279           0 :     Rectangle aOldOutRect( GetOutputRect() );
    1280           0 :     long nVirtHeight = aVirtOutputSize.Height();
    1281           0 :     long nVirtWidth = aVirtOutputSize.Width();
    1282             : 
    1283           0 :     Size aOSize( pView->Control::GetOutputSizePixel() );
    1284           0 :     long nRealHeight = aOSize.Height();
    1285           0 :     long nRealWidth = aOSize.Width();
    1286             : 
    1287           0 :     PositionScrollBars( nRealWidth, nRealHeight );
    1288             : 
    1289           0 :     const MapMode& rMapMode = pView->GetMapMode();
    1290           0 :     Point aOrigin( rMapMode.GetOrigin() );
    1291             : 
    1292             :     long nVisibleWidth;
    1293           0 :     if( nRealWidth > nVirtWidth )
    1294           0 :         nVisibleWidth = nVirtWidth + aOrigin.X();
    1295             :     else
    1296           0 :         nVisibleWidth = nRealWidth;
    1297             : 
    1298             :     long nVisibleHeight;
    1299           0 :     if( nRealHeight > nVirtHeight )
    1300           0 :         nVisibleHeight = nVirtHeight + aOrigin.Y();
    1301             :     else
    1302           0 :         nVisibleHeight = nRealHeight;
    1303             : 
    1304           0 :     sal_Bool bVerSBar = ( nWinBits & WB_VSCROLL ) != 0;
    1305           0 :     sal_Bool bHorSBar = ( nWinBits & WB_HSCROLL ) != 0;
    1306           0 :     sal_Bool bNoVerSBar = ( nWinBits & WB_NOVSCROLL ) != 0;
    1307           0 :     sal_Bool bNoHorSBar = ( nWinBits & WB_NOHSCROLL ) != 0;
    1308             : 
    1309           0 :     sal_uInt16 nResult = 0;
    1310           0 :     if( nVirtHeight )
    1311             :     {
    1312             :         // activate vertical scrollbar?
    1313           0 :         if( !bNoVerSBar && (bVerSBar || ( nVirtHeight > nVisibleHeight)) )
    1314             :         {
    1315           0 :             nResult = 0x0001;
    1316           0 :             nRealWidth -= nVerSBarWidth;
    1317             : 
    1318           0 :             if( nRealWidth > nVirtWidth )
    1319           0 :                 nVisibleWidth = nVirtWidth + aOrigin.X();
    1320             :             else
    1321           0 :                 nVisibleWidth = nRealWidth;
    1322             : 
    1323           0 :             nFlags |= F_HOR_SBARSIZE_WITH_VBAR;
    1324             :         }
    1325             :         // activate horizontal scrollbar?
    1326           0 :         if( !bNoHorSBar && (bHorSBar || (nVirtWidth > nVisibleWidth)) )
    1327             :         {
    1328           0 :             nResult |= 0x0002;
    1329           0 :             nRealHeight -= nHorSBarHeight;
    1330             : 
    1331           0 :             if( nRealHeight > nVirtHeight )
    1332           0 :                 nVisibleHeight = nVirtHeight + aOrigin.Y();
    1333             :             else
    1334           0 :                 nVisibleHeight = nRealHeight;
    1335             : 
    1336             :             // do we need a vertical scrollbar after all?
    1337           0 :             if( !(nResult & 0x0001) &&  // only if not already there
    1338             :                 ( !bNoVerSBar && ((nVirtHeight > nVisibleHeight) || bVerSBar)) )
    1339             :             {
    1340           0 :                 nResult = 3; // both turned on
    1341           0 :                 nRealWidth -= nVerSBarWidth;
    1342             : 
    1343           0 :                 if( nRealWidth > nVirtWidth )
    1344           0 :                     nVisibleWidth = nVirtWidth + aOrigin.X();
    1345             :                 else
    1346           0 :                     nVisibleWidth = nRealWidth;
    1347             : 
    1348           0 :                 nFlags |= F_VER_SBARSIZE_WITH_HBAR;
    1349             :             }
    1350             :         }
    1351             :     }
    1352             : 
    1353             :     // size vertical scrollbar
    1354           0 :     long nThumb = aVerSBar.GetThumbPos();
    1355           0 :     Size aSize( nVerSBarWidth, nRealHeight );
    1356           0 :     aSize.Height() += 2;
    1357           0 :     if( aSize != aVerSBar.GetSizePixel() )
    1358           0 :         aVerSBar.SetSizePixel( aSize );
    1359           0 :     aVerSBar.SetVisibleSize( nVisibleHeight );
    1360           0 :     aVerSBar.SetPageSize( GetScrollBarPageSize( nVisibleHeight ));
    1361             : 
    1362           0 :     if( nResult & 0x0001 )
    1363             :     {
    1364           0 :         aVerSBar.SetThumbPos( nThumb );
    1365           0 :         aVerSBar.Show();
    1366             :     }
    1367             :     else
    1368             :     {
    1369           0 :         aVerSBar.SetThumbPos( 0 );
    1370           0 :         aVerSBar.Hide();
    1371             :     }
    1372             : 
    1373             :     // size horizontal scrollbar
    1374           0 :     nThumb = aHorSBar.GetThumbPos();
    1375           0 :     aSize.Width() = nRealWidth;
    1376           0 :     aSize.Height() = nHorSBarHeight;
    1377           0 :     aSize.Width()++;
    1378           0 :     if( nResult & 0x0001 ) // vertical scrollbar?
    1379             :     {
    1380           0 :         aSize.Width()++;
    1381           0 :         nRealWidth++;
    1382             :     }
    1383           0 :     if( aSize != aHorSBar.GetSizePixel() )
    1384           0 :         aHorSBar.SetSizePixel( aSize );
    1385           0 :     aHorSBar.SetVisibleSize( nVisibleWidth );
    1386           0 :     aHorSBar.SetPageSize( GetScrollBarPageSize(nVisibleWidth ));
    1387           0 :     if( nResult & 0x0002 )
    1388             :     {
    1389           0 :         aHorSBar.SetThumbPos( nThumb );
    1390           0 :         aHorSBar.Show();
    1391             :     }
    1392             :     else
    1393             :     {
    1394           0 :         aHorSBar.SetThumbPos( 0 );
    1395           0 :         aHorSBar.Hide();
    1396             :     }
    1397             : 
    1398           0 :     aOutputSize.Width() = nRealWidth;
    1399           0 :     if( nResult & 0x0002 ) // horizontal scrollbar ?
    1400           0 :         nRealHeight++; // because lower border is clipped
    1401           0 :     aOutputSize.Height() = nRealHeight;
    1402             : 
    1403           0 :     Rectangle aNewOutRect( GetOutputRect() );
    1404           0 :     if( aNewOutRect != aOldOutRect && pView->HasBackground() )
    1405             :     {
    1406           0 :         Wallpaper aPaper( pView->GetBackground() );
    1407           0 :         aPaper.SetRect( aNewOutRect );
    1408           0 :         pView->SetBackground( aPaper );
    1409             :     }
    1410             : 
    1411           0 :     if( (nResult & (0x0001|0x0002)) == (0x0001|0x0002) )
    1412           0 :         aScrBarBox.Show();
    1413             :     else
    1414           0 :         aScrBarBox.Hide();
    1415           0 : }
    1416             : 
    1417           0 : void SvxIconChoiceCtrl_Impl::Resize()
    1418             : {
    1419           0 :     StopEditTimer();
    1420           0 :     InitScrollBarBox();
    1421           0 :     aOutputSize = pView->GetOutputSizePixel();
    1422           0 :     pImpCursor->Clear();
    1423           0 :     pGridMap->OutputSizeChanged();
    1424             : 
    1425           0 :     const Size& rSize = pView->Control::GetOutputSizePixel();
    1426           0 :     PositionScrollBars( rSize.Width(), rSize.Height() );
    1427             :     // The scrollbars are shown/hidden asynchronously, so derived classes can
    1428             :     // do an Arrange during Resize, without the scrollbars suddenly turning
    1429             :     // on and off again.
    1430             :     // If an event is already underway, we don't need to send a new one, at least
    1431             :     // as long as there is only one event type.
    1432           0 :     if ( ! nUserEventAdjustScrBars )
    1433             :         nUserEventAdjustScrBars =
    1434             :             Application::PostUserEvent( LINK( this, SvxIconChoiceCtrl_Impl, UserEventHdl),
    1435           0 :                 EVENTID_ADJUST_SCROLLBARS);
    1436             : 
    1437           0 :     if( pView->HasBackground() && !pView->GetBackground().IsScrollable() )
    1438             :     {
    1439           0 :         Rectangle aRect( GetOutputRect());
    1440           0 :         Wallpaper aPaper( pView->GetBackground() );
    1441           0 :         aPaper.SetRect( aRect );
    1442           0 :         pView->SetBackground( aPaper );
    1443             :     }
    1444           0 :     VisRectChanged();
    1445           0 : }
    1446             : 
    1447           0 : sal_Bool SvxIconChoiceCtrl_Impl::CheckHorScrollBar()
    1448             : {
    1449           0 :     if( !pZOrderList || !aHorSBar.IsVisible() )
    1450           0 :         return sal_False;
    1451           0 :     const MapMode& rMapMode = pView->GetMapMode();
    1452           0 :     Point aOrigin( rMapMode.GetOrigin() );
    1453           0 :     if(!( nWinBits & WB_HSCROLL) && !aOrigin.X() )
    1454             :     {
    1455           0 :         long nWidth = aOutputSize.Width();
    1456           0 :         const size_t nCount = pZOrderList->size();
    1457           0 :         long nMostRight = 0;
    1458           0 :         for( size_t nCur = 0; nCur < nCount; nCur++ )
    1459             :         {
    1460           0 :             SvxIconChoiceCtrlEntry* pEntry = (*pZOrderList)[ nCur ];
    1461           0 :             long nRight = GetEntryBoundRect(pEntry).Right();
    1462           0 :             if( nRight > nWidth )
    1463           0 :                 return sal_False;
    1464           0 :             if( nRight > nMostRight )
    1465           0 :                 nMostRight = nRight;
    1466             :         }
    1467           0 :         aHorSBar.Hide();
    1468           0 :         aOutputSize.Height() += nHorSBarHeight;
    1469           0 :         aVirtOutputSize.Width() = nMostRight;
    1470           0 :         aHorSBar.SetThumbPos( 0 );
    1471           0 :         Range aRange;
    1472           0 :         aRange.Max() = nMostRight - 1;
    1473           0 :         aHorSBar.SetRange( aRange  );
    1474           0 :         if( aVerSBar.IsVisible() )
    1475             :         {
    1476           0 :             Size aSize( aVerSBar.GetSizePixel());
    1477           0 :             aSize.Height() += nHorSBarHeight;
    1478           0 :             aVerSBar.SetSizePixel( aSize );
    1479             :         }
    1480           0 :         return sal_True;
    1481             :     }
    1482           0 :     return sal_False;
    1483             : }
    1484             : 
    1485           0 : sal_Bool SvxIconChoiceCtrl_Impl::CheckVerScrollBar()
    1486             : {
    1487           0 :     if( !pZOrderList || !aVerSBar.IsVisible() )
    1488           0 :         return sal_False;
    1489           0 :     const MapMode& rMapMode = pView->GetMapMode();
    1490           0 :     Point aOrigin( rMapMode.GetOrigin() );
    1491           0 :     if(!( nWinBits & WB_VSCROLL) && !aOrigin.Y() )
    1492             :     {
    1493           0 :         long nDeepest = 0;
    1494           0 :         long nHeight = aOutputSize.Height();
    1495           0 :         const size_t nCount = pZOrderList->size();
    1496           0 :         for( size_t nCur = 0; nCur < nCount; nCur++ )
    1497             :         {
    1498           0 :             SvxIconChoiceCtrlEntry* pEntry = (*pZOrderList)[ nCur ];
    1499           0 :             long nBottom = GetEntryBoundRect(pEntry).Bottom();
    1500           0 :             if( nBottom > nHeight )
    1501           0 :                 return sal_False;
    1502           0 :             if( nBottom > nDeepest )
    1503           0 :                 nDeepest = nBottom;
    1504             :         }
    1505           0 :         aVerSBar.Hide();
    1506           0 :         aOutputSize.Width() += nVerSBarWidth;
    1507           0 :         aVirtOutputSize.Height() = nDeepest;
    1508           0 :         aVerSBar.SetThumbPos( 0 );
    1509           0 :         Range aRange;
    1510           0 :         aRange.Max() = nDeepest - 1;
    1511           0 :         aVerSBar.SetRange( aRange  );
    1512           0 :         if( aHorSBar.IsVisible() )
    1513             :         {
    1514           0 :             Size aSize( aHorSBar.GetSizePixel());
    1515           0 :             aSize.Width() += nVerSBarWidth;
    1516           0 :             aHorSBar.SetSizePixel( aSize );
    1517             :         }
    1518           0 :         return sal_True;
    1519             :     }
    1520           0 :     return sal_False;
    1521             : }
    1522             : 
    1523             : 
    1524             : // hides scrollbars if they're unnecessary
    1525           0 : void SvxIconChoiceCtrl_Impl::CheckScrollBars()
    1526             : {
    1527           0 :     CheckVerScrollBar();
    1528           0 :     if( CheckHorScrollBar() )
    1529           0 :         CheckVerScrollBar();
    1530           0 :     if( aVerSBar.IsVisible() && aHorSBar.IsVisible() )
    1531           0 :         aScrBarBox.Show();
    1532             :     else
    1533           0 :         aScrBarBox.Hide();
    1534           0 : }
    1535             : 
    1536             : 
    1537           0 : void SvxIconChoiceCtrl_Impl::GetFocus()
    1538             : {
    1539           0 :     RepaintEntries( ICNVIEW_FLAG_SELECTED );
    1540           0 :     if( pCursor )
    1541             :     {
    1542           0 :         pCursor->SetFlags( ICNVIEW_FLAG_FOCUSED );
    1543           0 :         ShowCursor( sal_True );
    1544             :     }
    1545           0 : }
    1546             : 
    1547           0 : void SvxIconChoiceCtrl_Impl::LoseFocus()
    1548             : {
    1549           0 :     StopEditTimer();
    1550           0 :     if( pCursor )
    1551           0 :         pCursor->ClearFlags( ICNVIEW_FLAG_FOCUSED );
    1552           0 :     ShowCursor( sal_False );
    1553             : 
    1554             : //  HideFocus ();
    1555             : //  pView->Invalidate ( aFocus.aRect );
    1556             : 
    1557           0 :     RepaintEntries( ICNVIEW_FLAG_SELECTED );
    1558           0 : }
    1559             : 
    1560           0 : void SvxIconChoiceCtrl_Impl::SetUpdateMode( sal_Bool bUpdate )
    1561             : {
    1562           0 :     if( bUpdate != bUpdateMode )
    1563             :     {
    1564           0 :         bUpdateMode = bUpdate;
    1565           0 :         if( bUpdate )
    1566             :         {
    1567           0 :             AdjustScrollBars();
    1568           0 :             pImpCursor->Clear();
    1569           0 :             pGridMap->Clear();
    1570           0 :             pView->Invalidate(INVALIDATE_NOCHILDREN);
    1571             :         }
    1572             :     }
    1573           0 : }
    1574             : 
    1575           0 : void SvxIconChoiceCtrl_Impl::PaintEntry( SvxIconChoiceCtrlEntry* pEntry, sal_Bool bIsBackgroundPainted )
    1576             : {
    1577           0 :     Point aPos( GetEntryPos( pEntry ) );
    1578           0 :     PaintEntry( pEntry, aPos, 0, bIsBackgroundPainted );
    1579           0 : }
    1580             : 
    1581             : // priorities of the emphasis:  bDropTarget => bCursored => bSelected
    1582           0 : void SvxIconChoiceCtrl_Impl::PaintEmphasis(
    1583             :     const Rectangle& rTextRect, const Rectangle& rImageRect,
    1584             :     sal_Bool bSelected, sal_Bool bDropTarget, sal_Bool bCursored, OutputDevice* pOut,
    1585             :     sal_Bool bIsBackgroundPainted )
    1586             : {
    1587           0 :     static Color aTransparent( COL_TRANSPARENT );
    1588             : 
    1589           0 :     if( !pOut )
    1590           0 :         pOut = pView;
    1591             : 
    1592             : #ifdef OV_CHECK_EMPH_RECTS
    1593             :     {
    1594             :         Color aXOld( pOut->GetFillColor() );
    1595             :         pOut->SetFillColor( Color( COL_GREEN ));
    1596             :         pOut->DrawRect( rTextRect );
    1597             :         pOut->DrawRect( rImageRect );
    1598             :         pOut->SetFillColor( aXOld );
    1599             :     }
    1600             : #endif
    1601             : 
    1602           0 :     const StyleSettings& rSettings = pOut->GetSettings().GetStyleSettings();
    1603           0 :     Color aOldFillColor( pOut->GetFillColor() );
    1604             : 
    1605           0 :     sal_Bool bSolidTextRect = sal_False;
    1606           0 :     sal_Bool bSolidImageRect = sal_False;
    1607             : 
    1608           0 :     if( bDropTarget && ( eSelectionMode != NO_SELECTION ) )
    1609             :     {
    1610           0 :         pOut->SetFillColor( rSettings.GetHighlightColor() );
    1611           0 :         bSolidTextRect = sal_True;
    1612           0 :         bSolidImageRect = sal_True;
    1613             :     }
    1614             :     else
    1615             :     {
    1616           0 :         if ( !bSelected || bCursored )
    1617             :         {
    1618           0 :             if( !pView->HasFontFillColor() )
    1619           0 :                 pOut->SetFillColor( pOut->GetBackground().GetColor() );
    1620             :             else
    1621             :             {
    1622           0 :                 const Color& rFillColor = pView->GetFont().GetFillColor();
    1623           0 :                 pOut->SetFillColor( rFillColor );
    1624           0 :                 if( rFillColor != aTransparent )
    1625           0 :                     bSolidTextRect = sal_True;
    1626             :             }
    1627             :         }
    1628             :     }
    1629             : 
    1630             :     // draw text rectangle
    1631           0 :     if( !bSolidTextRect )
    1632             :     {
    1633           0 :         if( !bIsBackgroundPainted )
    1634           0 :             pOut->Erase( rTextRect );
    1635             :     }
    1636             :     else
    1637             :     {
    1638           0 :         Color aOldLineColor;
    1639           0 :         if( bCursored )
    1640             :         {
    1641           0 :             aOldLineColor = pOut->GetLineColor();
    1642           0 :             pOut->SetLineColor( Color( COL_GRAY ) );
    1643             :         }
    1644           0 :         pOut->DrawRect( rTextRect );
    1645           0 :         if( bCursored )
    1646           0 :             pOut->SetLineColor( aOldLineColor );
    1647             :     }
    1648             : 
    1649             :     // draw image rectangle
    1650           0 :     if( !bSolidImageRect )
    1651             :     {
    1652           0 :         if( !bIsBackgroundPainted )
    1653           0 :             pOut->Erase( rImageRect );
    1654             :     }
    1655             : // the emphasis of the images has to be drawn by the derived class (in the
    1656             : // virtual function DrawEntryImage)
    1657             : //  else
    1658             : //      pOut->DrawRect( rImageRect );
    1659             : 
    1660           0 :     pOut->SetFillColor( aOldFillColor );
    1661           0 : }
    1662             : 
    1663             : 
    1664           0 : void SvxIconChoiceCtrl_Impl::PaintItem( const Rectangle& rRect,
    1665             :     IcnViewFieldType eItem, SvxIconChoiceCtrlEntry* pEntry, sal_uInt16 nPaintFlags,
    1666             :     OutputDevice* pOut, const String* pStr, ::vcl::ControlLayoutData* _pLayoutData )
    1667             : {
    1668           0 :     if( eItem == IcnViewFieldTypeText )
    1669             :     {
    1670           0 :         String aText;
    1671           0 :         if( !pStr )
    1672           0 :             aText = pView->GetEntryText( pEntry, sal_False );
    1673             :         else
    1674           0 :             aText = *pStr;
    1675             : 
    1676           0 :         if ( _pLayoutData )
    1677             :         {
    1678             :             pOut->DrawText( rRect, aText, nCurTextDrawFlags,
    1679           0 :                 &_pLayoutData->m_aUnicodeBoundRects, &_pLayoutData->m_aDisplayText );
    1680             :         }
    1681             :         else
    1682             :         {
    1683           0 :             Color aOldFontColor = pOut->GetTextColor();
    1684           0 :             if ( pView->AutoFontColor() )
    1685             :             {
    1686           0 :                 Color aBkgColor( pOut->GetBackground().GetColor() );
    1687           0 :                 Color aFontColor;
    1688           0 :                 sal_uInt16 nColor = ( aBkgColor.GetRed() + aBkgColor.GetGreen() + aBkgColor.GetBlue() ) / 3;
    1689           0 :                 if ( nColor > 127 )
    1690           0 :                     aFontColor.SetColor ( COL_BLACK );
    1691             :                 else
    1692           0 :                     aFontColor.SetColor( COL_WHITE );
    1693           0 :                 pOut->SetTextColor( aFontColor );
    1694             :             }
    1695             : 
    1696           0 :             pOut->DrawText( rRect, aText, nCurTextDrawFlags );
    1697             : 
    1698           0 :             if ( pView->AutoFontColor() )
    1699           0 :                 pOut->SetTextColor( aOldFontColor );
    1700             : 
    1701           0 :             if( pEntry->IsFocused() )
    1702             :             {
    1703           0 :                 Rectangle aRect ( CalcFocusRect( (SvxIconChoiceCtrlEntry*)pEntry ) );
    1704           0 :                 /*pView->*/ShowFocus( aRect );
    1705           0 :                 DrawFocusRect( pOut );
    1706             :             }
    1707           0 :         }
    1708             :     }
    1709             :     else
    1710             :     {
    1711           0 :         Point aPos( rRect.TopLeft() );
    1712           0 :         if( nPaintFlags & PAINTFLAG_HOR_CENTERED )
    1713           0 :             aPos.X() += (rRect.GetWidth() - aImageSize.Width() ) / 2;
    1714           0 :         if( nPaintFlags & PAINTFLAG_VER_CENTERED )
    1715           0 :             aPos.Y() += (rRect.GetHeight() - aImageSize.Height() ) / 2;
    1716           0 :         pView->DrawEntryImage( pEntry, aPos, *pOut );
    1717             :     }
    1718           0 : }
    1719             : 
    1720           0 : void SvxIconChoiceCtrl_Impl::PaintEntryVirtOutDev( SvxIconChoiceCtrlEntry* pEntry )
    1721             : {
    1722             : #ifdef OV_NO_VIRT_OUTDEV
    1723             :     PaintEntry( pEntry );
    1724             : #else
    1725           0 :     if( !pEntryPaintDev )
    1726             :     {
    1727           0 :         pEntryPaintDev = new VirtualDevice( *pView );
    1728           0 :         pEntryPaintDev->SetFont( pView->GetFont() );
    1729           0 :         pEntryPaintDev->SetLineColor();
    1730             :         //pEntryPaintDev->SetBackground( pView->GetBackground() );
    1731             :     }
    1732           0 :     const Rectangle& rRect = GetEntryBoundRect( pEntry );
    1733           0 :     Rectangle aOutRect( GetOutputRect() );
    1734           0 :     if( !rRect.IsOver( aOutRect ) )
    1735           0 :         return;
    1736           0 :     Wallpaper aPaper( pView->GetBackground() );
    1737           0 :     Rectangle aRect( aPaper.GetRect() );
    1738             : 
    1739             :     // move rectangle, so the bounding rectangle of the entry lies in
    1740             :     // VirtOut-Dev at 0,0
    1741           0 :     aRect.Move( -rRect.Left(), -rRect.Top() );
    1742           0 :     aPaper.SetRect( aRect );
    1743           0 :     pEntryPaintDev->SetBackground( aPaper );
    1744           0 :     pEntryPaintDev->SetFont( pView->GetFont() );
    1745             : 
    1746           0 :     Size aSize( rRect.GetSize() );
    1747           0 :     pEntryPaintDev->SetOutputSizePixel( aSize );
    1748             :     pEntryPaintDev->DrawOutDev(
    1749           0 :         Point(), aSize, rRect.TopLeft(), aSize, *pView );
    1750             : 
    1751           0 :     PaintEntry( pEntry, Point(), pEntryPaintDev );
    1752             : 
    1753             :     pView->DrawOutDev(
    1754             :         rRect.TopLeft(),
    1755             :         aSize,
    1756             :         Point(),
    1757             :         aSize,
    1758           0 :         *pEntryPaintDev );
    1759             : #endif
    1760             : }
    1761             : 
    1762             : 
    1763           0 : void SvxIconChoiceCtrl_Impl::PaintEntry( SvxIconChoiceCtrlEntry* pEntry, const Point& rPos,
    1764             :     OutputDevice* pOut, sal_Bool bIsBackgroundPainted )
    1765             : {
    1766           0 :     if( !pOut )
    1767           0 :         pOut = pView;
    1768             : 
    1769           0 :     sal_Bool bSelected = sal_False;
    1770             : 
    1771           0 :     if( eSelectionMode != NO_SELECTION )
    1772           0 :         bSelected = pEntry->IsSelected();
    1773             : 
    1774           0 :     sal_Bool bCursored = pEntry->IsCursored();
    1775           0 :     sal_Bool bDropTarget = pEntry->IsDropTarget();
    1776           0 :     sal_Bool bNoEmphasis = pEntry->IsBlockingEmphasis();
    1777             : 
    1778           0 :     Font aTempFont( pOut->GetFont() );
    1779             : 
    1780             :     // AutoFontColor
    1781             :     /*
    1782             :     if ( pView->AutoFontColor() )
    1783             :     {
    1784             :         aTempFont.SetColor ( aFontColor );
    1785             :     }
    1786             :     */
    1787             : 
    1788           0 :     String aEntryText( pView->GetEntryText( pEntry, sal_False ) );
    1789           0 :     Rectangle aTextRect( CalcTextRect(pEntry,&rPos,sal_False,&aEntryText));
    1790           0 :     Rectangle aBmpRect( CalcBmpRect(pEntry, &rPos ) );
    1791             : 
    1792             :     sal_Bool    bShowSelection =
    1793             :         (   (   ( bSelected && !bCursored )
    1794             :             ||  bDropTarget
    1795             :             )
    1796             :         &&  !bNoEmphasis
    1797             :         &&  ( eSelectionMode != NO_SELECTION )
    1798           0 :         );
    1799           0 :     sal_Bool bActiveSelection = ( 0 != ( nWinBits & WB_NOHIDESELECTION ) ) || pView->HasFocus();
    1800             : 
    1801           0 :     if ( bShowSelection )
    1802             :     {
    1803           0 :         const StyleSettings& rSettings = pOut->GetSettings().GetStyleSettings();
    1804           0 :         Font aNewFont( aTempFont );
    1805             : 
    1806             :         // font fill colors that are attributed "hard" need corresponding "hard"
    1807             :         // attributed highlight colors
    1808           0 :         if( pView->HasFontFillColor() )
    1809             :         {
    1810           0 :             if( (nWinBits & WB_NOHIDESELECTION) || pView->HasFocus() )
    1811           0 :                 aNewFont.SetFillColor( rSettings.GetHighlightColor() );
    1812             :             else
    1813           0 :                 aNewFont.SetFillColor( rSettings.GetDeactiveColor() );
    1814             :         }
    1815             : 
    1816           0 :         Color aWinCol = rSettings.GetWindowTextColor();
    1817           0 :         if ( !bActiveSelection && rSettings.GetFaceColor().IsBright() == aWinCol.IsBright() )
    1818           0 :             aNewFont.SetColor( rSettings.GetWindowTextColor() );
    1819             :         else
    1820           0 :             aNewFont.SetColor( rSettings.GetHighlightTextColor() );
    1821             : 
    1822           0 :         pOut->SetFont( aNewFont );
    1823             : 
    1824           0 :         pOut->SetFillColor( pOut->GetBackground().GetColor() );
    1825           0 :         pOut->DrawRect( CalcFocusRect( pEntry ) );
    1826           0 :         pOut->SetFillColor( );
    1827             :     }
    1828             : 
    1829           0 :     sal_Bool bResetClipRegion = sal_False;
    1830           0 :     if( !pView->IsClipRegion() && (aVerSBar.IsVisible() || aHorSBar.IsVisible()) )
    1831             :     {
    1832           0 :         Rectangle aOutputArea( GetOutputRect() );
    1833           0 :         if( aOutputArea.IsOver(aTextRect) || aOutputArea.IsOver(aBmpRect) )
    1834             :         {
    1835           0 :             pView->SetClipRegion( aOutputArea );
    1836           0 :             bResetClipRegion = sal_True;
    1837             :         }
    1838             :     }
    1839             : 
    1840             : #ifdef OV_DRAWBOUNDRECT
    1841             :     {
    1842             :         Color aXOldColor = pOut->GetLineColor();
    1843             :         pOut->SetLineColor( Color( COL_LIGHTRED ) );
    1844             :         Rectangle aXRect( pEntry->aRect );
    1845             :         aXRect.SetPos( rPos );
    1846             :         pOut->DrawRect( aXRect );
    1847             :         pOut->SetLineColor( aXOldColor );
    1848             :     }
    1849             : #endif
    1850             : 
    1851           0 :     sal_Bool bLargeIconMode = WB_ICON == ( nWinBits & (VIEWMODE_MASK) );
    1852           0 :     sal_uInt16 nBmpPaintFlags = PAINTFLAG_VER_CENTERED;
    1853           0 :     if ( bLargeIconMode )
    1854           0 :         nBmpPaintFlags |= PAINTFLAG_HOR_CENTERED;
    1855           0 :     sal_uInt16 nTextPaintFlags = bLargeIconMode ? PAINTFLAG_HOR_CENTERED : PAINTFLAG_VER_CENTERED;
    1856             : 
    1857           0 :     if( !bNoEmphasis )
    1858           0 :         PaintEmphasis(aTextRect,aBmpRect,bSelected,bDropTarget,bCursored,pOut,bIsBackgroundPainted);
    1859             : 
    1860           0 :     if ( bShowSelection )
    1861             :         pView->DrawSelectionBackground( CalcFocusRect( pEntry ),
    1862           0 :         bActiveSelection ? 1 : 2 /* highlight */, sal_False /* check */, sal_True /* border */, sal_False /* ext border only */ );
    1863             : 
    1864           0 :     PaintItem( aBmpRect, IcnViewFieldTypeImage, pEntry, nBmpPaintFlags, pOut );
    1865             : 
    1866             :     PaintItem( aTextRect, IcnViewFieldTypeText, pEntry,
    1867           0 :         nTextPaintFlags, pOut );
    1868             : 
    1869             :     // draw highlight frame
    1870           0 :     if( pEntry == pCurHighlightFrame && !bNoEmphasis )
    1871           0 :         DrawHighlightFrame( pOut, CalcFocusRect( pEntry ), sal_False );
    1872             : 
    1873           0 :     pOut->SetFont( aTempFont );
    1874           0 :     if( bResetClipRegion )
    1875           0 :         pView->SetClipRegion();
    1876           0 : }
    1877             : 
    1878           0 : void SvxIconChoiceCtrl_Impl::SetEntryPos( SvxIconChoiceCtrlEntry* pEntry, const Point& rPos,
    1879             :     sal_Bool bAdjustAtGrid, sal_Bool bCheckScrollBars, sal_Bool bKeepGridMap )
    1880             : {
    1881           0 :     ShowCursor( sal_False );
    1882           0 :     Rectangle aBoundRect( GetEntryBoundRect( pEntry ));
    1883           0 :     pView->Invalidate( aBoundRect );
    1884           0 :     ToTop( pEntry );
    1885           0 :     if( !IsAutoArrange() )
    1886             :     {
    1887           0 :         sal_Bool bAdjustVirtSize = sal_False;
    1888           0 :         if( rPos != aBoundRect.TopLeft() )
    1889             :         {
    1890             :             Point aGridOffs(
    1891           0 :                 pEntry->aGridRect.TopLeft() - pEntry->aRect.TopLeft() );
    1892           0 :             pImpCursor->Clear();
    1893           0 :             if( !bKeepGridMap )
    1894           0 :                 pGridMap->Clear();
    1895           0 :             aBoundRect.SetPos( rPos );
    1896           0 :             pEntry->aRect = aBoundRect;
    1897           0 :             pEntry->aGridRect.SetPos( rPos + aGridOffs );
    1898           0 :             bAdjustVirtSize = sal_True;
    1899             :         }
    1900           0 :         if( bAdjustAtGrid )
    1901             :         {
    1902           0 :             if( bAdjustVirtSize )
    1903             :             {
    1904             :                 // By aligning the (in some cases newly positioned) entry, it
    1905             :                 // can become completely visible again, so that maybe we don't
    1906             :                 // need a scrollbar after all. To avoid suddenly turning the
    1907             :                 // scrollbar(s) on and then off again, we use the aligned
    1908             :                 // bounding rectangle of the entry to enlarge the virtual
    1909             :                 // output size. The virtual size has to be adapted, because
    1910             :                 // AdjustEntryAtGrid depends on it.
    1911           0 :                 const Rectangle& rBoundRect = GetEntryBoundRect( pEntry );
    1912           0 :                 Rectangle aCenterRect( CalcBmpRect( pEntry, 0 ));
    1913           0 :                 Point aNewPos( AdjustAtGrid( aCenterRect, rBoundRect ) );
    1914           0 :                 Rectangle aNewBoundRect( aNewPos, pEntry->aRect.GetSize());
    1915           0 :                 AdjustVirtSize( aNewBoundRect );
    1916           0 :                 bAdjustVirtSize = sal_False;
    1917             :             }
    1918           0 :             AdjustEntryAtGrid( pEntry );
    1919           0 :             ToTop( pEntry );
    1920             :         }
    1921           0 :         if( bAdjustVirtSize )
    1922           0 :             AdjustVirtSize( pEntry->aRect );
    1923             : 
    1924           0 :         if( bCheckScrollBars && bUpdateMode )
    1925           0 :             CheckScrollBars();
    1926             : 
    1927           0 :         pView->Invalidate( pEntry->aRect );
    1928           0 :         pGridMap->OccupyGrids( pEntry );
    1929             :     }
    1930             :     else
    1931             :     {
    1932           0 :         SvxIconChoiceCtrlEntry* pPrev = FindEntryPredecessor( pEntry, rPos );
    1933           0 :         SetEntryPredecessor( pEntry, pPrev );
    1934           0 :         aAutoArrangeTimer.Start();
    1935             :     }
    1936           0 :     ShowCursor( sal_True );
    1937           0 : }
    1938             : 
    1939           0 : void SvxIconChoiceCtrl_Impl::SetNoSelection()
    1940             : {
    1941             :     // block recursive calls via SelectEntry
    1942           0 :     if( !(nFlags & F_CLEARING_SELECTION ))
    1943             :     {
    1944           0 :         nFlags |= F_CLEARING_SELECTION;
    1945           0 :         DeselectAllBut( 0, sal_True );
    1946           0 :         nFlags &= ~F_CLEARING_SELECTION;
    1947             :     }
    1948           0 : }
    1949             : 
    1950           0 : SvxIconChoiceCtrlEntry* SvxIconChoiceCtrl_Impl::GetEntry( const Point& rDocPos, sal_Bool bHit )
    1951             : {
    1952           0 :     CheckBoundingRects();
    1953             :     // search through z-order list from the end
    1954           0 :     size_t nCount = pZOrderList->size();
    1955           0 :     while( nCount )
    1956             :     {
    1957           0 :         nCount--;
    1958           0 :         SvxIconChoiceCtrlEntry* pEntry = (*pZOrderList)[ nCount ];
    1959           0 :         if( pEntry->aRect.IsInside( rDocPos ) )
    1960             :         {
    1961           0 :             if( bHit )
    1962             :             {
    1963           0 :                 Rectangle aRect = CalcBmpRect( pEntry );
    1964           0 :                 aRect.Top() -= 3;
    1965           0 :                 aRect.Bottom() += 3;
    1966           0 :                 aRect.Left() -= 3;
    1967           0 :                 aRect.Right() += 3;
    1968           0 :                 if( aRect.IsInside( rDocPos ) )
    1969           0 :                     return pEntry;
    1970           0 :                 aRect = CalcTextRect( pEntry );
    1971           0 :                 if( aRect.IsInside( rDocPos ) )
    1972           0 :                     return pEntry;
    1973             :             }
    1974             :             else
    1975           0 :                 return pEntry;
    1976             :         }
    1977             :     }
    1978           0 :     return 0;
    1979             : }
    1980             : 
    1981           0 : Point SvxIconChoiceCtrl_Impl::GetEntryPos( SvxIconChoiceCtrlEntry* pEntry )
    1982             : {
    1983           0 :     return pEntry->aRect.TopLeft();
    1984             : }
    1985             : 
    1986           0 : void SvxIconChoiceCtrl_Impl::MakeEntryVisible( SvxIconChoiceCtrlEntry* pEntry, sal_Bool bBound )
    1987             : {
    1988           0 :     if ( bBound )
    1989             :     {
    1990           0 :         const Rectangle& rRect = GetEntryBoundRect( pEntry );
    1991           0 :         MakeVisible( rRect );
    1992             :     }
    1993             :     else
    1994             :     {
    1995           0 :         Rectangle aRect = CalcBmpRect( pEntry );
    1996           0 :         aRect.Union( CalcTextRect( pEntry ) );
    1997           0 :         aRect.Top() += TBOFFS_BOUND;
    1998           0 :         aRect.Bottom() += TBOFFS_BOUND;
    1999           0 :         aRect.Left() += LROFFS_BOUND;
    2000           0 :         aRect.Right() += LROFFS_BOUND;
    2001           0 :         MakeVisible( aRect );
    2002             :     }
    2003           0 : }
    2004             : 
    2005           0 : const Rectangle& SvxIconChoiceCtrl_Impl::GetEntryBoundRect( SvxIconChoiceCtrlEntry* pEntry )
    2006             : {
    2007           0 :     if( !IsBoundingRectValid( pEntry->aRect ))
    2008           0 :         FindBoundingRect( pEntry );
    2009           0 :     return pEntry->aRect;
    2010             : }
    2011             : 
    2012           0 : Rectangle SvxIconChoiceCtrl_Impl::CalcBmpRect( SvxIconChoiceCtrlEntry* pEntry, const Point* pPos )
    2013             : {
    2014           0 :     Rectangle aBound = GetEntryBoundRect( pEntry );
    2015           0 :     if( pPos )
    2016           0 :         aBound.SetPos( *pPos );
    2017           0 :     Point aPos( aBound.TopLeft() );
    2018             : 
    2019           0 :     switch( nWinBits & (VIEWMODE_MASK) )
    2020             :     {
    2021             :         case WB_ICON:
    2022             :         {
    2023           0 :             aPos.X() += ( aBound.GetWidth() - aImageSize.Width() ) / 2;
    2024           0 :             return Rectangle( aPos, aImageSize );
    2025             :         }
    2026             : 
    2027             :         case WB_SMALLICON:
    2028             :         case WB_DETAILS:
    2029           0 :             aPos.Y() += ( aBound.GetHeight() - aImageSize.Height() ) / 2;
    2030             :             //TODO: determine horizontal distance to bounding rectangle
    2031           0 :             return Rectangle( aPos, aImageSize );
    2032             : 
    2033             :         default:
    2034             :             OSL_FAIL("IconView: Viewmode not set");
    2035           0 :             return aBound;
    2036             :     }
    2037             : }
    2038             : 
    2039           0 : Rectangle SvxIconChoiceCtrl_Impl::CalcTextRect( SvxIconChoiceCtrlEntry* pEntry,
    2040             :     const Point* pEntryPos, sal_Bool bEdit, const String* pStr )
    2041             : {
    2042           0 :     String aEntryText;
    2043           0 :     if( !pStr )
    2044           0 :         aEntryText = pView->GetEntryText( pEntry, bEdit );
    2045             :     else
    2046           0 :         aEntryText = *pStr;
    2047             : 
    2048           0 :     const Rectangle aMaxTextRect( CalcMaxTextRect( pEntry ) );
    2049           0 :     Rectangle aBound( GetEntryBoundRect( pEntry ) );
    2050           0 :     if( pEntryPos )
    2051           0 :         aBound.SetPos( *pEntryPos );
    2052             : 
    2053           0 :     Rectangle aTextRect( aMaxTextRect );
    2054           0 :     if( !bEdit )
    2055           0 :         aTextRect = pView->GetTextRect( aTextRect, aEntryText, nCurTextDrawFlags );
    2056             : 
    2057           0 :     Size aTextSize( aTextRect.GetSize() );
    2058             : 
    2059           0 :     Point aPos( aBound.TopLeft() );
    2060           0 :     long nBoundWidth = aBound.GetWidth();
    2061           0 :     long nBoundHeight = aBound.GetHeight();
    2062             : 
    2063           0 :     switch( nWinBits & (VIEWMODE_MASK) )
    2064             :     {
    2065             :         case WB_ICON:
    2066           0 :             aPos.Y() += aImageSize.Height();
    2067           0 :             aPos.Y() += VER_DIST_BMP_STRING;
    2068             :             // at little more space when editing
    2069           0 :             if( bEdit )
    2070             :             {
    2071             :                 // +20%
    2072           0 :                 long nMinWidth = (( (aImageSize.Width()*10) / 100 ) * 2 ) +
    2073           0 :                                  aImageSize.Width();
    2074           0 :                 if( nMinWidth > nBoundWidth )
    2075           0 :                     nMinWidth = nBoundWidth;
    2076             : 
    2077           0 :                 if( aTextSize.Width() < nMinWidth )
    2078           0 :                     aTextSize.Width() = nMinWidth;
    2079             : 
    2080             :                 // when editing, overlap with the area below is allowed
    2081           0 :                 Size aOptSize = aMaxTextRect.GetSize();
    2082           0 :                 if( aOptSize.Height() > aTextSize.Height() )
    2083           0 :                     aTextSize.Height() = aOptSize.Height();
    2084             :             }
    2085           0 :             aPos.X() += (nBoundWidth - aTextSize.Width()) / 2;
    2086           0 :             break;
    2087             : 
    2088             :         case WB_SMALLICON:
    2089             :         case WB_DETAILS:
    2090           0 :             aPos.X() += aImageSize.Width();
    2091           0 :             aPos.X() += HOR_DIST_BMP_STRING;
    2092           0 :             aPos.Y() += (nBoundHeight - aTextSize.Height()) / 2;
    2093           0 :             break;
    2094             :     }
    2095           0 :     return Rectangle( aPos, aTextSize );
    2096             : }
    2097             : 
    2098             : 
    2099           0 : long SvxIconChoiceCtrl_Impl::CalcBoundingWidth( SvxIconChoiceCtrlEntry* pEntry ) const
    2100             : {
    2101           0 :     long nStringWidth = GetItemSize( pEntry, IcnViewFieldTypeText ).Width();
    2102             : //  nStringWidth += 2*LROFFS_TEXT;
    2103           0 :     long nWidth = 0;
    2104             : 
    2105           0 :     switch( nWinBits & (VIEWMODE_MASK) )
    2106             :     {
    2107             :         case WB_ICON:
    2108           0 :             nWidth = Max( nStringWidth, aImageSize.Width() );
    2109           0 :             break;
    2110             : 
    2111             :         case WB_SMALLICON:
    2112             :         case WB_DETAILS:
    2113           0 :             nWidth = aImageSize.Width();
    2114           0 :             nWidth += HOR_DIST_BMP_STRING;
    2115           0 :             nWidth += nStringWidth;
    2116           0 :             break;
    2117             :     }
    2118           0 :     return nWidth;
    2119             : }
    2120             : 
    2121           0 : long SvxIconChoiceCtrl_Impl::CalcBoundingHeight( SvxIconChoiceCtrlEntry* pEntry ) const
    2122             : {
    2123           0 :     long nStringHeight = GetItemSize( pEntry, IcnViewFieldTypeText).Height();
    2124           0 :     long nHeight = 0;
    2125             : 
    2126           0 :     switch( nWinBits & (VIEWMODE_MASK) )
    2127             :     {
    2128             :         case WB_ICON:
    2129           0 :             nHeight = aImageSize.Height();
    2130           0 :             nHeight += VER_DIST_BMP_STRING;
    2131           0 :             nHeight += nStringHeight;
    2132           0 :             break;
    2133             : 
    2134             :         case WB_SMALLICON:
    2135             :         case WB_DETAILS:
    2136           0 :             nHeight = Max( aImageSize.Height(), nStringHeight );
    2137           0 :             break;
    2138             :     }
    2139           0 :     if( nHeight > nMaxBoundHeight )
    2140             :     {
    2141           0 :         ((SvxIconChoiceCtrl_Impl*)this)->nMaxBoundHeight = nHeight;
    2142           0 :         ((SvxIconChoiceCtrl_Impl*)this)->aHorSBar.SetLineSize( GetScrollBarLineSize() );
    2143           0 :         ((SvxIconChoiceCtrl_Impl*)this)->aVerSBar.SetLineSize( GetScrollBarLineSize() );
    2144             :     }
    2145           0 :     return nHeight;
    2146             : }
    2147             : 
    2148           0 : Size SvxIconChoiceCtrl_Impl::CalcBoundingSize( SvxIconChoiceCtrlEntry* pEntry ) const
    2149             : {
    2150             :     return Size( CalcBoundingWidth( pEntry ),
    2151           0 :                  CalcBoundingHeight( pEntry ) );
    2152             : }
    2153             : 
    2154           0 : void SvxIconChoiceCtrl_Impl::RecalcAllBoundingRectsSmart()
    2155             : {
    2156           0 :     nMaxBoundHeight = 0;
    2157           0 :     pZOrderList->clear();
    2158             :     size_t nCur;
    2159             :     SvxIconChoiceCtrlEntry* pEntry;
    2160           0 :     const size_t nCount = aEntries.size();
    2161             : 
    2162           0 :     if( !IsAutoArrange() || !pHead )
    2163             :     {
    2164           0 :         for( nCur = 0; nCur < nCount; nCur++ )
    2165             :         {
    2166           0 :             pEntry = aEntries[ nCur ];
    2167           0 :             if( IsBoundingRectValid( pEntry->aRect ))
    2168             :             {
    2169           0 :                 Size aBoundSize( pEntry->aRect.GetSize() );
    2170           0 :                 if( aBoundSize.Height() > nMaxBoundHeight )
    2171           0 :                     nMaxBoundHeight = aBoundSize.Height();
    2172             :             }
    2173             :             else
    2174           0 :                 FindBoundingRect( pEntry );
    2175           0 :             pZOrderList->push_back( pEntry );
    2176             :         }
    2177             :     }
    2178             :     else
    2179             :     {
    2180           0 :         nCur = 0;
    2181           0 :         pEntry = pHead;
    2182           0 :         while( nCur != nCount )
    2183             :         {
    2184             :             DBG_ASSERT(pEntry->pflink&&pEntry->pblink,"SvxIconChoiceCtrl_Impl::RecalcAllBoundingRect > Bad link(s)");
    2185           0 :             if( IsBoundingRectValid( pEntry->aRect ))
    2186             :             {
    2187           0 :                 Size aBoundSize( pEntry->aRect.GetSize() );
    2188           0 :                 if( aBoundSize.Height() > nMaxBoundHeight )
    2189           0 :                     nMaxBoundHeight = aBoundSize.Height();
    2190             :             }
    2191             :             else
    2192           0 :                 FindBoundingRect( pEntry );
    2193           0 :             pZOrderList->push_back( pEntry );
    2194           0 :             pEntry = pEntry->pflink;
    2195           0 :             nCur++;
    2196             :         }
    2197             :     }
    2198           0 :     AdjustScrollBars();
    2199           0 : }
    2200             : 
    2201           0 : void SvxIconChoiceCtrl_Impl::FindBoundingRect( SvxIconChoiceCtrlEntry* pEntry )
    2202             : {
    2203             :     DBG_ASSERT(!pEntry->IsPosLocked(),"Locked entry pos in FindBoundingRect");
    2204           0 :     if( pEntry->IsPosLocked() && IsBoundingRectValid( pEntry->aRect) )
    2205             :     {
    2206           0 :         AdjustVirtSize( pEntry->aRect );
    2207           0 :         return;
    2208             :     }
    2209           0 :     Size aSize( CalcBoundingSize( pEntry ) );
    2210           0 :     Point aPos(pGridMap->GetGridRect(pGridMap->GetUnoccupiedGrid(sal_True)).TopLeft());
    2211           0 :     SetBoundingRect_Impl( pEntry, aPos, aSize );
    2212             : }
    2213             : 
    2214           0 : void SvxIconChoiceCtrl_Impl::SetBoundingRect_Impl( SvxIconChoiceCtrlEntry* pEntry, const Point& rPos,
    2215             :     const Size& /*rBoundingSize*/ )
    2216             : {
    2217           0 :     Rectangle aGridRect( rPos, Size(nGridDX, nGridDY) );
    2218           0 :     pEntry->aGridRect = aGridRect;
    2219           0 :     Center( pEntry );
    2220           0 :     AdjustVirtSize( pEntry->aRect );
    2221           0 :     pGridMap->OccupyGrids( pEntry );
    2222           0 : }
    2223             : 
    2224             : 
    2225           0 : void SvxIconChoiceCtrl_Impl::SetCursor( SvxIconChoiceCtrlEntry* pEntry, sal_Bool bSyncSingleSelection,
    2226             :     sal_Bool bShowFocusAsync )
    2227             : {
    2228           0 :     if( pEntry == pCursor )
    2229             :     {
    2230           0 :         if( pCursor && eSelectionMode == SINGLE_SELECTION && bSyncSingleSelection &&
    2231           0 :                 !pCursor->IsSelected() )
    2232           0 :             SelectEntry( pCursor, sal_True, sal_True );
    2233           0 :         return;
    2234             :     }
    2235           0 :     ShowCursor( sal_False );
    2236           0 :     SvxIconChoiceCtrlEntry* pOldCursor = pCursor;
    2237           0 :     pCursor = pEntry;
    2238           0 :     if( pOldCursor )
    2239             :     {
    2240           0 :         pOldCursor->ClearFlags( ICNVIEW_FLAG_FOCUSED );
    2241           0 :         if( eSelectionMode == SINGLE_SELECTION && bSyncSingleSelection )
    2242           0 :             SelectEntry( pOldCursor, sal_False, sal_True ); // deselect old cursor
    2243             :     }
    2244           0 :     if( pCursor )
    2245             :     {
    2246           0 :         ToTop( pCursor );
    2247           0 :         pCursor->SetFlags( ICNVIEW_FLAG_FOCUSED );
    2248           0 :         if( eSelectionMode == SINGLE_SELECTION && bSyncSingleSelection )
    2249           0 :             SelectEntry( pCursor, sal_True, sal_True );
    2250           0 :         if( !bShowFocusAsync )
    2251           0 :             ShowCursor( sal_True );
    2252             :         else
    2253             :         {
    2254           0 :             if( !nUserEventShowCursor )
    2255             :                 nUserEventShowCursor =
    2256             :                     Application::PostUserEvent( LINK( this, SvxIconChoiceCtrl_Impl, UserEventHdl),
    2257           0 :                         EVENTID_SHOW_CURSOR );
    2258             :         }
    2259             :     }
    2260             : }
    2261             : 
    2262             : 
    2263           0 : void SvxIconChoiceCtrl_Impl::ShowCursor( sal_Bool bShow )
    2264             : {
    2265           0 :     if( !pCursor || !bShow || !pView->HasFocus() )
    2266             :     {
    2267           0 :         pView->HideFocus();
    2268           0 :         return;
    2269             :     }
    2270           0 :     Rectangle aRect ( CalcFocusRect( pCursor ) );
    2271           0 :     /*pView->*/ShowFocus( aRect );
    2272             : }
    2273             : 
    2274             : 
    2275           0 : void SvxIconChoiceCtrl_Impl::HideDDIcon()
    2276             : {
    2277           0 :     pView->Update();
    2278           0 :     ImpHideDDIcon();
    2279           0 :     pDDBufDev = pDDDev;
    2280           0 :     pDDDev = 0;
    2281           0 : }
    2282             : 
    2283           0 : void SvxIconChoiceCtrl_Impl::ImpHideDDIcon()
    2284             : {
    2285           0 :     if( pDDDev )
    2286             :     {
    2287           0 :         Size aSize( pDDDev->GetOutputSizePixel() );
    2288             :         // restore pView
    2289           0 :         pView->DrawOutDev( aDDLastRectPos, aSize, Point(), aSize, *pDDDev );
    2290             :     }
    2291           0 : }
    2292             : 
    2293           0 : sal_Bool SvxIconChoiceCtrl_Impl::HandleScrollCommand( const CommandEvent& rCmd )
    2294             : {
    2295           0 :     Rectangle aDocRect( GetDocumentRect() );
    2296           0 :     Rectangle aVisRect( GetVisibleRect() );
    2297           0 :     if( aVisRect.IsInside( aDocRect ))
    2298           0 :         return sal_False;
    2299           0 :     Size aDocSize( aDocRect.GetSize() );
    2300           0 :     Size aVisSize( aVisRect.GetSize() );
    2301           0 :     sal_Bool bHor = aDocSize.Width() > aVisSize.Width();
    2302           0 :     sal_Bool bVer = aDocSize.Height() > aVisSize.Height();
    2303             : 
    2304           0 :     long nScrollDX = 0, nScrollDY = 0;
    2305             : 
    2306           0 :     switch( rCmd.GetCommand() )
    2307             :     {
    2308             :         case COMMAND_STARTAUTOSCROLL:
    2309             :         {
    2310           0 :             pView->EndTracking();
    2311           0 :             sal_uInt16 nScrollFlags = 0;
    2312           0 :             if( bHor )
    2313           0 :                 nScrollFlags |= AUTOSCROLL_HORZ;
    2314           0 :             if( bVer )
    2315           0 :                 nScrollFlags |= AUTOSCROLL_VERT;
    2316           0 :             if( nScrollFlags )
    2317             :             {
    2318           0 :                 pView->StartAutoScroll( nScrollFlags );
    2319           0 :                 return sal_True;
    2320             :             }
    2321             :         }
    2322           0 :         break;
    2323             : 
    2324             :         case COMMAND_WHEEL:
    2325             :         {
    2326           0 :             const CommandWheelData* pData = rCmd.GetWheelData();
    2327           0 :             if( pData && (COMMAND_WHEEL_SCROLL == pData->GetMode()) && !pData->IsHorz() )
    2328             :             {
    2329           0 :                 sal_uLong nScrollLines = pData->GetScrollLines();
    2330           0 :                 if( nScrollLines == COMMAND_WHEEL_PAGESCROLL )
    2331             :                 {
    2332           0 :                     nScrollDY = GetScrollBarPageSize( aVisSize.Width() );
    2333           0 :                     if( pData->GetDelta() < 0 )
    2334           0 :                         nScrollDY *= -1;
    2335             :                 }
    2336             :                 else
    2337             :                 {
    2338           0 :                     nScrollDY = pData->GetNotchDelta() * (long)nScrollLines;
    2339           0 :                     nScrollDY *= GetScrollBarLineSize();
    2340             :                 }
    2341             :             }
    2342             :         }
    2343           0 :         break;
    2344             : 
    2345             :         case COMMAND_AUTOSCROLL:
    2346             :         {
    2347           0 :             const CommandScrollData* pData = rCmd.GetAutoScrollData();
    2348           0 :             if( pData )
    2349             :             {
    2350           0 :                 nScrollDX = pData->GetDeltaX() * GetScrollBarLineSize();
    2351           0 :                 nScrollDY = pData->GetDeltaY() * GetScrollBarLineSize();
    2352             :             }
    2353             :         }
    2354           0 :         break;
    2355             :     }
    2356             : 
    2357           0 :     if( nScrollDX || nScrollDY )
    2358             :     {
    2359           0 :         aVisRect.Top() -= nScrollDY;
    2360           0 :         aVisRect.Bottom() -= nScrollDY;
    2361           0 :         aVisRect.Left() -= nScrollDX;
    2362           0 :         aVisRect.Right() -= nScrollDX;
    2363           0 :         MakeVisible( aVisRect );
    2364           0 :         return sal_True;
    2365             :     }
    2366           0 :     return sal_False;
    2367             : }
    2368             : 
    2369             : 
    2370           0 : void SvxIconChoiceCtrl_Impl::Command( const CommandEvent& rCEvt )
    2371             : {
    2372             :     // scroll mouse event?
    2373           0 :     if( (rCEvt.GetCommand() == COMMAND_WHEEL) ||
    2374           0 :         (rCEvt.GetCommand() == COMMAND_STARTAUTOSCROLL) ||
    2375           0 :         (rCEvt.GetCommand() == COMMAND_AUTOSCROLL) )
    2376             :     {
    2377           0 :         if( HandleScrollCommand( rCEvt ) )
    2378           0 :             return;
    2379             :     }
    2380             : }
    2381             : 
    2382           0 : void SvxIconChoiceCtrl_Impl::ToTop( SvxIconChoiceCtrlEntry* pEntry )
    2383             : {
    2384           0 :     if( !pZOrderList->empty()
    2385           0 :     &&  pEntry != pZOrderList->back()
    2386             :     ) {
    2387           0 :         for(
    2388           0 :             SvxIconChoiceCtrlEntryList_impl::iterator it = pZOrderList->begin();
    2389           0 :             it != pZOrderList->end();
    2390             :             ++it
    2391             :         ) {
    2392           0 :             if ( *it == pEntry )
    2393             :             {
    2394           0 :                 pZOrderList->erase( it );
    2395           0 :                 pZOrderList->push_back( pEntry );
    2396           0 :                 break;
    2397             :             }
    2398             :         }
    2399             :     }
    2400           0 : }
    2401             : 
    2402           0 : void SvxIconChoiceCtrl_Impl::ClipAtVirtOutRect( Rectangle& rRect ) const
    2403             : {
    2404           0 :     if( rRect.Bottom() >= aVirtOutputSize.Height() )
    2405           0 :         rRect.Bottom() = aVirtOutputSize.Height() - 1;
    2406           0 :     if( rRect.Right() >= aVirtOutputSize.Width() )
    2407           0 :         rRect.Right() = aVirtOutputSize.Width() - 1;
    2408           0 :     if( rRect.Top() < 0 )
    2409           0 :         rRect.Top() = 0;
    2410           0 :     if( rRect.Left() < 0 )
    2411           0 :         rRect.Left() = 0;
    2412           0 : }
    2413             : 
    2414             : // rRect: area of the document (in document coordinates) that we want to make
    2415             : // visible
    2416             : // bScrBar == sal_True: rectangle was calculated because of a scrollbar event
    2417             : 
    2418           0 : void SvxIconChoiceCtrl_Impl::MakeVisible( const Rectangle& rRect, sal_Bool bScrBar,
    2419             :     sal_Bool bCallRectChangedHdl )
    2420             : {
    2421           0 :     Rectangle aVirtRect( rRect );
    2422           0 :     ClipAtVirtOutRect( aVirtRect );
    2423           0 :     Point aOrigin( pView->GetMapMode().GetOrigin() );
    2424             :     // convert to document coordinate
    2425           0 :     aOrigin *= -1;
    2426           0 :     Rectangle aOutputArea( GetOutputRect() );
    2427           0 :     if( aOutputArea.IsInside( aVirtRect ) )
    2428           0 :         return; // is already visible
    2429             : 
    2430             :     long nDy;
    2431           0 :     if( aVirtRect.Top() < aOutputArea.Top() )
    2432             :     {
    2433             :         // scroll up (nDy < 0)
    2434           0 :         nDy = aVirtRect.Top() - aOutputArea.Top();
    2435             :     }
    2436           0 :     else if( aVirtRect.Bottom() > aOutputArea.Bottom() )
    2437             :     {
    2438             :         // scroll down (nDy > 0)
    2439           0 :         nDy = aVirtRect.Bottom() - aOutputArea.Bottom();
    2440             :     }
    2441             :     else
    2442           0 :         nDy = 0;
    2443             : 
    2444             :     long nDx;
    2445           0 :     if( aVirtRect.Left() < aOutputArea.Left() )
    2446             :     {
    2447             :         // scroll to the left (nDx < 0)
    2448           0 :         nDx = aVirtRect.Left() - aOutputArea.Left();
    2449             :     }
    2450           0 :     else if( aVirtRect.Right() > aOutputArea.Right() )
    2451             :     {
    2452             :         // scroll to the right (nDx > 0)
    2453           0 :         nDx = aVirtRect.Right() - aOutputArea.Right();
    2454             :     }
    2455             :     else
    2456           0 :         nDx = 0;
    2457             : 
    2458           0 :     aOrigin.X() += nDx;
    2459           0 :     aOrigin.Y() += nDy;
    2460           0 :     aOutputArea.SetPos( aOrigin );
    2461           0 :     if( GetUpdateMode() )
    2462             :     {
    2463           0 :         HideDDIcon();
    2464           0 :         pView->Update();
    2465           0 :         ShowCursor( sal_False );
    2466             :     }
    2467             : 
    2468             :     // invert origin for SV (so we can scroll/paint using document coordinates)
    2469           0 :     aOrigin *= -1;
    2470           0 :     SetOrigin( aOrigin );
    2471             : 
    2472           0 :     sal_Bool bScrollable = pView->GetBackground().IsScrollable();
    2473           0 :     if( pView->HasBackground() && !bScrollable )
    2474             :     {
    2475           0 :         Rectangle aRect( GetOutputRect());
    2476           0 :         Wallpaper aPaper( pView->GetBackground() );
    2477           0 :         aPaper.SetRect( aRect );
    2478           0 :         pView->SetBackground( aPaper );
    2479             :     }
    2480             : 
    2481           0 :     if( bScrollable && GetUpdateMode() )
    2482             :     {
    2483             :         // scroll in reverse direction!
    2484             :         pView->Control::Scroll( -nDx, -nDy, aOutputArea,
    2485           0 :             SCROLL_NOCHILDREN | SCROLL_USECLIPREGION | SCROLL_CLIP );
    2486             :     }
    2487             :     else
    2488           0 :         pView->Invalidate(INVALIDATE_NOCHILDREN);
    2489             : 
    2490           0 :     if( aHorSBar.IsVisible() || aVerSBar.IsVisible() )
    2491             :     {
    2492           0 :         if( !bScrBar )
    2493             :         {
    2494           0 :             aOrigin *= -1;
    2495             :             // correct thumbs
    2496           0 :             if(aHorSBar.IsVisible() && aHorSBar.GetThumbPos() != aOrigin.X())
    2497           0 :                 aHorSBar.SetThumbPos( aOrigin.X() );
    2498           0 :             if(aVerSBar.IsVisible() && aVerSBar.GetThumbPos() != aOrigin.Y())
    2499           0 :                 aVerSBar.SetThumbPos( aOrigin.Y() );
    2500             :         }
    2501             :     }
    2502             : 
    2503           0 :     if( GetUpdateMode() )
    2504           0 :         ShowCursor( sal_True );
    2505             : 
    2506             :     // check if we still need scrollbars
    2507           0 :     CheckScrollBars();
    2508           0 :     if( bScrollable && GetUpdateMode() )
    2509           0 :         pView->Update();
    2510             : 
    2511             :     // If the requested area can not be made completely visible, the
    2512             :     // Vis-Rect-Changed handler is called in any case. This case may occur e.g.
    2513             :     // if only few pixels of the lower border are invisible, but a scrollbar has
    2514             :     // a larger line size.
    2515           0 :     if( bCallRectChangedHdl || GetOutputRect() != rRect )
    2516           0 :         VisRectChanged();
    2517             : }
    2518             : 
    2519           0 : sal_uLong SvxIconChoiceCtrl_Impl::GetSelectionCount() const
    2520             : {
    2521           0 :     if( (nWinBits & WB_HIGHLIGHTFRAME) && pCurHighlightFrame )
    2522           0 :         return 1;
    2523           0 :     return nSelectionCount;
    2524             : }
    2525             : 
    2526           0 : void SvxIconChoiceCtrl_Impl::ToggleSelection( SvxIconChoiceCtrlEntry* pEntry )
    2527             : {
    2528             :     sal_Bool bSel;
    2529           0 :     if( pEntry->IsSelected() )
    2530           0 :         bSel = sal_False;
    2531             :     else
    2532           0 :         bSel = sal_True;
    2533           0 :     SelectEntry( pEntry, bSel, sal_True, sal_True );
    2534           0 : }
    2535             : 
    2536           0 : void SvxIconChoiceCtrl_Impl::DeselectAllBut( SvxIconChoiceCtrlEntry* pThisEntryNot,
    2537             :     sal_Bool bPaintSync )
    2538             : {
    2539           0 :     ClearSelectedRectList();
    2540             :     //
    2541             :     // TODO: work through z-order list, if necessary!
    2542             :     //
    2543           0 :     size_t nCount = aEntries.size();
    2544           0 :     for( size_t nCur = 0; nCur < nCount; nCur++ )
    2545             :     {
    2546           0 :         SvxIconChoiceCtrlEntry* pEntry = aEntries[ nCur ];
    2547           0 :         if( pEntry != pThisEntryNot && pEntry->IsSelected() )
    2548           0 :             SelectEntry( pEntry, sal_False, sal_True, sal_True, bPaintSync );
    2549             :     }
    2550           0 :     pAnchor = 0;
    2551           0 :     nFlags &= (~F_ADD_MODE);
    2552           0 : }
    2553             : 
    2554           0 : Size SvxIconChoiceCtrl_Impl::GetMinGrid() const
    2555             : {
    2556           0 :     Size aMinSize( aImageSize );
    2557           0 :     aMinSize.Width() += 2 * LROFFS_BOUND;
    2558           0 :     aMinSize.Height() += TBOFFS_BOUND;  // single offset is enough (FileDlg)
    2559           0 :     String aStrDummy( RTL_CONSTASCII_USTRINGPARAM( "XXX" ) );
    2560           0 :     Size aTextSize( pView->GetTextWidth( aStrDummy ), pView->GetTextHeight() );
    2561           0 :     if( nWinBits & WB_ICON )
    2562             :     {
    2563           0 :         aMinSize.Height() += VER_DIST_BMP_STRING;
    2564           0 :         aMinSize.Height() += aTextSize.Height();
    2565             :     }
    2566             :     else
    2567             :     {
    2568           0 :         aMinSize.Width() += HOR_DIST_BMP_STRING;
    2569           0 :         aMinSize.Width() += aTextSize.Width();
    2570             :     }
    2571           0 :     return aMinSize;
    2572             : }
    2573             : 
    2574           0 : void SvxIconChoiceCtrl_Impl::SetGrid( const Size& rSize )
    2575             : {
    2576           0 :     Size aSize( rSize );
    2577           0 :     Size aMinSize( GetMinGrid() );
    2578           0 :     if( aSize.Width() < aMinSize.Width() )
    2579           0 :         aSize.Width() = aMinSize.Width();
    2580           0 :     if( aSize.Height() < aMinSize.Height() )
    2581           0 :         aSize.Height() = aMinSize.Height();
    2582             : 
    2583           0 :     nGridDX = aSize.Width();
    2584             :     // HACK: Detail mode is not yet fully implemented, this workaround makes it
    2585             :     // fly with a single column
    2586           0 :     if( nWinBits & WB_DETAILS )
    2587             :     {
    2588           0 :         const SvxIconChoiceCtrlColumnInfo* pCol = GetColumn( 0 );
    2589           0 :         if( pCol )
    2590           0 :             ((SvxIconChoiceCtrlColumnInfo*)pCol)->SetWidth( nGridDX );
    2591             :     }
    2592           0 :     nGridDY = aSize.Height();
    2593           0 :     SetDefaultTextSize();
    2594           0 : }
    2595             : 
    2596             : // Calculates the maximum size that the text rectangle may use within its
    2597             : // bounding rectangle. In WB_ICON mode with IcnShowTextFull, Bottom is set to
    2598             : // LONG_MAX.
    2599             : 
    2600           0 : Rectangle SvxIconChoiceCtrl_Impl::CalcMaxTextRect( const SvxIconChoiceCtrlEntry* pEntry ) const
    2601             : {
    2602           0 :     Rectangle aBoundRect;
    2603             :     // avoid infinite recursion: don't calculate the bounding rectangle here
    2604           0 :     if( IsBoundingRectValid( pEntry->aRect ) )
    2605           0 :         aBoundRect = pEntry->aRect;
    2606             :     else
    2607           0 :         aBoundRect = pEntry->aGridRect;
    2608             : 
    2609             :     Rectangle aBmpRect( ((SvxIconChoiceCtrl_Impl*)this)->CalcBmpRect(
    2610           0 :         (SvxIconChoiceCtrlEntry*)pEntry ) );
    2611           0 :     if( nWinBits & WB_ICON )
    2612             :     {
    2613           0 :         aBoundRect.Top() = aBmpRect.Bottom();
    2614           0 :         aBoundRect.Top() += VER_DIST_BMP_STRING;
    2615           0 :         if( aBoundRect.Top() > aBoundRect.Bottom())
    2616           0 :             aBoundRect.Top() = aBoundRect.Bottom();
    2617           0 :         aBoundRect.Left() += LROFFS_BOUND;
    2618           0 :         aBoundRect.Left()++;
    2619           0 :         aBoundRect.Right() -= LROFFS_BOUND;
    2620           0 :         aBoundRect.Right()--;
    2621           0 :         if( aBoundRect.Left() > aBoundRect.Right())
    2622           0 :             aBoundRect.Left() = aBoundRect.Right();
    2623           0 :         if( GetEntryTextModeSmart( pEntry ) == IcnShowTextFull )
    2624           0 :             aBoundRect.Bottom() = LONG_MAX;
    2625             :     }
    2626             :     else
    2627             :     {
    2628           0 :         aBoundRect.Left() = aBmpRect.Right();
    2629           0 :         aBoundRect.Left() += HOR_DIST_BMP_STRING;
    2630           0 :         aBoundRect.Right() -= LROFFS_BOUND;
    2631           0 :         if( aBoundRect.Left() > aBoundRect.Right() )
    2632           0 :             aBoundRect.Left() = aBoundRect.Right();
    2633           0 :         long nHeight = aBoundRect.GetSize().Height();
    2634           0 :         nHeight = nHeight - aDefaultTextSize.Height();
    2635           0 :         nHeight /= 2;
    2636           0 :         aBoundRect.Top() += nHeight;
    2637           0 :         aBoundRect.Bottom() -= nHeight;
    2638             :     }
    2639           0 :     return aBoundRect;
    2640             : }
    2641             : 
    2642           0 : void SvxIconChoiceCtrl_Impl::SetDefaultTextSize()
    2643             : {
    2644           0 :     long nDY = nGridDY;
    2645           0 :     nDY -= aImageSize.Height();
    2646           0 :     nDY -= VER_DIST_BMP_STRING;
    2647           0 :     nDY -= 2*TBOFFS_BOUND;
    2648           0 :     if( nDY <= 0 )
    2649           0 :         nDY = 2;
    2650             : 
    2651           0 :     long nDX = nGridDX;
    2652           0 :     nDX -= 2*LROFFS_BOUND;
    2653           0 :     nDX -= 2;
    2654           0 :     if( nDX <= 0 )
    2655           0 :         nDX = 2;
    2656             : 
    2657           0 :     String aStrDummy( RTL_CONSTASCII_USTRINGPARAM( "X" ) );
    2658           0 :     long nHeight = pView->GetTextHeight();
    2659           0 :     if( nDY < nHeight )
    2660           0 :         nDY = nHeight;
    2661           0 :     aDefaultTextSize = Size( nDX, nDY );
    2662           0 : }
    2663             : 
    2664             : 
    2665           0 : void SvxIconChoiceCtrl_Impl::Center( SvxIconChoiceCtrlEntry* pEntry ) const
    2666             : {
    2667           0 :     pEntry->aRect = pEntry->aGridRect;
    2668           0 :     Size aSize( CalcBoundingSize( pEntry ) );
    2669           0 :     if( nWinBits & WB_ICON )
    2670             :     {
    2671             :         // center horizontally
    2672           0 :         long nBorder = pEntry->aGridRect.GetWidth() - aSize.Width();
    2673           0 :         pEntry->aRect.Left() += nBorder / 2;
    2674           0 :         pEntry->aRect.Right() -= nBorder / 2;
    2675             :     }
    2676             :     // center vertically
    2677           0 :     pEntry->aRect.Bottom() = pEntry->aRect.Top() + aSize.Height();
    2678           0 : }
    2679             : 
    2680             : 
    2681             : // The deltas are the offsets by which the view is moved on the document.
    2682             : // left, up: offsets < 0
    2683             : // right, down: offsets > 0
    2684           0 : void SvxIconChoiceCtrl_Impl::Scroll( long nDeltaX, long nDeltaY, sal_Bool bScrollBar )
    2685             : {
    2686           0 :     const MapMode& rMapMode = pView->GetMapMode();
    2687           0 :     Point aOrigin( rMapMode.GetOrigin() );
    2688             :     // convert to document coordinate
    2689           0 :     aOrigin *= -1;
    2690           0 :     aOrigin.Y() += nDeltaY;
    2691           0 :     aOrigin.X() += nDeltaX;
    2692           0 :     Rectangle aRect( aOrigin, aOutputSize );
    2693           0 :     MakeVisible( aRect, bScrollBar );
    2694           0 : }
    2695             : 
    2696             : 
    2697           0 : const Size& SvxIconChoiceCtrl_Impl::GetItemSize( SvxIconChoiceCtrlEntry*,
    2698             :     IcnViewFieldType eItem ) const
    2699             : {
    2700           0 :     if( eItem == IcnViewFieldTypeText )
    2701           0 :         return aDefaultTextSize;
    2702           0 :     return aImageSize;
    2703             : }
    2704             : 
    2705           0 : Rectangle SvxIconChoiceCtrl_Impl::CalcFocusRect( SvxIconChoiceCtrlEntry* pEntry )
    2706             : {
    2707           0 :     Rectangle aBmpRect( CalcBmpRect( pEntry ) );
    2708           0 :     Rectangle aTextRect( CalcTextRect( pEntry ) );
    2709           0 :     Rectangle aBoundRect( GetEntryBoundRect( pEntry ) );
    2710           0 :     Rectangle aFocusRect( aBoundRect.Left(), aBmpRect.Top() - 1,
    2711           0 :                           aBoundRect.Right() - 4, aTextRect.Bottom() + 1 );
    2712             :     // the focus rectangle should not touch the text
    2713           0 :     if( aFocusRect.Left() - 1 >= pEntry->aRect.Left() )
    2714           0 :         aFocusRect.Left()--;
    2715           0 :     if( aFocusRect.Right() + 1 <= pEntry->aRect.Right() )
    2716           0 :         aFocusRect.Right()++;
    2717             : 
    2718           0 :     return aFocusRect;
    2719             : }
    2720             : 
    2721             : // the hot spot is the inner 50 % of the rectangle
    2722           0 : static Rectangle GetHotSpot( const Rectangle& rRect )
    2723             : {
    2724           0 :     Rectangle aResult( rRect );
    2725           0 :     aResult.Justify();
    2726           0 :     Size aSize( rRect.GetSize() );
    2727           0 :     long nDelta = aSize.Width() / 4;
    2728           0 :     aResult.Left() += nDelta;
    2729           0 :     aResult.Right() -= nDelta;
    2730           0 :     nDelta = aSize.Height() / 4;
    2731           0 :     aResult.Top() += nDelta;
    2732           0 :     aResult.Bottom() -= nDelta;
    2733           0 :     return aResult;
    2734             : }
    2735             : 
    2736           0 : void SvxIconChoiceCtrl_Impl::SelectRect( SvxIconChoiceCtrlEntry* pEntry1, SvxIconChoiceCtrlEntry* pEntry2,
    2737             :     sal_Bool bAdd, std::vector<Rectangle*>* pOtherRects )
    2738             : {
    2739             :     DBG_ASSERT(pEntry1 && pEntry2,"SelectEntry: Invalid Entry-Ptr");
    2740           0 :     Rectangle aRect( GetEntryBoundRect( pEntry1 ) );
    2741           0 :     aRect.Union( GetEntryBoundRect( pEntry2 ) );
    2742           0 :     SelectRect( aRect, bAdd, pOtherRects );
    2743           0 : }
    2744             : 
    2745           0 : void SvxIconChoiceCtrl_Impl::SelectRect( const Rectangle& rRect, bool bAdd,
    2746             :     std::vector<Rectangle*>* pOtherRects )
    2747             : {
    2748           0 :     aCurSelectionRect = rRect;
    2749           0 :     if( !pZOrderList || !pZOrderList->size() )
    2750           0 :         return;
    2751             : 
    2752             :     // set flag, so ToTop won't be called in Select
    2753           0 :     sal_Bool bAlreadySelectingRect = nFlags & F_SELECTING_RECT ? sal_True : sal_False;
    2754           0 :     nFlags |= F_SELECTING_RECT;
    2755             : 
    2756           0 :     CheckBoundingRects();
    2757           0 :     pView->Update();
    2758           0 :     const size_t nCount = pZOrderList->size();
    2759             : 
    2760           0 :     Rectangle aRect( rRect );
    2761           0 :     aRect.Justify();
    2762           0 :     bool bCalcOverlap = (bAdd && pOtherRects && !pOtherRects->empty()) ? true : false;
    2763             : 
    2764           0 :     sal_Bool bResetClipRegion = sal_False;
    2765           0 :     if( !pView->IsClipRegion() )
    2766             :     {
    2767           0 :         bResetClipRegion = sal_True;
    2768           0 :         pView->SetClipRegion( GetOutputRect() );
    2769             :     }
    2770             : 
    2771           0 :     for( size_t nPos = 0; nPos < nCount; nPos++ )
    2772             :     {
    2773           0 :         SvxIconChoiceCtrlEntry* pEntry = (*pZOrderList)[ nPos ];
    2774             : 
    2775           0 :         if( !IsBoundingRectValid( pEntry->aRect ))
    2776           0 :             FindBoundingRect( pEntry );
    2777           0 :         Rectangle aBoundRect( GetHotSpot( pEntry->aRect ) );
    2778           0 :         sal_Bool bSelected = pEntry->IsSelected();
    2779             : 
    2780             :         sal_Bool bOverlaps;
    2781           0 :         if( bCalcOverlap )
    2782           0 :             bOverlaps = IsOver( pOtherRects, aBoundRect );
    2783             :         else
    2784           0 :             bOverlaps = sal_False;
    2785           0 :         sal_Bool bOver = aRect.IsOver( aBoundRect );
    2786             : 
    2787           0 :         if( bOver && !bOverlaps )
    2788             :         {
    2789             :             // is inside the new selection rectangle and outside of any old one
    2790             :             // => select
    2791           0 :             if( !bSelected )
    2792           0 :                 SelectEntry( pEntry, sal_True, sal_True, sal_True );
    2793             :         }
    2794           0 :         else if( !bAdd )
    2795             :         {
    2796             :             // is outside of the selection rectangle
    2797             :             // => deselect
    2798           0 :             if( bSelected )
    2799           0 :                 SelectEntry( pEntry, sal_False, sal_True, sal_True );
    2800             :         }
    2801           0 :         else if( bAdd && bOverlaps )
    2802             :         {
    2803             :             // The entry is inside an old (=>span multiple rectangles with Ctrl)
    2804             :             // selection rectangle.
    2805             : 
    2806             :             // There is still a bug here! The selection status of an entry in a
    2807             :             // previous rectangle has to be restored, if it was touched by the
    2808             :             // current selection rectangle but is not inside it any more.
    2809             :             // For simplicity's sake, let's assume that all entries in the old
    2810             :             // rectangles were correctly selected. It is wrong to just deselect
    2811             :             // the intersection.
    2812             :             // Possible solution: remember a snapshot of the selection before
    2813             :             // spanning the rectangle.
    2814           0 :             if( aBoundRect.IsOver( rRect))
    2815             :             {
    2816             :                 // deselect intersection between old rectangles and current rectangle
    2817           0 :                 if( bSelected )
    2818           0 :                     SelectEntry( pEntry, sal_False, sal_True, sal_True );
    2819             :             }
    2820             :             else
    2821             :             {
    2822             :                 // select entry of an old rectangle
    2823           0 :                 if( !bSelected )
    2824           0 :                     SelectEntry( pEntry, sal_True, sal_True, sal_True );
    2825             :             }
    2826             :         }
    2827           0 :         else if( !bOver && bSelected )
    2828             :         {
    2829             :             // this entry is completely outside the rectangle => deselect it
    2830           0 :             SelectEntry( pEntry, sal_False, sal_True, sal_True );
    2831             :         }
    2832             :     }
    2833             : 
    2834           0 :     if( !bAlreadySelectingRect )
    2835           0 :         nFlags &= ~F_SELECTING_RECT;
    2836             : 
    2837           0 :     pView->Update();
    2838           0 :     if( bResetClipRegion )
    2839           0 :         pView->SetClipRegion();
    2840             : }
    2841             : 
    2842           0 : void SvxIconChoiceCtrl_Impl::SelectRange(
    2843             :                         SvxIconChoiceCtrlEntry* pStart,
    2844             :                         SvxIconChoiceCtrlEntry* pEnd,
    2845             :                         sal_Bool bAdd )
    2846             : {
    2847           0 :     sal_uLong nFront = GetEntryListPos( pStart );
    2848           0 :     sal_uLong nBack  = GetEntryListPos( pEnd );
    2849           0 :     sal_uLong nFirst = std::min( nFront, nBack );
    2850           0 :     sal_uLong nLast  = std::max( nFront, nBack );
    2851             :     sal_uLong i;
    2852             :     SvxIconChoiceCtrlEntry* pEntry;
    2853             : 
    2854           0 :     if ( ! bAdd )
    2855             :     {
    2856             :         // deselect everything before the first entry if not in
    2857             :         // adding mode
    2858           0 :         for ( i=0; i<nFirst; i++ )
    2859             :         {
    2860           0 :             pEntry = GetEntry( i );
    2861           0 :             if( pEntry->IsSelected() )
    2862           0 :                 SelectEntry( pEntry, sal_False, sal_True, sal_True, sal_True );
    2863             :         }
    2864             :     }
    2865             : 
    2866             :     // select everything between nFirst and nLast
    2867           0 :     for ( i=nFirst; i<=nLast; i++ )
    2868             :     {
    2869           0 :         pEntry = GetEntry( i );
    2870           0 :         if( ! pEntry->IsSelected() )
    2871           0 :             SelectEntry( pEntry, sal_True, sal_True,  sal_True, sal_True );
    2872             :     }
    2873             : 
    2874           0 :     if ( ! bAdd )
    2875             :     {
    2876             :         // deselect everything behind the last entry if not in
    2877             :         // adding mode
    2878           0 :         sal_uLong nEnd = GetEntryCount();
    2879           0 :         for ( ; i<nEnd; i++ )
    2880             :         {
    2881           0 :             pEntry = GetEntry( i );
    2882           0 :             if( pEntry->IsSelected() )
    2883           0 :                 SelectEntry( pEntry, sal_False, sal_True, sal_True, sal_True );
    2884             :         }
    2885             :     }
    2886           0 : }
    2887             : 
    2888           0 : bool SvxIconChoiceCtrl_Impl::IsOver( std::vector<Rectangle*>* pRectList, const Rectangle& rBoundRect ) const
    2889             : {
    2890           0 :     const sal_uInt16 nCount = pRectList->size();
    2891           0 :     for( sal_uInt16 nCur = 0; nCur < nCount; nCur++ )
    2892             :     {
    2893           0 :         Rectangle* pRect = (*pRectList)[ nCur ];
    2894           0 :         if( rBoundRect.IsOver( *pRect ))
    2895           0 :             return true;
    2896             :     }
    2897           0 :     return false;
    2898             : }
    2899             : 
    2900           0 : void SvxIconChoiceCtrl_Impl::AddSelectedRect( SvxIconChoiceCtrlEntry* pEntry1,
    2901             :     SvxIconChoiceCtrlEntry* pEntry2 )
    2902             : {
    2903             :     DBG_ASSERT(pEntry1 && pEntry2,"SelectEntry: Invalid Entry-Ptr");
    2904           0 :     Rectangle aRect( GetEntryBoundRect( pEntry1 ) );
    2905           0 :     aRect.Union( GetEntryBoundRect( pEntry2 ) );
    2906           0 :     AddSelectedRect( aRect );
    2907           0 : }
    2908             : 
    2909           0 : void SvxIconChoiceCtrl_Impl::AddSelectedRect( const Rectangle& rRect )
    2910             : {
    2911           0 :     Rectangle* pRect = new Rectangle( rRect );
    2912           0 :     pRect->Justify();
    2913           0 :     aSelectedRectList.push_back( pRect );
    2914           0 : }
    2915             : 
    2916           0 : void SvxIconChoiceCtrl_Impl::ClearSelectedRectList()
    2917             : {
    2918           0 :     const sal_uInt16 nCount = aSelectedRectList.size();
    2919           0 :     for( sal_uInt16 nCur = 0; nCur < nCount; nCur++ )
    2920             :     {
    2921           0 :         Rectangle* pRect = aSelectedRectList[ nCur ];
    2922           0 :         delete pRect;
    2923             :     }
    2924           0 :     aSelectedRectList.clear();
    2925           0 : }
    2926             : 
    2927           0 : IMPL_LINK_NOARG(SvxIconChoiceCtrl_Impl, AutoArrangeHdl)
    2928             : {
    2929           0 :     aAutoArrangeTimer.Stop();
    2930           0 :     Arrange( IsAutoArrange() );
    2931           0 :     return 0;
    2932             : }
    2933             : 
    2934           0 : IMPL_LINK_NOARG(SvxIconChoiceCtrl_Impl, VisRectChangedHdl)
    2935             : {
    2936           0 :     aVisRectChangedTimer.Stop();
    2937           0 :     pView->VisibleRectChanged();
    2938           0 :     return 0;
    2939             : }
    2940             : 
    2941           0 : IMPL_LINK_NOARG(SvxIconChoiceCtrl_Impl, DocRectChangedHdl)
    2942             : {
    2943           0 :     aDocRectChangedTimer.Stop();
    2944           0 :     pView->DocumentRectChanged();
    2945           0 :     return 0;
    2946             : }
    2947             : 
    2948           0 : sal_Bool SvxIconChoiceCtrl_Impl::IsTextHit( SvxIconChoiceCtrlEntry* pEntry, const Point& rDocPos )
    2949             : {
    2950           0 :     Rectangle aRect( CalcTextRect( pEntry ));
    2951           0 :     if( aRect.IsInside( rDocPos ) )
    2952           0 :         return sal_True;
    2953           0 :     return sal_False;
    2954             : }
    2955             : 
    2956           0 : IMPL_LINK_NOARG(SvxIconChoiceCtrl_Impl, EditTimeoutHdl)
    2957             : {
    2958           0 :     SvxIconChoiceCtrlEntry* pEntry = GetCurEntry();
    2959           0 :     if( bEntryEditingEnabled && pEntry &&
    2960           0 :         pEntry->IsSelected())
    2961             :     {
    2962           0 :         if( pView->EditingEntry( pEntry ))
    2963           0 :             EditEntry( pEntry );
    2964             :     }
    2965           0 :     return 0;
    2966             : }
    2967             : 
    2968             : 
    2969             : //
    2970             : // Function to align entries to the grid
    2971             : //
    2972             : 
    2973             : // pStart == 0: align all entries
    2974             : // else: align all entries of the row from pStart on (including pStart)
    2975           0 : void SvxIconChoiceCtrl_Impl::AdjustEntryAtGrid( SvxIconChoiceCtrlEntry* pStart )
    2976             : {
    2977           0 :     IconChoiceMap aLists;
    2978           0 :     pImpCursor->CreateGridAjustData( aLists, pStart );
    2979           0 :     for (IconChoiceMap::const_iterator iter = aLists.begin();
    2980           0 :             iter != aLists.end(); ++iter)
    2981             :     {
    2982           0 :         AdjustAtGrid(iter->second, pStart);
    2983             :     }
    2984           0 :     IcnCursor_Impl::DestroyGridAdjustData( aLists );
    2985           0 :     CheckScrollBars();
    2986           0 : }
    2987             : 
    2988             : // align a row, might expand width, doesn't break the line
    2989           0 : void SvxIconChoiceCtrl_Impl::AdjustAtGrid( const SvxIconChoiceCtrlEntryPtrVec& rRow, SvxIconChoiceCtrlEntry* pStart )
    2990             : {
    2991           0 :     if( rRow.empty() )
    2992           0 :         return;
    2993             : 
    2994             :     sal_Bool bGo;
    2995           0 :     if( !pStart )
    2996           0 :         bGo = sal_True;
    2997             :     else
    2998           0 :         bGo = sal_False;
    2999             : 
    3000           0 :     long nCurRight = 0;
    3001           0 :     for( sal_uInt16 nCur = 0; nCur < rRow.size(); nCur++ )
    3002             :     {
    3003           0 :         SvxIconChoiceCtrlEntry* pCur = rRow[ nCur ];
    3004           0 :         if( !bGo && pCur == pStart )
    3005           0 :             bGo = sal_True;
    3006             : 
    3007             :         // SvIcnVwDataEntry* pViewData = ICNVIEWDATA(pCur);
    3008             :         // Decisive (for our eye) is the bitmap, else, the entry might jump too
    3009             :         // much within long texts.
    3010           0 :         const Rectangle& rBoundRect = GetEntryBoundRect( pCur );
    3011           0 :         Rectangle aCenterRect( CalcBmpRect( pCur, 0 ));
    3012           0 :         if( bGo && !pCur->IsPosLocked() )
    3013             :         {
    3014           0 :             long nWidth = aCenterRect.GetSize().Width();
    3015           0 :             Point aNewPos( AdjustAtGrid( aCenterRect, rBoundRect ) );
    3016           0 :             while( aNewPos.X() < nCurRight )
    3017           0 :                 aNewPos.X() += nGridDX;
    3018           0 :             if( aNewPos != rBoundRect.TopLeft() )
    3019             :             {
    3020           0 :                 SetEntryPos( pCur, aNewPos );
    3021           0 :                 pCur->SetFlags( ICNVIEW_FLAG_POS_MOVED );
    3022           0 :                 nFlags |= F_MOVED_ENTRIES;
    3023             :             }
    3024           0 :             nCurRight = aNewPos.X() + nWidth;
    3025             :         }
    3026             :         else
    3027             :         {
    3028           0 :             nCurRight = rBoundRect.Right();
    3029             :         }
    3030             :     }
    3031             : }
    3032             : 
    3033             : // Aligns a rectangle to the grid, but doesn't guarantee that the new position
    3034             : // is vacant. The position can be used for SetEntryPos. The CenterRect describes
    3035             : // a part of the bounding rectangle that is used for calculating the target
    3036             : // rectangle.
    3037           0 : Point SvxIconChoiceCtrl_Impl::AdjustAtGrid( const Rectangle& rCenterRect,
    3038             :     const Rectangle& rBoundRect ) const
    3039             : {
    3040           0 :     Point aPos( rCenterRect.TopLeft() );
    3041           0 :     Size aSize( rCenterRect.GetSize() );
    3042             : 
    3043           0 :     aPos.X() -= LROFFS_WINBORDER;
    3044           0 :     aPos.Y() -= TBOFFS_WINBORDER;
    3045             : 
    3046             :     // align (the center of the rectangle is the reference)
    3047           0 :     short nGridX = (short)((aPos.X()+(aSize.Width()/2)) / nGridDX);
    3048           0 :     short nGridY = (short)((aPos.Y()+(aSize.Height()/2)) / nGridDY);
    3049           0 :     aPos.X() = nGridX * nGridDX;
    3050           0 :     aPos.Y() = nGridY * nGridDY;
    3051             :     // horizontal center
    3052           0 :     aPos.X() += (nGridDX - rBoundRect.GetSize().Width() ) / 2;
    3053             : 
    3054           0 :     aPos.X() += LROFFS_WINBORDER;
    3055           0 :     aPos.Y() += TBOFFS_WINBORDER;
    3056             : 
    3057           0 :     return aPos;
    3058             : }
    3059             : 
    3060           0 : void SvxIconChoiceCtrl_Impl::SetEntryTextMode( SvxIconChoiceCtrlTextMode eMode, SvxIconChoiceCtrlEntry* pEntry )
    3061             : {
    3062           0 :     if( !pEntry )
    3063             :     {
    3064           0 :         if( eTextMode != eMode )
    3065             :         {
    3066           0 :             if( eTextMode == IcnShowTextDontKnow )
    3067           0 :                 eTextMode = IcnShowTextShort;
    3068           0 :             eTextMode = eMode;
    3069           0 :             Arrange( sal_True );
    3070             :         }
    3071             :     }
    3072             :     else
    3073             :     {
    3074           0 :         if( pEntry->eTextMode != eMode )
    3075             :         {
    3076           0 :             pEntry->eTextMode = eMode;
    3077           0 :             InvalidateEntry( pEntry );
    3078           0 :             pView->Invalidate( GetEntryBoundRect( pEntry ) );
    3079           0 :             AdjustVirtSize( pEntry->aRect );
    3080             :         }
    3081             :     }
    3082           0 : }
    3083             : 
    3084           0 : SvxIconChoiceCtrlTextMode SvxIconChoiceCtrl_Impl::GetEntryTextModeSmart( const SvxIconChoiceCtrlEntry* pEntry ) const
    3085             : {
    3086             :     DBG_ASSERT(pEntry,"GetEntryTextModeSmart: Entry not set");
    3087           0 :     SvxIconChoiceCtrlTextMode eMode = pEntry->GetTextMode();
    3088           0 :     if( eMode == IcnShowTextDontKnow )
    3089           0 :         return eTextMode;
    3090           0 :     return eMode;
    3091             : }
    3092             : 
    3093             : ////////////////////////////////////////////////////////////////////////////////////////////////
    3094             : //
    3095             : // Draw my own focusrect, because the focusrect of the outputdevice has got the inverted color
    3096             : // of the background. But what will we see, if the the backgroundcolor is gray ? - We will see
    3097             : // a gray focusrect on a gray background !!!
    3098             : //
    3099           0 : void SvxIconChoiceCtrl_Impl::ShowFocus ( Rectangle& rRect )
    3100             : {
    3101           0 :     Color aBkgColor ( pView->GetBackground().GetColor() );
    3102           0 :     Color aPenColor;
    3103           0 :     sal_uInt16 nColor = ( aBkgColor.GetRed() + aBkgColor.GetGreen() + aBkgColor.GetBlue() ) / 3;
    3104           0 :     if ( nColor > 128 )
    3105           0 :         aPenColor.SetColor ( COL_BLACK );
    3106             :     else
    3107           0 :         aPenColor.SetColor( COL_WHITE );
    3108             : 
    3109           0 :     aFocus.bOn = sal_True;
    3110           0 :     aFocus.aPenColor = aPenColor;
    3111           0 :     aFocus.aRect = rRect;
    3112           0 : }
    3113             : 
    3114           0 : void SvxIconChoiceCtrl_Impl::DrawFocusRect ( OutputDevice* pOut )
    3115             : {
    3116           0 :     pOut->SetLineColor( aFocus.aPenColor );
    3117           0 :     pOut->SetFillColor();
    3118           0 :     Polygon aPolygon ( aFocus.aRect );
    3119             : 
    3120           0 :     LineInfo aLineInfo ( LINE_DASH );
    3121             : 
    3122           0 :     aLineInfo.SetDashLen ( 1 );
    3123             : 
    3124           0 :     aLineInfo.SetDotLen ( 1L );
    3125           0 :     aLineInfo.SetDistance ( 1L );
    3126           0 :     aLineInfo.SetDotCount ( 1 );
    3127             : 
    3128           0 :     pOut->DrawPolyLine ( aPolygon, aLineInfo );
    3129           0 : }
    3130             : 
    3131           0 : sal_Bool SvxIconChoiceCtrl_Impl::IsMnemonicChar( sal_Unicode cChar, sal_uLong& rPos ) const
    3132             : {
    3133           0 :     sal_Bool bRet = sal_False;
    3134           0 :     const vcl::I18nHelper& rI18nHelper = Application::GetSettings().GetUILocaleI18nHelper();
    3135           0 :     size_t nEntryCount = GetEntryCount();
    3136           0 :     for ( size_t i = 0; i < nEntryCount; ++i )
    3137             :     {
    3138           0 :         if ( rI18nHelper.MatchMnemonic( GetEntry( i )->GetText(), cChar ) )
    3139             :         {
    3140           0 :             bRet = sal_True;
    3141           0 :             rPos = i;
    3142           0 :             break;
    3143             :         }
    3144             :     }
    3145             : 
    3146           0 :     return bRet;
    3147             : }
    3148             : 
    3149             : //
    3150             : ////////////////////////////////////////////////////////////////////////////////////////////////
    3151             : 
    3152           0 : IMPL_LINK(SvxIconChoiceCtrl_Impl, UserEventHdl, void*, nId )
    3153             : {
    3154           0 :     if( nId == EVENTID_ADJUST_SCROLLBARS )
    3155             :     {
    3156           0 :         nUserEventAdjustScrBars = 0;
    3157           0 :         AdjustScrollBars();
    3158             :     }
    3159           0 :     else if( nId == EVENTID_SHOW_CURSOR )
    3160             :     {
    3161           0 :         nUserEventShowCursor = 0;
    3162           0 :         ShowCursor( sal_True );
    3163             :     }
    3164           0 :     return 0;
    3165             : }
    3166             : 
    3167           0 : void SvxIconChoiceCtrl_Impl::CancelUserEvents()
    3168             : {
    3169           0 :     if( nUserEventAdjustScrBars )
    3170             :     {
    3171           0 :         Application::RemoveUserEvent( nUserEventAdjustScrBars );
    3172           0 :         nUserEventAdjustScrBars = 0;
    3173             :     }
    3174           0 :     if( nUserEventShowCursor )
    3175             :     {
    3176           0 :         Application::RemoveUserEvent( nUserEventShowCursor );
    3177           0 :         nUserEventShowCursor = 0;
    3178             :     }
    3179           0 : }
    3180             : 
    3181           0 : void SvxIconChoiceCtrl_Impl::InvalidateEntry( SvxIconChoiceCtrlEntry* pEntry )
    3182             : {
    3183           0 :     if( pEntry == pCursor )
    3184           0 :         ShowCursor( sal_False );
    3185           0 :     pView->Invalidate( pEntry->aRect );
    3186           0 :     Center( pEntry );
    3187           0 :     pView->Invalidate( pEntry->aRect );
    3188           0 :     if( pEntry == pCursor )
    3189           0 :         ShowCursor( sal_True );
    3190           0 : }
    3191             : 
    3192           0 : void SvxIconChoiceCtrl_Impl::EditEntry( SvxIconChoiceCtrlEntry* pEntry )
    3193             : {
    3194             :     DBG_ASSERT(pEntry,"EditEntry: Entry not set");
    3195           0 :     if( !pEntry )
    3196           0 :         return;
    3197             : 
    3198           0 :     StopEntryEditing( sal_True );
    3199           0 :     DELETEZ(pEdit);
    3200           0 :     SetNoSelection();
    3201             : 
    3202           0 :     pCurEditedEntry = pEntry;
    3203           0 :     String aEntryText( pView->GetEntryText( pEntry, sal_True ) );
    3204           0 :     Rectangle aRect( CalcTextRect( pEntry, 0, sal_True, &aEntryText ) );
    3205           0 :     MakeVisible( aRect );
    3206           0 :     Point aPos( aRect.TopLeft() );
    3207           0 :     aPos = pView->GetPixelPos( aPos );
    3208           0 :     aRect.SetPos( aPos );
    3209           0 :     pView->HideFocus();
    3210             :     pEdit = new IcnViewEdit_Impl(
    3211             :         pView,
    3212             :         aRect.TopLeft(),
    3213             :         aRect.GetSize(),
    3214             :         aEntryText,
    3215           0 :         LINK( this, SvxIconChoiceCtrl_Impl, TextEditEndedHdl ) );
    3216             : }
    3217             : 
    3218           0 : IMPL_LINK_NOARG(SvxIconChoiceCtrl_Impl, TextEditEndedHdl)
    3219             : {
    3220             :     DBG_ASSERT(pEdit,"TextEditEnded: pEdit not set");
    3221           0 :     if( !pEdit )
    3222             :     {
    3223           0 :         pCurEditedEntry = 0;
    3224           0 :         return 0;
    3225             :     }
    3226             :     DBG_ASSERT(pCurEditedEntry,"TextEditEnded: pCurEditedEntry not set");
    3227             : 
    3228           0 :     if( !pCurEditedEntry )
    3229             :     {
    3230           0 :         pEdit->Hide();
    3231           0 :         if( pEdit->IsGrabFocus() )
    3232           0 :             pView->GrabFocus();
    3233           0 :         return 0;
    3234             :     }
    3235             : 
    3236           0 :     String aText;
    3237           0 :     if ( !pEdit->EditingCanceled() )
    3238           0 :         aText = pEdit->GetText();
    3239             :     else
    3240           0 :         aText = pEdit->GetSavedValue();
    3241             : 
    3242           0 :     if( pView->EditedEntry( pCurEditedEntry, aText, pEdit->EditingCanceled() ) )
    3243           0 :         InvalidateEntry( pCurEditedEntry );
    3244           0 :     if( !GetSelectionCount() )
    3245           0 :         SelectEntry( pCurEditedEntry, sal_True );
    3246             : 
    3247           0 :     pEdit->Hide();
    3248           0 :     if( pEdit->IsGrabFocus() )
    3249           0 :         pView->GrabFocus();
    3250             :     // The edit can not be deleted here, because it is not within a handler. It
    3251             :     // will be deleted in the dtor or in the next EditEntry.
    3252           0 :     pCurEditedEntry = 0;
    3253           0 :     return 0;
    3254             : }
    3255             : 
    3256           0 : void SvxIconChoiceCtrl_Impl::StopEntryEditing( sal_Bool bCancel )
    3257             : {
    3258           0 :     if( pEdit )
    3259           0 :         pEdit->StopEditing( bCancel );
    3260           0 : }
    3261             : 
    3262           0 : SvxIconChoiceCtrlEntry* SvxIconChoiceCtrl_Impl::GetFirstSelectedEntry( sal_uLong& rPos ) const
    3263             : {
    3264           0 :     if( !GetSelectionCount() )
    3265           0 :         return 0;
    3266             : 
    3267           0 :     if( (nWinBits & WB_HIGHLIGHTFRAME) && (eSelectionMode == NO_SELECTION) )
    3268             :     {
    3269           0 :         rPos = pView->GetEntryListPos( pCurHighlightFrame );
    3270           0 :         return pCurHighlightFrame;
    3271             :     }
    3272             : 
    3273           0 :     size_t nCount = aEntries.size();
    3274           0 :     if( !pHead )
    3275             :     {
    3276           0 :         for( size_t nCur = 0; nCur < nCount; nCur++ )
    3277             :         {
    3278           0 :             SvxIconChoiceCtrlEntry* pEntry = aEntries[ nCur ];
    3279           0 :             if( pEntry->IsSelected() )
    3280             :             {
    3281           0 :                 rPos = nCur;
    3282           0 :                 return pEntry;
    3283             :             }
    3284             :         }
    3285             :     }
    3286             :     else
    3287             :     {
    3288           0 :         SvxIconChoiceCtrlEntry* pEntry = pHead;
    3289           0 :         while( nCount-- )
    3290             :         {
    3291           0 :             if( pEntry->IsSelected() )
    3292             :             {
    3293           0 :                 rPos = GetEntryListPos( pEntry );
    3294           0 :                 return pEntry;
    3295             :             }
    3296           0 :             pEntry = pEntry->pflink;
    3297           0 :             if( nCount && pEntry == pHead )
    3298             :             {
    3299             :                 OSL_FAIL("SvxIconChoiceCtrl_Impl::GetFirstSelectedEntry > infinite loop!");
    3300           0 :                 return 0;
    3301             :             }
    3302             :         }
    3303             :     }
    3304           0 :     return 0;
    3305             : }
    3306             : 
    3307           0 : void SvxIconChoiceCtrl_Impl::SelectAll( sal_Bool bSelect, sal_Bool bPaint )
    3308             : {
    3309           0 :     bPaint = sal_True;
    3310             : 
    3311           0 :     size_t nCount = aEntries.size();
    3312           0 :     for( size_t nCur = 0; nCur < nCount && (bSelect || GetSelectionCount() ); nCur++ )
    3313             :     {
    3314           0 :         SvxIconChoiceCtrlEntry* pEntry = aEntries[ nCur ];
    3315           0 :         SelectEntry( pEntry, bSelect, sal_True, sal_True, bPaint );
    3316             :     }
    3317           0 :     nFlags &= (~F_ADD_MODE);
    3318           0 :     pAnchor = 0;
    3319           0 : }
    3320             : 
    3321           0 : IcnViewEdit_Impl::IcnViewEdit_Impl( SvtIconChoiceCtrl* pParent, const Point& rPos,
    3322             :     const Size& rSize, const XubString& rData, const Link& rNotifyEditEnd ) :
    3323           0 :     MultiLineEdit( pParent, (pParent->GetStyle() & WB_ICON) ? WB_CENTER : WB_LEFT),
    3324             :     aCallBackHdl( rNotifyEditEnd ),
    3325             :     bCanceled( sal_False ),
    3326             :     bAlreadyInCallback( sal_False ),
    3327           0 :     bGrabFocus( sal_False )
    3328             : {
    3329           0 :     Font aFont( pParent->GetPointFont() );
    3330           0 :     aFont.SetTransparent( sal_False );
    3331           0 :     SetControlFont( aFont );
    3332           0 :     if( !pParent->HasFontFillColor() )
    3333             :     {
    3334           0 :         Color aColor( pParent->GetBackground().GetColor() );
    3335           0 :         SetControlBackground( aColor );
    3336             :     }
    3337             :     else
    3338           0 :         SetControlBackground( aFont.GetFillColor() );
    3339           0 :     SetControlForeground( aFont.GetColor() );
    3340           0 :     SetPosPixel( rPos );
    3341           0 :     SetSizePixel( CalcAdjustedSize(rSize) );
    3342           0 :     SetText( rData );
    3343           0 :     SaveValue();
    3344             : 
    3345           0 :     aAccReturn.InsertItem( IMPICNVIEW_ACC_RETURN, KeyCode(KEY_RETURN) );
    3346           0 :     aAccEscape.InsertItem( IMPICNVIEW_ACC_ESCAPE, KeyCode(KEY_ESCAPE) );
    3347             : 
    3348           0 :     aAccReturn.SetActivateHdl( LINK( this, IcnViewEdit_Impl, ReturnHdl_Impl) );
    3349           0 :     aAccEscape.SetActivateHdl( LINK( this, IcnViewEdit_Impl, EscapeHdl_Impl) );
    3350           0 :     GetpApp()->InsertAccel( &aAccReturn);//, ACCEL_ALWAYS );
    3351           0 :     GetpApp()->InsertAccel( &aAccEscape);//, ACCEL_ALWAYS );
    3352           0 :     Show();
    3353           0 :     GrabFocus();
    3354           0 : }
    3355             : 
    3356           0 : IcnViewEdit_Impl::~IcnViewEdit_Impl()
    3357             : {
    3358           0 :     if( !bAlreadyInCallback )
    3359             :     {
    3360           0 :         GetpApp()->RemoveAccel( &aAccReturn );
    3361           0 :         GetpApp()->RemoveAccel( &aAccEscape );
    3362             :     }
    3363           0 : }
    3364             : 
    3365           0 : void IcnViewEdit_Impl::CallCallBackHdl_Impl()
    3366             : {
    3367           0 :     aTimer.Stop();
    3368           0 :     if ( !bAlreadyInCallback )
    3369             :     {
    3370           0 :         bAlreadyInCallback = sal_True;
    3371           0 :         GetpApp()->RemoveAccel( &aAccReturn );
    3372           0 :         GetpApp()->RemoveAccel( &aAccEscape );
    3373           0 :         Hide();
    3374           0 :         aCallBackHdl.Call( this );
    3375             :     }
    3376           0 : }
    3377             : 
    3378           0 : IMPL_LINK_NOARG(IcnViewEdit_Impl, Timeout_Impl)
    3379             : {
    3380           0 :     CallCallBackHdl_Impl();
    3381           0 :     return 0;
    3382             : }
    3383             : 
    3384           0 : IMPL_LINK( IcnViewEdit_Impl, ReturnHdl_Impl, Accelerator*, EMPTYARG  )
    3385             : {
    3386           0 :     bCanceled = sal_False;
    3387           0 :     bGrabFocus = sal_True;
    3388           0 :     CallCallBackHdl_Impl();
    3389           0 :     return 1;
    3390             : }
    3391             : 
    3392           0 : IMPL_LINK( IcnViewEdit_Impl, EscapeHdl_Impl, Accelerator*, EMPTYARG  )
    3393             : {
    3394           0 :     bCanceled = sal_True;
    3395           0 :     bGrabFocus = sal_True;
    3396           0 :     CallCallBackHdl_Impl();
    3397           0 :     return 1;
    3398             : }
    3399             : 
    3400           0 : void IcnViewEdit_Impl::KeyInput( const KeyEvent& rKEvt )
    3401             : {
    3402           0 :     KeyCode aCode = rKEvt.GetKeyCode();
    3403           0 :     sal_uInt16 nCode = aCode.GetCode();
    3404             : 
    3405           0 :     switch ( nCode )
    3406             :     {
    3407             :         case KEY_ESCAPE:
    3408           0 :             bCanceled = sal_True;
    3409           0 :             bGrabFocus = sal_True;
    3410           0 :             CallCallBackHdl_Impl();
    3411           0 :             break;
    3412             : 
    3413             :         case KEY_RETURN:
    3414           0 :             bCanceled = sal_False;
    3415           0 :             bGrabFocus = sal_True;
    3416           0 :             CallCallBackHdl_Impl();
    3417           0 :             break;
    3418             : 
    3419             :         default:
    3420           0 :             MultiLineEdit::KeyInput( rKEvt );
    3421             :     }
    3422           0 : }
    3423             : 
    3424           0 : long IcnViewEdit_Impl::PreNotify( NotifyEvent& rNEvt )
    3425             : {
    3426           0 :     if( rNEvt.GetType() == EVENT_LOSEFOCUS )
    3427             :     {
    3428           0 :         if ( !bAlreadyInCallback &&
    3429           0 :             ((!Application::GetFocusWindow()) || !IsChild(Application::GetFocusWindow())))
    3430             :         {
    3431           0 :             bCanceled = sal_False;
    3432           0 :             aTimer.SetTimeout(10);
    3433           0 :             aTimer.SetTimeoutHdl(LINK(this,IcnViewEdit_Impl,Timeout_Impl));
    3434           0 :             aTimer.Start();
    3435             :         }
    3436             :     }
    3437           0 :     return 0;
    3438             : }
    3439             : 
    3440           0 : void IcnViewEdit_Impl::StopEditing( sal_Bool bCancel )
    3441             : {
    3442           0 :     if ( !bAlreadyInCallback )
    3443             :     {
    3444           0 :         bCanceled = bCancel;
    3445           0 :         CallCallBackHdl_Impl();
    3446             :     }
    3447           0 : }
    3448             : 
    3449           0 : sal_uLong SvxIconChoiceCtrl_Impl::GetEntryListPos( SvxIconChoiceCtrlEntry* pEntry ) const
    3450             : {
    3451           0 :     if( !(nFlags & F_ENTRYLISTPOS_VALID ))
    3452           0 :         ((SvxIconChoiceCtrl_Impl*)this)->SetListPositions();
    3453           0 :     return pEntry->nPos;
    3454             : }
    3455             : 
    3456           0 : void SvxIconChoiceCtrl_Impl::InitSettings()
    3457             : {
    3458           0 :     const StyleSettings& rStyleSettings = pView->GetSettings().GetStyleSettings();
    3459             : 
    3460           0 :     if( !pView->HasFont() )
    3461             :     {
    3462             :         // unit (from settings) is Point
    3463           0 :         Font aFont( rStyleSettings.GetFieldFont() );
    3464             :         //const Font& rFont = pView->GetFont();
    3465             :         //if( pView->HasFontTextColor() )
    3466           0 :             aFont.SetColor( rStyleSettings.GetWindowTextColor() );
    3467             :         //if( pView->HasFontFillColor() )
    3468             :             //aFont.SetFillColor( rFont.GetFillColor() );
    3469           0 :         pView->SetPointFont( aFont );
    3470           0 :         SetDefaultTextSize();
    3471             :     }
    3472             : 
    3473             :     //if( !pView->HasFontTextColor() )
    3474           0 :         pView->SetTextColor( rStyleSettings.GetFieldTextColor() );
    3475             :     //if( !pView->HasFontFillColor() )
    3476           0 :         pView->SetTextFillColor();
    3477             : 
    3478             :     //if( !pView->HasBackground() )
    3479           0 :         pView->SetBackground( rStyleSettings.GetFieldColor());
    3480             : 
    3481           0 :     long nScrBarSize = rStyleSettings.GetScrollBarSize();
    3482           0 :     if( nScrBarSize != nHorSBarHeight || nScrBarSize != nVerSBarWidth )
    3483             :     {
    3484           0 :         nHorSBarHeight = nScrBarSize;
    3485           0 :         Size aSize( aHorSBar.GetSizePixel() );
    3486           0 :         aSize.Height() = nScrBarSize;
    3487           0 :         aHorSBar.Hide();
    3488           0 :         aHorSBar.SetSizePixel( aSize );
    3489             : 
    3490           0 :         nVerSBarWidth = nScrBarSize;
    3491           0 :         aSize = aVerSBar.GetSizePixel();
    3492           0 :         aSize.Width() = nScrBarSize;
    3493           0 :         aVerSBar.Hide();
    3494           0 :         aVerSBar.SetSizePixel( aSize );
    3495             : 
    3496           0 :         Size aOSize( pView->Control::GetOutputSizePixel() );
    3497           0 :         PositionScrollBars( aOSize.Width(), aOSize.Height() );
    3498           0 :         AdjustScrollBars();
    3499             :     }
    3500           0 : }
    3501             : 
    3502           0 : EntryList_Impl::EntryList_Impl( SvxIconChoiceCtrl_Impl* pOwner ) :
    3503           0 :     _pOwner( pOwner )
    3504             : {
    3505           0 :     _pOwner->pHead = 0;
    3506           0 : }
    3507             : 
    3508           0 : EntryList_Impl::~EntryList_Impl()
    3509             : {
    3510           0 :     _pOwner->pHead = 0;
    3511           0 : }
    3512             : 
    3513           0 : void EntryList_Impl::clear()
    3514             : {
    3515           0 :     _pOwner->pHead = 0;
    3516           0 :     maIconChoiceCtrlEntryList.clear();
    3517           0 : }
    3518             : 
    3519           0 : void EntryList_Impl::insert( size_t nPos, SvxIconChoiceCtrlEntry* pEntry )
    3520             : {
    3521           0 :     if ( nPos < maIconChoiceCtrlEntryList.size() ) {
    3522           0 :         maIconChoiceCtrlEntryList.insert( maIconChoiceCtrlEntryList.begin() + nPos, pEntry );
    3523             :     } else {
    3524           0 :         maIconChoiceCtrlEntryList.push_back( pEntry );
    3525             :     }
    3526           0 :     if( _pOwner->pHead )
    3527           0 :         pEntry->SetBacklink( _pOwner->pHead->pblink );
    3528           0 : }
    3529             : 
    3530           0 : void SvxIconChoiceCtrl_Impl::SetPositionMode( SvxIconChoiceCtrlPositionMode eMode )
    3531             : {
    3532           0 :     if( eMode == ePositionMode )
    3533           0 :         return;
    3534             : 
    3535           0 :     SvxIconChoiceCtrlPositionMode eOldMode = ePositionMode;
    3536           0 :     ePositionMode = eMode;
    3537           0 :     size_t nCount = aEntries.size();
    3538             : 
    3539           0 :     if( eOldMode == IcnViewPositionModeAutoArrange )
    3540             :     {
    3541             :         // when positioning moved entries "hard", there are problems with
    3542             :         // unwanted overlaps, as these entries aren't taken into account in
    3543             :         // Arrange.
    3544           0 :         if( aEntries.size() )
    3545           0 :             aAutoArrangeTimer.Start();
    3546           0 :         return;
    3547             :     }
    3548             : 
    3549           0 :     if( ePositionMode == IcnViewPositionModeAutoArrange )
    3550             :     {
    3551           0 :         for( size_t nCur = 0; nCur < nCount; nCur++ )
    3552             :         {
    3553           0 :             SvxIconChoiceCtrlEntry* pEntry = aEntries[ nCur ];
    3554           0 :             if( pEntry->GetFlags() & (ICNVIEW_FLAG_POS_LOCKED | ICNVIEW_FLAG_POS_MOVED))
    3555           0 :                 SetEntryPos(pEntry, GetEntryBoundRect( pEntry ).TopLeft());
    3556             :         }
    3557             : 
    3558           0 :         if( aEntries.size() )
    3559           0 :             aAutoArrangeTimer.Start();
    3560             :     }
    3561           0 :     else if( ePositionMode == IcnViewPositionModeAutoAdjust )
    3562             :     {
    3563           0 :         AdjustEntryAtGrid( 0 );
    3564             :     }
    3565             : }
    3566             : 
    3567           0 : void SvxIconChoiceCtrl_Impl::SetEntryPredecessor( SvxIconChoiceCtrlEntry* pEntry,
    3568             :     SvxIconChoiceCtrlEntry* pPredecessor )
    3569             : {
    3570           0 :     if( !IsAutoArrange() )
    3571           0 :         return;
    3572             : 
    3573           0 :     if( pEntry == pPredecessor )
    3574           0 :         return;
    3575             : 
    3576           0 :     sal_uLong nPos1 = GetEntryListPos( pEntry );
    3577           0 :     if( !pHead )
    3578             :     {
    3579           0 :         if( pPredecessor )
    3580             :         {
    3581           0 :             sal_uLong nPos2 = GetEntryListPos( pPredecessor );
    3582           0 :             if( nPos1 == (nPos2 + 1) )
    3583           0 :                 return; // is already the predecessor
    3584             :         }
    3585           0 :         else if( !nPos1 )
    3586           0 :             return;
    3587             :     }
    3588             : 
    3589           0 :     if( !pHead )
    3590           0 :         InitPredecessors();
    3591             : 
    3592           0 :     if( !pPredecessor && pHead == pEntry )
    3593           0 :         return; // is already the first one
    3594             : 
    3595           0 :     sal_Bool bSetHead = sal_False;
    3596           0 :     if( !pPredecessor )
    3597             :     {
    3598           0 :         bSetHead = sal_True;
    3599           0 :         pPredecessor = pHead->pblink;
    3600             :     }
    3601           0 :     if( pEntry == pHead )
    3602             :     {
    3603           0 :         pHead = pHead->pflink;
    3604           0 :         bSetHead = sal_False;
    3605             :     }
    3606           0 :     if( pEntry != pPredecessor )
    3607             :     {
    3608           0 :         pEntry->Unlink();
    3609           0 :         pEntry->SetBacklink( pPredecessor );
    3610             :     }
    3611           0 :     if( bSetHead )
    3612           0 :         pHead = pEntry;
    3613           0 :     pEntry->SetFlags( ICNVIEW_FLAG_PRED_SET );
    3614           0 :     aAutoArrangeTimer.Start();
    3615             : }
    3616             : 
    3617           0 : SvxIconChoiceCtrlEntry* SvxIconChoiceCtrl_Impl::FindEntryPredecessor( SvxIconChoiceCtrlEntry* pEntry,
    3618             :     const Point& rPosTopLeft )
    3619             : {
    3620           0 :     Point aPos( rPosTopLeft ); //TopLeft
    3621           0 :     Rectangle aCenterRect( CalcBmpRect( pEntry, &aPos ));
    3622           0 :     Point aNewPos( aCenterRect.Center() );
    3623           0 :     sal_uLong nGrid = GetPredecessorGrid( aNewPos );
    3624           0 :     size_t nCount = aEntries.size();
    3625           0 :     if( nGrid == ULONG_MAX )
    3626           0 :         return 0;
    3627           0 :     if( nGrid >= nCount )
    3628           0 :         nGrid = nCount - 1;
    3629           0 :     if( !pHead )
    3630           0 :         return aEntries[ nGrid ];
    3631             : 
    3632           0 :     SvxIconChoiceCtrlEntry* pCur = pHead; // Grid 0
    3633             :     // TODO: go through list from the end if nGrid > nCount/2
    3634           0 :     for( sal_uLong nCur = 0; nCur < nGrid; nCur++ )
    3635           0 :         pCur = pCur->pflink;
    3636             : 
    3637           0 :     return pCur;
    3638             : }
    3639             : 
    3640           0 : sal_uLong SvxIconChoiceCtrl_Impl::GetPredecessorGrid( const Point& rPos) const
    3641             : {
    3642           0 :     Point aPos( rPos );
    3643           0 :     aPos.X() -= LROFFS_WINBORDER;
    3644           0 :     aPos.Y() -= TBOFFS_WINBORDER;
    3645           0 :     sal_uInt16 nMaxCol = (sal_uInt16)(aVirtOutputSize.Width() / nGridDX);
    3646           0 :     if( nMaxCol )
    3647           0 :         nMaxCol--;
    3648           0 :     sal_uInt16 nGridX = (sal_uInt16)(aPos.X() / nGridDX);
    3649           0 :     if( nGridX > nMaxCol )
    3650           0 :         nGridX = nMaxCol;
    3651           0 :     sal_uInt16 nGridY = (sal_uInt16)(aPos.Y() / nGridDY);
    3652           0 :     sal_uInt16 nGridsX = (sal_uInt16)(aOutputSize.Width() / nGridDX);
    3653           0 :     sal_uLong nGrid = (nGridY * nGridsX) + nGridX;
    3654           0 :     long nMiddle = (nGridX * nGridDX) + (nGridDX / 2);
    3655           0 :     if( rPos.X() < nMiddle )
    3656             :     {
    3657           0 :         if( !nGrid )
    3658           0 :             nGrid = ULONG_MAX;
    3659             :         else
    3660           0 :             nGrid--;
    3661             :     }
    3662           0 :     return nGrid;
    3663             : }
    3664             : 
    3665           0 : sal_Bool SvxIconChoiceCtrl_Impl::RequestHelp( const HelpEvent& rHEvt )
    3666             : {
    3667           0 :     if ( !(rHEvt.GetMode() & HELPMODE_QUICK ) )
    3668           0 :         return sal_False;
    3669             : 
    3670           0 :     Point aPos( pView->ScreenToOutputPixel(rHEvt.GetMousePosPixel() ) );
    3671           0 :     aPos -= pView->GetMapMode().GetOrigin();
    3672           0 :     SvxIconChoiceCtrlEntry* pEntry = GetEntry( aPos, sal_True );
    3673             : 
    3674           0 :     if ( !pEntry )
    3675           0 :         return sal_False;
    3676             : 
    3677           0 :     String sQuickHelpText = pEntry->GetQuickHelpText();
    3678           0 :     String aEntryText( pView->GetEntryText( pEntry, sal_False ) );
    3679           0 :     Rectangle aTextRect( CalcTextRect( pEntry, 0, sal_False, &aEntryText ) );
    3680           0 :     if ( ( !aTextRect.IsInside( aPos ) || !aEntryText.Len() ) && !sQuickHelpText.Len() )
    3681           0 :         return sal_False;
    3682             : 
    3683           0 :     Rectangle aOptTextRect( aTextRect );
    3684           0 :     aOptTextRect.Bottom() = LONG_MAX;
    3685           0 :     sal_uInt16 nNewFlags = nCurTextDrawFlags;
    3686           0 :     nNewFlags &= ~( TEXT_DRAW_CLIP | TEXT_DRAW_ENDELLIPSIS );
    3687           0 :     aOptTextRect = pView->GetTextRect( aOptTextRect, aEntryText, nNewFlags );
    3688           0 :     if ( aOptTextRect != aTextRect || sQuickHelpText.Len() > 0 )
    3689             :     {
    3690             :         //aTextRect.Right() = aTextRect.Left() + aRealSize.Width() + 4;
    3691           0 :         Point aPt( aOptTextRect.TopLeft() );
    3692           0 :         aPt += pView->GetMapMode().GetOrigin();
    3693           0 :         aPt = pView->OutputToScreenPixel( aPt );
    3694             :         // subtract border of tooltip help
    3695           0 :         aPt.Y() -= 1;
    3696           0 :         aPt.X() -= 3;
    3697           0 :         aOptTextRect.SetPos( aPt );
    3698           0 :         String sHelpText;
    3699           0 :         if ( sQuickHelpText.Len() > 0 )
    3700           0 :             sHelpText = sQuickHelpText;
    3701             :         else
    3702           0 :             sHelpText = aEntryText;
    3703           0 :         Help::ShowQuickHelp( (Window*)pView, aOptTextRect, sHelpText, QUICKHELP_LEFT | QUICKHELP_VCENTER );
    3704             :     }
    3705             : 
    3706           0 :     return sal_True;
    3707             : }
    3708             : 
    3709           0 : void SvxIconChoiceCtrl_Impl::ClearColumnList()
    3710             : {
    3711           0 :     if( !pColumns )
    3712           0 :         return;
    3713             : 
    3714           0 :     pColumns->clear();
    3715           0 :     DELETEZ(pColumns);
    3716             : }
    3717             : 
    3718           0 : void SvxIconChoiceCtrl_Impl::SetColumn( sal_uInt16 nIndex, const SvxIconChoiceCtrlColumnInfo& rInfo)
    3719             : {
    3720           0 :     if( !pColumns )
    3721           0 :         pColumns = new SvxIconChoiceCtrlColumnInfoMap;
    3722             : 
    3723           0 :     SvxIconChoiceCtrlColumnInfo* pInfo = new SvxIconChoiceCtrlColumnInfo( rInfo );
    3724           0 :     pColumns->insert( nIndex,  pInfo );
    3725             : 
    3726             :     // HACK: Detail mode is not yet fully implemented, this workaround makes it
    3727             :     // fly with a single column
    3728           0 :     if( !nIndex && (nWinBits & WB_DETAILS) )
    3729           0 :         nGridDX = pInfo->GetWidth();
    3730             : 
    3731           0 :     if( GetUpdateMode() )
    3732           0 :         Arrange( IsAutoArrange() );
    3733           0 : }
    3734             : 
    3735           0 : const SvxIconChoiceCtrlColumnInfo* SvxIconChoiceCtrl_Impl::GetColumn( sal_uInt16 nIndex ) const
    3736             : {
    3737           0 :     if (!pColumns)
    3738           0 :         return 0;
    3739           0 :     SvxIconChoiceCtrlColumnInfoMap::const_iterator it = pColumns->find( nIndex );
    3740           0 :     if( it == pColumns->end() )
    3741           0 :         return 0;
    3742           0 :     return it->second;
    3743             : }
    3744             : 
    3745           0 : void SvxIconChoiceCtrl_Impl::DrawHighlightFrame(
    3746             :     OutputDevice* pOut, const Rectangle& rBmpRect, sal_Bool bHide )
    3747             : {
    3748           0 :     Rectangle aBmpRect( rBmpRect );
    3749           0 :     long nBorder = 2;
    3750           0 :     if( aImageSize.Width() < 32 )
    3751           0 :         nBorder = 1;
    3752           0 :     aBmpRect.Right() += nBorder;
    3753           0 :     aBmpRect.Left() -= nBorder;
    3754           0 :     aBmpRect.Bottom() += nBorder;
    3755           0 :     aBmpRect.Top() -= nBorder;
    3756             : 
    3757           0 :     if ( bHide )
    3758           0 :         pView->Invalidate( aBmpRect );
    3759             :     else
    3760             :     {
    3761           0 :         DecorationView aDecoView( pOut );
    3762             :         sal_uInt16 nDecoFlags;
    3763           0 :         if ( bHighlightFramePressed )
    3764           0 :             nDecoFlags = FRAME_HIGHLIGHT_TESTBACKGROUND | FRAME_HIGHLIGHT_IN;
    3765             :         else
    3766           0 :             nDecoFlags = FRAME_HIGHLIGHT_TESTBACKGROUND | FRAME_HIGHLIGHT_OUT;
    3767           0 :         aDecoView.DrawHighlightFrame( aBmpRect, nDecoFlags );
    3768             :     }
    3769           0 : }
    3770             : 
    3771           0 : void SvxIconChoiceCtrl_Impl::SetEntryHighlightFrame( SvxIconChoiceCtrlEntry* pEntry,
    3772             :     sal_Bool bKeepHighlightFlags )
    3773             : {
    3774           0 :     if( pEntry == pCurHighlightFrame )
    3775           0 :         return;
    3776             : 
    3777           0 :     if( !bKeepHighlightFlags )
    3778           0 :         bHighlightFramePressed = sal_False;
    3779             : 
    3780           0 :     HideEntryHighlightFrame();
    3781           0 :     pCurHighlightFrame = pEntry;
    3782           0 :     if( pEntry )
    3783             :     {
    3784           0 :         Rectangle aBmpRect( CalcFocusRect(pEntry) );
    3785           0 :         DrawHighlightFrame( pView, aBmpRect, sal_False );
    3786             :     }
    3787             : }
    3788             : 
    3789           0 : void SvxIconChoiceCtrl_Impl::HideEntryHighlightFrame()
    3790             : {
    3791           0 :     if( !pCurHighlightFrame )
    3792           0 :         return;
    3793             : 
    3794           0 :     SvxIconChoiceCtrlEntry* pEntry = pCurHighlightFrame;
    3795           0 :     pCurHighlightFrame = 0;
    3796           0 :     Rectangle aBmpRect( CalcFocusRect(pEntry) );
    3797           0 :     DrawHighlightFrame( pView, aBmpRect, sal_True );
    3798             : }
    3799             : 
    3800           0 : void SvxIconChoiceCtrl_Impl::CallSelectHandler( SvxIconChoiceCtrlEntry* )
    3801             : {
    3802             :     // When single-click mode is active, the selection handler should be called
    3803             :     // synchronously, as the selection is automatically taken away once the
    3804             :     // mouse cursor doesn't touch the object any more. Else, we might run into
    3805             :     // missing calls to Select if the object is selected from a mouse movement,
    3806             :     // because when starting the timer, the mouse cursor might have already left
    3807             :     // the object.
    3808             :     // In special cases (=>SfxFileDialog!), synchronous calls can be forced via
    3809             :     // WB_NOASYNCSELECTHDL.
    3810           0 :     if( nWinBits & (WB_NOASYNCSELECTHDL | WB_HIGHLIGHTFRAME) )
    3811             :     {
    3812           0 :         pHdlEntry = 0;
    3813           0 :         pView->ClickIcon();
    3814             :         //pView->Select();
    3815             :     }
    3816             :     else
    3817           0 :         aCallSelectHdlTimer.Start();
    3818           0 : }
    3819             : 
    3820           0 : IMPL_LINK_NOARG(SvxIconChoiceCtrl_Impl, CallSelectHdlHdl)
    3821             : {
    3822           0 :     pHdlEntry = 0;
    3823           0 :     pView->ClickIcon();
    3824             :     //pView->Select();
    3825           0 :     return 0;
    3826             : }
    3827             : 
    3828           0 : void SvxIconChoiceCtrl_Impl::SetOrigin( const Point& rPos, sal_Bool bDoNotUpdateWallpaper )
    3829             : {
    3830           0 :     MapMode aMapMode( pView->GetMapMode() );
    3831           0 :     aMapMode.SetOrigin( rPos );
    3832           0 :     pView->SetMapMode( aMapMode );
    3833           0 :     if( !bDoNotUpdateWallpaper )
    3834             :     {
    3835           0 :         sal_Bool bScrollable = pView->GetBackground().IsScrollable();
    3836           0 :         if( pView->HasBackground() && !bScrollable )
    3837             :         {
    3838           0 :             Rectangle aRect( GetOutputRect());
    3839           0 :             Wallpaper aPaper( pView->GetBackground() );
    3840           0 :             aPaper.SetRect( aRect );
    3841           0 :             pView->SetBackground( aPaper );
    3842             :         }
    3843           0 :     }
    3844           0 : }
    3845             : 
    3846           0 : void SvxIconChoiceCtrl_Impl::CallEventListeners( sal_uLong nEvent, void* pData )
    3847             : {
    3848           0 :     pView->CallImplEventListeners( nEvent, pData );
    3849           0 : }
    3850             : 
    3851             : 
    3852             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10