tools/designer/src/lib/shared/actionrepository.cpp
changeset 0 1918ee327afb
child 3 41300fa6a67c
equal deleted inserted replaced
-1:000000000000 0:1918ee327afb
       
     1 /****************************************************************************
       
     2 **
       
     3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
       
     4 ** All rights reserved.
       
     5 ** Contact: Nokia Corporation (qt-info@nokia.com)
       
     6 **
       
     7 ** This file is part of the Qt Designer of the Qt Toolkit.
       
     8 **
       
     9 ** $QT_BEGIN_LICENSE:LGPL$
       
    10 ** No Commercial Usage
       
    11 ** This file contains pre-release code and may not be distributed.
       
    12 ** You may use this file in accordance with the terms and conditions
       
    13 ** contained in the Technology Preview License Agreement accompanying
       
    14 ** this package.
       
    15 **
       
    16 ** GNU Lesser General Public License Usage
       
    17 ** Alternatively, this file may be used under the terms of the GNU Lesser
       
    18 ** General Public License version 2.1 as published by the Free Software
       
    19 ** Foundation and appearing in the file LICENSE.LGPL included in the
       
    20 ** packaging of this file.  Please review the following information to
       
    21 ** ensure the GNU Lesser General Public License version 2.1 requirements
       
    22 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
       
    23 **
       
    24 ** In addition, as a special exception, Nokia gives you certain additional
       
    25 ** rights.  These rights are described in the Nokia Qt LGPL Exception
       
    26 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
       
    27 **
       
    28 ** If you have questions regarding the use of this file, please contact
       
    29 ** Nokia at qt-info@nokia.com.
       
    30 **
       
    31 **
       
    32 **
       
    33 **
       
    34 **
       
    35 **
       
    36 **
       
    37 **
       
    38 ** $QT_END_LICENSE$
       
    39 **
       
    40 ****************************************************************************/
       
    41 
       
    42 #include "actionrepository_p.h"
       
    43 #include "qtresourceview_p.h"
       
    44 #include "iconloader_p.h"
       
    45 #include "qdesigner_utils_p.h"
       
    46 
       
    47 #include <QtDesigner/QDesignerFormEditorInterface>
       
    48 #include <QtDesigner/QDesignerPropertySheetExtension>
       
    49 #include <QtDesigner/QExtensionManager>
       
    50 
       
    51 #include <QtGui/QDrag>
       
    52 #include <QtGui/QContextMenuEvent>
       
    53 #include <QtGui/QStandardItemModel>
       
    54 #include <QtGui/QToolButton>
       
    55 #include <QtGui/QPixmap>
       
    56 #include <QtGui/QAction>
       
    57 #include <QtGui/QHeaderView>
       
    58 #include <QtGui/QToolBar>
       
    59 #include <QtGui/QMenu>
       
    60 #include <QtGui/qevent.h>
       
    61 #include <QtCore/QSet>
       
    62 #include <QtCore/QDebug>
       
    63 
       
    64 Q_DECLARE_METATYPE(QAction*)
       
    65 
       
    66 QT_BEGIN_NAMESPACE
       
    67 
       
    68 namespace {
       
    69     enum { listModeIconSize = 16, iconModeIconSize = 24 };
       
    70 }
       
    71 
       
    72 static const char *actionMimeType = "action-repository/actions";
       
    73 static const char *plainTextMimeType = "text/plain";
       
    74 
       
    75 static inline QAction *actionOfItem(const QStandardItem* item)
       
    76 {
       
    77     return qvariant_cast<QAction*>(item->data(qdesigner_internal::ActionModel::ActionRole));
       
    78 }
       
    79 
       
    80 static QIcon fixActionIcon(const QIcon &icon)
       
    81 {
       
    82     if (icon.isNull())
       
    83         return qdesigner_internal::emptyIcon();
       
    84     return icon;
       
    85 }
       
    86 
       
    87 namespace qdesigner_internal {
       
    88 
       
    89 // ----------- ActionModel
       
    90 ActionModel::ActionModel(QWidget *parent ) :
       
    91     QStandardItemModel(parent),
       
    92     m_core(0)
       
    93 {
       
    94     QStringList headers;
       
    95     headers += tr("Name");
       
    96     headers += tr("Used");
       
    97     headers += tr("Text");
       
    98     headers += tr("Shortcut");
       
    99     headers += tr("Checkable");
       
   100     headers += tr("ToolTip");
       
   101     Q_ASSERT(NumColumns == headers.size());
       
   102     setHorizontalHeaderLabels(headers);
       
   103 }
       
   104 
       
   105 void ActionModel::clearActions()
       
   106 {
       
   107     removeRows(0, rowCount());
       
   108 }
       
   109 
       
   110 int ActionModel::findAction(QAction *action) const
       
   111 {
       
   112     const int rows = rowCount();
       
   113     for (int i = 0; i < rows; i++)
       
   114        if (action == actionOfItem(item(i)))
       
   115            return i;
       
   116     return -1;
       
   117 }
       
   118 
       
   119 void ActionModel::update(int row)
       
   120 {
       
   121     Q_ASSERT(m_core);
       
   122     // need to create the row list ... grrr..
       
   123     if (row >= rowCount())
       
   124        return;
       
   125 
       
   126     QStandardItemList list;
       
   127     for (int i = 0; i < NumColumns; i++)
       
   128        list += item(row, i);
       
   129 
       
   130     setItems(m_core, actionOfItem(list.front()), list);
       
   131 }
       
   132 
       
   133 void ActionModel::remove(int row)
       
   134 {
       
   135     qDeleteAll(takeRow(row));
       
   136 }
       
   137 
       
   138 QModelIndex ActionModel::addAction(QAction *action)
       
   139 {
       
   140     Q_ASSERT(m_core);
       
   141     QStandardItemList items;
       
   142     const  Qt::ItemFlags flags = Qt::ItemIsSelectable|Qt::ItemIsDropEnabled|Qt::ItemIsDragEnabled|Qt::ItemIsEnabled;
       
   143 
       
   144     QVariant itemData;
       
   145     qVariantSetValue(itemData, action);
       
   146 
       
   147     for (int i = 0; i < NumColumns; i++) {
       
   148         QStandardItem *item = new QStandardItem;
       
   149         item->setData(itemData, ActionRole);
       
   150         item->setFlags(flags);
       
   151         items.push_back(item);
       
   152     }
       
   153     setItems(m_core, action, items);
       
   154     appendRow(items);
       
   155     return indexFromItem(items.front());
       
   156 }
       
   157 
       
   158 // Find the associated menus and toolbars, ignore toolbuttons
       
   159 QWidgetList ActionModel::associatedWidgets(const QAction *action)
       
   160 {
       
   161     QWidgetList rc = action->associatedWidgets();
       
   162     for (QWidgetList::iterator it = rc.begin(); it != rc.end(); )
       
   163         if (qobject_cast<const QMenu *>(*it) || qobject_cast<const QToolBar *>(*it)) {
       
   164             ++it;
       
   165         } else {
       
   166             it = rc.erase(it);
       
   167         }
       
   168     return rc;
       
   169 }
       
   170 
       
   171 // shortcut is a fake property, need to retrieve it via property sheet.
       
   172 PropertySheetKeySequenceValue ActionModel::actionShortCut(QDesignerFormEditorInterface *core, QAction *action)
       
   173 {
       
   174     QDesignerPropertySheetExtension *sheet = qt_extension<QDesignerPropertySheetExtension*>(core->extensionManager(), action);
       
   175     if (!sheet)
       
   176         return PropertySheetKeySequenceValue();
       
   177     return actionShortCut(sheet);
       
   178 }
       
   179 
       
   180 PropertySheetKeySequenceValue ActionModel::actionShortCut(const QDesignerPropertySheetExtension *sheet)
       
   181 {
       
   182     const int index = sheet->indexOf(QLatin1String("shortcut"));
       
   183     if (index == -1)
       
   184         return PropertySheetKeySequenceValue();
       
   185     return qvariant_cast<PropertySheetKeySequenceValue>(sheet->property(index));
       
   186 }
       
   187 
       
   188 void  ActionModel::setItems(QDesignerFormEditorInterface *core, QAction *action, QStandardItemList &sl)
       
   189 {
       
   190 
       
   191     // Tooltip, mostly for icon view mode
       
   192     QString firstTooltip = action->objectName();
       
   193     const QString text = action->text();
       
   194     if (!text.isEmpty()) {
       
   195         firstTooltip += QLatin1Char('\n');
       
   196         firstTooltip += text;
       
   197     }
       
   198 
       
   199     Q_ASSERT(sl.size() == NumColumns);
       
   200 
       
   201     QStandardItem *item =  sl[NameColumn];
       
   202     item->setText(action->objectName());
       
   203     item->setIcon(fixActionIcon(action->icon()));
       
   204     item->setToolTip(firstTooltip);
       
   205     item->setWhatsThis(firstTooltip);
       
   206     // Used
       
   207     const QWidgetList associatedDesignerWidgets = associatedWidgets(action);
       
   208     const bool used = !associatedDesignerWidgets.empty();
       
   209     item = sl[UsedColumn];
       
   210     item->setCheckState(used ? Qt::Checked : Qt::Unchecked);
       
   211     if (used) {
       
   212         QString usedToolTip;
       
   213         const QString separator = QLatin1String(", ");
       
   214         const int count = associatedDesignerWidgets.size();
       
   215         for (int i = 0; i < count; i++) {
       
   216             if (i)
       
   217                 usedToolTip += separator;
       
   218             usedToolTip += associatedDesignerWidgets.at(i)->objectName();
       
   219         }
       
   220         item->setToolTip(usedToolTip);
       
   221     } else {
       
   222         item->setToolTip(QString());
       
   223     }
       
   224     // text
       
   225     item = sl[TextColumn];
       
   226     item->setText(action->text());
       
   227     item->setToolTip(action->text());
       
   228     // shortcut
       
   229     const QString shortcut = actionShortCut(core, action).value().toString();
       
   230     item = sl[ShortCutColumn];
       
   231     item->setText(shortcut);
       
   232     item->setToolTip(shortcut);
       
   233     // checkable
       
   234     sl[CheckedColumn]->setCheckState(action->isCheckable() ?  Qt::Checked : Qt::Unchecked);
       
   235     // ToolTip. This might be multi-line, rich text
       
   236     QString toolTip = action->toolTip();
       
   237     item = sl[ToolTipColumn];
       
   238     item->setToolTip(toolTip);
       
   239     item->setText(toolTip.replace(QLatin1Char('\n'), QLatin1Char(' ')));
       
   240 }
       
   241 
       
   242 QMimeData *ActionModel::mimeData(const QModelIndexList &indexes ) const
       
   243 {
       
   244     ActionRepositoryMimeData::ActionList actionList;
       
   245 
       
   246     QSet<QAction*> actions;
       
   247     foreach (const  QModelIndex &index, indexes)
       
   248         if (QStandardItem *item = itemFromIndex(index))
       
   249             if (QAction *action = actionOfItem(item))
       
   250                 actions.insert(action);
       
   251     return new ActionRepositoryMimeData(actions.toList(), Qt::CopyAction);
       
   252 }
       
   253 
       
   254 // Resource images are plain text. The drag needs to be restricted, however.
       
   255 QStringList ActionModel::mimeTypes() const
       
   256 {
       
   257     return QStringList(QLatin1String(plainTextMimeType));
       
   258 }
       
   259 
       
   260 QString ActionModel::actionName(int row) const
       
   261 {
       
   262     return item(row, NameColumn)->text();
       
   263 }
       
   264 
       
   265 bool ActionModel::dropMimeData(const QMimeData *data, Qt::DropAction action, int row, int column, const QModelIndex &)
       
   266 {
       
   267   if (action != Qt::CopyAction)
       
   268         return false;
       
   269 
       
   270     QStandardItem *droppedItem = item(row, column);
       
   271     if (!droppedItem)
       
   272         return false;
       
   273 
       
   274 
       
   275     QtResourceView::ResourceType type;
       
   276     QString path;
       
   277     if (!QtResourceView::decodeMimeData(data, &type, &path) || type !=  QtResourceView::ResourceImage)
       
   278         return false;
       
   279 
       
   280     emit resourceImageDropped(path, actionOfItem(droppedItem));
       
   281     return true;
       
   282 }
       
   283 
       
   284 QAction *ActionModel::actionAt(const  QModelIndex &index) const
       
   285 {
       
   286     if (!index.isValid())
       
   287         return 0;
       
   288     QStandardItem *i = itemFromIndex(index);
       
   289     if (!i)
       
   290         return 0;
       
   291     return actionOfItem(i);
       
   292 }
       
   293 
       
   294 // helpers
       
   295 
       
   296 static bool handleImageDragEnterMoveEvent(QDropEvent *event)
       
   297 {
       
   298     QtResourceView::ResourceType type;
       
   299     const bool rc = QtResourceView::decodeMimeData(event->mimeData(), &type) && type ==  QtResourceView::ResourceImage;
       
   300     if (rc)
       
   301         event->acceptProposedAction();
       
   302     else
       
   303         event->ignore();
       
   304     return rc;
       
   305 }
       
   306 
       
   307 static void handleImageDropEvent(const QAbstractItemView *iv, QDropEvent *event, ActionModel *am)
       
   308 {
       
   309     const QModelIndex index = iv->indexAt(event->pos());
       
   310     if (!index.isValid()) {
       
   311         event->ignore();
       
   312         return;
       
   313     }
       
   314 
       
   315     if (!handleImageDragEnterMoveEvent(event))
       
   316         return;
       
   317 
       
   318     am->dropMimeData(event->mimeData(),  event->proposedAction(), index.row(), 0, iv->rootIndex());
       
   319 }
       
   320 
       
   321 // Basically mimic  QAbstractItemView's startDrag routine, except that
       
   322 // another pixmap is used, we don't want the whole row.
       
   323 
       
   324 void startActionDrag(QWidget *dragParent, ActionModel *model, const QModelIndexList &indexes, Qt::DropActions supportedActions)
       
   325 {
       
   326     if (indexes.empty())
       
   327         return;
       
   328 
       
   329     QDrag *drag = new QDrag(dragParent);
       
   330     QMimeData *data = model->mimeData(indexes);
       
   331     drag->setMimeData(data);
       
   332     if (ActionRepositoryMimeData *actionMimeData = qobject_cast<ActionRepositoryMimeData *>(data))
       
   333         drag->setPixmap(ActionRepositoryMimeData::actionDragPixmap(actionMimeData->actionList().front()));
       
   334 
       
   335     drag->start(supportedActions);
       
   336 }
       
   337 
       
   338 // ---------------- ActionTreeView:
       
   339 ActionTreeView::ActionTreeView(ActionModel *model, QWidget *parent) :
       
   340     QTreeView(parent),
       
   341     m_model(model)
       
   342 {
       
   343     setDragEnabled(true);
       
   344     setAcceptDrops(true);
       
   345     setDropIndicatorShown(true);
       
   346     setDragDropMode(DragDrop);
       
   347     setModel(model);
       
   348     setRootIsDecorated(false);
       
   349     setTextElideMode(Qt::ElideMiddle);
       
   350 
       
   351     setModel(model);
       
   352     connect(this, SIGNAL(activated(QModelIndex)), this, SLOT(slotActivated(QModelIndex)));
       
   353     connect(header(), SIGNAL(sectionDoubleClicked(int)), this, SLOT(resizeColumnToContents(int)));
       
   354 
       
   355     setIconSize(QSize(listModeIconSize, listModeIconSize));
       
   356 
       
   357 }
       
   358 
       
   359 QAction *ActionTreeView::currentAction() const
       
   360 {
       
   361     return m_model->actionAt(currentIndex());
       
   362 }
       
   363 
       
   364 void ActionTreeView::filter(const QString &text)
       
   365 {
       
   366     const int rowCount = m_model->rowCount();
       
   367     const bool empty = text.isEmpty();
       
   368     const QModelIndex parent = rootIndex();
       
   369     for (int i = 0; i < rowCount; i++)
       
   370         setRowHidden(i, parent, !empty && !m_model->actionName(i).contains(text, Qt::CaseInsensitive));
       
   371 }
       
   372 
       
   373 void ActionTreeView::dragEnterEvent(QDragEnterEvent *event)
       
   374 {
       
   375     handleImageDragEnterMoveEvent(event);
       
   376 }
       
   377 
       
   378 void ActionTreeView::dragMoveEvent(QDragMoveEvent *event)
       
   379 {
       
   380     handleImageDragEnterMoveEvent(event);
       
   381 }
       
   382 
       
   383 void ActionTreeView::dropEvent(QDropEvent *event)
       
   384 {
       
   385     handleImageDropEvent(this, event, m_model);
       
   386 }
       
   387 
       
   388 void ActionTreeView::focusInEvent(QFocusEvent *event)
       
   389 {
       
   390     QTreeView::focusInEvent(event);
       
   391     // Make property editor display current action
       
   392     if (QAction *a = currentAction())
       
   393        emit currentChanged(a);
       
   394 }
       
   395 
       
   396 void ActionTreeView::contextMenuEvent(QContextMenuEvent *event)
       
   397 {
       
   398     emit contextMenuRequested(event, m_model->actionAt(indexAt(event->pos())));
       
   399 }
       
   400 
       
   401 void ActionTreeView::currentChanged(const QModelIndex &current, const QModelIndex &/*previous*/)
       
   402 {
       
   403     emit currentChanged(m_model->actionAt(current));
       
   404 }
       
   405 
       
   406 void ActionTreeView::slotActivated(const QModelIndex &index)
       
   407 {
       
   408     emit activated(m_model->actionAt(index));
       
   409 }
       
   410 
       
   411 void ActionTreeView::startDrag(Qt::DropActions supportedActions)
       
   412 {
       
   413     startActionDrag(this, m_model, selectedIndexes(), supportedActions);
       
   414 }
       
   415 
       
   416 // ---------------- ActionListView:
       
   417 ActionListView::ActionListView(ActionModel *model, QWidget *parent) :
       
   418     QListView(parent),
       
   419     m_model(model)
       
   420 {
       
   421     setDragEnabled(true);
       
   422     setAcceptDrops(true);
       
   423     setDropIndicatorShown(true);
       
   424     setDragDropMode(DragDrop);
       
   425     setModel(model);
       
   426     setTextElideMode(Qt::ElideMiddle);
       
   427     connect(this, SIGNAL(activated(QModelIndex)), this, SLOT(slotActivated(QModelIndex)));
       
   428 
       
   429     // We actually want 'Static' as the user should be able to
       
   430     // drag away actions only (not to rearrange icons).
       
   431     // We emulate that by not accepting our own
       
   432     // drag data. 'Static' causes the list view to disable drag and drop
       
   433     // on the viewport.
       
   434     setMovement(Snap);
       
   435     setViewMode(IconMode);
       
   436     setIconSize(QSize(iconModeIconSize, iconModeIconSize));
       
   437     setGridSize(QSize(4 * iconModeIconSize, 2 *  iconModeIconSize));
       
   438     setSpacing(iconModeIconSize / 3);
       
   439 }
       
   440 
       
   441 QAction *ActionListView::currentAction() const
       
   442 {
       
   443     return m_model->actionAt(currentIndex());
       
   444 }
       
   445 
       
   446 void ActionListView::filter(const QString &text)
       
   447 {
       
   448     const int rowCount = m_model->rowCount();
       
   449     const bool empty = text.isEmpty();
       
   450     for (int i = 0; i < rowCount; i++)
       
   451         setRowHidden(i, !empty && !m_model->actionName(i).contains(text, Qt::CaseInsensitive));
       
   452 }
       
   453 
       
   454 void ActionListView::dragEnterEvent(QDragEnterEvent *event)
       
   455 {
       
   456     handleImageDragEnterMoveEvent(event);
       
   457 }
       
   458 
       
   459 void ActionListView::dragMoveEvent(QDragMoveEvent *event)
       
   460 {
       
   461     handleImageDragEnterMoveEvent(event);
       
   462 }
       
   463 
       
   464 void ActionListView::dropEvent(QDropEvent *event)
       
   465 {
       
   466     handleImageDropEvent(this, event, m_model);
       
   467 }
       
   468 
       
   469 void ActionListView::focusInEvent(QFocusEvent *event)
       
   470 {
       
   471     QListView::focusInEvent(event);
       
   472     // Make property editor display current action
       
   473     if (QAction *a = currentAction())
       
   474        emit currentChanged(a);
       
   475 }
       
   476 
       
   477 void ActionListView::contextMenuEvent(QContextMenuEvent *event)
       
   478 {
       
   479     emit contextMenuRequested(event, m_model->actionAt(indexAt(event->pos())));
       
   480 }
       
   481 
       
   482 void ActionListView::currentChanged(const QModelIndex &current, const QModelIndex & /*previous*/)
       
   483 {
       
   484     emit currentChanged(m_model->actionAt(current));
       
   485 }
       
   486 
       
   487 void ActionListView::slotActivated(const QModelIndex &index)
       
   488 {
       
   489     emit activated(m_model->actionAt(index));
       
   490 }
       
   491 
       
   492 void ActionListView::startDrag(Qt::DropActions supportedActions)
       
   493 {
       
   494     startActionDrag(this, m_model, selectedIndexes(), supportedActions);
       
   495 }
       
   496 
       
   497 //  ActionView
       
   498 ActionView::ActionView(QWidget *parent) :
       
   499     QStackedWidget(parent),
       
   500     m_model(new ActionModel(this)),
       
   501     m_actionTreeView(new ActionTreeView(m_model)),
       
   502     m_actionListView(new ActionListView(m_model))
       
   503 {
       
   504     addWidget(m_actionListView);
       
   505     addWidget(m_actionTreeView);
       
   506     // Wire signals
       
   507     connect(m_actionTreeView, SIGNAL(contextMenuRequested(QContextMenuEvent*, QAction*)),
       
   508             this, SIGNAL(contextMenuRequested(QContextMenuEvent*, QAction*)));
       
   509     connect(m_actionListView, SIGNAL(contextMenuRequested(QContextMenuEvent*, QAction*)),
       
   510             this, SIGNAL(contextMenuRequested(QContextMenuEvent*, QAction*)));
       
   511 
       
   512     // make it possible for vs integration to reimplement edit action dialog
       
   513     // [which it shouldn't do actually]
       
   514     connect(m_actionListView, SIGNAL(activated(QAction*)), this, SIGNAL(activated(QAction*)));
       
   515     connect(m_actionTreeView, SIGNAL(activated(QAction*)), this, SIGNAL(activated(QAction*)));
       
   516 
       
   517     connect(m_actionListView, SIGNAL(currentChanged(QAction*)),this, SLOT(slotCurrentChanged(QAction*)));
       
   518     connect(m_actionTreeView, SIGNAL(currentChanged(QAction*)),this, SLOT(slotCurrentChanged(QAction*)));
       
   519 
       
   520     connect(m_model, SIGNAL(resourceImageDropped(QString,QAction*)),
       
   521             this, SIGNAL(resourceImageDropped(QString,QAction*)));
       
   522 
       
   523     // sync selection models
       
   524     QItemSelectionModel *selectionModel = m_actionTreeView->selectionModel();
       
   525     m_actionListView->setSelectionModel(selectionModel);
       
   526     connect(selectionModel, SIGNAL(selectionChanged(QItemSelection,QItemSelection)),
       
   527             this, SIGNAL(selectionChanged(QItemSelection,QItemSelection)));
       
   528 }
       
   529 
       
   530 int ActionView::viewMode() const
       
   531 {
       
   532     return currentWidget() == m_actionListView ? IconView : DetailedView;
       
   533 }
       
   534 
       
   535 void ActionView::setViewMode(int lm)
       
   536 {
       
   537     if (viewMode() == lm)
       
   538         return;
       
   539 
       
   540     switch (lm) {
       
   541     case IconView:
       
   542         setCurrentWidget(m_actionListView);
       
   543         break;
       
   544     case DetailedView:
       
   545         setCurrentWidget(m_actionTreeView);
       
   546         break;
       
   547     default:
       
   548         break;
       
   549     }
       
   550 }
       
   551 
       
   552 void ActionView::slotCurrentChanged(QAction *action)
       
   553 {
       
   554     // emit only for currently visible
       
   555     if (sender() == currentWidget())
       
   556         emit currentChanged(action);
       
   557 }
       
   558 
       
   559 void ActionView::filter(const QString &text)
       
   560 {
       
   561     m_actionTreeView->filter(text);
       
   562     m_actionListView->filter(text);
       
   563 }
       
   564 
       
   565 void ActionView::selectAll()
       
   566 {
       
   567     m_actionTreeView->selectAll();
       
   568 }
       
   569 
       
   570 void ActionView::clearSelection()
       
   571 {
       
   572     m_actionTreeView->selectionModel()->clearSelection();
       
   573 }
       
   574 
       
   575 void ActionView::setCurrentIndex(const QModelIndex &index)
       
   576 {
       
   577     m_actionTreeView->setCurrentIndex(index);
       
   578 }
       
   579 
       
   580 QAction *ActionView::currentAction() const
       
   581 {
       
   582     return m_actionListView->currentAction();
       
   583 }
       
   584 
       
   585 void ActionView::setSelectionMode(QAbstractItemView::SelectionMode sm)
       
   586 {
       
   587     m_actionTreeView->setSelectionMode(sm);
       
   588     m_actionListView->setSelectionMode(sm);
       
   589 }
       
   590 
       
   591 QAbstractItemView::SelectionMode ActionView::selectionMode() const
       
   592 {
       
   593     return m_actionListView->selectionMode();
       
   594 }
       
   595 
       
   596 QItemSelection ActionView::selection() const
       
   597 {
       
   598     return  m_actionListView->selectionModel()->selection();
       
   599 }
       
   600 
       
   601 ActionView::ActionList ActionView::selectedActions() const
       
   602 {
       
   603     ActionList rc;
       
   604     foreach (const QModelIndex &index, selection().indexes())
       
   605         if (index.column() == 0)
       
   606             rc += actionOfItem(m_model->itemFromIndex(index));
       
   607     return rc;
       
   608 }
       
   609 // ----------  ActionRepositoryMimeData
       
   610 ActionRepositoryMimeData::ActionRepositoryMimeData(QAction *a, Qt::DropAction dropAction) :
       
   611     m_dropAction(dropAction)
       
   612 {
       
   613     m_actionList += a;
       
   614 }
       
   615 
       
   616 ActionRepositoryMimeData::ActionRepositoryMimeData(const ActionList &al, Qt::DropAction dropAction) :
       
   617     m_dropAction(dropAction),
       
   618     m_actionList(al)
       
   619 {
       
   620 }
       
   621 
       
   622 QStringList ActionRepositoryMimeData::formats() const
       
   623 {
       
   624     return QStringList(QLatin1String(actionMimeType));
       
   625 }
       
   626 
       
   627 QPixmap  ActionRepositoryMimeData::actionDragPixmap(const QAction *action)
       
   628 {
       
   629 
       
   630     // Try to find a suitable pixmap. Grab either widget or icon.
       
   631     const QIcon icon = action->icon();
       
   632     if (!icon.isNull())
       
   633         return icon.pixmap(QSize(22, 22));
       
   634 
       
   635     foreach (QWidget *w, action->associatedWidgets())
       
   636         if (QToolButton *tb = qobject_cast<QToolButton *>(w))
       
   637             return QPixmap::grabWidget(tb);
       
   638 
       
   639     // Create a QToolButton
       
   640     QToolButton *tb = new QToolButton;
       
   641     tb->setText(action->text());
       
   642     tb->setToolButtonStyle(Qt::ToolButtonTextOnly);
       
   643 #ifdef Q_WS_WIN // Force alien off to make adjustSize() take the system minimumsize into account.
       
   644     tb->createWinId();
       
   645 #endif
       
   646     tb->adjustSize();
       
   647     const QPixmap rc = QPixmap::grabWidget(tb);
       
   648     tb->deleteLater();
       
   649     return rc;
       
   650 }
       
   651 
       
   652 void ActionRepositoryMimeData::accept(QDragMoveEvent *event) const
       
   653 {
       
   654     if (event->proposedAction() == m_dropAction) {
       
   655         event->acceptProposedAction();
       
   656     } else {
       
   657         event->setDropAction(m_dropAction);
       
   658         event->accept();
       
   659     }
       
   660 }
       
   661 
       
   662 } // namespace qdesigner_internal
       
   663 
       
   664 QT_END_NAMESPACE