LCOV - code coverage report
Current view: top level - vcl/source/window - dlgctrl.cxx (source / functions) Hit Total Coverage
Test: commit 0e63ca4fde4e446f346e35849c756a30ca294aab Lines: 241 652 37.0 %
Date: 2014-04-11 Functions: 21 29 72.4 %
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             : #include <tools/debug.hxx>
      21             : 
      22             : #include <svdata.hxx>
      23             : #include <window.h>
      24             : 
      25             : #include <vcl/event.hxx>
      26             : #include <vcl/fixed.hxx>
      27             : #include <vcl/layout.hxx>
      28             : #include <vcl/svapp.hxx>
      29             : #include <vcl/tabpage.hxx>
      30             : #include <vcl/tabctrl.hxx>
      31             : #include <vcl/tabdlg.hxx>
      32             : #include <vcl/button.hxx>
      33             : #include <vcl/settings.hxx>
      34             : #include <vcl/unohelp.hxx>
      35             : 
      36             : #include <com/sun/star/i18n/XCharacterClassification.hpp>
      37             : 
      38             : using namespace ::com::sun::star;
      39             : 
      40        5901 : static bool ImplHasIndirectTabParent( Window* pWindow )
      41             : {
      42             :     // The window has inderect tab parent if it is included in tab hierarchy
      43             :     // of the indirect parent window
      44             : 
      45        5901 :     Window* pNonLayoutParent = getNonLayoutParent(pWindow);
      46             :     return ( pNonLayoutParent
      47        5901 :           && ( pNonLayoutParent->ImplGetWindow()->GetStyle() & WB_CHILDDLGCTRL ) );
      48             : }
      49             : 
      50       25547 : static Window* ImplGetTopParentOfTabHierarchy( Window* pParent )
      51             : {
      52             :     // The method allows to find the most close parent containing all the
      53             :     // window from the current tab-hierarchy
      54             :     // The direct parent should be provided as a parameter here
      55             : 
      56       25547 :     Window* pResult = pParent;
      57             : 
      58       25547 :     if ( pResult )
      59             :     {
      60       25547 :         Window* pNonLayoutParent = getNonLayoutParent(pResult);
      61       51094 :         while ( pNonLayoutParent && ( pResult->ImplGetWindow()->GetStyle() & WB_CHILDDLGCTRL ) )
      62             :         {
      63           0 :             pResult = pNonLayoutParent;
      64           0 :             pNonLayoutParent = getNonLayoutParent(pResult);
      65             :         }
      66             :     }
      67             : 
      68       25547 :     return pResult;
      69             : }
      70             : 
      71       42478 : static Window* ImplGetSubChildWindow( Window* pParent, sal_uInt16 n, sal_uInt16& nIndex )
      72             : {
      73       42478 :     Window*     pTabPage = NULL;
      74       42478 :     Window*     pFoundWindow = NULL;
      75             : 
      76       42478 :     Window*     pWindow = firstLogicalChildOfParent(pParent);
      77       42478 :     Window*     pNextWindow = pWindow;
      78      141474 :     while ( pWindow )
      79             :     {
      80       76616 :         pWindow = pWindow->ImplGetWindow();
      81             : 
      82             :         // skip invisible and disabled windows
      83       76616 :         if ( pTabPage || isVisibleInLayout(pWindow) )
      84             :         {
      85             :             // if the last control was a TabControl, take its TabPage
      86       63172 :             if ( pTabPage )
      87             :             {
      88           0 :                 pFoundWindow = ImplGetSubChildWindow( pTabPage, n, nIndex );
      89           0 :                 pTabPage = NULL;
      90             :             }
      91             :             else
      92             :             {
      93       63172 :                 pFoundWindow = pWindow;
      94             : 
      95             :                 // for a TabControl, remember the current TabPage for later use
      96       63172 :                 if ( pWindow->GetType() == WINDOW_TABCONTROL )
      97             :                 {
      98           0 :                     TabControl* pTabControl = ((TabControl*)pWindow);
      99             :                     // Check if the TabPage is a Child of the TabControl and still exists (by
     100             :                     // walking all child windows); because it could be that the TabPage has been
     101             :                     // destroyed already by a Dialog-Dtor, event that the TabControl still exists.
     102           0 :                     TabPage* pTempTabPage = pTabControl->GetTabPage( pTabControl->GetCurPageId() );
     103           0 :                     if ( pTempTabPage )
     104             :                     {
     105           0 :                         Window* pTempWindow = pTabControl->GetWindow( WINDOW_FIRSTCHILD );
     106           0 :                         while ( pTempWindow )
     107             :                         {
     108           0 :                             if ( pTempWindow->ImplGetWindow() == pTempTabPage )
     109             :                             {
     110           0 :                                 pTabPage = pTempTabPage;
     111           0 :                                 break;
     112             :                             }
     113           0 :                             pTempWindow = nextLogicalChildOfParent(pTabControl, pTempWindow);
     114             :                         }
     115             :                     }
     116             :                 }
     117      126344 :                 else if ( ( pWindow->GetStyle() & WB_DIALOGCONTROL )
     118       63172 :                        || ( pWindow->GetStyle() & WB_CHILDDLGCTRL ) )
     119       16931 :                     pFoundWindow = ImplGetSubChildWindow( pWindow, n, nIndex );
     120             :             }
     121             : 
     122       63172 :             if ( n == nIndex )
     123       20098 :                 return pFoundWindow;
     124       43074 :             nIndex++;
     125             :         }
     126             : 
     127       56518 :         if ( pTabPage )
     128           0 :             pWindow = pTabPage;
     129             :         else
     130             :         {
     131       56518 :             pWindow = nextLogicalChildOfParent(pParent, pNextWindow);
     132       56518 :             pNextWindow = pWindow;
     133             :         }
     134             :     }
     135             : 
     136       22380 :     nIndex--;
     137       22380 :     return pFoundWindow;
     138             : }
     139             : 
     140       25547 : static Window* ImplGetChildWindow( Window* pParent, sal_uInt16 n, sal_uInt16& nIndex, bool bTestEnable )
     141             : {
     142       25547 :     pParent = ImplGetTopParentOfTabHierarchy( pParent );
     143             : 
     144       25547 :     nIndex = 0;
     145       25547 :     Window* pWindow = ImplGetSubChildWindow( pParent, n, nIndex );
     146       25547 :     if ( bTestEnable )
     147             :     {
     148         492 :         sal_uInt16 n2 = nIndex;
     149         984 :         while ( pWindow && (!isEnabledInLayout(pWindow) || !pWindow->IsInputEnabled()) )
     150             :         {
     151           0 :             n2 = nIndex+1;
     152           0 :             nIndex = 0;
     153           0 :             pWindow = ImplGetSubChildWindow( pParent, n2, nIndex );
     154           0 :             if ( nIndex < n2 )
     155           0 :                 break;
     156             :         }
     157             : 
     158         492 :         if ( (nIndex < n2) && n )
     159             :         {
     160           0 :             do
     161             :             {
     162           0 :                 n--;
     163           0 :                 nIndex = 0;
     164           0 :                 pWindow = ImplGetSubChildWindow( pParent, n, nIndex );
     165             :             }
     166           0 :             while ( pWindow && n && (!isEnabledInLayout(pWindow) || !pWindow->IsInputEnabled()) );
     167             :         }
     168             :     }
     169       25547 :     return pWindow;
     170             : }
     171             : 
     172        9053 : static Window* ImplGetNextWindow( Window* pParent, sal_uInt16 n, sal_uInt16& nIndex, bool bTestEnable )
     173             : {
     174        9053 :     Window* pWindow = ImplGetChildWindow( pParent, n+1, nIndex, bTestEnable );
     175        9053 :     if ( n == nIndex )
     176             :     {
     177        3723 :         n = 0;
     178        3723 :         pWindow = ImplGetChildWindow( pParent, n, nIndex, bTestEnable );
     179             :     }
     180        9053 :     return pWindow;
     181             : }
     182             : 
     183          84 : Window* Window::ImplGetDlgWindow( sal_uInt16 nIndex, sal_uInt16 nType,
     184             :                                   sal_uInt16 nFormStart, sal_uInt16 nFormEnd,
     185             :                                   sal_uInt16* pIndex )
     186             : {
     187             :     DBG_ASSERT( (nIndex >= nFormStart) && (nIndex <= nFormEnd),
     188             :                 "Window::ImplGetDlgWindow() - nIndex not in Form" );
     189             : 
     190          84 :     Window* pWindow = NULL;
     191             :     sal_uInt16  i;
     192             :     sal_uInt16  nTemp;
     193             :     sal_uInt16  nStartIndex;
     194             : 
     195          84 :     if ( nType == DLGWINDOW_PREV )
     196             :     {
     197           0 :         i = nIndex;
     198           0 :         do
     199             :         {
     200           0 :             if ( i > nFormStart )
     201           0 :                 i--;
     202             :             else
     203           0 :                 i = nFormEnd;
     204           0 :             pWindow = ImplGetChildWindow( this, i, nTemp, true );
     205           0 :             if ( !pWindow )
     206           0 :                 break;
     207           0 :             if ( (i == nTemp) && (pWindow->GetStyle() & WB_TABSTOP) )
     208           0 :                 break;
     209             :         }
     210           0 :         while ( i != nIndex );
     211             :     }
     212             :     else
     213             :     {
     214          84 :         i = nIndex;
     215          84 :         pWindow = ImplGetChildWindow( this, i, i, (nType == DLGWINDOW_FIRST) );
     216          84 :         if ( pWindow )
     217             :         {
     218          73 :             nStartIndex = i;
     219             : 
     220          73 :             if ( nType == DLGWINDOW_NEXT )
     221             :             {
     222           0 :                 if ( i < nFormEnd )
     223             :                 {
     224           0 :                     pWindow = ImplGetNextWindow( this, i, i, true );
     225           0 :                     if ( (i > nFormEnd) || (i < nFormStart) )
     226           0 :                         pWindow = ImplGetChildWindow( this, nFormStart, i, true );
     227             :                 }
     228             :                 else
     229           0 :                     pWindow = ImplGetChildWindow( this, nFormStart, i, true );
     230             :             }
     231             : 
     232          73 :             if ( i <= nFormEnd )
     233             :             {
     234             :                 // carry the 2nd index, in case all controls are disabled
     235          73 :                 sal_uInt16 nStartIndex2 = i;
     236          73 :                 sal_uInt16 nOldIndex = i+1;
     237             : 
     238         346 :                 do
     239             :                 {
     240         357 :                     if ( pWindow->GetStyle() & WB_TABSTOP )
     241          11 :                         break;
     242         346 :                     if( i == nOldIndex ) // only disabled controls ?
     243             :                     {
     244           0 :                         i = nStartIndex2;
     245           0 :                         break;
     246             :                     }
     247         346 :                     nOldIndex = i;
     248         346 :                     if ( (i > nFormEnd) || (i < nFormStart) )
     249           0 :                         pWindow = ImplGetChildWindow( this, nFormStart, i, true );
     250             :                     else
     251         346 :                         pWindow = ImplGetNextWindow( this, i, i, true );
     252             :                 }
     253         630 :                 while ( (i != nStartIndex) && (i != nStartIndex2) );
     254             : 
     255         203 :                 if ( (i == nStartIndex2) &&
     256          74 :                      (!(pWindow->GetStyle() & WB_TABSTOP) || !isEnabledInLayout(pWindow)) )
     257          62 :                     i = nStartIndex;
     258             :             }
     259             :         }
     260             : 
     261          84 :         if ( nType == DLGWINDOW_FIRST )
     262             :         {
     263          84 :             if ( pWindow )
     264             :             {
     265          73 :                 if ( pWindow->GetType() == WINDOW_TABCONTROL )
     266             :                 {
     267           0 :                     Window* pNextWindow = ImplGetDlgWindow( i, DLGWINDOW_NEXT );
     268           0 :                     if ( pNextWindow )
     269             :                     {
     270           0 :                         if ( pWindow->IsChild( pNextWindow ) )
     271           0 :                             pWindow = pNextWindow;
     272             :                     }
     273             :                 }
     274             : 
     275          73 :                 if ( !(pWindow->GetStyle() & WB_TABSTOP) )
     276          62 :                     pWindow = NULL;
     277             :             }
     278             :         }
     279             :     }
     280             : 
     281          84 :     if ( pIndex )
     282           0 :         *pIndex = i;
     283             : 
     284          84 :     return pWindow;
     285             : }
     286             : 
     287        8427 : static Window* ImplFindDlgCtrlWindow( Window* pParent, Window* pWindow, sal_uInt16& rIndex,
     288             :                                       sal_uInt16& rFormStart, sal_uInt16& rFormEnd )
     289             : {
     290             :     Window* pSWindow;
     291        8427 :     Window* pSecondWindow = NULL;
     292        8427 :     Window* pTempWindow = NULL;
     293             :     sal_uInt16  i;
     294        8427 :     sal_uInt16  nSecond_i = 0;
     295        8427 :     sal_uInt16  nFormStart = 0;
     296        8427 :     sal_uInt16  nSecondFormStart = 0;
     297             :     sal_uInt16  nFormEnd;
     298             : 
     299             :     // find focus window in the child list
     300        8427 :     Window* pFirstChildWindow = pSWindow = ImplGetChildWindow( pParent, 0, i, false );
     301             : 
     302        8427 :     if( pWindow == NULL )
     303           0 :         pWindow = pSWindow;
     304             : 
     305       21800 :     while ( pSWindow )
     306             :     {
     307             :         // the DialogControlStart mark is only accepted for the direct children
     308       10534 :         if ( !ImplHasIndirectTabParent( pSWindow )
     309        5267 :           && pSWindow->ImplGetWindow()->IsDialogControlStart() )
     310           0 :             nFormStart = i;
     311             : 
     312             :         // SecondWindow for composit controls like ComboBoxes and arrays
     313        5267 :         if ( pSWindow->ImplIsWindowOrChild( pWindow ) )
     314             :         {
     315         586 :             pSecondWindow = pSWindow;
     316         586 :             nSecond_i = i;
     317         586 :             nSecondFormStart = nFormStart;
     318         586 :             if ( pSWindow == pWindow )
     319         321 :                 break;
     320             :         }
     321             : 
     322        4946 :         pSWindow = ImplGetNextWindow( pParent, i, i, false );
     323        4946 :         if ( !i )
     324        2569 :             pSWindow = NULL;
     325             :     }
     326             : 
     327        8427 :     if ( !pSWindow )
     328             :     {
     329             :         // Window not found; we cannot handle it
     330        8106 :         if ( !pSecondWindow )
     331        7841 :             return NULL;
     332             :         else
     333             :         {
     334         265 :             pSWindow = pSecondWindow;
     335         265 :             i = nSecond_i;
     336         265 :             nFormStart = nSecondFormStart;
     337             :         }
     338             :     }
     339             : 
     340             :     // initialize
     341         586 :     rIndex = i;
     342         586 :     rFormStart = nFormStart;
     343             : 
     344             :     // find end of template
     345         586 :     nFormEnd = nFormStart;
     346         586 :     pTempWindow = pSWindow;
     347         586 :     sal_Int32 nIteration = 0;
     348         634 :     do
     349             :     {
     350        1220 :         nFormEnd = i;
     351        1220 :         pTempWindow = ImplGetNextWindow( pParent, i, i, false );
     352             : 
     353             :         // the DialogControlStart mark is only accepted for the direct children
     354        2440 :         if ( !i
     355        1806 :           || ( pTempWindow && !ImplHasIndirectTabParent( pTempWindow )
     356         634 :                && pTempWindow->ImplGetWindow()->IsDialogControlStart() ) )
     357         586 :             break;
     358             : 
     359         634 :         if ( pTempWindow && pTempWindow == pFirstChildWindow )
     360             :         {
     361             :             // It is possible to go through the begin of hierarchy once
     362             :             // while looking for DialogControlStart mark.
     363             :             // If it happens second time, it looks like an endless loop,
     364             :             // that should be impossible, but just for the case...
     365           0 :             nIteration++;
     366           0 :             if ( nIteration >= 2 )
     367             :             {
     368             :                 // this is an unexpected scenario
     369             :                 DBG_ASSERT( false, "It seems to be an endless loop!" );
     370           0 :                 rFormStart = 0;
     371           0 :                 break;
     372             :             }
     373             :         }
     374             :     }
     375             :     while ( pTempWindow );
     376         586 :     rFormEnd = nFormEnd;
     377             : 
     378         586 :     return pSWindow;
     379             : }
     380             : 
     381           0 : static Window* ImplFindAccelWindow( Window* pParent, sal_uInt16& rIndex, sal_Unicode cCharCode,
     382             :                                     sal_uInt16 nFormStart, sal_uInt16 nFormEnd, bool bCheckEnable = true )
     383             : {
     384             :     DBG_ASSERT( (rIndex >= nFormStart) && (rIndex <= nFormEnd),
     385             :                 "Window::ImplFindAccelWindow() - rIndex not in Form" );
     386             : 
     387             :     sal_Unicode cCompareChar;
     388           0 :     sal_uInt16  nStart = rIndex;
     389           0 :     sal_uInt16  i = rIndex;
     390             :     Window* pWindow;
     391             : 
     392             :     // MT: Where can we keep the CharClass?!
     393           0 :     static uno::Reference< i18n::XCharacterClassification > xCharClass;
     394           0 :     if ( !xCharClass.is() )
     395           0 :         xCharClass = vcl::unohelper::CreateCharacterClassification();
     396             : 
     397           0 :     const ::com::sun::star::lang::Locale& rLocale = Application::GetSettings().GetUILanguageTag().getLocale();
     398           0 :     cCharCode = xCharClass->toUpper( OUString(cCharCode), 0, 1, rLocale )[0];
     399             : 
     400           0 :     if ( i < nFormEnd )
     401           0 :         pWindow = ImplGetNextWindow( pParent, i, i, true );
     402             :     else
     403           0 :         pWindow = ImplGetChildWindow( pParent, nFormStart, i, true );
     404           0 :     while( pWindow )
     405             :     {
     406           0 :         const OUString aStr = pWindow->GetText();
     407           0 :         sal_Int32 nPos = aStr.indexOf( '~' );
     408           0 :         while (nPos != -1)
     409             :         {
     410           0 :             cCompareChar = aStr[nPos+1];
     411           0 :             cCompareChar = xCharClass->toUpper( OUString(cCompareChar), 0, 1, rLocale )[0];
     412           0 :             if ( cCompareChar == cCharCode )
     413             :             {
     414           0 :                 if (pWindow->GetType() == WINDOW_FIXEDTEXT)
     415             :                 {
     416           0 :                     FixedText *pFixedText = static_cast<FixedText*>(pWindow);
     417           0 :                     Window *pMnemonicWidget = pFixedText->get_mnemonic_widget();
     418             :                     SAL_WARN_IF(isContainerWindow(pFixedText->GetParent()) && !pMnemonicWidget,
     419             :                         "vcl.a11y", "label missing mnemonic_widget?");
     420           0 :                     if (pMnemonicWidget)
     421           0 :                         return pMnemonicWidget;
     422             :                 }
     423             : 
     424             :                 // skip Static-Controls
     425           0 :                 if ( (pWindow->GetType() == WINDOW_FIXEDTEXT)   ||
     426           0 :                      (pWindow->GetType() == WINDOW_FIXEDLINE)   ||
     427           0 :                      (pWindow->GetType() == WINDOW_GROUPBOX) )
     428           0 :                     pWindow = pParent->ImplGetDlgWindow( i, DLGWINDOW_NEXT );
     429           0 :                 rIndex = i;
     430           0 :                 return pWindow;
     431             :             }
     432           0 :             nPos = aStr.indexOf( '~', nPos+1 );
     433             :         }
     434             : 
     435             :         // #i93011# it would have made sense to have this really recursive
     436             :         // right from the start. However this would cause unpredictable side effects now
     437             :         // so instead we have a style bit for some child windows, that want their
     438             :         // children checked for accelerators
     439           0 :         if( (pWindow->GetStyle() & WB_CHILDDLGCTRL) != 0 )
     440             :         {
     441             :             sal_uInt16  nChildIndex;
     442             :             sal_uInt16  nChildFormStart;
     443             :             sal_uInt16  nChildFormEnd;
     444             : 
     445             :             // get form start and end
     446             :             ::ImplFindDlgCtrlWindow( pWindow, NULL,
     447           0 :                                      nChildIndex, nChildFormStart, nChildFormEnd );
     448             :             Window* pAccelWin = ImplFindAccelWindow( pWindow, nChildIndex, cCharCode,
     449             :                                                      nChildFormStart, nChildFormEnd,
     450           0 :                                                      bCheckEnable );
     451           0 :             if( pAccelWin )
     452           0 :                 return pAccelWin;
     453             :         }
     454             : 
     455           0 :         if ( i == nStart )
     456           0 :             break;
     457             : 
     458           0 :         if ( i < nFormEnd )
     459             :         {
     460           0 :             pWindow = ImplGetNextWindow( pParent, i, i, bCheckEnable );
     461           0 :             if( ! pWindow )
     462           0 :                 pWindow = ImplGetChildWindow( pParent, nFormStart, i, bCheckEnable );
     463             :         }
     464             :         else
     465           0 :             pWindow = ImplGetChildWindow( pParent, nFormStart, i, bCheckEnable );
     466           0 :     }
     467             : 
     468           0 :     return NULL;
     469             : }
     470             : 
     471          11 : void Window::ImplControlFocus( sal_uInt16 nFlags )
     472             : {
     473          11 :     if ( nFlags & GETFOCUS_MNEMONIC )
     474             :     {
     475           0 :         if ( GetType() == WINDOW_RADIOBUTTON )
     476             :         {
     477           0 :             if ( !((RadioButton*)this)->IsChecked() )
     478           0 :                 ((RadioButton*)this)->ImplCallClick( true, nFlags );
     479             :             else
     480           0 :                 ImplGrabFocus( nFlags );
     481             :         }
     482             :         else
     483             :         {
     484           0 :             ImplGrabFocus( nFlags );
     485           0 :             if ( nFlags & GETFOCUS_UNIQUEMNEMONIC )
     486             :             {
     487           0 :                 if ( GetType() == WINDOW_CHECKBOX )
     488           0 :                     ((CheckBox*)this)->ImplCheck();
     489           0 :                 else if ( mpWindowImpl->mbPushButton )
     490             :                 {
     491           0 :                     ((PushButton*)this)->SetPressed( true );
     492           0 :                     ((PushButton*)this)->SetPressed( false );
     493           0 :                     ((PushButton*)this)->Click();
     494             :                 }
     495             :             }
     496             :         }
     497             :     }
     498             :     else
     499             :     {
     500          11 :         if ( GetType() == WINDOW_RADIOBUTTON )
     501             :         {
     502           0 :             if ( !((RadioButton*)this)->IsChecked() )
     503           0 :                 ((RadioButton*)this)->ImplCallClick( true, nFlags );
     504             :             else
     505           0 :                 ImplGrabFocus( nFlags );
     506             :         }
     507             :         else
     508          11 :             ImplGrabFocus( nFlags );
     509             :     }
     510          11 : }
     511             : 
     512             : namespace
     513             : {
     514           0 :     bool isSuitableDestination(Window *pWindow)
     515             :     {
     516           0 :         return (pWindow && isVisibleInLayout(pWindow) &&
     517           0 :                 isEnabledInLayout(pWindow) && pWindow->IsInputEnabled() &&
     518             :                 //Pure window shouldn't get window after controls such as
     519             :                 //buttons.
     520           0 :                 (pWindow->GetType() != WINDOW_WINDOW && pWindow->GetType() != WINDOW_SYSWINDOW &&
     521           0 :                   pWindow->GetType() != WINDOW_WORKWINDOW && pWindow->GetType() != WINDOW_CONTROL)
     522           0 :                );
     523             :     }
     524             : 
     525           0 :     bool focusNextInGroup(std::vector<RadioButton*>::iterator aStart, std::vector<RadioButton*> &rGroup)
     526             :     {
     527           0 :         std::vector<RadioButton*>::iterator aI(aStart);
     528             : 
     529           0 :         if (aStart != rGroup.end())
     530           0 :             ++aI;
     531             : 
     532           0 :         for (; aI != rGroup.end(); ++aI)
     533             :         {
     534           0 :             Window *pWindow = *aI;
     535             : 
     536           0 :             if (isSuitableDestination(pWindow))
     537             :             {
     538           0 :                 pWindow->ImplControlFocus( GETFOCUS_CURSOR | GETFOCUS_FORWARD );
     539           0 :                 return true;
     540             :             }
     541             :         }
     542             : 
     543           0 :         for (aI = rGroup.begin(); aI != aStart; ++aI)
     544             :         {
     545           0 :             Window *pWindow = *aI;
     546             : 
     547           0 :             if (isSuitableDestination(pWindow))
     548             :             {
     549           0 :                 pWindow->ImplControlFocus( GETFOCUS_CURSOR | GETFOCUS_FORWARD );
     550           0 :                 return true;
     551             :             }
     552             :         }
     553             : 
     554           0 :         return false;
     555             :     }
     556             : 
     557           0 :     bool nextInGroup(RadioButton *pSourceWindow, bool bBackward)
     558             :     {
     559           0 :         std::vector<RadioButton*> aGroup(pSourceWindow->GetRadioButtonGroup(true));
     560             : 
     561           0 :         if (aGroup.size() == 1) //only one button in group
     562           0 :             return false;
     563             : 
     564           0 :         if (bBackward)
     565           0 :             std::reverse(aGroup.begin(), aGroup.end());
     566             : 
     567           0 :         std::vector<RadioButton*>::iterator aStart(std::find(aGroup.begin(), aGroup.end(), pSourceWindow));
     568             : 
     569             :         assert(aStart != aGroup.end());
     570             : 
     571           0 :         return focusNextInGroup(aStart, aGroup);
     572             :     }
     573             : }
     574             : 
     575           0 : bool Window::ImplDlgCtrl( const KeyEvent& rKEvt, bool bKeyInput )
     576             : {
     577           0 :     KeyCode aKeyCode = rKEvt.GetKeyCode();
     578           0 :     sal_uInt16  nKeyCode = aKeyCode.GetCode();
     579             :     Window* pSWindow;
     580             :     Window* pTempWindow;
     581             :     Window* pButtonWindow;
     582             :     sal_uInt16  i;
     583             :     sal_uInt16  iButton;
     584             :     sal_uInt16  iButtonStart;
     585             :     sal_uInt16  iTemp;
     586             :     sal_uInt16  nIndex;
     587             :     sal_uInt16  nFormStart;
     588             :     sal_uInt16  nFormEnd;
     589             :     sal_uInt16  nDlgCtrlFlags;
     590             : 
     591             :     // we cannot take over control without Focus-window
     592           0 :     Window* pFocusWindow = Application::GetFocusWindow();
     593           0 :     if ( !pFocusWindow || !ImplIsWindowOrChild( pFocusWindow ) )
     594           0 :         return false;
     595             : 
     596             :     // find Focus-Window in the child list
     597             :     pSWindow = ::ImplFindDlgCtrlWindow( this, pFocusWindow,
     598           0 :                                         nIndex, nFormStart, nFormEnd );
     599           0 :     if ( !pSWindow )
     600           0 :         return false;
     601           0 :     i = nIndex;
     602             : 
     603           0 :     nDlgCtrlFlags = 0;
     604           0 :     pTempWindow = pSWindow;
     605           0 :     do
     606             :     {
     607           0 :         nDlgCtrlFlags |= pTempWindow->GetDialogControlFlags();
     608           0 :         if ( pTempWindow == this )
     609           0 :             break;
     610           0 :         pTempWindow = pTempWindow->ImplGetParent();
     611             :     }
     612             :     while ( pTempWindow );
     613             : 
     614           0 :     pButtonWindow = NULL;
     615             : 
     616           0 :     if ( nKeyCode == KEY_RETURN )
     617             :     {
     618             :         // search first for a DefPushButton/CancelButton
     619           0 :         pButtonWindow = ImplGetChildWindow( this, nFormStart, iButton, true );
     620           0 :         iButtonStart = iButton;
     621           0 :         while ( pButtonWindow )
     622             :         {
     623           0 :             if ( (pButtonWindow->GetStyle() & WB_DEFBUTTON) &&
     624             :                  pButtonWindow->mpWindowImpl->mbPushButton )
     625           0 :                 break;
     626             : 
     627           0 :             pButtonWindow = ImplGetNextWindow( this, iButton, iButton, true );
     628           0 :             if ( (iButton <= iButtonStart) || (iButton > nFormEnd) )
     629           0 :                 pButtonWindow = NULL;
     630             :         }
     631             : 
     632           0 :         if ( bKeyInput && !pButtonWindow && (nDlgCtrlFlags & WINDOW_DLGCTRL_RETURN) )
     633             :         {
     634             :             sal_uInt16  nType;
     635           0 :             sal_uInt16  nGetFocusFlags = GETFOCUS_TAB;
     636             :             sal_uInt16  nNewIndex;
     637             :             sal_uInt16  iStart;
     638           0 :             if ( aKeyCode.IsShift() )
     639             :             {
     640           0 :                 nType = DLGWINDOW_PREV;
     641           0 :                 nGetFocusFlags |= GETFOCUS_BACKWARD;
     642             :             }
     643             :             else
     644             :             {
     645           0 :                 nType = DLGWINDOW_NEXT;
     646           0 :                 nGetFocusFlags |= GETFOCUS_FORWARD;
     647             :             }
     648           0 :             iStart = i;
     649           0 :             pTempWindow = ImplGetDlgWindow( i, nType, nFormStart, nFormEnd, &nNewIndex );
     650           0 :             while ( pTempWindow && (pTempWindow != pSWindow) )
     651             :             {
     652           0 :                 if ( !pTempWindow->mpWindowImpl->mbPushButton )
     653             :                 {
     654             :                     // get Around-Flag
     655           0 :                     if ( nType == DLGWINDOW_PREV )
     656             :                     {
     657           0 :                         if ( nNewIndex > iStart )
     658           0 :                             nGetFocusFlags |= GETFOCUS_AROUND;
     659             :                     }
     660             :                     else
     661             :                     {
     662           0 :                         if ( nNewIndex < iStart )
     663           0 :                             nGetFocusFlags |= GETFOCUS_AROUND;
     664             :                     }
     665           0 :                     pTempWindow->ImplControlFocus( nGetFocusFlags );
     666           0 :                     return true;
     667             :                 }
     668             :                 else
     669             :                 {
     670           0 :                     i = nNewIndex;
     671           0 :                     pTempWindow = ImplGetDlgWindow( i, nType, nFormStart, nFormEnd, &nNewIndex );
     672             :                 }
     673           0 :                 if ( (i <= iStart) || (i > nFormEnd) )
     674           0 :                     pTempWindow = NULL;
     675             :             }
     676             :             // if this is the same window, simulate a Get/LoseFocus,
     677             :             // in case AROUND is being processed
     678           0 :             if ( pTempWindow && (pTempWindow == pSWindow) )
     679             :             {
     680           0 :                 NotifyEvent aNEvt1( EVENT_LOSEFOCUS, pSWindow );
     681           0 :                 if ( !ImplCallPreNotify( aNEvt1 ) )
     682           0 :                     pSWindow->LoseFocus();
     683           0 :                 pSWindow->mpWindowImpl->mnGetFocusFlags = nGetFocusFlags | GETFOCUS_AROUND;
     684           0 :                 NotifyEvent aNEvt2( EVENT_GETFOCUS, pSWindow );
     685           0 :                 if ( !ImplCallPreNotify( aNEvt2 ) )
     686           0 :                     pSWindow->GetFocus();
     687           0 :                 pSWindow->mpWindowImpl->mnGetFocusFlags = 0;
     688           0 :                 return true;
     689             :             }
     690             :         }
     691             :     }
     692           0 :     else if ( nKeyCode == KEY_ESCAPE )
     693             :     {
     694             :         // search first for a DefPushButton/CancelButton
     695           0 :         pButtonWindow = ImplGetChildWindow( this, nFormStart, iButton, true );
     696           0 :         iButtonStart = iButton;
     697           0 :         while ( pButtonWindow )
     698             :         {
     699           0 :             if ( pButtonWindow->GetType() == WINDOW_CANCELBUTTON )
     700           0 :                 break;
     701             : 
     702           0 :             pButtonWindow = ImplGetNextWindow( this, iButton, iButton, true );
     703           0 :             if ( (iButton <= iButtonStart) || (iButton > nFormEnd) )
     704           0 :                 pButtonWindow = NULL;
     705             :         }
     706             : 
     707           0 :         if ( bKeyInput && mpWindowImpl->mpDlgCtrlDownWindow )
     708             :         {
     709           0 :             if ( mpWindowImpl->mpDlgCtrlDownWindow != pButtonWindow )
     710             :             {
     711           0 :                 ((PushButton*)mpWindowImpl->mpDlgCtrlDownWindow)->SetPressed( false );
     712           0 :                 mpWindowImpl->mpDlgCtrlDownWindow = NULL;
     713           0 :                 return true;
     714             :             }
     715             :         }
     716             :     }
     717           0 :     else if ( bKeyInput )
     718             :     {
     719           0 :         if ( nKeyCode == KEY_TAB )
     720             :         {
     721             :             // do not skip Alt key, for MS Windows
     722           0 :             if ( !aKeyCode.IsMod2() )
     723             :             {
     724             :                 sal_uInt16  nType;
     725           0 :                 sal_uInt16  nGetFocusFlags = GETFOCUS_TAB;
     726             :                 sal_uInt16  nNewIndex;
     727           0 :                 bool        bFormular = false;
     728             : 
     729             :                 // for Ctrl-Tab check if we want to jump to next template
     730           0 :                 if ( aKeyCode.IsMod1() )
     731             :                 {
     732             :                     // search group
     733           0 :                     Window* pFormularFirstWindow = NULL;
     734           0 :                     Window* pLastFormularFirstWindow = NULL;
     735           0 :                     pTempWindow = ImplGetChildWindow( this, 0, iTemp, false );
     736           0 :                     Window* pPrevFirstFormularFirstWindow = NULL;
     737           0 :                     Window* pFirstFormularFirstWindow = pTempWindow;
     738           0 :                     while ( pTempWindow )
     739             :                     {
     740           0 :                         if ( pTempWindow->ImplGetWindow()->IsDialogControlStart() )
     741             :                         {
     742           0 :                             if ( iTemp != 0 )
     743           0 :                                 bFormular = true;
     744           0 :                             if ( aKeyCode.IsShift() )
     745             :                             {
     746           0 :                                 if ( iTemp <= nIndex )
     747           0 :                                     pFormularFirstWindow = pPrevFirstFormularFirstWindow;
     748           0 :                                 pPrevFirstFormularFirstWindow = pTempWindow;
     749             :                             }
     750             :                             else
     751             :                             {
     752           0 :                                 if ( (iTemp > nIndex) && !pFormularFirstWindow )
     753           0 :                                     pFormularFirstWindow = pTempWindow;
     754             :                             }
     755           0 :                             pLastFormularFirstWindow = pTempWindow;
     756             :                         }
     757             : 
     758           0 :                         pTempWindow = ImplGetNextWindow( this, iTemp, iTemp, false );
     759           0 :                         if ( !iTemp )
     760           0 :                             pTempWindow = NULL;
     761             :                     }
     762             : 
     763           0 :                     if ( bFormular )
     764             :                     {
     765           0 :                         if ( !pFormularFirstWindow )
     766             :                         {
     767           0 :                             if ( aKeyCode.IsShift() )
     768           0 :                                 pFormularFirstWindow = pLastFormularFirstWindow;
     769             :                             else
     770           0 :                                 pFormularFirstWindow = pFirstFormularFirstWindow;
     771             :                         }
     772             : 
     773           0 :                         sal_uInt16 nFoundFormStart = 0;
     774           0 :                         sal_uInt16 nFoundFormEnd = 0;
     775           0 :                         sal_uInt16 nTempIndex = 0;
     776           0 :                         if ( ::ImplFindDlgCtrlWindow( this, pFormularFirstWindow, nTempIndex,
     777           0 :                                                       nFoundFormStart, nFoundFormEnd ) )
     778             :                         {
     779           0 :                             nTempIndex = nFoundFormStart;
     780           0 :                             pFormularFirstWindow = ImplGetDlgWindow( nTempIndex, DLGWINDOW_FIRST, nFoundFormStart, nFoundFormEnd );
     781           0 :                             if ( pFormularFirstWindow )
     782             :                             {
     783           0 :                                 pFormularFirstWindow->ImplControlFocus();
     784           0 :                                 return true;
     785             :                             }
     786             :                         }
     787             :                     }
     788             :                 }
     789             : 
     790           0 :                 if ( !bFormular )
     791             :                 {
     792             :                     // Only use Ctrl-TAB if it was allowed for the whole
     793             :                     // dialog or for the current control (#103667#)
     794           0 :                     if ( !aKeyCode.IsMod1() || (nDlgCtrlFlags & WINDOW_DLGCTRL_MOD1TAB) ||
     795           0 :                         ( pSWindow->GetStyle() & WINDOW_DLGCTRL_MOD1TAB) )
     796             :                     {
     797           0 :                         if ( aKeyCode.IsShift() )
     798             :                         {
     799           0 :                             nType = DLGWINDOW_PREV;
     800           0 :                             nGetFocusFlags |= GETFOCUS_BACKWARD;
     801             :                         }
     802             :                         else
     803             :                         {
     804           0 :                             nType = DLGWINDOW_NEXT;
     805           0 :                             nGetFocusFlags |= GETFOCUS_FORWARD;
     806             :                         }
     807           0 :                         Window* pWindow = ImplGetDlgWindow( i, nType, nFormStart, nFormEnd, &nNewIndex );
     808             :                         // if this is the same window, simulate a Get/LoseFocus,
     809             :                         // in case AROUND is being processed
     810           0 :                         if ( pWindow == pSWindow )
     811             :                         {
     812           0 :                             NotifyEvent aNEvt1( EVENT_LOSEFOCUS, pSWindow );
     813           0 :                             if ( !ImplCallPreNotify( aNEvt1 ) )
     814           0 :                                 pSWindow->LoseFocus();
     815           0 :                             pSWindow->mpWindowImpl->mnGetFocusFlags = nGetFocusFlags | GETFOCUS_AROUND;
     816           0 :                             NotifyEvent aNEvt2( EVENT_GETFOCUS, pSWindow );
     817           0 :                             if ( !ImplCallPreNotify( aNEvt2 ) )
     818           0 :                                 pSWindow->GetFocus();
     819           0 :                             pSWindow->mpWindowImpl->mnGetFocusFlags = 0;
     820           0 :                             return true;
     821             :                         }
     822           0 :                         else if ( pWindow )
     823             :                         {
     824             :                             // get Around-Flag
     825           0 :                             if ( nType == DLGWINDOW_PREV )
     826             :                             {
     827           0 :                                 if ( nNewIndex > i )
     828           0 :                                     nGetFocusFlags |= GETFOCUS_AROUND;
     829             :                             }
     830             :                             else
     831             :                             {
     832           0 :                                 if ( nNewIndex < i )
     833           0 :                                     nGetFocusFlags |= GETFOCUS_AROUND;
     834             :                             }
     835           0 :                             pWindow->ImplControlFocus( nGetFocusFlags );
     836           0 :                             return true;
     837             :                         }
     838             :                     }
     839             :                 }
     840             :             }
     841             :         }
     842           0 :         else if ( (nKeyCode == KEY_LEFT) || (nKeyCode == KEY_UP) )
     843             :         {
     844           0 :             if (pSWindow->GetType() == WINDOW_RADIOBUTTON)
     845           0 :                 return nextInGroup(static_cast<RadioButton*>(pSWindow), true);
     846             :             else
     847             :             {
     848           0 :                 WinBits nStyle = pSWindow->GetStyle();
     849           0 :                 if ( !(nStyle & WB_GROUP) )
     850             :                 {
     851           0 :                     Window* pWindow = prevLogicalChildOfParent(this, pSWindow);
     852           0 :                     while ( pWindow )
     853             :                     {
     854           0 :                         pWindow = pWindow->ImplGetWindow();
     855             : 
     856           0 :                         nStyle = pWindow->GetStyle();
     857             : 
     858           0 :                         if (isSuitableDestination(pWindow))
     859             :                         {
     860           0 :                             if ( pWindow != pSWindow )
     861           0 :                                 pWindow->ImplControlFocus( GETFOCUS_CURSOR | GETFOCUS_BACKWARD );
     862           0 :                             return true;
     863             :                         }
     864             : 
     865           0 :                         if ( nStyle & WB_GROUP )
     866           0 :                             break;
     867             : 
     868           0 :                         pWindow = prevLogicalChildOfParent(this, pWindow);
     869             :                     }
     870             :                 }
     871           0 :             }
     872             :         }
     873           0 :         else if ( (nKeyCode == KEY_RIGHT) || (nKeyCode == KEY_DOWN) )
     874             :         {
     875           0 :             if (pSWindow->GetType() == WINDOW_RADIOBUTTON)
     876           0 :                 return nextInGroup(static_cast<RadioButton*>(pSWindow), false);
     877             :             else
     878             :             {
     879           0 :                 Window* pWindow = nextLogicalChildOfParent(this, pSWindow);
     880           0 :                 while ( pWindow )
     881             :                 {
     882           0 :                     pWindow = pWindow->ImplGetWindow();
     883             : 
     884           0 :                     WinBits nStyle = pWindow->GetStyle();
     885             : 
     886           0 :                     if ( nStyle & WB_GROUP )
     887           0 :                         break;
     888             : 
     889           0 :                     if (isSuitableDestination(pWindow))
     890             :                     {
     891           0 :                         pWindow->ImplControlFocus( GETFOCUS_CURSOR | GETFOCUS_BACKWARD );
     892           0 :                         return true;
     893             :                     }
     894             : 
     895           0 :                     pWindow = nextLogicalChildOfParent(this, pWindow);
     896             :                 }
     897           0 :             }
     898             :         }
     899             :         else
     900             :         {
     901           0 :             sal_Unicode c = rKEvt.GetCharCode();
     902           0 :             if ( c )
     903             :             {
     904           0 :                 pSWindow = ::ImplFindAccelWindow( this, i, c, nFormStart, nFormEnd );
     905           0 :                 if ( pSWindow )
     906             :                 {
     907           0 :                     sal_uInt16 nGetFocusFlags = GETFOCUS_MNEMONIC;
     908           0 :                     if ( pSWindow == ::ImplFindAccelWindow( this, i, c, nFormStart, nFormEnd ) )
     909           0 :                         nGetFocusFlags |= GETFOCUS_UNIQUEMNEMONIC;
     910           0 :                     pSWindow->ImplControlFocus( nGetFocusFlags );
     911           0 :                     return true;
     912             :                 }
     913             :             }
     914             :         }
     915             :     }
     916             : 
     917           0 :     if (isSuitableDestination(pButtonWindow))
     918             :     {
     919           0 :         if ( bKeyInput )
     920             :         {
     921           0 :             if ( mpWindowImpl->mpDlgCtrlDownWindow && (mpWindowImpl->mpDlgCtrlDownWindow != pButtonWindow) )
     922             :             {
     923           0 :                 ((PushButton*)mpWindowImpl->mpDlgCtrlDownWindow)->SetPressed( false );
     924           0 :                 mpWindowImpl->mpDlgCtrlDownWindow = NULL;
     925             :             }
     926             : 
     927           0 :             ((PushButton*)pButtonWindow)->SetPressed( true );
     928           0 :             mpWindowImpl->mpDlgCtrlDownWindow = pButtonWindow;
     929             :         }
     930           0 :         else if ( mpWindowImpl->mpDlgCtrlDownWindow == pButtonWindow )
     931             :         {
     932           0 :             mpWindowImpl->mpDlgCtrlDownWindow = NULL;
     933           0 :             ((PushButton*)pButtonWindow)->SetPressed( false );
     934           0 :             ((PushButton*)pButtonWindow)->Click();
     935             :         }
     936             : 
     937           0 :         return true;
     938             :     }
     939             : 
     940           0 :     return false;
     941             : }
     942             : 
     943             : // checks if this window has dialog control
     944           0 : bool Window::ImplHasDlgCtrl()
     945             : {
     946             :     Window* pDlgCtrlParent;
     947             : 
     948             :     // lookup window for dialog control
     949           0 :     pDlgCtrlParent = ImplGetParent();
     950           0 :     while ( pDlgCtrlParent &&
     951           0 :             !pDlgCtrlParent->ImplIsOverlapWindow() &&
     952           0 :             ((pDlgCtrlParent->GetStyle() & (WB_DIALOGCONTROL | WB_NODIALOGCONTROL)) != WB_DIALOGCONTROL) )
     953           0 :         pDlgCtrlParent = pDlgCtrlParent->ImplGetParent();
     954             : 
     955           0 :     if ( !pDlgCtrlParent || ((pDlgCtrlParent->GetStyle() & (WB_DIALOGCONTROL | WB_NODIALOGCONTROL)) != WB_DIALOGCONTROL) )
     956           0 :         return false;
     957             :     else
     958           0 :         return true;
     959             : }
     960             : 
     961         327 : void Window::ImplDlgCtrlNextWindow()
     962             : {
     963             :     Window* pDlgCtrlParent;
     964             :     Window* pDlgCtrl;
     965             :     Window* pSWindow;
     966             :     sal_uInt16  nIndex;
     967             :     sal_uInt16  nFormStart;
     968             :     sal_uInt16  nFormEnd;
     969             : 
     970             :     // lookup window for dialog control
     971         327 :     pDlgCtrl = this;
     972         327 :     pDlgCtrlParent = ImplGetParent();
     973        3597 :     while ( pDlgCtrlParent &&
     974        2943 :             !pDlgCtrlParent->ImplIsOverlapWindow() &&
     975        1308 :             ((pDlgCtrlParent->GetStyle() & (WB_DIALOGCONTROL | WB_NODIALOGCONTROL)) != WB_DIALOGCONTROL) )
     976        1308 :         pDlgCtrlParent = pDlgCtrlParent->ImplGetParent();
     977             : 
     978         327 : if ( !pDlgCtrlParent || (GetStyle() & WB_NODIALOGCONTROL) || ((pDlgCtrlParent->GetStyle() & (WB_DIALOGCONTROL | WB_NODIALOGCONTROL)) != WB_DIALOGCONTROL) )
     979         654 :         return;
     980             : 
     981             :     // lookup window in child list
     982             :     pSWindow = ::ImplFindDlgCtrlWindow( pDlgCtrlParent, pDlgCtrl,
     983           0 :                                         nIndex, nFormStart, nFormEnd );
     984           0 :     if ( !pSWindow )
     985           0 :         return;
     986             : 
     987           0 :     Window* pWindow = pDlgCtrlParent->ImplGetDlgWindow( nIndex, DLGWINDOW_NEXT, nFormStart, nFormEnd );
     988           0 :     if ( pWindow && (pWindow != pSWindow) )
     989           0 :         pWindow->ImplControlFocus();
     990             : }
     991             : 
     992        4121 : static void ImplDlgCtrlUpdateDefButton( Window* pParent, Window* pFocusWindow,
     993             :                                         bool bGetFocus )
     994             : {
     995        4121 :     PushButton* pOldDefButton   = NULL;
     996        4121 :     PushButton* pNewDefButton   = NULL;
     997             :     Window*     pSWindow;
     998             :     sal_uInt16      i;
     999             :     sal_uInt16      nFormStart;
    1000             :     sal_uInt16      nFormEnd;
    1001             : 
    1002             :     // find template
    1003        4121 :     pSWindow = ::ImplFindDlgCtrlWindow( pParent, pFocusWindow, i, nFormStart, nFormEnd );
    1004        4121 :     if ( !pSWindow )
    1005             :     {
    1006        4003 :         nFormStart = 0;
    1007        4003 :         nFormEnd = 0xFFFF;
    1008             :     }
    1009             : 
    1010        4121 :     pSWindow = ImplGetChildWindow( pParent, nFormStart, i, false );
    1011       10783 :     while ( pSWindow )
    1012             :     {
    1013        2541 :         if ( pSWindow->ImplIsPushButton() )
    1014             :         {
    1015         275 :             PushButton* pPushButton = (PushButton*)pSWindow;
    1016         275 :             if ( pPushButton->ImplIsDefButton() )
    1017           3 :                 pOldDefButton = pPushButton;
    1018         275 :             if ( pPushButton->HasChildPathFocus() )
    1019           4 :                 pNewDefButton = pPushButton;
    1020         271 :             else if ( !pNewDefButton && (pPushButton->GetStyle() & WB_DEFBUTTON) )
    1021           0 :                 pNewDefButton = pPushButton;
    1022             :         }
    1023             : 
    1024        2541 :         pSWindow = ImplGetNextWindow( pParent, i, i, false );
    1025        2541 :         if ( !i || (i > nFormEnd) )
    1026         506 :             pSWindow = NULL;
    1027             :     }
    1028             : 
    1029        4121 :     if ( !bGetFocus )
    1030             :     {
    1031             :         sal_uInt16 nDummy;
    1032        2068 :         Window* pNewFocusWindow = Application::GetFocusWindow();
    1033        2068 :         if ( !pNewFocusWindow || !pParent->ImplIsWindowOrChild( pNewFocusWindow ) )
    1034        1921 :             pNewDefButton = NULL;
    1035         346 :         else if ( !::ImplFindDlgCtrlWindow( pParent, pNewFocusWindow, i, nDummy, nDummy ) ||
    1036         199 :                   (i < nFormStart) || (i > nFormEnd) )
    1037          95 :             pNewDefButton = NULL;
    1038             :     }
    1039             : 
    1040        4121 :     if ( pOldDefButton != pNewDefButton )
    1041             :     {
    1042           3 :         if ( pOldDefButton )
    1043           1 :             pOldDefButton->ImplSetDefButton( false );
    1044           3 :         if ( pNewDefButton )
    1045           2 :             pNewDefButton->ImplSetDefButton( true );
    1046             :     }
    1047        4121 : }
    1048             : 
    1049        4121 : void Window::ImplDlgCtrlFocusChanged( Window* pWindow, bool bGetFocus )
    1050             : {
    1051        4121 :     if ( mpWindowImpl->mpDlgCtrlDownWindow && !bGetFocus )
    1052             :     {
    1053           0 :         ((PushButton*)mpWindowImpl->mpDlgCtrlDownWindow)->SetPressed( false );
    1054           0 :         mpWindowImpl->mpDlgCtrlDownWindow = NULL;
    1055             :     }
    1056             : 
    1057        4121 :     ImplDlgCtrlUpdateDefButton( this, pWindow, bGetFocus );
    1058        4121 : }
    1059             : 
    1060           0 : Window* Window::ImplFindDlgCtrlWindow( Window* pWindow )
    1061             : {
    1062             :     sal_uInt16  nIndex;
    1063             :     sal_uInt16  nFormStart;
    1064             :     sal_uInt16  nFormEnd;
    1065             : 
    1066             :     // find Focus-Window in the Child-List and return
    1067           0 :     return ::ImplFindDlgCtrlWindow( this, pWindow, nIndex, nFormStart, nFormEnd );
    1068             : }
    1069             : 
    1070           1 : Window* Window::GetParentLabelFor( const Window* ) const
    1071             : {
    1072           1 :     return NULL;
    1073             : }
    1074             : 
    1075        2076 : Window* Window::GetParentLabeledBy( const Window* ) const
    1076             : {
    1077        2076 :     return NULL;
    1078             : }
    1079             : 
    1080           1 : static sal_Unicode getAccel( const OUString& rStr )
    1081             : {
    1082           1 :     sal_Unicode nChar = 0;
    1083           1 :     sal_Int32 nPos = 0;
    1084           1 :     do
    1085             :     {
    1086           1 :         nPos = rStr.indexOf( '~', nPos );
    1087           1 :         if( nPos != -1 && nPos < rStr.getLength() )
    1088           0 :             nChar = rStr[ ++nPos ];
    1089             :         else
    1090           1 :             nChar = 0;
    1091             :     } while( nChar == '~' );
    1092           1 :     return nChar;
    1093             : }
    1094             : 
    1095           2 : static Window* ImplGetLabelFor( Window* pFrameWindow, WindowType nMyType, Window* pLabel, sal_Unicode nAccel )
    1096             : {
    1097           2 :     Window* pWindow = NULL;
    1098             : 
    1099           2 :     if( nMyType == WINDOW_FIXEDTEXT     ||
    1100           0 :         nMyType == WINDOW_FIXEDLINE     ||
    1101             :         nMyType == WINDOW_GROUPBOX )
    1102             :     {
    1103             :         // #i100833# MT 2010/02: Group box and fixed lines can also lable a fixed text.
    1104             :         // See tools/options/print for example.
    1105           2 :         bool bThisIsAGroupControl = (nMyType == WINDOW_GROUPBOX) || (nMyType == WINDOW_FIXEDLINE);
    1106             :         // get index, form start and form end
    1107           2 :         sal_uInt16 nIndex=0, nFormStart=0, nFormEnd=0;
    1108             :         ::ImplFindDlgCtrlWindow( pFrameWindow,
    1109             :                                            pLabel,
    1110             :                                            nIndex,
    1111             :                                            nFormStart,
    1112           2 :                                            nFormEnd );
    1113           2 :         if( nAccel )
    1114             :         {
    1115             :             // find the accelerated window
    1116             :             pWindow = ::ImplFindAccelWindow( pFrameWindow,
    1117             :                                              nIndex,
    1118             :                                              nAccel,
    1119             :                                              nFormStart,
    1120             :                                              nFormEnd,
    1121           0 :                                              false );
    1122             :         }
    1123             :         else
    1124             :         {
    1125             :             // find the next control; if that is a fixed text
    1126             :             // fixed line or group box, then return NULL
    1127           4 :             while( nIndex < nFormEnd )
    1128             :             {
    1129           0 :                 nIndex++;
    1130             :                 Window* pSWindow = ::ImplGetChildWindow( pFrameWindow,
    1131             :                                                  nIndex,
    1132             :                                                  nIndex,
    1133           0 :                                                  false );
    1134           0 :                 if( pSWindow && isVisibleInLayout(pSWindow) && ! (pSWindow->GetStyle() & WB_NOLABEL) )
    1135             :                 {
    1136           0 :                     WindowType nType = pSWindow->GetType();
    1137           0 :                     if( nType != WINDOW_FIXEDTEXT   &&
    1138           0 :                         nType != WINDOW_FIXEDLINE   &&
    1139             :                         nType != WINDOW_GROUPBOX )
    1140             :                     {
    1141           0 :                         pWindow = pSWindow;
    1142             :                     }
    1143           0 :                     else if( bThisIsAGroupControl && ( nType == WINDOW_FIXEDTEXT ) )
    1144             :                     {
    1145           0 :                         pWindow = pSWindow;
    1146             :                     }
    1147           0 :                     break;
    1148             :                 }
    1149             :             }
    1150             :         }
    1151             :     }
    1152             : 
    1153           2 :     return pWindow;
    1154             : }
    1155             : 
    1156        6685 : Window* Window::getLegacyNonLayoutAccessibleRelationLabelFor() const
    1157             : {
    1158        6685 :     Window* pWindow = NULL;
    1159        6685 :     Window* pFrameWindow = ImplGetFrameWindow();
    1160             : 
    1161        6685 :     WinBits nFrameStyle = pFrameWindow->GetStyle();
    1162        6685 :     if( ! ( nFrameStyle & WB_DIALOGCONTROL )
    1163           1 :         || ( nFrameStyle & WB_NODIALOGCONTROL )
    1164             :         )
    1165        6684 :         return NULL;
    1166             : 
    1167           1 :     if ( mpWindowImpl->mpRealParent )
    1168           1 :         pWindow = mpWindowImpl->mpRealParent->GetParentLabelFor( this );
    1169             : 
    1170           1 :     if( pWindow )
    1171           0 :         return pWindow;
    1172             : 
    1173           1 :     sal_Unicode nAccel = getAccel( GetText() );
    1174             : 
    1175           1 :     pWindow = ImplGetLabelFor( pFrameWindow, GetType(), const_cast<Window*>(this), nAccel );
    1176           1 :     if( ! pWindow && mpWindowImpl->mpRealParent )
    1177           1 :         pWindow = ImplGetLabelFor( mpWindowImpl->mpRealParent, GetType(), const_cast<Window*>(this), nAccel );
    1178           1 :     return pWindow;
    1179             : }
    1180             : 
    1181        4152 : static Window* ImplGetLabeledBy( Window* pFrameWindow, WindowType nMyType, Window* pLabeled )
    1182             : {
    1183        4152 :     Window* pWindow = NULL;
    1184        4152 :     if ( (nMyType != WINDOW_GROUPBOX) && (nMyType != WINDOW_FIXEDLINE) )
    1185             :     {
    1186             :         // search for a control that labels this window
    1187             :         // a label is considered the last fixed text, fixed line or group box
    1188             :         // that comes before this control; with the exception of push buttons
    1189             :         // which are labeled only if the fixed text, fixed line or group box
    1190             :         // is directly before the control
    1191             : 
    1192             :         // get form start and form end and index of this control
    1193             :         sal_uInt16 nIndex, nFormStart, nFormEnd;
    1194             :         Window* pSWindow = ::ImplFindDlgCtrlWindow( pFrameWindow,
    1195             :                                                     pLabeled,
    1196             :                                                     nIndex,
    1197             :                                                     nFormStart,
    1198        4152 :                                                     nFormEnd );
    1199        4152 :         if( pSWindow && nIndex != nFormStart )
    1200             :         {
    1201         139 :             if( nMyType == WINDOW_PUSHBUTTON        ||
    1202         139 :                 nMyType == WINDOW_HELPBUTTON        ||
    1203         139 :                 nMyType == WINDOW_OKBUTTON      ||
    1204             :                 nMyType == WINDOW_CANCELBUTTON )
    1205             :             {
    1206           0 :                 nFormStart = nIndex-1;
    1207             :             }
    1208         278 :             for( sal_uInt16 nSearchIndex = nIndex-1; nSearchIndex >= nFormStart; nSearchIndex-- )
    1209             :             {
    1210         139 :                 sal_uInt16 nFoundIndex = 0;
    1211             :                 pSWindow = ::ImplGetChildWindow( pFrameWindow,
    1212             :                                                  nSearchIndex,
    1213             :                                                  nFoundIndex,
    1214         139 :                                                  false );
    1215         139 :                 if( pSWindow && isVisibleInLayout(pSWindow) && !(pSWindow->GetStyle() & WB_NOLABEL) )
    1216             :                 {
    1217         139 :                     WindowType nType = pSWindow->GetType();
    1218         139 :                     if ( ( nType == WINDOW_FIXEDTEXT    ||
    1219         139 :                           nType == WINDOW_FIXEDLINE ||
    1220             :                           nType == WINDOW_GROUPBOX ) )
    1221             :                     {
    1222             :                         // a fixed text can't be labeld by a fixed text.
    1223           0 :                         if ( ( nMyType != WINDOW_FIXEDTEXT ) || ( nType != WINDOW_FIXEDTEXT ) )
    1224           0 :                             pWindow = pSWindow;
    1225         139 :                         break;
    1226             :                     }
    1227             :                 }
    1228         139 :                 if( nFoundIndex > nSearchIndex || nSearchIndex == 0 )
    1229             :                     break;
    1230             :             }
    1231             :         }
    1232             :     }
    1233        4152 :     return pWindow;
    1234             : }
    1235             : 
    1236        2076 : Window* Window::getLegacyNonLayoutAccessibleRelationLabeledBy() const
    1237             : {
    1238        2076 :     Window* pWindow = NULL;
    1239        2076 :     Window* pFrameWindow = ImplGetFrameWindow();
    1240             : 
    1241        2076 :     if ( mpWindowImpl->mpRealParent )
    1242             :     {
    1243        2076 :         pWindow = mpWindowImpl->mpRealParent->GetParentLabeledBy( this );
    1244             : 
    1245        2076 :         if( pWindow )
    1246           0 :             return pWindow;
    1247             :     }
    1248             : 
    1249             :     // #i62723#, #104191# checkboxes and radiobuttons are not supposed to have labels
    1250        2076 :     if( GetType() == WINDOW_CHECKBOX || GetType() == WINDOW_RADIOBUTTON )
    1251           0 :         return NULL;
    1252             : 
    1253             : //    if( ! ( GetType() == WINDOW_FIXEDTEXT     ||
    1254             : //            GetType() == WINDOW_FIXEDLINE     ||
    1255             : //            GetType() == WINDOW_GROUPBOX ) )
    1256             :     // #i100833# MT 2010/02: Group box and fixed lines can also lable a fixed text.
    1257             :     // See tools/options/print for example.
    1258             : 
    1259        2076 :     pWindow = ImplGetLabeledBy( pFrameWindow, GetType(), const_cast<Window*>(this) );
    1260        2076 :     if( ! pWindow && mpWindowImpl->mpRealParent )
    1261        2076 :         pWindow = ImplGetLabeledBy( mpWindowImpl->mpRealParent, GetType(), const_cast<Window*>(this) );
    1262             : 
    1263        2076 :     return pWindow;
    1264             : }
    1265             : 
    1266           5 : Window* Window::getLegacyNonLayoutAccessibleRelationMemberOf() const
    1267             : {
    1268           5 :     Window* pWindow = NULL;
    1269           5 :     Window* pFrameWindow = GetParent();
    1270           5 :     if ( !pFrameWindow )
    1271             :     {
    1272           0 :         pFrameWindow = ImplGetFrameWindow();
    1273             :     }
    1274             :     // if( ! ( GetType() == WINDOW_FIXEDTEXT        ||
    1275          10 :     if( !( GetType() == WINDOW_FIXEDLINE ||
    1276           5 :         GetType() == WINDOW_GROUPBOX ) )
    1277             :     {
    1278             :         // search for a control that makes member of this window
    1279             :         // it is considered the last fixed line or group box
    1280             :         // that comes before this control; with the exception of push buttons
    1281             :         // which are labeled only if the fixed line or group box
    1282             :         // is directly before the control
    1283             :         // get form start and form end and index of this control
    1284             :         sal_uInt16 nIndex, nFormStart, nFormEnd;
    1285             :         Window* pSWindow = ::ImplFindDlgCtrlWindow( pFrameWindow,
    1286             :             const_cast<Window*>(this),
    1287             :             nIndex,
    1288             :             nFormStart,
    1289           5 :             nFormEnd );
    1290           5 :         if( pSWindow && nIndex != nFormStart )
    1291             :         {
    1292           0 :             if( GetType() == WINDOW_PUSHBUTTON      ||
    1293           0 :                 GetType() == WINDOW_HELPBUTTON      ||
    1294           0 :                 GetType() == WINDOW_OKBUTTON        ||
    1295           0 :                 GetType() == WINDOW_CANCELBUTTON )
    1296             :             {
    1297           0 :                 nFormStart = nIndex-1;
    1298             :             }
    1299           0 :             for( sal_uInt16 nSearchIndex = nIndex-1; nSearchIndex >= nFormStart; nSearchIndex-- )
    1300             :             {
    1301           0 :                 sal_uInt16 nFoundIndex = 0;
    1302             :                 pSWindow = ::ImplGetChildWindow( pFrameWindow,
    1303             :                     nSearchIndex,
    1304             :                     nFoundIndex,
    1305           0 :                     false );
    1306           0 :                 if( pSWindow && pSWindow->IsVisible() &&
    1307           0 :                     ( pSWindow->GetType() == WINDOW_FIXEDLINE   ||
    1308           0 :                     pSWindow->GetType() == WINDOW_GROUPBOX ) )
    1309             :                 {
    1310           0 :                     pWindow = pSWindow;
    1311           0 :                     break;
    1312             :                 }
    1313           0 :                 if( nFoundIndex > nSearchIndex || nSearchIndex == 0 )
    1314             :                     break;
    1315             :             }
    1316             :         }
    1317             :     }
    1318           5 :     return pWindow;
    1319             : }
    1320             : 
    1321           0 : KeyEvent Window::GetActivationKey() const
    1322             : {
    1323           0 :     KeyEvent aKeyEvent;
    1324             : 
    1325           0 :     sal_Unicode nAccel = getAccel( GetText() );
    1326           0 :     if( ! nAccel )
    1327             :     {
    1328           0 :         Window* pWindow = GetAccessibleRelationLabeledBy();
    1329           0 :         if( pWindow )
    1330           0 :             nAccel = getAccel( pWindow->GetText() );
    1331             :     }
    1332           0 :     if( nAccel )
    1333             :     {
    1334           0 :         sal_uInt16 nCode = 0;
    1335           0 :         if( nAccel >= 'a' && nAccel <= 'z' )
    1336           0 :             nCode = KEY_A + (nAccel-'a');
    1337           0 :         else if( nAccel >= 'A' && nAccel <= 'Z' )
    1338           0 :             nCode = KEY_A + (nAccel-'A');
    1339           0 :         else if( nAccel >= '0' && nAccel <= '9' )
    1340           0 :             nCode = KEY_0 + (nAccel-'0');
    1341           0 :         else if( nAccel == '.' )
    1342           0 :             nCode = KEY_POINT;
    1343           0 :         else if( nAccel == '-' )
    1344           0 :             nCode = KEY_SUBTRACT;
    1345           0 :         KeyCode aKeyCode( nCode, false, false, true, false );
    1346           0 :         aKeyEvent = KeyEvent( nAccel, aKeyCode );
    1347             :     }
    1348           0 :     return aKeyEvent;
    1349         516 : }
    1350             : 
    1351             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10