1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
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 "XAccessibleComponentTester.hxx"
22 #include <cppunit/TestAssert.h>
24 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
25 #include <com/sun/star/accessibility/XAccessible.hpp>
26 #include <com/sun/star/accessibility/XAccessibleComponent.hpp>
27 #include <com/sun/star/accessibility/XAccessibleContext.hpp>
28 #include <com/sun/star/awt/Point.hpp>
29 #include <com/sun/star/uno/Reference.hxx>
31 #include <tools/color.hxx>
33 #include <test/a11y/AccessibilityTools.hxx>
38 * @brief Checks the component's bounds
40 * Checks the X and Y coordinates are non-negative, and that the width and
41 * height are greater than 0.
43 * Coherence with @c getLocation() is tested in the test for the
46 void XAccessibleComponentTester::testBounds()
48 auto bounds
= mxComponent
->getBounds();
49 std::cout
<< "bounds: " << bounds
.Width
<< "x" << bounds
.Height
<< std::showpos
<< bounds
.X
50 << bounds
.Y
<< std::noshowpos
<< std::endl
;
51 CPPUNIT_ASSERT_GREATEREQUAL(static_cast<sal_Int32
>(0), bounds
.X
);
52 CPPUNIT_ASSERT_GREATEREQUAL(static_cast<sal_Int32
>(0), bounds
.Y
);
53 CPPUNIT_ASSERT_GREATER(static_cast<sal_Int32
>(0), bounds
.Width
);
54 CPPUNIT_ASSERT_GREATER(static_cast<sal_Int32
>(0), bounds
.Height
);
58 * @brief Tests results of XAccessibleComponent::getSize()
60 * Succeeds if the size is the same as in bounds.
62 void XAccessibleComponentTester::testSize()
64 auto bounds
= mxComponent
->getBounds();
65 auto size
= mxComponent
->getSize();
66 CPPUNIT_ASSERT_EQUAL(bounds
.Width
, size
.Width
);
67 CPPUNIT_ASSERT_EQUAL(bounds
.Height
, size
.Height
);
71 * @brief Tests results of XAccessibleComponent::getBounds()
73 * First checks 4 inner bounds (upper, lower, left and right) of component
74 * bounding box to contain at least one point of the component. Second 4 outer
75 * bounds are checked to not contain any component points.
77 * Succeeds if inner bounds contain component points and outer bounds don't
78 * contain any component points.
80 void XAccessibleComponentTester::testContainsPoint()
82 auto bounds
= mxComponent
->getBounds();
86 while (!mxComponent
->containsPoint(awt::Point(curX
, 0)) && curX
< bounds
.Width
)
88 CPPUNIT_ASSERT_MESSAGE("Upper bound of box contains no component points", curX
< bounds
.Width
);
89 std::cout
<< "Upper bound of box contains point (" << curX
<< ",0)" << std::endl
;
92 while (!mxComponent
->containsPoint(awt::Point(curX
, bounds
.Height
- 1)) && curX
< bounds
.Width
)
94 CPPUNIT_ASSERT_MESSAGE("Lower bound of box contains no component points", curX
< bounds
.Width
);
95 std::cout
<< "Lower bound of box contains point (" << curX
<< "," << (bounds
.Height
- 1) << ")"
99 while (!mxComponent
->containsPoint(awt::Point(0, curY
)) && curY
< bounds
.Height
)
101 CPPUNIT_ASSERT_MESSAGE("Left bound of box contains no component points", curY
< bounds
.Height
);
102 std::cout
<< "Left bound of box contains point (0," << curY
<< ")" << std::endl
;
105 while (!mxComponent
->containsPoint(awt::Point(bounds
.Width
- 1, curY
)) && curY
< bounds
.Height
)
107 CPPUNIT_ASSERT_MESSAGE("Right bound of box contains no component points", curY
< bounds
.Height
);
108 std::cout
<< "Right bound of box contains point (" << (bounds
.Width
- 1) << "," << curY
<< ")"
110 /* no match outside the bounds */
111 for (int x
= -1; x
<= bounds
.Width
; x
++)
113 CPPUNIT_ASSERT_MESSAGE("Outer upper bound CONTAINS a component point",
114 !mxComponent
->containsPoint(awt::Point(x
, -1)));
115 CPPUNIT_ASSERT_MESSAGE("Outer lower bound CONTAINS a component point",
116 !mxComponent
->containsPoint(awt::Point(x
, bounds
.Height
)));
118 for (int y
= -1; y
<= bounds
.Height
; y
++)
120 CPPUNIT_ASSERT_MESSAGE("Outer left bound CONTAINS a component point",
121 !mxComponent
->containsPoint(awt::Point(-1, y
)));
122 CPPUNIT_ASSERT_MESSAGE("Outer right bound CONTAINS a component point",
123 !mxComponent
->containsPoint(awt::Point(bounds
.Width
, y
)));
128 * @brief Tests results of XAccessibleComponent::getAccessibleAtPoint()
130 * Iterates through all children which implement
131 * <code>XAccessibleComponent</code> (if they exist) determines their
132 * boundaries and tries to get each child by <code>getAccessibleAtPoint</code>
133 * passing point which belongs to the child.
134 * Also the point is checked which doesn't belong to child boundary box.
136 * Succeeds if in the first cases the right children are returned, and in the
137 * second <code>null</code> or another child is returned.
139 void XAccessibleComponentTester::testAccessibleAtPoint()
141 sal_Int64 count
= mxContext
->getAccessibleChildCount();
142 std::cout
<< "Found " << count
<< " children" << std::endl
;
143 for (sal_Int64 i
= 0; i
< count
&& i
< AccessibilityTools::MAX_CHILDREN
; i
++)
145 auto child
= mxContext
->getAccessibleChild(i
);
146 uno::Reference
<accessibility::XAccessibleContext
> childContext(
147 child
->getAccessibleContext(), uno::UNO_SET_THROW
);
148 std::cout
<< "* Found child: " << AccessibilityTools::debugString(child
) << std::endl
;
149 std::cout
<< " states: "
150 << AccessibilityTools::debugAccessibleStateSet(
151 childContext
->getAccessibleStateSet())
153 uno::Reference
<accessibility::XAccessibleComponent
> xChildComponent(childContext
,
155 std::cout
<< " component: " << xChildComponent
<< std::endl
;
156 if (!xChildComponent
)
159 auto childBounds
= xChildComponent
->getBounds();
160 if (childBounds
.X
== -1)
162 std::cout
<< " bounds: " << childBounds
.Width
<< "x" << childBounds
.Height
<< std::showpos
163 << childBounds
.X
<< childBounds
.Y
<< std::noshowpos
<< std::endl
;
165 std::cout
<< "finding the point which lies on the component" << std::endl
;
168 while (!xChildComponent
->containsPoint(awt::Point(curX
, curY
)) && curX
< childBounds
.Width
)
173 if (curX
>= childBounds
.Width
)
175 std::cout
<< "Couldn't find a point with contains" << std::endl
;
180 std::cout
<< "Child found at point +" << childBounds
.X
+ curX
<< "+"
181 << childBounds
.Y
+ curY
<< std::endl
;
184 // trying the point laying on child
186 = mxComponent
->getAccessibleAtPoint(awt::Point(childBounds
.X
, childBounds
.Y
));
187 CPPUNIT_ASSERT_MESSAGE("Child not found at point", xAccAtPoint
.is());
188 if (!AccessibilityTools::equals(child
, xAccAtPoint
))
190 auto idxExpected
= childContext
->getAccessibleIndexInParent();
191 auto idxResult
= xAccAtPoint
->getAccessibleContext()->getAccessibleIndexInParent();
192 std::cout
<< "The child found (" << AccessibilityTools::debugString(xAccAtPoint
)
193 << ") is not the expected one (" << AccessibilityTools::debugString(child
)
195 if (idxExpected
< idxResult
)
197 std::cout
<< "-- it probably is hidden behind? Skipping." << std::endl
;
201 CPPUNIT_ASSERT_EQUAL_MESSAGE("The child found is NOT the expected one", child
,
206 // trying the point NOT laying on child
208 = mxComponent
->getAccessibleAtPoint(awt::Point(childBounds
.X
- 1, childBounds
.Y
- 1));
209 if (xAccAtPoint
.is())
211 CPPUNIT_ASSERT_MESSAGE("Child found OUTSIDE its bounds",
212 !AccessibilityTools::equals(child
, xAccAtPoint
));
218 * @brief Tests results of XAccessibleComponent::getLocation()
220 * Succeeds if the location is the same as location of boundary obtained by
221 * the <code>getBounds()</code> method.
223 void XAccessibleComponentTester::testLocation()
225 auto bounds
= mxComponent
->getBounds();
226 auto location
= mxComponent
->getLocation();
227 CPPUNIT_ASSERT_EQUAL_MESSAGE("Invalid X location", bounds
.X
, location
.X
);
228 CPPUNIT_ASSERT_EQUAL_MESSAGE("Invalid Y location", bounds
.Y
, location
.Y
);
232 * @brief Tests results of XAccessibleComponent::getLocationOnScreen()
233 * @returns @c true on success.
235 * Get the screen location of the component and its parent
236 * (if it exists and supports <code>XAccessibleComponent</code>).
238 * Succeeds component screen location equals to screen location of its parent
239 * plus location of the component relative to the parent.
241 void XAccessibleComponentTester::testLocationOnScreen()
243 auto location
= mxComponent
->getLocationOnScreen();
244 std::cout
<< "location on screen: +" << location
.X
<< "+" << location
.Y
<< std::endl
;
246 auto xParent
= mxContext
->getAccessibleParent();
248 std::cout
<< "No parent" << std::endl
;
251 std::cout
<< "Found parent: " << AccessibilityTools::debugString(xParent
) << std::endl
;
252 uno::Reference
<accessibility::XAccessibleComponent
> xParentComponent(
253 xParent
->getAccessibleContext(), uno::UNO_QUERY
);
254 if (!xParentComponent
.is())
255 std::cout
<< "Parent is not a Component" << std::endl
;
258 auto bounds
= mxComponent
->getBounds();
259 auto parentLocation
= xParentComponent
->getLocationOnScreen();
260 CPPUNIT_ASSERT_EQUAL_MESSAGE("Invalid X screen location", parentLocation
.X
+ bounds
.X
,
262 CPPUNIT_ASSERT_EQUAL_MESSAGE("Invalid Y screen location", parentLocation
.Y
+ bounds
.Y
,
269 * Just calls the method.
271 void XAccessibleComponentTester::testGrabFocus() { mxComponent
->grabFocus(); }
274 * Just calls the method.
276 void XAccessibleComponentTester::testGetForeground()
278 auto color
= mxComponent
->getForeground();
279 std::cout
<< "foreground color: " << Color(ColorAlpha
, color
) << std::endl
;
283 * Just calls the method.
285 void XAccessibleComponentTester::testGetBackground()
287 auto color
= mxComponent
->getBackground();
288 std::cout
<< "background color: " << Color(ColorAlpha
, color
) << std::endl
;
291 /* vim:set shiftwidth=4 softtabstop=4 expandtab cinoptions=b1,g0,N-s cinkeys+=0=break: */