4#ifndef QTESTACCESSIBLE_H
5#define QTESTACCESSIBLE_H
9#pragma qt_no_master_include
12#include <QtCore/qglobal.h>
14#define QVERIFY_EVENT(event) \
15 QVERIFY(QTestAccessibility::verifyEvent(event))
17#include <QtCore/qlist.h>
18#include <QtCore/qdebug.h>
19#include <QtGui/qaccessible.h>
20#include <QtGui/qguiapplication.h>
21#include <QtTest/qttestglobal.h>
22#include <QtTest/qtestsystem.h>
24#if QT_CONFIG(accessibility)
34bool operator==(
const QAccessibleEvent &l,
const QAccessibleEvent &
r)
36 if (l.type() !=
r.type()) {
40 if (l.object() !=
r.object() ||
41 l.child() !=
r.child()) {
46 if (l.type() == QAccessible::StateChanged) {
47 return static_cast<const QAccessibleStateChangeEvent*
>(&l)->changedStates()
48 ==
static_cast<const QAccessibleStateChangeEvent*
>(&
r)->changedStates();
49 }
else if (l.type() == QAccessible::TextCaretMoved) {
50 return static_cast<const QAccessibleTextCursorEvent*
>(&l)->cursorPosition()
51 ==
static_cast<const QAccessibleTextCursorEvent*
>(&
r)->cursorPosition();
52 }
else if (l.type() == QAccessible::TextSelectionChanged) {
53 const QAccessibleTextSelectionEvent *
le =
static_cast<const QAccessibleTextSelectionEvent*
>(&l);
54 const QAccessibleTextSelectionEvent *re =
static_cast<const QAccessibleTextSelectionEvent*
>(&
r);
55 return le->cursorPosition() == re->cursorPosition() &&
56 le->selectionStart() == re->selectionStart() &&
57 le->selectionEnd() == re->selectionEnd();
58 }
else if (l.type() == QAccessible::TextInserted) {
59 const QAccessibleTextInsertEvent *
le =
static_cast<const QAccessibleTextInsertEvent*
>(&l);
60 const QAccessibleTextInsertEvent *re =
static_cast<const QAccessibleTextInsertEvent*
>(&
r);
61 return le->cursorPosition() == re->cursorPosition() &&
62 le->changePosition() == re->changePosition() &&
63 le->textInserted() == re->textInserted();
64 }
else if (l.type() == QAccessible::TextRemoved) {
65 const QAccessibleTextRemoveEvent *
le =
static_cast<const QAccessibleTextRemoveEvent*
>(&l);
66 const QAccessibleTextRemoveEvent *re =
static_cast<const QAccessibleTextRemoveEvent*
>(&
r);
67 return le->cursorPosition() == re->cursorPosition() &&
68 le->changePosition() == re->changePosition() &&
69 le->textRemoved() == re->textRemoved();
70 }
else if (l.type() == QAccessible::TextUpdated) {
71 const QAccessibleTextUpdateEvent *
le =
static_cast<const QAccessibleTextUpdateEvent*
>(&l);
72 const QAccessibleTextUpdateEvent *re =
static_cast<const QAccessibleTextUpdateEvent*
>(&
r);
73 return le->cursorPosition() == re->cursorPosition() &&
74 le->changePosition() == re->changePosition() &&
75 le->textInserted() == re->textInserted() &&
76 le->textRemoved() == re->textRemoved();
77 }
else if (l.type() == QAccessible::ValueChanged) {
78 const QAccessibleValueChangeEvent *
le =
static_cast<const QAccessibleValueChangeEvent*
>(&l);
79 const QAccessibleValueChangeEvent *re =
static_cast<const QAccessibleValueChangeEvent*
>(&
r);
80 return le->value() == re->value();
85class QTestAccessibility
91 instance() =
new QTestAccessibility;
101 static void clearEvents() { eventList().clear(); }
102 static EventList events() {
return eventList(); }
103 static bool verifyEvent(QAccessibleEvent *ev)
105 for (
int i = 0; eventList().isEmpty() &&
i < 5; ++
i)
107 if (eventList().isEmpty()) {
108 qWarning(
"Timeout waiting for accessibility event.");
111 const bool res = *eventList().first() == *ev;
114 delete eventList().takeFirst();
117 static bool containsEvent(QAccessibleEvent *
event) {
118 for (
const QAccessibleEvent *ev :
std::as_const(eventList())) {
128 QAccessible::installUpdateHandler(updateHandler);
129 QAccessible::installRootObjectHandler(rootObjectHandler);
132 ~QTestAccessibility()
134 QAccessible::installUpdateHandler(
nullptr);
135 QAccessible::installRootObjectHandler(
nullptr);
138 static void rootObjectHandler(
QObject *
object)
144 qWarning(
"root Object is not a QGuiApplication!");
146 qWarning(
"root Object called with 0 pointer");
150 static void updateHandler(QAccessibleEvent *
event)
152 auto ev = copyEvent(
event);
153 if (
auto obj = ev->object()) {
155 auto index= eventList().indexOf(ev);
158 eventList().at(
index)->m_object =
nullptr;
161 eventList().append(ev);
163 static QAccessibleEvent *copyEvent(QAccessibleEvent *
event)
165 QAccessibleEvent *ev;
166 if (
event->type() == QAccessible::StateChanged) {
168 ev =
new QAccessibleStateChangeEvent(
event->object(),
169 static_cast<QAccessibleStateChangeEvent*
>(
event)->changedStates());
171 ev =
new QAccessibleStateChangeEvent(
event->accessibleInterface(),
172 static_cast<QAccessibleStateChangeEvent*
>(
event)->changedStates());
173 }
else if (
event->type() == QAccessible::TextCaretMoved) {
175 ev =
new QAccessibleTextCursorEvent(
event->object(),
static_cast<QAccessibleTextCursorEvent*
>(
event)->cursorPosition());
177 ev =
new QAccessibleTextCursorEvent(
event->accessibleInterface(),
static_cast<QAccessibleTextCursorEvent*
>(
event)->cursorPosition());
178 }
else if (
event->type() == QAccessible::TextSelectionChanged) {
179 const QAccessibleTextSelectionEvent *original =
static_cast<QAccessibleTextSelectionEvent*
>(
event);
180 QAccessibleTextSelectionEvent *sel;
182 sel =
new QAccessibleTextSelectionEvent(
event->object(), original->selectionStart(), original->selectionEnd());
184 sel =
new QAccessibleTextSelectionEvent(
event->accessibleInterface(), original->selectionStart(), original->selectionEnd());
185 sel->setCursorPosition(original->cursorPosition());
187 }
else if (
event->type() == QAccessible::TextInserted) {
188 const QAccessibleTextInsertEvent *original =
static_cast<QAccessibleTextInsertEvent*
>(
event);
189 QAccessibleTextInsertEvent *ins;
190 if (original->object())
191 ins =
new QAccessibleTextInsertEvent(
event->object(), original->changePosition(), original->textInserted());
193 ins =
new QAccessibleTextInsertEvent(
event->accessibleInterface(), original->changePosition(), original->textInserted());
194 ins->setCursorPosition(original->cursorPosition());
196 }
else if (
event->type() == QAccessible::TextRemoved) {
197 const QAccessibleTextRemoveEvent *original =
static_cast<QAccessibleTextRemoveEvent*
>(
event);
198 QAccessibleTextRemoveEvent *rem;
200 rem =
new QAccessibleTextRemoveEvent(
event->object(), original->changePosition(), original->textRemoved());
202 rem =
new QAccessibleTextRemoveEvent(
event->accessibleInterface(), original->changePosition(), original->textRemoved());
203 rem->setCursorPosition(original->cursorPosition());
205 }
else if (
event->type() == QAccessible::TextUpdated) {
206 const QAccessibleTextUpdateEvent *original =
static_cast<QAccessibleTextUpdateEvent*
>(
event);
207 QAccessibleTextUpdateEvent *upd;
209 upd =
new QAccessibleTextUpdateEvent(
event->object(), original->changePosition(), original->textRemoved(), original->textInserted());
211 upd =
new QAccessibleTextUpdateEvent(
event->accessibleInterface(), original->changePosition(), original->textRemoved(), original->textInserted());
212 upd->setCursorPosition(original->cursorPosition());
214 }
else if (
event->type() == QAccessible::ValueChanged) {
216 ev =
new QAccessibleValueChangeEvent(
event->object(),
static_cast<QAccessibleValueChangeEvent*
>(
event)->value());
218 ev =
new QAccessibleValueChangeEvent(
event->accessibleInterface(),
static_cast<QAccessibleValueChangeEvent*
>(
event)->value());
219 }
else if (
event->type() == QAccessible::TableModelChanged) {
220 QAccessibleTableModelChangeEvent *oldEvent =
static_cast<QAccessibleTableModelChangeEvent*
>(
event);
221 QAccessibleTableModelChangeEvent *newEvent;
223 newEvent =
new QAccessibleTableModelChangeEvent(
event->object(), oldEvent->modelChangeType());
225 newEvent =
new QAccessibleTableModelChangeEvent(
event->accessibleInterface(), oldEvent->modelChangeType());
226 newEvent->setFirstRow(oldEvent->firstRow());
227 newEvent->setFirstColumn(oldEvent->firstColumn());
228 newEvent->setLastRow(oldEvent->lastRow());
229 newEvent->setLastColumn(oldEvent->lastColumn());
233 ev =
new QAccessibleEvent(
event->object(),
event->type());
235 ev =
new QAccessibleEvent(
event->accessibleInterface(),
event->type());
237 ev->setChild(
event->child());
241 static EventList &eventList()
243 static EventList
list;
247 static QTestAccessibility *&instance()
249 static QTestAccessibility *ta =
nullptr;
254 static QString msgAccessibilityEventListMismatch(
const EventList &haystack,
255 const QAccessibleEvent *needle)
259 str <<
"Event " << *needle
260 <<
" not found at head of event list of size " << haystack.
size() <<
" :";
261 for (
const QAccessibleEvent *
e : haystack)
static QMetaObject::Connection connect(const QObject *sender, const char *signal, const QObject *receiver, const char *member, Qt::ConnectionType=Qt::AutoConnection)
\threadsafe
void destroyed(QObject *=nullptr)
This signal is emitted immediately before the object obj is destroyed, after any instances of QPointe...
\macro QT_RESTRICTED_CAST_FROM_ASCII
qsizetype size() const
Returns the number of characters in this string.
Combined button and popup list for selecting options.
Q_CORE_EXPORT void qWait(int ms)
This is an overloaded member function, provided for convenience. It differs from the above function o...
void qAddPostRoutine(QtCleanUpFunction p)
bool operator==(const QRandomGenerator &rng1, const QRandomGenerator &rng2)
#define qPrintable(string)
QApplication app(argc, argv)
[0]