From b5099480fcba2118cec4d0fa60718f1704e23a43 Mon Sep 17 00:00:00 2001
From: Jarek Kobus <jkobus@trolltech.com>
Date: Fri, 8 Jan 2010 13:10:04 +0100
Subject: [PATCH] Designer shortcuts fixes, TaskWindow's copy action fixed

Reverted the commit 59ecb9cf8 which could break wrongly written code
(or the cases like designer).
Fix one of such case (copy action in task window).
Fix synchronization of designer shortcuts by connecting to the
keySequenceChanged() signal of their Command representation.

Reviewed-by: con
Task-number: QTCREATORBUG-471
---
 .../coreplugin/actionmanager/command.cpp      |  12 --
 .../coreplugin/actionmanager/command_p.h      |   1 -
 src/plugins/designer/formeditorw.cpp          | 125 +++++++++++-------
 src/plugins/designer/formeditorw.h            |  22 +++
 src/plugins/projectexplorer/taskwindow.cpp    |   5 +-
 5 files changed, 101 insertions(+), 64 deletions(-)

diff --git a/src/plugins/coreplugin/actionmanager/command.cpp b/src/plugins/coreplugin/actionmanager/command.cpp
index b92720f4cd9..6e84d29c554 100644
--- a/src/plugins/coreplugin/actionmanager/command.cpp
+++ b/src/plugins/coreplugin/actionmanager/command.cpp
@@ -500,7 +500,6 @@ void OverrideableAction::addOverrideAction(QAction *action, const QList<int> &co
             m_contextActionMap.insert(k, action);
         }
     }
-    action->setShortcut(OverrideableAction::action()->shortcut());
 }
 
 void OverrideableAction::actionChanged()
@@ -530,14 +529,3 @@ bool OverrideableAction::isActive() const
 {
     return m_active;
 }
-
-void OverrideableAction::setKeySequence(const QKeySequence &key)
-{
-    QMap<int, QPointer<QAction> >::const_iterator it = m_contextActionMap.constBegin();
-    QMap<int, QPointer<QAction> >::const_iterator itEnd = m_contextActionMap.constEnd();
-    while (it != itEnd) {
-        it.value()->setShortcut(key);
-        ++it;
-    }
-    Action::setKeySequence(key);
-}
diff --git a/src/plugins/coreplugin/actionmanager/command_p.h b/src/plugins/coreplugin/actionmanager/command_p.h
index accb15e4acb..176866dfeeb 100644
--- a/src/plugins/coreplugin/actionmanager/command_p.h
+++ b/src/plugins/coreplugin/actionmanager/command_p.h
@@ -143,7 +143,6 @@ public:
     bool setCurrentContext(const QList<int> &context);
     void addOverrideAction(QAction *action, const QList<int> &context);
     bool isActive() const;
-    void setKeySequence(const QKeySequence &key);
 
 private slots:
     void actionChanged();
diff --git a/src/plugins/designer/formeditorw.cpp b/src/plugins/designer/formeditorw.cpp
index 72b92d2ef61..5761513bdda 100644
--- a/src/plugins/designer/formeditorw.cpp
+++ b/src/plugins/designer/formeditorw.cpp
@@ -105,33 +105,8 @@ static inline QIcon designerIcon(const QString &iconName)
     return icon;
 }
 
-// Create an action to activate a designer tool
-static inline QAction *createEditModeAction(QActionGroup *ag,
-                                     const QList<int> &context,
-                                     Core::ActionManager *am,
-                                     Core::ActionContainer *medit,
-                                     const QString &actionName,
-                                     const QString &name,
-                                     int toolNumber,
-                                     const QString &iconName =  QString(),
-                                     const QString &keySequence = QString())
-{
-    QAction *rc = new QAction(actionName, ag);
-    rc->setCheckable(true);
-    if (!iconName.isEmpty())
-         rc->setIcon(designerIcon(iconName));
-    Core::Command *command = am->registerAction(rc, name, context);
-    if (!keySequence.isEmpty())
-        command->setDefaultKeySequence(QKeySequence(keySequence));
-    medit->addAction(command, Core::Constants::G_EDIT_OTHER);
-    rc->setData(toolNumber);
-    ag->addAction(rc);
-    return rc;
-}
-
-
-// Create a menu separato
-static inline QAction * createSeparator(QObject *parent,
+// Create a menu separator
+static inline QAction *createSeparator(QObject *parent,
                                  Core::ActionManager *am,
                                  const QList<int> &context,
                                  Core::ActionContainer *container,
@@ -145,20 +120,6 @@ static inline QAction * createSeparator(QObject *parent,
     return actSeparator;
 }
 
-// Create a tool action
-static inline void addToolAction(QAction *a,
-                   Core::ActionManager *am,
-                   const QList<int> &context,
-                   const QString &name,
-                   Core::ActionContainer *c1,
-                   const QString &keySequence = QString())
-{
-    Core::Command *command = am->registerAction(a, name, context);
-    if (!keySequence.isEmpty())
-        command->setDefaultKeySequence(QKeySequence(keySequence));
-    c1->addAction(command);
-}
-
 using namespace Designer;
 using namespace Designer::Internal;
 using namespace Designer::Constants;
@@ -237,7 +198,8 @@ FormEditorW::FormEditorW() :
     m_actionPrint(0),
     m_actionPreview(0),
     m_actionGroupPreviewInStyle(0),
-    m_actionAboutPlugins(0)
+    m_actionAboutPlugins(0),
+    m_shortcutMapper(new QSignalMapper(this))
 {
     if (Designer::Constants::Internal::debug)
         qDebug() << Q_FUNC_INFO;
@@ -270,6 +232,8 @@ FormEditorW::FormEditorW() :
 
     connect(m_core->editorManager(), SIGNAL(currentEditorChanged(Core::IEditor *)),
             this, SLOT(currentEditorChanged(Core::IEditor *)));
+    connect(m_shortcutMapper, SIGNAL(mapped(QObject *)),
+            this, SLOT(updateShortcut(QObject *)));
 }
 
 FormEditorW::~FormEditorW()
@@ -397,20 +361,21 @@ void FormEditorW::setupActions()
     mtools->addMenu(mformtools);
 
     //overridden actions
-    am->registerAction(m_fwm->actionUndo(), Core::Constants::UNDO, m_context);
-    am->registerAction(m_fwm->actionRedo(), Core::Constants::REDO, m_context);
-    am->registerAction(m_fwm->actionCut(), Core::Constants::CUT, m_context);
-    am->registerAction(m_fwm->actionCopy(), Core::Constants::COPY, m_context);
-    am->registerAction(m_fwm->actionPaste(), Core::Constants::PASTE, m_context);
-    am->registerAction(m_fwm->actionSelectAll(), Core::Constants::SELECTALL, m_context);
+    bindShortcut(am->registerAction(m_fwm->actionUndo(), Core::Constants::UNDO, m_context), m_fwm->actionUndo());
+    bindShortcut(am->registerAction(m_fwm->actionRedo(), Core::Constants::REDO, m_context), m_fwm->actionRedo());
+    bindShortcut(am->registerAction(m_fwm->actionCut(), Core::Constants::CUT, m_context), m_fwm->actionCut());
+    bindShortcut(am->registerAction(m_fwm->actionCopy(), Core::Constants::COPY, m_context), m_fwm->actionCopy());
+    bindShortcut(am->registerAction(m_fwm->actionPaste(), Core::Constants::PASTE, m_context), m_fwm->actionPaste());
+    bindShortcut(am->registerAction(m_fwm->actionSelectAll(), Core::Constants::SELECTALL, m_context), m_fwm->actionSelectAll());
 
     m_actionPrint = new QAction(this);
-    am->registerAction(m_actionPrint, Core::Constants::PRINT, m_context);
+    bindShortcut(am->registerAction(m_actionPrint, Core::Constants::PRINT, m_context), m_actionPrint);
     connect(m_actionPrint, SIGNAL(triggered()), this, SLOT(print()));
 
     //'delete' action
     command = am->registerAction(m_fwm->actionDelete(), QLatin1String("FormEditor.Edit.Delete"), m_context);
     command->setDefaultKeySequence(QKeySequence::Delete);
+    bindShortcut(command, m_fwm->actionDelete());
     command->setAttribute(Core::Command::CA_Hide);
     medit->addAction(command, Core::Constants::G_EDIT_COPYPASTE);
 
@@ -613,6 +578,7 @@ Core::ActionContainer *FormEditorW::createPreviewStyleMenu(Core::ActionManager *
         }
         name += data.toString();
         Core::Command *command = am->registerAction(a, name, m_context);
+        bindShortcut(command, a);
         if (isDeviceProfile) {
             command->setAttribute(Core::Command::CA_UpdateText);
             command->setAttribute(Core::Command::CA_NonConfigureable);
@@ -642,6 +608,56 @@ void FormEditorW::critical(const QString &errorMessage)
     QMessageBox::critical(m_core->mainWindow(), tr("Designer"),  errorMessage);
 }
 
+// Apply the command shortcut to the action and connects to the command's keySequenceChanged signal
+void FormEditorW::bindShortcut(Core::Command *command, QAction *action)
+{
+    m_commandToDesignerAction.insert(command, action);
+    connect(command, SIGNAL(keySequenceChanged()),
+            m_shortcutMapper, SLOT(map()));
+    m_shortcutMapper->setMapping(command, command);
+    updateShortcut(command);
+}
+
+// Create an action to activate a designer tool
+QAction *FormEditorW::createEditModeAction(QActionGroup *ag,
+                                     const QList<int> &context,
+                                     Core::ActionManager *am,
+                                     Core::ActionContainer *medit,
+                                     const QString &actionName,
+                                     const QString &name,
+                                     int toolNumber,
+                                     const QString &iconName,
+                                     const QString &keySequence)
+{
+    QAction *rc = new QAction(actionName, ag);
+    rc->setCheckable(true);
+    if (!iconName.isEmpty())
+         rc->setIcon(designerIcon(iconName));
+    Core::Command *command = am->registerAction(rc, name, context);
+    if (!keySequence.isEmpty())
+        command->setDefaultKeySequence(QKeySequence(keySequence));
+    bindShortcut(command, rc);
+    medit->addAction(command, Core::Constants::G_EDIT_OTHER);
+    rc->setData(toolNumber);
+    ag->addAction(rc);
+    return rc;
+}
+
+// Create a tool action
+void FormEditorW::addToolAction(QAction *a,
+                   Core::ActionManager *am,
+                   const QList<int> &context,
+                   const QString &name,
+                   Core::ActionContainer *c1,
+                   const QString &keySequence)
+{
+    Core::Command *command = am->registerAction(a, name, context);
+    if (!keySequence.isEmpty())
+        command->setDefaultKeySequence(QKeySequence(keySequence));
+    bindShortcut(command, a);
+    c1->addAction(command);
+}
+
 FormWindowEditor *FormEditorW::createFormWindowEditor(QWidget* parentWidget)
 {
     m_fwm->closeAllPreviews();
@@ -673,6 +689,17 @@ void FormEditorW::editorDestroyed()
     }
 }
 
+void FormEditorW::updateShortcut(QObject *command)
+{
+    Core::Command *c = qobject_cast<Core::Command *>(command);
+    if (!c)
+        return;
+    QAction *a = m_commandToDesignerAction.value(c);
+    if (!a)
+        return;
+    a->setShortcut(c->action()->shortcut());
+}
+
 void FormEditorW::currentEditorChanged(Core::IEditor *editor)
 {
     if (Designer::Constants::Internal::debug)
diff --git a/src/plugins/designer/formeditorw.h b/src/plugins/designer/formeditorw.h
index e592cfacf28..b3293b52074 100644
--- a/src/plugins/designer/formeditorw.h
+++ b/src/plugins/designer/formeditorw.h
@@ -36,6 +36,7 @@
 #include <QtCore/QObject>
 #include <QtCore/QPointer>
 #include <QtCore/QStringList>
+#include <QtCore/QSignalMapper>
 #include <QtGui/QAction>
 
 #include "designerconstants.h"
@@ -65,6 +66,7 @@ class ActionManager;
 class ActionContainer;
 class ICore;
 class IEditor;
+class Command;
 }
 
 namespace Designer {
@@ -141,6 +143,7 @@ private slots:
     void resetToDefaultLayout();
 
     void editorDestroyed();
+    void updateShortcut(QObject *command);
 
 private:
     FormEditorW();
@@ -158,6 +161,23 @@ private:
                                                    QActionGroup *actionGroup);
 
     void critical(const QString &errorMessage);
+    void bindShortcut(Core::Command *command, QAction *action);
+    QAction *createEditModeAction(QActionGroup *ag,
+                                         const QList<int> &context,
+                                         Core::ActionManager *am,
+                                         Core::ActionContainer *medit,
+                                         const QString &actionName,
+                                         const QString &name,
+                                         int toolNumber,
+                                         const QString &iconName = QString(),
+                                         const QString &keySequence = QString());
+    void addToolAction(QAction *a,
+                       Core::ActionManager *am,
+                       const QList<int> &context,
+                       const QString &name,
+                       Core::ActionContainer *c1,
+                       const QString &keySequence = QString());
+
 
     static FormEditorW *m_self;
 
@@ -184,6 +204,8 @@ private:
 
     EditorList m_formWindows;
     QStringList m_toolActionIds;
+    QSignalMapper *m_shortcutMapper;
+    QMap<Core::Command *, QAction *> m_commandToDesignerAction;
 };
 
 } // namespace Internal
diff --git a/src/plugins/projectexplorer/taskwindow.cpp b/src/plugins/projectexplorer/taskwindow.cpp
index 5134035a003..271bc15ea22 100644
--- a/src/plugins/projectexplorer/taskwindow.cpp
+++ b/src/plugins/projectexplorer/taskwindow.cpp
@@ -34,6 +34,7 @@
 #include <coreplugin/editormanager/editormanager.h>
 #include <coreplugin/icore.h>
 #include <coreplugin/uniqueidmanager.h>
+#include <coreplugin/actionmanager/command.h>
 #include <texteditor/basetexteditor.h>
 #include <texteditor/itexteditor.h>
 
@@ -456,9 +457,9 @@ TaskWindow::TaskWindow()
     core->addContextObject(m_taskWindowContext);
 
     m_copyAction = new QAction(QIcon(Core::Constants::ICON_COPY), tr("&Copy"), this);
-    core->actionManager()->
+    Core::Command *command = core->actionManager()->
             registerAction(m_copyAction, Core::Constants::COPY, m_taskWindowContext->context());
-    m_listview->addAction(m_copyAction);
+    m_listview->addAction(command->action());
 
     connect(m_listview->selectionModel(), SIGNAL(currentChanged(const QModelIndex &, const QModelIndex &)),
             tld, SLOT(currentChanged(const QModelIndex &, const QModelIndex &)));
-- 
GitLab