LCOV - code coverage report
Current view: top level - sfx2/source/sidebar - FocusManager.cxx (source / functions) Hit Total Coverage
Test: commit c8344322a7af75b84dd3ca8f78b05543a976dfd5 Lines: 90 294 30.6 %
Date: 2015-06-13 12:38:46 Functions: 17 30 56.7 %
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 "FocusManager.hxx"
      21             : #include "Panel.hxx"
      22             : #include "DeckTitleBar.hxx"
      23             : #include "PanelTitleBar.hxx"
      24             : #include <sfx2/sidebar/Tools.hxx>
      25             : #include "TitleBar.hxx"
      26             : #include <vcl/button.hxx>
      27             : #include <vcl/toolbox.hxx>
      28             : #include <toolkit/helper/vclunohelper.hxx>
      29             : 
      30             : namespace sfx2 { namespace sidebar {
      31             : 
      32           0 : FocusManager::FocusLocation::FocusLocation (const PanelComponent eComponent, const sal_Int32 nIndex)
      33             :     : meComponent(eComponent),
      34           0 :       mnIndex(nIndex)
      35             : {
      36           0 : }
      37             : 
      38        3155 : FocusManager::FocusManager(const std::function<void(const Panel&)>& rShowPanelFunctor)
      39             :     : mpDeckTitleBar(),
      40             :       maPanels(),
      41             :       maButtons(),
      42             :       maShowPanelFunctor(rShowPanelFunctor),
      43             :       mbObservingContentControlFocus(false),
      44             :       mpFirstFocusedContentControl(NULL),
      45        3155 :       mpLastFocusedWindow(NULL)
      46             : {
      47        3155 : }
      48             : 
      49        5626 : FocusManager::~FocusManager()
      50             : {
      51        2813 :     Clear();
      52        2813 : }
      53             : 
      54           0 : void FocusManager::GrabFocus()
      55             : {
      56           0 :     FocusDeckTitle();
      57           0 : }
      58             : 
      59       12937 : void FocusManager::Clear()
      60             : {
      61       12937 :     SetDeckTitle(NULL);
      62       12937 :     ClearPanels();
      63       12937 :     ClearButtons();
      64       12937 : }
      65             : 
      66       16702 : void FocusManager::ClearPanels()
      67             : {
      68       16702 :     std::vector<VclPtr<Panel> > aPanels;
      69       16702 :     aPanels.swap(maPanels);
      70       21075 :     for (auto iPanel(aPanels.begin()),iEnd(aPanels.end()); iPanel != iEnd; ++iPanel)
      71             :     {
      72        4373 :         UnregisterWindow(**iPanel);
      73        4373 :         if ((*iPanel)->GetTitleBar() != NULL)
      74             :         {
      75        4373 :             UnregisterWindow(*(*iPanel)->GetTitleBar());
      76        4373 :             UnregisterWindow((*iPanel)->GetTitleBar()->GetToolBox());
      77             :         }
      78             : 
      79        4373 :         (*iPanel)->RemoveChildEventListener(LINK(this, FocusManager, ChildEventListener));
      80       16702 :     }
      81       16702 : }
      82             : 
      83       16702 : void FocusManager::ClearButtons()
      84             : {
      85       16702 :     std::vector<VclPtr<Button> > aButtons;
      86       16702 :     aButtons.swap(maButtons);
      87       23368 :     for (auto iButton = aButtons.begin(); iButton != aButtons.end(); ++iButton)
      88             :     {
      89        6666 :         UnregisterWindow(**iButton);
      90       16702 :     }
      91       16702 : }
      92             : 
      93       16702 : void FocusManager::SetDeckTitle (DeckTitleBar* pDeckTitleBar)
      94             : {
      95       16702 :     if (mpDeckTitleBar != nullptr)
      96             :     {
      97        3765 :         UnregisterWindow(*mpDeckTitleBar);
      98        3765 :         UnregisterWindow(mpDeckTitleBar->GetToolBox());
      99             :     }
     100       16702 :     mpDeckTitleBar = pDeckTitleBar;
     101             : 
     102       16702 :     if (mpDeckTitleBar != nullptr)
     103             :     {
     104        3765 :         RegisterWindow(*mpDeckTitleBar);
     105        3765 :         RegisterWindow(mpDeckTitleBar->GetToolBox());
     106             :     }
     107       16702 : }
     108             : 
     109        3765 : void FocusManager::SetPanels (const SharedPanelContainer& rPanels)
     110             : {
     111        3765 :     ClearPanels();
     112        8138 :     for (auto iPanel = rPanels.begin(); iPanel != rPanels.end(); ++iPanel)
     113             :     {
     114        4373 :         RegisterWindow(**iPanel);
     115        4373 :         if ((*iPanel)->GetTitleBar() != NULL)
     116             :         {
     117        4373 :             RegisterWindow(*(*iPanel)->GetTitleBar());
     118        4373 :             RegisterWindow((*iPanel)->GetTitleBar()->GetToolBox());
     119             :         }
     120             : 
     121             :         // Register also as child event listener at the panel.
     122        4373 :         (*iPanel)->AddChildEventListener(LINK(this, FocusManager, ChildEventListener));
     123             : 
     124        4373 :         maPanels.push_back(iPanel->get());
     125             :     }
     126        3765 : }
     127             : 
     128        3765 : void FocusManager::SetButtons (const ::std::vector<Button*>& rButtons)
     129             : {
     130        3765 :     ClearButtons();
     131       10550 :     for (auto iButton = rButtons.begin(); iButton != rButtons.end(); ++iButton)
     132             :     {
     133        6785 :         RegisterWindow(**iButton);
     134        6785 :         maButtons.push_back(*iButton);
     135             :     }
     136        3765 : }
     137             : 
     138       27434 : void FocusManager::RegisterWindow (vcl::Window& rWindow)
     139             : {
     140       27434 :     rWindow.AddEventListener(LINK(this, FocusManager, WindowEventListener));
     141       27434 : }
     142             : 
     143       27434 : void FocusManager::UnregisterWindow (vcl::Window& rWindow)
     144             : {
     145       27434 :     rWindow.RemoveEventListener(LINK(this, FocusManager, WindowEventListener));
     146       27434 : }
     147             : 
     148           0 : FocusManager::FocusLocation FocusManager::GetFocusLocation (const vcl::Window& rWindow) const
     149             : {
     150             :     // Check the deck title.
     151           0 :     if (mpDeckTitleBar != nullptr)
     152             :     {
     153           0 :         if (mpDeckTitleBar == &rWindow)
     154           0 :             return FocusLocation(PC_DeckTitle, -1);
     155           0 :         else if (&mpDeckTitleBar->GetToolBox() == &rWindow)
     156           0 :             return FocusLocation(PC_DeckToolBox, -1);
     157             :     }
     158             : 
     159             :     // Search the panels.
     160           0 :     for (size_t nIndex = 0; nIndex < maPanels.size(); ++nIndex)
     161             :     {
     162           0 :         if (maPanels[nIndex] == &rWindow)
     163           0 :             return FocusLocation(PC_PanelContent, nIndex);
     164           0 :         TitleBar* pTitleBar = maPanels[nIndex]->GetTitleBar();
     165           0 :         if (pTitleBar == &rWindow)
     166           0 :             return FocusLocation(PC_PanelTitle, nIndex);
     167           0 :         if (pTitleBar!=NULL && &pTitleBar->GetToolBox()==&rWindow)
     168           0 :             return FocusLocation(PC_PanelToolBox, nIndex);
     169             :     }
     170             : 
     171             :     // Search the buttons.
     172           0 :     for (size_t nIndex=0; nIndex < maButtons.size(); ++nIndex)
     173             :     {
     174           0 :         if (maButtons[nIndex] == &rWindow)
     175           0 :             return FocusLocation(PC_TabBar, nIndex);
     176             :     }
     177           0 :     return FocusLocation(PC_None, -1);
     178             : }
     179             : 
     180           0 : void FocusManager::FocusDeckTitle()
     181             : {
     182           0 :     if (mpDeckTitleBar != nullptr)
     183             :     {
     184           0 :         if (IsDeckTitleVisible())
     185             :         {
     186           0 :             mpDeckTitleBar->GrabFocus();
     187             :         }
     188           0 :         else if (mpDeckTitleBar->GetToolBox().GetItemCount() > 0)
     189             :         {
     190           0 :             ToolBox& rToolBox = mpDeckTitleBar->GetToolBox();
     191           0 :             rToolBox.GrabFocus();
     192           0 :             rToolBox.Invalidate();
     193             :         }
     194             :         else
     195           0 :             FocusPanel(0, false);
     196             :     }
     197             :     else
     198           0 :         FocusPanel(0, false);
     199           0 : }
     200             : 
     201           0 : bool FocusManager::IsDeckTitleVisible() const
     202             : {
     203           0 :     return mpDeckTitleBar != nullptr && mpDeckTitleBar->IsVisible();
     204             : }
     205             : 
     206           0 : bool FocusManager::IsPanelTitleVisible (const sal_Int32 nPanelIndex) const
     207             : {
     208           0 :     if (nPanelIndex<0 || nPanelIndex>=static_cast<sal_Int32>(maPanels.size()))
     209           0 :         return false;
     210             : 
     211           0 :     TitleBar* pTitleBar = maPanels[nPanelIndex]->GetTitleBar();
     212           0 :     if (pTitleBar==NULL)
     213           0 :         return false;
     214           0 :     return pTitleBar->IsVisible();
     215             : }
     216             : 
     217           0 : void FocusManager::FocusPanel (
     218             :     const sal_Int32 nPanelIndex,
     219             :     const bool bFallbackToDeckTitle)
     220             : {
     221           0 :     if (nPanelIndex<0 || nPanelIndex>=static_cast<sal_Int32>(maPanels.size()))
     222             :     {
     223           0 :         if (bFallbackToDeckTitle)
     224           0 :             FocusDeckTitle();
     225           0 :         return;
     226             :     }
     227             : 
     228           0 :     Panel& rPanel (*maPanels[nPanelIndex]);
     229           0 :     TitleBar* pTitleBar = rPanel.GetTitleBar();
     230           0 :     if (pTitleBar!=NULL && pTitleBar->IsVisible())
     231             :     {
     232           0 :         rPanel.SetExpanded(true);
     233           0 :         pTitleBar->GrabFocus();
     234             :     }
     235           0 :     else if (bFallbackToDeckTitle)
     236             :     {
     237             :         // The panel title is not visible, fall back to the deck
     238             :         // title.
     239             :         // Make sure that the desk title is visible here to prevent a
     240             :         // loop when both the title of panel 0 and the deck title are
     241             :         // not present.
     242           0 :         if (IsDeckTitleVisible())
     243           0 :             FocusDeckTitle();
     244             :         else
     245           0 :             FocusPanelContent(nPanelIndex);
     246             :     }
     247             :     else
     248           0 :         FocusPanelContent(nPanelIndex);
     249             : 
     250           0 :     if (maShowPanelFunctor)
     251           0 :         maShowPanelFunctor(rPanel);
     252             : }
     253             : 
     254           0 : void FocusManager::FocusPanelContent (const sal_Int32 nPanelIndex)
     255             : {
     256           0 :     vcl::Window* pWindow = VCLUnoHelper::GetWindow(maPanels[nPanelIndex]->GetElementWindow());
     257           0 :     if (pWindow != NULL)
     258             :     {
     259           0 :         mbObservingContentControlFocus = true;
     260           0 :         pWindow->GrabFocus();
     261           0 :         mbObservingContentControlFocus = false;
     262             :     }
     263           0 : }
     264             : 
     265           0 : void FocusManager::FocusButton (const sal_Int32 nButtonIndex)
     266             : {
     267           0 :     maButtons[nButtonIndex]->GrabFocus();
     268           0 :     maButtons[nButtonIndex]->Invalidate();
     269           0 : }
     270             : 
     271           0 : void FocusManager::ClickButton (const sal_Int32 nButtonIndex)
     272             : {
     273           0 :     maButtons[nButtonIndex]->Click();
     274           0 :     if (nButtonIndex > 0)
     275           0 :         if ( ! maPanels.empty())
     276           0 :             FocusPanel(0, true);
     277           0 :     maButtons[nButtonIndex]->GetParent()->Invalidate();
     278           0 : }
     279             : 
     280         119 : void FocusManager::RemoveWindow (vcl::Window& rWindow)
     281             : {
     282         119 :     auto iPanel (::std::find(maPanels.begin(), maPanels.end(), &rWindow));
     283         119 :     if (iPanel != maPanels.end())
     284             :     {
     285           0 :         UnregisterWindow(rWindow);
     286           0 :         if ((*iPanel)->GetTitleBar() != NULL)
     287             :         {
     288           0 :             UnregisterWindow(*(*iPanel)->GetTitleBar());
     289           0 :             UnregisterWindow((*iPanel)->GetTitleBar()->GetToolBox());
     290             :         }
     291           0 :         maPanels.erase(iPanel);
     292         119 :         return;
     293             :     }
     294             : 
     295         119 :     auto iButton (::std::find(maButtons.begin(), maButtons.end(), &rWindow));
     296         119 :     if (iButton != maButtons.end())
     297             :     {
     298         119 :         UnregisterWindow(rWindow);
     299         119 :         maButtons.erase(iButton);
     300         119 :         return;
     301             :     }
     302             : }
     303             : 
     304           0 : bool FocusManager::MoveFocusInsidePanel (
     305             :     const FocusLocation& rFocusLocation,
     306             :     const sal_Int32 nDirection)
     307             : {
     308             :     const bool bHasToolBoxItem (
     309           0 :         maPanels[rFocusLocation.mnIndex]->GetTitleBar()->GetToolBox().GetItemCount() > 0);
     310           0 :     switch (rFocusLocation.meComponent)
     311             :     {
     312             :         case  PC_PanelTitle:
     313           0 :             if (nDirection > 0 && bHasToolBoxItem)
     314           0 :                 maPanels[rFocusLocation.mnIndex]->GetTitleBar()->GetToolBox().GrabFocus();
     315             :             else
     316           0 :                 FocusPanelContent(rFocusLocation.mnIndex);
     317           0 :             return true;
     318             : 
     319             :         case PC_PanelToolBox:
     320           0 :             if (nDirection < 0 && bHasToolBoxItem)
     321           0 :                 maPanels[rFocusLocation.mnIndex]->GetTitleBar()->GrabFocus();
     322             :             else
     323           0 :                 FocusPanelContent(rFocusLocation.mnIndex);
     324           0 :             return true;
     325             : 
     326             :         default:
     327           0 :             return false;
     328             :     }
     329             : }
     330             : 
     331           0 : bool FocusManager::MoveFocusInsideDeckTitle (
     332             :     const FocusLocation& rFocusLocation,
     333             :     const sal_Int32 nDirection)
     334             : {
     335             :     // Note that when the title bar of the first (and only) panel is
     336             :     // not visible then the deck title takes its place and the focus
     337             :     // is moved between a) deck title, b) deck closer and c) content
     338             :     // of panel 0.
     339             :     const bool bHasToolBoxItem (
     340           0 :         mpDeckTitleBar->GetToolBox().GetItemCount() > 0);
     341           0 :     switch (rFocusLocation.meComponent)
     342             :     {
     343             :         case  PC_DeckTitle:
     344           0 :             if (nDirection<0 && ! IsPanelTitleVisible(0))
     345           0 :                 FocusPanelContent(0);
     346           0 :             else if (bHasToolBoxItem)
     347           0 :                 mpDeckTitleBar->GetToolBox().GrabFocus();
     348           0 :             return true;
     349             : 
     350             :         case PC_DeckToolBox:
     351           0 :             if (nDirection>0 && ! IsPanelTitleVisible(0))
     352           0 :                 FocusPanelContent(0);
     353             :             else
     354           0 :                 mpDeckTitleBar->GrabFocus();
     355           0 :             return true;
     356             : 
     357             :         default:
     358           0 :             return false;
     359             :     }
     360             : }
     361             : 
     362           0 : void FocusManager::HandleKeyEvent (
     363             :     const vcl::KeyCode& rKeyCode,
     364             :     const vcl::Window& rWindow)
     365             : {
     366           0 :     const FocusLocation aLocation (GetFocusLocation(rWindow));
     367           0 :     mpLastFocusedWindow = NULL;
     368             : 
     369           0 :     switch (rKeyCode.GetCode())
     370             :     {
     371             :         case KEY_SPACE:
     372           0 :             switch (aLocation.meComponent)
     373             :             {
     374             :                 case PC_PanelTitle:
     375             :                     // Toggle panel between expanded and collapsed.
     376           0 :                     maPanels[aLocation.mnIndex]->SetExpanded( ! maPanels[aLocation.mnIndex]->IsExpanded());
     377           0 :                     break;
     378             : 
     379             :                 case PC_TabBar:
     380             :                     // Activate the button.
     381           0 :                     ClickButton(aLocation.mnIndex);
     382           0 :                     break;
     383             : 
     384             :                 default:
     385           0 :                     break;
     386             :             }
     387           0 :             return;
     388             : 
     389             :         case KEY_RETURN:
     390           0 :             switch (aLocation.meComponent)
     391             :             {
     392             :                 case PC_DeckToolBox:
     393           0 :                     FocusButton(0);
     394           0 :                     break;
     395             : 
     396             :                 case PC_PanelTitle:
     397             :                     // Enter the panel.
     398           0 :                     FocusPanelContent(aLocation.mnIndex);
     399           0 :                     break;
     400             : 
     401             :                 case PC_TabBar:
     402             :                     // Activate the button.
     403           0 :                     ClickButton(aLocation.mnIndex);
     404           0 :                     break;
     405             : 
     406             :                 default:
     407           0 :                     break;
     408             :             }
     409           0 :             return;
     410             : 
     411             :         case KEY_TAB:
     412             :         {
     413             :             const sal_Int32 nDirection (
     414           0 :                 rKeyCode.IsShift()
     415             :                     ? -1
     416           0 :                     : +1);
     417           0 :             switch (aLocation.meComponent)
     418             :             {
     419             :                 case PC_PanelTitle:
     420             :                 case PC_PanelToolBox:
     421             :                 case PC_PanelContent:
     422           0 :                     MoveFocusInsidePanel(aLocation, nDirection);
     423           0 :                     break;
     424             : 
     425             :                 case PC_DeckTitle:
     426             :                 case PC_DeckToolBox:
     427           0 :                     MoveFocusInsideDeckTitle(aLocation, nDirection);
     428           0 :                     break;
     429             : 
     430             :                 default:
     431           0 :                     break;
     432             :             }
     433           0 :             break;
     434             :         }
     435             : 
     436             :         case KEY_LEFT:
     437             :         case KEY_UP:
     438           0 :             switch (aLocation.meComponent)
     439             :             {
     440             :                 case PC_PanelTitle:
     441             :                 case PC_PanelToolBox:
     442             :                 case PC_PanelContent:
     443             :                     // Go to previous panel or the deck title.
     444           0 :                     if (aLocation.mnIndex > 0)
     445           0 :                         FocusPanel(aLocation.mnIndex-1, true);
     446           0 :                     else if (IsDeckTitleVisible())
     447           0 :                         FocusDeckTitle();
     448             :                     else
     449           0 :                         FocusButton(maButtons.size()-1);
     450           0 :                     break;
     451             : 
     452             :                 case PC_DeckTitle:
     453             :                 case PC_DeckToolBox:
     454             :                     // Focus the last button.
     455           0 :                     FocusButton(maButtons.size()-1);
     456           0 :                     break;
     457             : 
     458             :                 case PC_TabBar:
     459             :                     // Go to previous tab bar item.
     460           0 :                     if (aLocation.mnIndex == 0)
     461           0 :                         FocusPanel(maPanels.size()-1, true);
     462             :                     else
     463           0 :                         FocusButton((aLocation.mnIndex + maButtons.size() - 1) % maButtons.size());
     464           0 :                     break;
     465             : 
     466             :                 default:
     467           0 :                     break;
     468             :             }
     469           0 :             break;
     470             : 
     471             :         case KEY_RIGHT:
     472             :         case KEY_DOWN:
     473           0 :             switch(aLocation.meComponent)
     474             :             {
     475             :                 case PC_PanelTitle:
     476             :                 case PC_PanelToolBox:
     477             :                 case PC_PanelContent:
     478             :                     // Go to next panel.
     479           0 :                     if (aLocation.mnIndex < static_cast<sal_Int32>(maPanels.size())-1)
     480           0 :                         FocusPanel(aLocation.mnIndex+1, false);
     481             :                     else
     482           0 :                         FocusButton(0);
     483           0 :                     break;
     484             : 
     485             :                 case PC_DeckTitle:
     486             :                 case PC_DeckToolBox:
     487             :                     // Focus the first panel.
     488           0 :                     if (IsPanelTitleVisible(0))
     489           0 :                         FocusPanel(0, false);
     490             :                     else
     491           0 :                         FocusButton(0);
     492           0 :                     break;
     493             : 
     494             :                 case PC_TabBar:
     495             :                     // Go to next tab bar item.
     496           0 :                     if (aLocation.mnIndex < static_cast<sal_Int32>(maButtons.size())-1)
     497           0 :                         FocusButton(aLocation.mnIndex + 1);
     498           0 :                     else if (IsDeckTitleVisible())
     499           0 :                         FocusDeckTitle();
     500             :                     else
     501           0 :                         FocusPanel(0, true);
     502           0 :                     break;
     503             : 
     504             :                 default:
     505           0 :                     break;
     506             :             }
     507           0 :             break;
     508             :     }
     509             : }
     510             : 
     511       61622 : IMPL_LINK(FocusManager, WindowEventListener, VclSimpleEvent*, pEvent)
     512             : {
     513       30811 :     if (pEvent == NULL)
     514           0 :         return 0;
     515             : 
     516       30811 :     if ( ! pEvent->ISA(VclWindowEvent))
     517           0 :         return 0;
     518             : 
     519       30811 :     VclWindowEvent* pWindowEvent = static_cast<VclWindowEvent*>(pEvent);
     520       30811 :     vcl::Window* pSource = pWindowEvent->GetWindow();
     521       30811 :     if (pSource == NULL)
     522           0 :         return 0;
     523             : 
     524       30811 :     switch (pWindowEvent->GetId())
     525             :     {
     526             :         case VCLEVENT_WINDOW_KEYINPUT:
     527             :         {
     528           0 :             KeyEvent* pKeyEvent = static_cast<KeyEvent*>(pWindowEvent->GetData());
     529           0 :             HandleKeyEvent(pKeyEvent->GetKeyCode(), *pSource);
     530           0 :             return 1;
     531             :         }
     532             : 
     533             :         case VCLEVENT_OBJECT_DYING:
     534         119 :             RemoveWindow(*pSource);
     535         119 :             return 1;
     536             : 
     537             :         case VCLEVENT_WINDOW_GETFOCUS:
     538             :         case VCLEVENT_WINDOW_LOSEFOCUS:
     539           0 :             pSource->Invalidate();
     540           0 :             return 1;
     541             : 
     542             :         default:
     543       30692 :             break;
     544             :     }
     545             : 
     546       30692 :     return 0;
     547             : }
     548             : 
     549      116848 : IMPL_LINK(FocusManager, ChildEventListener, VclSimpleEvent*, pEvent)
     550             : {
     551       58424 :     if (pEvent == NULL)
     552           0 :         return 0;
     553             : 
     554       58424 :     if (!pEvent->ISA(VclWindowEvent))
     555           0 :         return 0;
     556             : 
     557       58424 :     VclWindowEvent* pWindowEvent = static_cast<VclWindowEvent*>(pEvent);
     558       58424 :     vcl::Window* pSource = pWindowEvent->GetWindow();
     559       58424 :     if (pSource == NULL)
     560           0 :         return 0;
     561             : 
     562       58424 :     switch (pWindowEvent->GetId())
     563             :     {
     564             :         case VCLEVENT_WINDOW_KEYINPUT:
     565             :         {
     566           0 :             KeyEvent* pKeyEvent = static_cast<KeyEvent*>(pWindowEvent->GetData());
     567             : 
     568             :             // Go up the window hierarchy to find out whether the
     569             :             // parent of the event source is known to us.
     570           0 :             vcl::Window* pWindow = pSource;
     571           0 :             FocusLocation aLocation (PC_None, -1);
     572             :             while (true)
     573             :             {
     574           0 :                 if (pWindow == NULL)
     575           0 :                     break;
     576           0 :                 aLocation = GetFocusLocation(*pWindow);
     577           0 :                 if (aLocation.meComponent != PC_None)
     578           0 :                     break;
     579           0 :                 pWindow = pWindow->GetParent();
     580             :             }
     581             : 
     582           0 :             if (aLocation.meComponent != PC_None)
     583             :             {
     584           0 :                 switch (pKeyEvent->GetKeyCode().GetCode())
     585             :                 {
     586             :                     case KEY_ESCAPE:
     587             :                         // Return focus back to the panel title.
     588           0 :                         FocusPanel(aLocation.mnIndex, true);
     589           0 :                         break;
     590             : 
     591             :                     case KEY_TAB:
     592           0 :                         if (mpFirstFocusedContentControl!=nullptr
     593           0 :                             && mpLastFocusedWindow == mpFirstFocusedContentControl)
     594             :                         {
     595             :                             // Move focus back to panel (or deck)
     596             :                             // title.
     597           0 :                             FocusPanel(aLocation.mnIndex, true);
     598             :                         }
     599           0 :                         break;
     600             : 
     601             :                     default:
     602           0 :                         break;
     603             :                 }
     604             :             }
     605           0 :             return 1;
     606             :         }
     607             : 
     608             :         case VCLEVENT_WINDOW_GETFOCUS:
     609             :             // Keep track of focused controls in panel content.
     610             :             // Remember the first focused control.  When it is later
     611             :             // focused again due to pressing the TAB key then the
     612             :             // focus is moved to the panel or deck title.
     613           0 :             mpLastFocusedWindow = pSource;
     614           0 :             if (mbObservingContentControlFocus)
     615           0 :                 mpFirstFocusedContentControl = pSource;
     616           0 :             break;
     617             : 
     618             :         default:
     619       58424 :             break;
     620             :     }
     621             : 
     622       58424 :     return 0;
     623             : }
     624             : 
     625         648 : } } // end of namespace sfx2::sidebar
     626             : 
     627             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.11