1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
20 #include <config_features.h>
22 #include <i18nlangtag/mslangid.hxx>
24 #include "tools/time.hxx"
25 #include "tools/debug.hxx"
28 #include "unotools/fontcfg.hxx"
29 #include "unotools/confignode.hxx"
31 #include <vcl/layout.hxx>
32 #include <vcl/salgtype.hxx>
33 #include <vcl/event.hxx>
34 #include <vcl/fixed.hxx>
35 #include <vcl/help.hxx>
36 #include <vcl/cursor.hxx>
37 #include <vcl/svapp.hxx>
38 #include <vcl/window.hxx>
39 #include <vcl/syswin.hxx>
40 #include <vcl/syschild.hxx>
41 #include <vcl/dockwin.hxx>
42 #include <vcl/menu.hxx>
43 #include <vcl/wrkwin.hxx>
44 #include <vcl/wall.hxx>
45 #include <vcl/gradient.hxx>
46 #include <vcl/button.hxx>
47 #include <vcl/taskpanelist.hxx>
48 #include <vcl/dialog.hxx>
49 #include <vcl/unowrap.hxx>
50 #include <vcl/gdimtf.hxx>
51 #include <vcl/pdfextoutdevdata.hxx>
52 #include <vcl/popupmenuwindow.hxx>
53 #include <vcl/lazydelete.hxx>
54 #include <vcl/virdev.hxx>
55 #include <vcl/settings.hxx>
57 // declare system types in sysdata.hxx
58 #include <vcl/sysdata.hxx>
60 #include "salframe.hxx"
62 #include "salinst.hxx"
65 #include "fontinstance.hxx"
69 #include "PhysicalFontCollection.hxx"
71 #include "helpwin.hxx"
72 #include "sallayout.hxx"
73 #include "dndlistenercontainer.hxx"
74 #include "dndeventdispatcher.hxx"
76 #include "com/sun/star/accessibility/XAccessible.hpp"
77 #include "com/sun/star/accessibility/AccessibleRole.hpp"
78 #include "com/sun/star/datatransfer/dnd/XDragSource.hpp"
79 #include "com/sun/star/datatransfer/dnd/XDropTarget.hpp"
80 #include "com/sun/star/datatransfer/clipboard/XClipboard.hpp"
81 #include "com/sun/star/datatransfer/clipboard/SystemClipboard.hpp"
82 #include "com/sun/star/lang/XInitialization.hpp"
83 #include "com/sun/star/lang/XComponent.hpp"
84 #include "com/sun/star/lang/XServiceName.hpp"
85 #include "comphelper/processfactory.hxx"
87 #include <sal/macros.h>
88 #include <rtl/strbuf.hxx>
93 using namespace ::com::sun::star::uno
;
94 using namespace ::com::sun::star::lang
;
95 using namespace ::com::sun::star::datatransfer::clipboard
;
96 using namespace ::com::sun::star::datatransfer::dnd
;
97 using namespace ::com::sun::star
;
100 ImplAccessibleInfos::ImplAccessibleInfos()
102 nAccessibleRole
= 0xFFFF;
103 pAccessibleName
= nullptr;
104 pAccessibleDescription
= nullptr;
105 pLabeledByWindow
= nullptr;
106 pLabelForWindow
= nullptr;
107 pMemberOfWindow
= nullptr;
110 ImplAccessibleInfos::~ImplAccessibleInfos()
112 delete pAccessibleName
;
113 delete pAccessibleDescription
;
118 css::uno::Reference
< css::accessibility::XAccessible
> Window::GetAccessible( bool bCreate
)
120 // do not optimize hierarchy for the top level border win (ie, when there is no parent)
121 /* // do not optimize accessible hierarchy at all to better reflect real VCL hierarchy
122 if ( GetParent() && ( GetType() == WINDOW_BORDERWINDOW ) && ( GetChildCount() == 1 ) )
123 //if( !ImplIsAccessibleCandidate() )
125 vcl::Window* pChild = GetAccessibleChildWindow( 0 );
127 return pChild->GetAccessible();
131 return css::uno::Reference
< css::accessibility::XAccessible
>();
132 if ( !mpWindowImpl
->mxAccessible
.is() && bCreate
)
133 mpWindowImpl
->mxAccessible
= CreateAccessible();
135 return mpWindowImpl
->mxAccessible
;
138 css::uno::Reference
< css::accessibility::XAccessible
> Window::CreateAccessible()
140 css::uno::Reference
< css::accessibility::XAccessible
> xAcc( GetComponentInterface(), css::uno::UNO_QUERY
);
144 void Window::SetAccessible( const css::uno::Reference
< css::accessibility::XAccessible
>& x
)
146 assert(mpWindowImpl
);
147 mpWindowImpl
->mxAccessible
= x
;
150 // skip all border windows that are no top level frames
151 bool Window::ImplIsAccessibleCandidate() const
153 if( !mpWindowImpl
->mbBorderWin
)
156 // #101741 do not check for WB_CLOSEABLE because undecorated floaters (like menus!) are closeable
157 if( mpWindowImpl
->mbFrame
&& mpWindowImpl
->mnStyle
& (WB_MOVEABLE
| WB_SIZEABLE
) )
163 bool Window::ImplIsAccessibleNativeFrame() const
165 if( mpWindowImpl
->mbFrame
)
166 // #101741 do not check for WB_CLOSEABLE because undecorated floaters (like menus!) are closeable
167 if( (mpWindowImpl
->mnStyle
& (WB_MOVEABLE
| WB_SIZEABLE
)) )
175 vcl::Window
* Window::GetAccessibleParentWindow() const
177 if ( ImplIsAccessibleNativeFrame() )
180 vcl::Window
* pParent
= mpWindowImpl
->mpParent
;
181 if( GetType() == WINDOW_MENUBARWINDOW
)
183 // report the menubar as a child of THE workwindow
184 vcl::Window
*pWorkWin
= GetParent()->mpWindowImpl
->mpFirstChild
;
185 while( pWorkWin
&& (pWorkWin
== this) )
186 pWorkWin
= pWorkWin
->mpWindowImpl
->mpNext
;
189 // If this is a floating window which has a native border window, then that border should be reported as
190 // the accessible parent, unless the floating window is a PopupMenuFloatingWindow
192 // The logic here has to match that of AccessibleFactory::createAccessibleContext in
193 // accessibility/source/helper/acc_factory.cxx to avoid PopupMenuFloatingWindow
194 // becoming a11y parents of themselves
195 else if( GetType() == WINDOW_FLOATINGWINDOW
&&
196 mpWindowImpl
->mpBorderWindow
&& mpWindowImpl
->mpBorderWindow
->mpWindowImpl
->mbFrame
&&
197 !PopupMenuFloatingWindow::isPopupMenu(this))
199 pParent
= mpWindowImpl
->mpBorderWindow
;
201 else if( pParent
&& !pParent
->ImplIsAccessibleCandidate() )
203 pParent
= pParent
->mpWindowImpl
->mpParent
;
208 sal_uInt16
Window::GetAccessibleChildWindowCount()
210 sal_uInt16 nChildren
= 0;
211 vcl::Window
* pChild
= mpWindowImpl
->mpFirstChild
;
214 if( pChild
->IsVisible() )
216 pChild
= pChild
->mpWindowImpl
->mpNext
;
219 // report the menubarwindow as a child of THE workwindow
220 if( GetType() == WINDOW_BORDERWINDOW
)
222 ImplBorderWindow
*pBorderWindow
= static_cast<ImplBorderWindow
*>(this);
223 if( pBorderWindow
->mpMenuBarWindow
&&
224 pBorderWindow
->mpMenuBarWindow
->IsVisible()
228 else if( GetType() == WINDOW_WORKWINDOW
)
230 WorkWindow
*pWorkWindow
= static_cast<WorkWindow
*>(this);
231 if( pWorkWindow
->GetMenuBar() &&
232 pWorkWindow
->GetMenuBar()->GetWindow() &&
233 pWorkWindow
->GetMenuBar()->GetWindow()->IsVisible()
241 vcl::Window
* Window::GetAccessibleChildWindow( sal_uInt16 n
)
243 // report the menubarwindow as a the first child of THE workwindow
244 if( GetType() == WINDOW_WORKWINDOW
&& static_cast<WorkWindow
*>(this)->GetMenuBar() )
248 MenuBar
*pMenuBar
= static_cast<WorkWindow
*>(this)->GetMenuBar();
249 if( pMenuBar
->GetWindow() && pMenuBar
->GetWindow()->IsVisible() )
250 return pMenuBar
->GetWindow();
256 // transform n to child number including invisible children
257 sal_uInt16 nChildren
= n
;
258 vcl::Window
* pChild
= mpWindowImpl
->mpFirstChild
;
261 if( pChild
->IsVisible() )
267 pChild
= pChild
->mpWindowImpl
->mpNext
;
270 if( GetType() == WINDOW_BORDERWINDOW
&& pChild
&& pChild
->GetType() == WINDOW_MENUBARWINDOW
)
272 do pChild
= pChild
->mpWindowImpl
->mpNext
; while( pChild
&& ! pChild
->IsVisible() );
273 SAL_WARN_IF( !pChild
, "vcl", "GetAccessibleChildWindow(): wrong index in border window");
276 if ( pChild
&& ( pChild
->GetType() == WINDOW_BORDERWINDOW
) && ( pChild
->GetChildCount() == 1 ) )
278 pChild
= pChild
->GetChild( 0 );
283 void Window::SetAccessibleRole( sal_uInt16 nRole
)
285 if ( !mpWindowImpl
->mpAccessibleInfos
)
286 mpWindowImpl
->mpAccessibleInfos
= new ImplAccessibleInfos
;
288 SAL_WARN_IF( mpWindowImpl
->mpAccessibleInfos
->nAccessibleRole
!= 0xFFFF, "vcl", "AccessibleRole already set!" );
289 mpWindowImpl
->mpAccessibleInfos
->nAccessibleRole
= nRole
;
292 sal_uInt16
Window::getDefaultAccessibleRole() const
294 sal_uInt16 nRole
= 0xFFFF;
297 case WINDOW_MESSBOX
: // MT: Would be nice to have special roles!
299 case WINDOW_WARNINGBOX
:
300 case WINDOW_ERRORBOX
:
301 case WINDOW_QUERYBOX
: nRole
= accessibility::AccessibleRole::ALERT
; break;
303 case WINDOW_MODELESSDIALOG
:
304 case WINDOW_MODALDIALOG
:
305 case WINDOW_SYSTEMDIALOG
:
306 case WINDOW_PRINTERSETUPDIALOG
:
307 case WINDOW_PRINTDIALOG
:
308 case WINDOW_TABDIALOG
:
309 case WINDOW_BUTTONDIALOG
:
310 case WINDOW_DIALOG
: nRole
= accessibility::AccessibleRole::DIALOG
; break;
312 case WINDOW_PUSHBUTTON
:
313 case WINDOW_OKBUTTON
:
314 case WINDOW_CANCELBUTTON
:
315 case WINDOW_HELPBUTTON
:
316 case WINDOW_IMAGEBUTTON
:
317 case WINDOW_MOREBUTTON
:
318 case WINDOW_SPINBUTTON
:
319 case WINDOW_BUTTON
: nRole
= accessibility::AccessibleRole::PUSH_BUTTON
; break;
320 case WINDOW_MENUBUTTON
: nRole
= accessibility::AccessibleRole::BUTTON_MENU
; break;
322 case WINDOW_PATHDIALOG
: nRole
= accessibility::AccessibleRole::DIRECTORY_PANE
; break;
323 case WINDOW_FILEDIALOG
: nRole
= accessibility::AccessibleRole::FILE_CHOOSER
; break;
324 case WINDOW_COLORDIALOG
: nRole
= accessibility::AccessibleRole::COLOR_CHOOSER
; break;
325 case WINDOW_FONTDIALOG
: nRole
= accessibility::AccessibleRole::FONT_CHOOSER
; break;
327 case WINDOW_RADIOBUTTON
: nRole
= accessibility::AccessibleRole::RADIO_BUTTON
; break;
328 case WINDOW_TRISTATEBOX
:
329 case WINDOW_CHECKBOX
: nRole
= accessibility::AccessibleRole::CHECK_BOX
; break;
331 case WINDOW_MULTILINEEDIT
: nRole
= accessibility::AccessibleRole::SCROLL_PANE
; break;
333 case WINDOW_PATTERNFIELD
:
334 case WINDOW_CALCINPUTLINE
:
335 case WINDOW_EDIT
: nRole
= ( GetStyle() & WB_PASSWORD
) ? (accessibility::AccessibleRole::PASSWORD_TEXT
) : (accessibility::AccessibleRole::TEXT
); break;
337 case WINDOW_PATTERNBOX
:
338 case WINDOW_NUMERICBOX
:
339 case WINDOW_METRICBOX
:
340 case WINDOW_CURRENCYBOX
:
341 case WINDOW_LONGCURRENCYBOX
:
342 case WINDOW_COMBOBOX
: nRole
= accessibility::AccessibleRole::COMBO_BOX
; break;
345 case WINDOW_MULTILISTBOX
: nRole
= accessibility::AccessibleRole::LIST
; break;
347 case WINDOW_TREELISTBOX
: nRole
= accessibility::AccessibleRole::TREE
; break;
349 case WINDOW_FIXEDTEXT
: nRole
= accessibility::AccessibleRole::LABEL
; break;
350 case WINDOW_FIXEDLINE
:
351 if( !GetText().isEmpty() )
352 nRole
= accessibility::AccessibleRole::LABEL
;
354 nRole
= accessibility::AccessibleRole::SEPARATOR
;
357 case WINDOW_FIXEDBITMAP
:
358 case WINDOW_FIXEDIMAGE
: nRole
= accessibility::AccessibleRole::ICON
; break;
359 case WINDOW_GROUPBOX
: nRole
= accessibility::AccessibleRole::GROUP_BOX
; break;
360 case WINDOW_SCROLLBAR
: nRole
= accessibility::AccessibleRole::SCROLL_BAR
; break;
363 case WINDOW_SPLITTER
:
364 case WINDOW_SPLITWINDOW
: nRole
= accessibility::AccessibleRole::SPLIT_PANE
; break;
368 case WINDOW_DATEFIELD
:
369 case WINDOW_TIMEFIELD
: nRole
= accessibility::AccessibleRole::DATE_EDITOR
; break;
371 case WINDOW_NUMERICFIELD
:
372 case WINDOW_METRICFIELD
:
373 case WINDOW_CURRENCYFIELD
:
374 case WINDOW_LONGCURRENCYFIELD
:
375 case WINDOW_SPINFIELD
: nRole
= accessibility::AccessibleRole::SPIN_BOX
; break;
377 case WINDOW_TOOLBOX
: nRole
= accessibility::AccessibleRole::TOOL_BAR
; break;
378 case WINDOW_STATUSBAR
: nRole
= accessibility::AccessibleRole::STATUS_BAR
; break;
380 case WINDOW_TABPAGE
: nRole
= accessibility::AccessibleRole::PANEL
; break;
381 case WINDOW_TABCONTROL
: nRole
= accessibility::AccessibleRole::PAGE_TAB_LIST
; break;
383 case WINDOW_DOCKINGWINDOW
:
384 case WINDOW_SYSWINDOW
: nRole
= (mpWindowImpl
->mbFrame
) ? accessibility::AccessibleRole::FRAME
:
385 accessibility::AccessibleRole::PANEL
; break;
387 case WINDOW_FLOATINGWINDOW
: nRole
= ( mpWindowImpl
->mbFrame
||
388 (mpWindowImpl
->mpBorderWindow
&& mpWindowImpl
->mpBorderWindow
->mpWindowImpl
->mbFrame
) ||
389 (GetStyle() & WB_OWNERDRAWDECORATION
) ) ? accessibility::AccessibleRole::FRAME
:
390 accessibility::AccessibleRole::WINDOW
; break;
392 case WINDOW_WORKWINDOW
: nRole
= accessibility::AccessibleRole::ROOT_PANE
; break;
394 case WINDOW_SCROLLBARBOX
: nRole
= accessibility::AccessibleRole::FILLER
; break;
396 case WINDOW_HELPTEXTWINDOW
: nRole
= accessibility::AccessibleRole::TOOL_TIP
; break;
398 case WINDOW_RULER
: nRole
= accessibility::AccessibleRole::RULER
; break;
400 case WINDOW_SCROLLWINDOW
: nRole
= accessibility::AccessibleRole::SCROLL_PANE
; break;
404 case WINDOW_BORDERWINDOW
:
405 case WINDOW_SYSTEMCHILDWINDOW
:
407 if (ImplIsAccessibleNativeFrame() )
408 nRole
= accessibility::AccessibleRole::FRAME
;
409 else if( IsScrollable() )
410 nRole
= accessibility::AccessibleRole::SCROLL_PANE
;
411 else if( const_cast<vcl::Window
*>(this)->ImplGetWindow()->IsMenuFloatingWindow() )
412 nRole
= accessibility::AccessibleRole::WINDOW
; // #106002#, contextmenus are windows (i.e. toplevel)
414 // #104051# WINDOW seems to be a bad default role, use LAYEREDPANE instead
415 // a WINDOW is interpreted as a top-level window, which is typically not the case
416 //nRole = accessibility::AccessibleRole::WINDOW;
417 nRole
= accessibility::AccessibleRole::PANEL
;
422 sal_uInt16
Window::GetAccessibleRole() const
424 using namespace ::com::sun::star
;
426 sal_uInt16 nRole
= mpWindowImpl
->mpAccessibleInfos
? mpWindowImpl
->mpAccessibleInfos
->nAccessibleRole
: 0xFFFF;
427 if ( nRole
== 0xFFFF )
428 nRole
= getDefaultAccessibleRole();
432 void Window::SetAccessibleName( const OUString
& rName
)
434 if ( !mpWindowImpl
->mpAccessibleInfos
)
435 mpWindowImpl
->mpAccessibleInfos
= new ImplAccessibleInfos
;
437 OUString oldName
= GetAccessibleName();
439 delete mpWindowImpl
->mpAccessibleInfos
->pAccessibleName
;
440 mpWindowImpl
->mpAccessibleInfos
->pAccessibleName
= new OUString( rName
);
442 CallEventListeners( VCLEVENT_WINDOW_FRAMETITLECHANGED
, &oldName
);
445 OUString
Window::GetAccessibleName() const
447 if (mpWindowImpl
->mpAccessibleInfos
&& mpWindowImpl
->mpAccessibleInfos
->pAccessibleName
)
448 return *mpWindowImpl
->mpAccessibleInfos
->pAccessibleName
;
449 return getDefaultAccessibleName();
452 OUString
Window::getDefaultAccessibleName() const
454 OUString aAccessibleName
;
457 case WINDOW_MULTILINEEDIT
:
458 case WINDOW_PATTERNFIELD
:
459 case WINDOW_NUMERICFIELD
:
460 case WINDOW_METRICFIELD
:
461 case WINDOW_CURRENCYFIELD
:
462 case WINDOW_LONGCURRENCYFIELD
:
463 case WINDOW_CALCINPUTLINE
:
468 case WINDOW_CURRENCYBOX
:
469 case WINDOW_LONGCURRENCYBOX
:
470 case WINDOW_DATEFIELD
:
471 case WINDOW_TIMEFIELD
:
472 case WINDOW_SPINFIELD
:
474 case WINDOW_COMBOBOX
:
476 case WINDOW_MULTILISTBOX
:
477 case WINDOW_TREELISTBOX
:
478 case WINDOW_METRICBOX
:
480 vcl::Window
*pLabel
= GetAccessibleRelationLabeledBy();
481 if ( pLabel
&& pLabel
!= this )
482 aAccessibleName
= pLabel
->GetText();
483 if (aAccessibleName
.isEmpty())
484 aAccessibleName
= GetQuickHelpText();
488 case WINDOW_IMAGEBUTTON
:
489 case WINDOW_PUSHBUTTON
:
490 aAccessibleName
= GetText();
491 if (aAccessibleName
.isEmpty())
493 aAccessibleName
= GetQuickHelpText();
494 if (aAccessibleName
.isEmpty())
495 aAccessibleName
= GetHelpText();
500 aAccessibleName
= GetText();
503 case WINDOW_MOREBUTTON
:
504 aAccessibleName
= mpWindowImpl
->maText
;
508 aAccessibleName
= GetText();
512 return GetNonMnemonicString( aAccessibleName
);
515 void Window::SetAccessibleDescription( const OUString
& rDescription
)
517 if ( ! mpWindowImpl
->mpAccessibleInfos
)
518 mpWindowImpl
->mpAccessibleInfos
= new ImplAccessibleInfos
;
520 SAL_WARN_IF( mpWindowImpl
->mpAccessibleInfos
->pAccessibleDescription
, "vcl", "AccessibleDescription already set!" );
521 delete mpWindowImpl
->mpAccessibleInfos
->pAccessibleDescription
;
522 mpWindowImpl
->mpAccessibleInfos
->pAccessibleDescription
= new OUString( rDescription
);
525 OUString
Window::GetAccessibleDescription() const
527 OUString aAccessibleDescription
;
528 if ( mpWindowImpl
->mpAccessibleInfos
&& mpWindowImpl
->mpAccessibleInfos
->pAccessibleDescription
)
530 aAccessibleDescription
= *mpWindowImpl
->mpAccessibleInfos
->pAccessibleDescription
;
534 // Special code for help text windows. ZT asks the border window for the
535 // description so we have to forward this request to our inner window.
536 const vcl::Window
* pWin
= const_cast<vcl::Window
*>(this)->ImplGetWindow();
537 if ( pWin
->GetType() == WINDOW_HELPTEXTWINDOW
)
538 aAccessibleDescription
= pWin
->GetHelpText();
540 aAccessibleDescription
= GetHelpText();
543 return aAccessibleDescription
;
546 void Window::SetAccessibleRelationLabeledBy( vcl::Window
* pLabeledBy
)
548 if ( !mpWindowImpl
->mpAccessibleInfos
)
549 mpWindowImpl
->mpAccessibleInfos
= new ImplAccessibleInfos
;
550 mpWindowImpl
->mpAccessibleInfos
->pLabeledByWindow
= pLabeledBy
;
553 void Window::SetAccessibleRelationLabelFor( vcl::Window
* pLabelFor
)
555 if ( !mpWindowImpl
->mpAccessibleInfos
)
556 mpWindowImpl
->mpAccessibleInfos
= new ImplAccessibleInfos
;
557 mpWindowImpl
->mpAccessibleInfos
->pLabelForWindow
= pLabelFor
;
560 void Window::SetAccessibleRelationMemberOf( vcl::Window
* pMemberOfWin
)
562 if ( !mpWindowImpl
->mpAccessibleInfos
)
563 mpWindowImpl
->mpAccessibleInfos
= new ImplAccessibleInfos
;
564 mpWindowImpl
->mpAccessibleInfos
->pMemberOfWindow
= pMemberOfWin
;
567 vcl::Window
* Window::GetAccessibleRelationMemberOf() const
569 if (mpWindowImpl
->mpAccessibleInfos
&& mpWindowImpl
->mpAccessibleInfos
->pMemberOfWindow
)
570 return mpWindowImpl
->mpAccessibleInfos
->pMemberOfWindow
;
572 if (!isContainerWindow(this) && !isContainerWindow(GetParent()))
573 return getLegacyNonLayoutAccessibleRelationMemberOf();
578 vcl::Window
* Window::getAccessibleRelationLabelFor() const
580 if (mpWindowImpl
->mpAccessibleInfos
&& mpWindowImpl
->mpAccessibleInfos
->pLabelForWindow
)
581 return mpWindowImpl
->mpAccessibleInfos
->pLabelForWindow
;
586 vcl::Window
* Window::GetAccessibleRelationLabelFor() const
588 vcl::Window
* pWindow
= getAccessibleRelationLabelFor();
593 if (!isContainerWindow(this) && !isContainerWindow(GetParent()))
594 return getLegacyNonLayoutAccessibleRelationLabelFor();
599 vcl::Window
* Window::GetAccessibleRelationLabeledBy() const
601 if (mpWindowImpl
->mpAccessibleInfos
&& mpWindowImpl
->mpAccessibleInfos
->pLabeledByWindow
)
602 return mpWindowImpl
->mpAccessibleInfos
->pLabeledByWindow
;
604 std::vector
<VclPtr
<FixedText
> > aMnemonicLabels(list_mnemonic_labels());
605 if (!aMnemonicLabels
.empty())
607 //if we have multiple labels, then prefer the first that is visible
608 for (auto const & rCandidate
: aMnemonicLabels
)
610 if (rCandidate
->IsVisible())
613 return aMnemonicLabels
[0];
616 if (!isContainerWindow(this) && !isContainerWindow(GetParent()))
617 return getLegacyNonLayoutAccessibleRelationLabeledBy();
622 bool Window::IsAccessibilityEventsSuppressed( bool bTraverseParentPath
)
624 if( !bTraverseParentPath
)
625 return mpWindowImpl
->mbSuppressAccessibilityEvents
;
628 vcl::Window
*pParent
= this;
629 while ( pParent
&& pParent
->mpWindowImpl
)
631 if( pParent
->mpWindowImpl
->mbSuppressAccessibilityEvents
)
634 pParent
= pParent
->mpWindowImpl
->mpParent
; // do not use GetParent() to find borderwindows that are frames
640 void Window::SetAccessibilityEventsSuppressed(bool bSuppressed
)
642 mpWindowImpl
->mbSuppressAccessibilityEvents
= bSuppressed
;
645 } /* namespace vcl */
647 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */