~ubuntu-branches/ubuntu/wily/qtbase-opensource-src/wily

« back to all changes in this revision

Viewing changes to src/plugins/accessible/widgets/itemviews.cpp

  • Committer: Package Import Robot
  • Author(s): Timo Jyrinki
  • Date: 2013-02-05 12:46:17 UTC
  • Revision ID: package-import@ubuntu.com-20130205124617-c8jouts182j002fx
Tags: upstream-5.0.1+dfsg
ImportĀ upstreamĀ versionĀ 5.0.1+dfsg

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/****************************************************************************
 
2
**
 
3
** Copyright (C) 2012 Digia Plc and/or its subsidiary(-ies).
 
4
** Contact: http://www.qt-project.org/legal
 
5
**
 
6
** This file is part of the plugins of the Qt Toolkit.
 
7
**
 
8
** $QT_BEGIN_LICENSE:LGPL$
 
9
** Commercial License Usage
 
10
** Licensees holding valid commercial Qt licenses may use this file in
 
11
** accordance with the commercial license agreement provided with the
 
12
** Software or, alternatively, in accordance with the terms contained in
 
13
** a written agreement between you and Digia.  For licensing terms and
 
14
** conditions see http://qt.digia.com/licensing.  For further information
 
15
** use the contact form at http://qt.digia.com/contact-us.
 
16
**
 
17
** GNU Lesser General Public License Usage
 
18
** Alternatively, this file may be used under the terms of the GNU Lesser
 
19
** General Public License version 2.1 as published by the Free Software
 
20
** Foundation and appearing in the file LICENSE.LGPL included in the
 
21
** packaging of this file.  Please review the following information to
 
22
** ensure the GNU Lesser General Public License version 2.1 requirements
 
23
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
 
24
**
 
25
** In addition, as a special exception, Digia gives you certain additional
 
26
** rights.  These rights are described in the Digia Qt LGPL Exception
 
27
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
 
28
**
 
29
** GNU General Public License Usage
 
30
** Alternatively, this file may be used under the terms of the GNU
 
31
** General Public License version 3.0 as published by the Free Software
 
32
** Foundation and appearing in the file LICENSE.GPL included in the
 
33
** packaging of this file.  Please review the following information to
 
34
** ensure the GNU General Public License version 3.0 requirements will be
 
35
** met: http://www.gnu.org/copyleft/gpl.html.
 
36
**
 
37
**
 
38
** $QT_END_LICENSE$
 
39
**
 
40
****************************************************************************/
 
41
 
 
42
#include "itemviews.h"
 
43
 
 
44
#include <qheaderview.h>
 
45
#include <qtableview.h>
 
46
#include <qlistview.h>
 
47
#include <qtreeview.h>
 
48
#include <private/qtreewidget_p.h>
 
49
#include <qaccessible2.h>
 
50
#include <QDebug>
 
51
 
 
52
#ifndef QT_NO_ACCESSIBILITY
 
53
 
 
54
QT_BEGIN_NAMESPACE
 
55
 
 
56
QString Q_GUI_EXPORT qt_accStripAmp(const QString &text);
 
57
 
 
58
#ifndef QT_NO_ITEMVIEWS
 
59
/*
 
60
Implementation of the IAccessible2 table2 interface. Much simpler than
 
61
the other table interfaces since there is only the main table and cells:
 
62
 
 
63
TABLE/LIST/TREE
 
64
  |- HEADER CELL
 
65
  |- CELL
 
66
  |- CELL
 
67
  ...
 
68
*/
 
69
 
 
70
 
 
71
QAbstractItemView *QAccessibleTable::view() const
 
72
{
 
73
    return qobject_cast<QAbstractItemView*>(object());
 
74
}
 
75
 
 
76
int QAccessibleTable::logicalIndex(const QModelIndex &index) const
 
77
{
 
78
    if (!view()->model() || !index.isValid())
 
79
        return -1;
 
80
    int vHeader = verticalHeader() ? 1 : 0;
 
81
    int hHeader = horizontalHeader() ? 1 : 0;
 
82
    return (index.row() + hHeader)*(index.model()->columnCount() + vHeader) + (index.column() + vHeader);
 
83
}
 
84
 
 
85
QAccessibleInterface *QAccessibleTable::childFromLogical(int logicalIndex) const
 
86
{
 
87
    if (!view()->model())
 
88
        return 0;
 
89
 
 
90
    int vHeader = verticalHeader() ? 1 : 0;
 
91
    int hHeader = horizontalHeader() ? 1 : 0;
 
92
 
 
93
    int columns = view()->model()->columnCount() + vHeader;
 
94
 
 
95
    int row = logicalIndex / columns;
 
96
    int column = logicalIndex % columns;
 
97
 
 
98
    if (vHeader) {
 
99
        if (column == 0) {
 
100
            if (row == 0) {
 
101
                return new QAccessibleTableCornerButton(view());
 
102
            }
 
103
            return new QAccessibleTableHeaderCell(view(), row-1, Qt::Vertical);
 
104
        }
 
105
        --column;
 
106
    }
 
107
    if (hHeader) {
 
108
        if (row == 0) {
 
109
            return new QAccessibleTableHeaderCell(view(), column, Qt::Horizontal);
 
110
        }
 
111
        --row;
 
112
    }
 
113
 
 
114
    QModelIndex index = view()->model()->index(row, column, view()->rootIndex());
 
115
    if (!index.isValid()) {
 
116
        qWarning() << "QAccessibleTable::childFromLogical: Invalid index at: " << row << column;
 
117
        return 0;
 
118
    }
 
119
    return new QAccessibleTableCell(view(), index, cellRole());
 
120
}
 
121
 
 
122
QAccessibleTable::QAccessibleTable(QWidget *w)
 
123
    : QAccessibleObject(w)
 
124
{
 
125
    Q_ASSERT(view());
 
126
 
 
127
    if (qobject_cast<const QTableView*>(view())) {
 
128
        m_role = QAccessible::Table;
 
129
    } else if (qobject_cast<const QTreeView*>(view())) {
 
130
        m_role = QAccessible::Tree;
 
131
    } else if (qobject_cast<const QListView*>(view())) {
 
132
        m_role = QAccessible::List;
 
133
    } else {
 
134
        // is this our best guess?
 
135
        m_role = QAccessible::Table;
 
136
    }
 
137
}
 
138
 
 
139
QAccessibleTable::~QAccessibleTable()
 
140
{
 
141
}
 
142
 
 
143
QHeaderView *QAccessibleTable::horizontalHeader() const
 
144
{
 
145
    QHeaderView *header = 0;
 
146
    if (false) {
 
147
#ifndef QT_NO_TABLEVIEW
 
148
    } else if (const QTableView *tv = qobject_cast<const QTableView*>(view())) {
 
149
        header = tv->horizontalHeader();
 
150
#endif
 
151
#ifndef QT_NO_TREEVIEW
 
152
    } else if (const QTreeView *tv = qobject_cast<const QTreeView*>(view())) {
 
153
        header = tv->header();
 
154
#endif
 
155
    }
 
156
    return header;
 
157
}
 
158
 
 
159
QHeaderView *QAccessibleTable::verticalHeader() const
 
160
{
 
161
    QHeaderView *header = 0;
 
162
    if (false) {
 
163
#ifndef QT_NO_TABLEVIEW
 
164
    } else if (const QTableView *tv = qobject_cast<const QTableView*>(view())) {
 
165
        header = tv->verticalHeader();
 
166
#endif
 
167
    }
 
168
    return header;
 
169
}
 
170
 
 
171
QAccessibleTableCell *QAccessibleTable::cell(const QModelIndex &index) const
 
172
{
 
173
    if (index.isValid())
 
174
        return new QAccessibleTableCell(view(), index, cellRole());
 
175
    return 0;
 
176
}
 
177
 
 
178
QAccessibleInterface *QAccessibleTable::cellAt(int row, int column) const
 
179
{
 
180
    if (!view()->model())
 
181
        return 0;
 
182
    Q_ASSERT(role() != QAccessible::Tree);
 
183
    QModelIndex index = view()->model()->index(row, column, view()->rootIndex());
 
184
    if (!index.isValid()) {
 
185
        qWarning() << "QAccessibleTable::cellAt: invalid index: " << index << " for " << view();
 
186
        return 0;
 
187
    }
 
188
    return cell(index);
 
189
}
 
190
 
 
191
QAccessibleInterface *QAccessibleTable::caption() const
 
192
{
 
193
    return 0;
 
194
}
 
195
 
 
196
QString QAccessibleTable::columnDescription(int column) const
 
197
{
 
198
    if (!view()->model())
 
199
        return QString();
 
200
    return view()->model()->headerData(column, Qt::Horizontal).toString();
 
201
}
 
202
 
 
203
int QAccessibleTable::columnCount() const
 
204
{
 
205
    if (!view()->model())
 
206
        return 0;
 
207
    return view()->model()->columnCount();
 
208
}
 
209
 
 
210
int QAccessibleTable::rowCount() const
 
211
{
 
212
    if (!view()->model())
 
213
        return 0;
 
214
    return view()->model()->rowCount();
 
215
}
 
216
 
 
217
int QAccessibleTable::selectedCellCount() const
 
218
{
 
219
    if (!view()->selectionModel())
 
220
        return 0;
 
221
    return view()->selectionModel()->selectedIndexes().count();
 
222
}
 
223
 
 
224
int QAccessibleTable::selectedColumnCount() const
 
225
{
 
226
    if (!view()->selectionModel())
 
227
        return 0;
 
228
    return view()->selectionModel()->selectedColumns().count();
 
229
}
 
230
 
 
231
int QAccessibleTable::selectedRowCount() const
 
232
{
 
233
    if (!view()->selectionModel())
 
234
        return 0;
 
235
    return view()->selectionModel()->selectedRows().count();
 
236
}
 
237
 
 
238
QString QAccessibleTable::rowDescription(int row) const
 
239
{
 
240
    if (!view()->model())
 
241
        return QString();
 
242
    return view()->model()->headerData(row, Qt::Vertical).toString();
 
243
}
 
244
 
 
245
QList<QAccessibleInterface *> QAccessibleTable::selectedCells() const
 
246
{
 
247
    QList<QAccessibleInterface*> cells;
 
248
    if (!view()->selectionModel())
 
249
        return cells;
 
250
    Q_FOREACH (const QModelIndex &index, view()->selectionModel()->selectedIndexes()) {
 
251
        cells.append(cell(index));
 
252
    }
 
253
    return cells;
 
254
}
 
255
 
 
256
QList<int> QAccessibleTable::selectedColumns() const
 
257
{
 
258
    if (!view()->selectionModel())
 
259
        return QList<int>();
 
260
    QList<int> columns;
 
261
    Q_FOREACH (const QModelIndex &index, view()->selectionModel()->selectedColumns()) {
 
262
        columns.append(index.column());
 
263
    }
 
264
    return columns;
 
265
}
 
266
 
 
267
QList<int> QAccessibleTable::selectedRows() const
 
268
{
 
269
    if (!view()->selectionModel())
 
270
        return QList<int>();
 
271
    QList<int> rows;
 
272
    Q_FOREACH (const QModelIndex &index, view()->selectionModel()->selectedRows()) {
 
273
        rows.append(index.row());
 
274
    }
 
275
    return rows;
 
276
}
 
277
 
 
278
QAccessibleInterface *QAccessibleTable::summary() const
 
279
{
 
280
    return 0;
 
281
}
 
282
 
 
283
bool QAccessibleTable::isColumnSelected(int column) const
 
284
{
 
285
    if (!view()->selectionModel())
 
286
        return false;
 
287
    return view()->selectionModel()->isColumnSelected(column, QModelIndex());
 
288
}
 
289
 
 
290
bool QAccessibleTable::isRowSelected(int row) const
 
291
{
 
292
    if (!view()->selectionModel())
 
293
        return false;
 
294
    return view()->selectionModel()->isRowSelected(row, QModelIndex());
 
295
}
 
296
 
 
297
bool QAccessibleTable::selectRow(int row)
 
298
{
 
299
    if (!view()->model() || !view()->selectionModel())
 
300
        return false;
 
301
    QModelIndex index = view()->model()->index(row, 0, view()->rootIndex());
 
302
    if (!index.isValid() || view()->selectionMode() & QAbstractItemView::NoSelection)
 
303
        return false;
 
304
    view()->selectionModel()->select(index, QItemSelectionModel::Select);
 
305
    return true;
 
306
}
 
307
 
 
308
bool QAccessibleTable::selectColumn(int column)
 
309
{
 
310
    if (!view()->model() || !view()->selectionModel())
 
311
        return false;
 
312
    QModelIndex index = view()->model()->index(0, column, view()->rootIndex());
 
313
    if (!index.isValid() || view()->selectionMode() & QAbstractItemView::NoSelection)
 
314
        return false;
 
315
    view()->selectionModel()->select(index, QItemSelectionModel::Select);
 
316
    return true;
 
317
}
 
318
 
 
319
bool QAccessibleTable::unselectRow(int row)
 
320
{
 
321
    if (!view()->model() || !view()->selectionModel())
 
322
        return false;
 
323
    QModelIndex index = view()->model()->index(row, 0, view()->rootIndex());
 
324
    if (!index.isValid() || view()->selectionMode() & QAbstractItemView::NoSelection)
 
325
        return false;
 
326
    view()->selectionModel()->select(index, QItemSelectionModel::Deselect);
 
327
    return true;
 
328
}
 
329
 
 
330
bool QAccessibleTable::unselectColumn(int column)
 
331
{
 
332
    if (!view()->model() || !view()->selectionModel())
 
333
        return false;
 
334
    QModelIndex index = view()->model()->index(0, column, view()->rootIndex());
 
335
    if (!index.isValid() || view()->selectionMode() & QAbstractItemView::NoSelection)
 
336
        return false;
 
337
    view()->selectionModel()->select(index, QItemSelectionModel::Columns & QItemSelectionModel::Deselect);
 
338
    return true;
 
339
}
 
340
 
 
341
QAccessible::Role QAccessibleTable::role() const
 
342
{
 
343
    return m_role;
 
344
}
 
345
 
 
346
QAccessible::State QAccessibleTable::state() const
 
347
{
 
348
    return QAccessible::State();
 
349
}
 
350
 
 
351
QAccessibleInterface *QAccessibleTable::childAt(int x, int y) const
 
352
{
 
353
    QPoint viewportOffset = view()->viewport()->mapTo(view(), QPoint(0,0));
 
354
    QPoint indexPosition = view()->mapFromGlobal(QPoint(x, y) - viewportOffset);
 
355
    // FIXME: if indexPosition < 0 in one coordinate, return header
 
356
 
 
357
    QModelIndex index = view()->indexAt(indexPosition);
 
358
    if (index.isValid()) {
 
359
        return childFromLogical(logicalIndex(index));
 
360
    }
 
361
    return 0;
 
362
}
 
363
 
 
364
int QAccessibleTable::childCount() const
 
365
{
 
366
    if (!view()->model())
 
367
        return 0;
 
368
    int vHeader = verticalHeader() ? 1 : 0;
 
369
    int hHeader = horizontalHeader() ? 1 : 0;
 
370
    return (view()->model()->rowCount()+hHeader) * (view()->model()->columnCount()+vHeader);
 
371
}
 
372
 
 
373
int QAccessibleTable::indexOfChild(const QAccessibleInterface *iface) const
 
374
{
 
375
    if (!view()->model())
 
376
        return -1;
 
377
    QSharedPointer<QAccessibleInterface> parent(iface->parent());
 
378
    if (parent->object() != view())
 
379
        return -1;
 
380
 
 
381
    Q_ASSERT(iface->role() != QAccessible::TreeItem); // should be handled by tree class
 
382
    if (iface->role() == QAccessible::Cell || iface->role() == QAccessible::ListItem) {
 
383
        const QAccessibleTableCell* cell = static_cast<const QAccessibleTableCell*>(iface);
 
384
        return logicalIndex(cell->m_index);
 
385
    } else if (iface->role() == QAccessible::ColumnHeader){
 
386
        const QAccessibleTableHeaderCell* cell = static_cast<const QAccessibleTableHeaderCell*>(iface);
 
387
        return cell->index + (verticalHeader() ? 1 : 0);
 
388
    } else if (iface->role() == QAccessible::RowHeader){
 
389
        const QAccessibleTableHeaderCell* cell = static_cast<const QAccessibleTableHeaderCell*>(iface);
 
390
        return (cell->index + 1) * (view()->model()->rowCount() + 1);
 
391
    } else if (iface->role() == QAccessible::Pane) {
 
392
        return 0; // corner button
 
393
    } else {
 
394
        qWarning() << "WARNING QAccessibleTable::indexOfChild Fix my children..."
 
395
                   << iface->role() << iface->text(QAccessible::Name);
 
396
    }
 
397
    // FIXME: we are in denial of our children. this should stop.
 
398
    return -1;
 
399
}
 
400
 
 
401
QString QAccessibleTable::text(QAccessible::Text t) const
 
402
{
 
403
    if (t == QAccessible::Description)
 
404
        return view()->accessibleDescription();
 
405
    return view()->accessibleName();
 
406
}
 
407
 
 
408
QRect QAccessibleTable::rect() const
 
409
{
 
410
    if (!view()->isVisible())
 
411
        return QRect();
 
412
    QPoint pos = view()->mapToGlobal(QPoint(0, 0));
 
413
    return QRect(pos.x(), pos.y(), view()->width(), view()->height());
 
414
}
 
415
 
 
416
QAccessibleInterface *QAccessibleTable::parent() const
 
417
{
 
418
    if (view()->parent()) {
 
419
        if (qstrcmp("QComboBoxPrivateContainer", view()->parent()->metaObject()->className()) == 0) {
 
420
            return QAccessible::queryAccessibleInterface(view()->parent()->parent());
 
421
        }
 
422
        return QAccessible::queryAccessibleInterface(view()->parent());
 
423
    }
 
424
    return 0;
 
425
}
 
426
 
 
427
QAccessibleInterface *QAccessibleTable::child(int index) const
 
428
{
 
429
    return childFromLogical(index);
 
430
}
 
431
 
 
432
void *QAccessibleTable::interface_cast(QAccessible::InterfaceType t)
 
433
{
 
434
    if (t == QAccessible::TableInterface)
 
435
       return static_cast<QAccessibleTableInterface*>(this);
 
436
   return 0;
 
437
}
 
438
 
 
439
// TREE VIEW
 
440
 
 
441
QModelIndex QAccessibleTree::indexFromLogical(int row, int column) const
 
442
{
 
443
    if (!isValid() || !view()->model())
 
444
        return QModelIndex();
 
445
 
 
446
    const QTreeView *treeView = qobject_cast<const QTreeView*>(view());
 
447
    if ((row < 0) || (column < 0) || (treeView->d_func()->viewItems.count() <= row)) {
 
448
        qWarning() << "QAccessibleTree::indexFromLogical: invalid index: " << row << column << " for " << treeView;
 
449
        return QModelIndex();
 
450
    }
 
451
    QModelIndex modelIndex = treeView->d_func()->viewItems.at(row).index;
 
452
 
 
453
    if (modelIndex.isValid() && column > 0) {
 
454
        modelIndex = view()->model()->index(modelIndex.row(), column, modelIndex.parent());
 
455
    }
 
456
    return modelIndex;
 
457
}
 
458
 
 
459
QAccessibleInterface *QAccessibleTree::childAt(int x, int y) const
 
460
{
 
461
    if (!view()->model())
 
462
        return 0;
 
463
    QPoint viewportOffset = view()->viewport()->mapTo(view(), QPoint(0,0));
 
464
    QPoint indexPosition = view()->mapFromGlobal(QPoint(x, y) - viewportOffset);
 
465
 
 
466
    QModelIndex index = view()->indexAt(indexPosition);
 
467
    if (!index.isValid())
 
468
        return 0;
 
469
 
 
470
    const QTreeView *treeView = qobject_cast<const QTreeView*>(view());
 
471
    int row = treeView->d_func()->viewIndex(index) + (horizontalHeader() ? 1 : 0);
 
472
    int column = index.column();
 
473
 
 
474
    int i = row * view()->model()->columnCount() + column;
 
475
    return child(i);
 
476
}
 
477
 
 
478
int QAccessibleTree::childCount() const
 
479
{
 
480
    const QTreeView *treeView = qobject_cast<const QTreeView*>(view());
 
481
    Q_ASSERT(treeView);
 
482
    if (!view()->model())
 
483
        return 0;
 
484
 
 
485
    int hHeader = horizontalHeader() ? 1 : 0;
 
486
    return (treeView->d_func()->viewItems.count() + hHeader)* view()->model()->columnCount();
 
487
}
 
488
 
 
489
 
 
490
QAccessibleInterface *QAccessibleTree::child(int index) const
 
491
{
 
492
    if ((index < 0) || (!view()->model()))
 
493
        return 0;
 
494
    int hHeader = horizontalHeader() ? 1 : 0;
 
495
 
 
496
    if (hHeader) {
 
497
        if (index < view()->model()->columnCount()) {
 
498
            return new QAccessibleTableHeaderCell(view(), index, Qt::Horizontal);
 
499
        } else {
 
500
            index -= view()->model()->columnCount();
 
501
        }
 
502
    }
 
503
 
 
504
    int row = index / view()->model()->columnCount();
 
505
    int column = index % view()->model()->columnCount();
 
506
    QModelIndex modelIndex = indexFromLogical(row, column);
 
507
    if (modelIndex.isValid()) {
 
508
        return cell(modelIndex);
 
509
    }
 
510
    return 0;
 
511
}
 
512
 
 
513
int QAccessibleTree::rowCount() const
 
514
{
 
515
    const QTreeView *treeView = qobject_cast<const QTreeView*>(view());
 
516
    Q_ASSERT(treeView);
 
517
    return treeView->d_func()->viewItems.count();
 
518
}
 
519
 
 
520
int QAccessibleTree::indexOfChild(const QAccessibleInterface *iface) const
 
521
{
 
522
    if (!view()->model())
 
523
        return -1;
 
524
    QSharedPointer<QAccessibleInterface> parent(iface->parent());
 
525
    if (parent->object() != view())
 
526
        return -1;
 
527
 
 
528
    if (iface->role() == QAccessible::TreeItem) {
 
529
        const QAccessibleTableCell* cell = static_cast<const QAccessibleTableCell*>(iface);
 
530
        const QTreeView *treeView = qobject_cast<const QTreeView*>(view());
 
531
        Q_ASSERT(treeView);
 
532
        int row = treeView->d_func()->viewIndex(cell->m_index) + (horizontalHeader() ? 1 : 0);
 
533
        int column = cell->m_index.column();
 
534
 
 
535
        int index = row * view()->model()->columnCount() + column;
 
536
        //qDebug() << "QAccessibleTree::indexOfChild r " << row << " c " << column << "index " << index;
 
537
        Q_ASSERT(index >= treeView->model()->columnCount());
 
538
        return index;
 
539
    } else if (iface->role() == QAccessible::ColumnHeader){
 
540
        const QAccessibleTableHeaderCell* cell = static_cast<const QAccessibleTableHeaderCell*>(iface);
 
541
        //qDebug() << "QAccessibleTree::indexOfChild header " << cell->index;
 
542
        return cell->index;
 
543
    } else {
 
544
        qWarning() << "WARNING QAccessibleTable::indexOfChild invalid child"
 
545
                   << iface->role() << iface->text(QAccessible::Name);
 
546
    }
 
547
    // FIXME: add scrollbars and don't just ignore them
 
548
    return -1;
 
549
}
 
550
 
 
551
QAccessibleInterface *QAccessibleTree::cellAt(int row, int column) const
 
552
{
 
553
    QModelIndex index = indexFromLogical(row, column);
 
554
    if (!index.isValid()) {
 
555
        qWarning() << "Requested invalid tree cell: " << row << column;
 
556
        return 0;
 
557
    }
 
558
    return new QAccessibleTableCell(view(), index, cellRole());
 
559
}
 
560
 
 
561
QString QAccessibleTree::rowDescription(int) const
 
562
{
 
563
    return QString(); // no headers for rows in trees
 
564
}
 
565
 
 
566
bool QAccessibleTree::isRowSelected(int row) const
 
567
{
 
568
    if (!view()->selectionModel())
 
569
        return false;
 
570
    QModelIndex index = indexFromLogical(row);
 
571
    return view()->selectionModel()->isRowSelected(index.row(), index.parent());
 
572
}
 
573
 
 
574
bool QAccessibleTree::selectRow(int row)
 
575
{
 
576
    if (!view()->selectionModel())
 
577
        return false;
 
578
    QModelIndex index = indexFromLogical(row);
 
579
    if (!index.isValid() || view()->selectionMode() & QAbstractItemView::NoSelection)
 
580
        return false;
 
581
    view()->selectionModel()->select(index, QItemSelectionModel::Select);
 
582
    return true;
 
583
}
 
584
 
 
585
// TABLE CELL
 
586
 
 
587
QAccessibleTableCell::QAccessibleTableCell(QAbstractItemView *view_, const QModelIndex &index_, QAccessible::Role role_)
 
588
    : /* QAccessibleSimpleEditableTextInterface(this), */ view(view_), m_index(index_), m_role(role_)
 
589
{
 
590
    if (!index_.isValid())
 
591
        qWarning() << "QAccessibleTableCell::QAccessibleTableCell with invalid index: " << index_;
 
592
}
 
593
 
 
594
void *QAccessibleTableCell::interface_cast(QAccessible::InterfaceType t)
 
595
{
 
596
    if (t == QAccessible::TableCellInterface)
 
597
        return static_cast<QAccessibleTableCellInterface*>(this);
 
598
    return 0;
 
599
}
 
600
 
 
601
int QAccessibleTableCell::columnExtent() const { return 1; }
 
602
int QAccessibleTableCell::rowExtent() const { return 1; }
 
603
 
 
604
QList<QAccessibleInterface*> QAccessibleTableCell::rowHeaderCells() const
 
605
{
 
606
    QList<QAccessibleInterface*> headerCell;
 
607
    if (verticalHeader()) {
 
608
        headerCell.append(new QAccessibleTableHeaderCell(view, m_index.row(), Qt::Vertical));
 
609
    }
 
610
    return headerCell;
 
611
}
 
612
 
 
613
QList<QAccessibleInterface*> QAccessibleTableCell::columnHeaderCells() const
 
614
{
 
615
    QList<QAccessibleInterface*> headerCell;
 
616
    if (horizontalHeader()) {
 
617
        headerCell.append(new QAccessibleTableHeaderCell(view, m_index.column(), Qt::Horizontal));
 
618
    }
 
619
    return headerCell;
 
620
}
 
621
 
 
622
QHeaderView *QAccessibleTableCell::horizontalHeader() const
 
623
{
 
624
    QHeaderView *header = 0;
 
625
 
 
626
    if (false) {
 
627
#ifndef QT_NO_TABLEVIEW
 
628
    } else if (const QTableView *tv = qobject_cast<const QTableView*>(view)) {
 
629
        header = tv->horizontalHeader();
 
630
#endif
 
631
#ifndef QT_NO_TREEVIEW
 
632
    } else if (const QTreeView *tv = qobject_cast<const QTreeView*>(view)) {
 
633
        header = tv->header();
 
634
#endif
 
635
    }
 
636
 
 
637
    return header;
 
638
}
 
639
 
 
640
QHeaderView *QAccessibleTableCell::verticalHeader() const
 
641
{
 
642
    QHeaderView *header = 0;
 
643
#ifndef QT_NO_TABLEVIEW
 
644
    if (const QTableView *tv = qobject_cast<const QTableView*>(view))
 
645
        header = tv->verticalHeader();
 
646
#endif
 
647
    return header;
 
648
}
 
649
 
 
650
int QAccessibleTableCell::columnIndex() const
 
651
{
 
652
    return m_index.column();
 
653
}
 
654
 
 
655
int QAccessibleTableCell::rowIndex() const
 
656
{
 
657
    if (role() == QAccessible::TreeItem) {
 
658
       const QTreeView *treeView = qobject_cast<const QTreeView*>(view);
 
659
       Q_ASSERT(treeView);
 
660
       int row = treeView->d_func()->viewIndex(m_index);
 
661
       return row;
 
662
    }
 
663
    return m_index.row();
 
664
}
 
665
 
 
666
bool QAccessibleTableCell::isSelected() const
 
667
{
 
668
    return view->selectionModel()->isSelected(m_index);
 
669
}
 
670
 
 
671
void QAccessibleTableCell::rowColumnExtents(int *row, int *column, int *rowExtents, int *columnExtents, bool *selected) const
 
672
{
 
673
    *row = m_index.row();
 
674
    *column = m_index.column();
 
675
    *rowExtents = 1;
 
676
    *columnExtents = 1;
 
677
    *selected = isSelected();
 
678
}
 
679
 
 
680
QAccessibleInterface *QAccessibleTableCell::table() const
 
681
{
 
682
    return QAccessible::queryAccessibleInterface(view);
 
683
}
 
684
 
 
685
QAccessible::Role QAccessibleTableCell::role() const
 
686
{
 
687
    return m_role;
 
688
}
 
689
 
 
690
QAccessible::State QAccessibleTableCell::state() const
 
691
{
 
692
    QAccessible::State st;
 
693
    QRect globalRect = view->rect();
 
694
    globalRect.translate(view->mapToGlobal(QPoint(0,0)));
 
695
    if (!globalRect.intersects(rect()))
 
696
        st.invisible = true;
 
697
 
 
698
    if (view->selectionModel()->isSelected(m_index))
 
699
        st.selected = true;
 
700
    if (view->selectionModel()->currentIndex() == m_index)
 
701
        st.focused = true;
 
702
    if (m_index.model()->data(m_index, Qt::CheckStateRole).toInt() == Qt::Checked)
 
703
        st.checked = true;
 
704
 
 
705
    Qt::ItemFlags flags = m_index.flags();
 
706
    if (flags & Qt::ItemIsSelectable) {
 
707
        st.selectable = true;
 
708
        st.focusable = true;
 
709
        if (view->selectionMode() == QAbstractItemView::MultiSelection)
 
710
            st.multiSelectable = true;
 
711
        if (view->selectionMode() == QAbstractItemView::ExtendedSelection)
 
712
            st.extSelectable = true;
 
713
    }
 
714
    if (m_role == QAccessible::TreeItem) {
 
715
        const QTreeView *treeView = qobject_cast<const QTreeView*>(view);
 
716
        if (treeView->model()->hasChildren(m_index))
 
717
            st.expandable = true;
 
718
        if (treeView->isExpanded(m_index))
 
719
            st.expanded = true;
 
720
    }
 
721
    return st;
 
722
}
 
723
 
 
724
 
 
725
QRect QAccessibleTableCell::rect() const
 
726
{
 
727
    QRect r;
 
728
    r = view->visualRect(m_index);
 
729
 
 
730
    if (!r.isNull())
 
731
        r.translate(view->viewport()->mapTo(view, QPoint(0,0)));
 
732
        r.translate(view->mapToGlobal(QPoint(0, 0)));
 
733
    return r;
 
734
}
 
735
 
 
736
QString QAccessibleTableCell::text(QAccessible::Text t) const
 
737
{
 
738
    QAbstractItemModel *model = view->model();
 
739
    QString value;
 
740
    switch (t) {
 
741
    case QAccessible::Value:
 
742
    case QAccessible::Name:
 
743
        value = model->data(m_index, Qt::AccessibleTextRole).toString();
 
744
        if (value.isEmpty())
 
745
            value = model->data(m_index, Qt::DisplayRole).toString();
 
746
        break;
 
747
    case QAccessible::Description:
 
748
        value = model->data(m_index, Qt::AccessibleDescriptionRole).toString();
 
749
        break;
 
750
    default:
 
751
        break;
 
752
    }
 
753
    return value;
 
754
}
 
755
 
 
756
void QAccessibleTableCell::setText(QAccessible::Text /*t*/, const QString &text)
 
757
{
 
758
    if (!(m_index.flags() & Qt::ItemIsEditable))
 
759
        return;
 
760
    view->model()->setData(m_index, text);
 
761
}
 
762
 
 
763
bool QAccessibleTableCell::isValid() const
 
764
{
 
765
    return view && view->model() && m_index.isValid();
 
766
}
 
767
 
 
768
QAccessibleInterface *QAccessibleTableCell::parent() const
 
769
{
 
770
    if (m_role == QAccessible::TreeItem)
 
771
        return new QAccessibleTree(view);
 
772
 
 
773
    return new QAccessibleTable(view);
 
774
}
 
775
 
 
776
QAccessibleInterface *QAccessibleTableCell::child(int) const
 
777
{
 
778
    return 0;
 
779
}
 
780
 
 
781
QAccessibleTableHeaderCell::QAccessibleTableHeaderCell(QAbstractItemView *view_, int index_, Qt::Orientation orientation_)
 
782
    : view(view_), index(index_), orientation(orientation_)
 
783
{
 
784
    Q_ASSERT(index_ >= 0);
 
785
}
 
786
 
 
787
QAccessible::Role QAccessibleTableHeaderCell::role() const
 
788
{
 
789
    if (orientation == Qt::Horizontal)
 
790
        return QAccessible::ColumnHeader;
 
791
    return QAccessible::RowHeader;
 
792
}
 
793
 
 
794
QAccessible::State QAccessibleTableHeaderCell::state() const
 
795
{
 
796
    return QAccessible::State();
 
797
}
 
798
 
 
799
QRect QAccessibleTableHeaderCell::rect() const
 
800
{
 
801
    QHeaderView *header = 0;
 
802
    if (false) {
 
803
#ifndef QT_NO_TABLEVIEW
 
804
    } else if (const QTableView *tv = qobject_cast<const QTableView*>(view)) {
 
805
        if (orientation == Qt::Horizontal) {
 
806
            header = tv->horizontalHeader();
 
807
        } else {
 
808
            header = tv->verticalHeader();
 
809
        }
 
810
#endif
 
811
#ifndef QT_NO_TREEVIEW
 
812
    } else if (const QTreeView *tv = qobject_cast<const QTreeView*>(view)) {
 
813
        header = tv->header();
 
814
#endif
 
815
    }
 
816
    if (!header)
 
817
        return QRect();
 
818
    QPoint zero = header->mapToGlobal(QPoint(0, 0));
 
819
    int sectionSize = header->sectionSize(index);
 
820
    int sectionPos = header->sectionPosition(index);
 
821
    return orientation == Qt::Horizontal
 
822
            ? QRect(zero.x() + sectionPos, zero.y(), sectionSize, header->height())
 
823
            : QRect(zero.x(), zero.y() + sectionPos, header->width(), sectionSize);
 
824
}
 
825
 
 
826
QString QAccessibleTableHeaderCell::text(QAccessible::Text t) const
 
827
{
 
828
    QAbstractItemModel *model = view->model();
 
829
    QString value;
 
830
    switch (t) {
 
831
    case QAccessible::Value:
 
832
    case QAccessible::Name:
 
833
        value = model->headerData(index, orientation, Qt::AccessibleTextRole).toString();
 
834
        if (value.isEmpty())
 
835
            value = model->headerData(index, orientation, Qt::DisplayRole).toString();
 
836
        break;
 
837
    case QAccessible::Description:
 
838
        value = model->headerData(index, orientation, Qt::AccessibleDescriptionRole).toString();
 
839
        break;
 
840
    default:
 
841
        break;
 
842
    }
 
843
    return value;
 
844
}
 
845
 
 
846
void QAccessibleTableHeaderCell::setText(QAccessible::Text, const QString &)
 
847
{
 
848
    return;
 
849
}
 
850
 
 
851
bool QAccessibleTableHeaderCell::isValid() const
 
852
{
 
853
    return view && view->model() && (index >= 0)
 
854
            && ((orientation == Qt::Horizontal) ? (index < view->model()->columnCount()) : (index < view->model()->rowCount()));
 
855
}
 
856
 
 
857
QAccessibleInterface *QAccessibleTableHeaderCell::parent() const
 
858
{
 
859
    if (false) {
 
860
#ifndef QT_NO_TREEVIEW
 
861
    } else if (qobject_cast<const QTreeView*>(view)) {
 
862
        return new QAccessibleTree(view);
 
863
#endif
 
864
    } else {
 
865
        return new QAccessibleTable(view);
 
866
    }
 
867
}
 
868
 
 
869
QAccessibleInterface *QAccessibleTableHeaderCell::child(int) const
 
870
{
 
871
    return 0;
 
872
}
 
873
 
 
874
#endif // QT_NO_ITEMVIEWS
 
875
 
 
876
QT_END_NAMESPACE
 
877
 
 
878
#endif // QT_NO_ACCESSIBILITY