From: ana Date: Wed, 7 Jul 2010 12:27:54 +0000 (+0000) Subject: Introduce widgets preference items for editing of keyboard shortcuts X-Git-Tag: translate_resources_09Jul10 X-Git-Url: http://git.salome-platform.org/gitweb/?a=commitdiff_plain;h=refs%2Fheads%2FBR_Plotenh;p=modules%2Fgui.git Introduce widgets preference items for editing of keyboard shortcuts --- diff --git a/src/Qtx/Makefile.am b/src/Qtx/Makefile.am index 633d33df9..771008a03 100755 --- a/src/Qtx/Makefile.am +++ b/src/Qtx/Makefile.am @@ -67,6 +67,7 @@ salomeinclude_HEADERS = \ QtxResourceMgr.h \ QtxRubberBand.h \ QtxSearchTool.h \ + QtxShortcutEdit.h \ QtxSplash.h \ QtxToolBar.h \ QtxToolTip.h \ @@ -123,6 +124,7 @@ dist_libqtx_la_SOURCES = \ QtxResourceMgr.cxx \ QtxRubberBand.cxx \ QtxSearchTool.cxx \ + QtxShortcutEdit.cxx \ QtxSplash.cxx \ QtxToolBar.cxx \ QtxToolTip.cxx \ @@ -171,6 +173,7 @@ MOC_FILES = \ QtxPopupMgr_moc.cxx \ QtxRubberBand_moc.cxx \ QtxSearchTool_moc.cxx \ + QtxShortcutEdit_moc.cxx \ QtxSplash_moc.cxx \ QtxToolBar_moc.cxx \ QtxToolTip_moc.cxx \ diff --git a/src/Qtx/QtxPagePrefMgr.cxx b/src/Qtx/QtxPagePrefMgr.cxx index 98940ab20..28a9db0d8 100644 --- a/src/Qtx/QtxPagePrefMgr.cxx +++ b/src/Qtx/QtxPagePrefMgr.cxx @@ -29,6 +29,8 @@ #include "QtxIntSpinBox.h" #include "QtxColorButton.h" #include "QtxDoubleSpinBox.h" +#include "QtxShortcutEdit.h" +#include "QtxResourceMgr.h" #include #include @@ -4190,3 +4192,108 @@ void QtxPagePrefDateTimeItem::updateDateTime() myDateTime->setDisplayFormat( dispFmt ); } + +/*! + \brief Constructor. + \param title preference item title + \param parent parent preference item + \param sect resource file section associated with the preference item + \param param resource file parameter associated with the preference item +*/ +QtxPagePrefShortcutBtnsItem::QtxPagePrefShortcutBtnsItem( const QString& title, QtxPreferenceItem* parent, const QString& sect, + const QString& param ): QtxPageNamedPrefItem( title, parent, sect, param ) +{ + setControl( myShortcut = new QtxShortcutEdit() ); +} + +/*! + \brief Destructor. +*/ +QtxPagePrefShortcutBtnsItem::~QtxPagePrefShortcutBtnsItem() +{ +} + +/*! + \brief Store preference item to the resource manager. + \sa retrieve() +*/ +void QtxPagePrefShortcutBtnsItem::store() +{ + setString( myShortcut->shortcut().toString() ); +} + +/*! + \brief Retrieve preference item from the resource manager. + \sa store() +*/ +void QtxPagePrefShortcutBtnsItem::retrieve() +{ + myShortcut->setShortcut( QKeySequence::fromString( getString() ) ); +} + +/*! + \brief Constructor. + + Creates preference item for editing of key bindings + + \param title preference item title + \param parent parent preference item + \param sect resource file section associated with the preference item + \param param resource file parameter associated with the preference item +*/ +QtxPagePrefShortcutTreeItem::QtxPagePrefShortcutTreeItem( const QString& title, QtxPreferenceItem* parent, const QString& sect, + const QString& param ): QtxPageNamedPrefItem( title, parent, sect, "" ) +{ + mySection = sect; + myShortcutTree = new QtxShortcutTree(); + setControl( myShortcutTree ); +} + +/*! + \brief Destructor. +*/ +QtxPagePrefShortcutTreeItem::~QtxPagePrefShortcutTreeItem() +{ +} + +/*! + \brief Retrieve preference item from the resource manager. + \sa store() +*/ +void QtxPagePrefShortcutTreeItem::retrieve() +{ + QtxResourceMgr* resMgr = resourceMgr(); + if ( resMgr ){ + QStringList secLst = resMgr->subSections( mySection, false ); + ShortcutMap aMap; QStringList paramLst; + for( int i = 0; i < secLst.size(); i++ ) { + paramLst = resMgr->parameters( QStringList() << mySection << secLst.at( i ) ); + for( int j = 0; j < paramLst.size(); j++ ) + resMgr->value( mySection + resMgr->sectionsToken() + secLst.at( i ), paramLst.at( j ),aMap[ paramLst.at( j ) ], false ); + myShortcutTree->setBindings( secLst.at( i ), aMap ); + aMap.clear(); + } + } +} + +/*! + \brief Store preference item to the resource manager. + \sa retrieve() +*/ +void QtxPagePrefShortcutTreeItem::store() +{ + QStringList lst = myShortcutTree->sections(); + QString aSection; + QtxResourceMgr* resMgr = resourceMgr(); + + if ( resMgr ) { + for( int i = 0; i < lst.size(); i++ ) { + ShortcutMap* aMap( myShortcutTree->bindings( lst.at( i ) ) ); + aSection = mySection + resMgr->sectionsToken() + lst.at( i ); + for( ShortcutMap::const_iterator it = aMap->constBegin(); it != aMap->constEnd(); ++it ) + resMgr->setValue( aSection, it.key(), it.value() ); + } + } +} + + diff --git a/src/Qtx/QtxPagePrefMgr.h b/src/Qtx/QtxPagePrefMgr.h index 5501fdf23..d824a3f33 100644 --- a/src/Qtx/QtxPagePrefMgr.h +++ b/src/Qtx/QtxPagePrefMgr.h @@ -38,6 +38,8 @@ class QtxFontEdit; class QtxGroupBox; class QtxComboBox; class QtxColorButton; +class QtxShortcutEdit; +class QtxShortcutTree; class QToolBox; class QLineEdit; @@ -50,6 +52,7 @@ class QFileDialog; class QDateTimeEdit; class QStackedWidget; class QSlider; +class QTreeWidget; class QTX_EXPORT QtxPagePrefMgr : public QFrame, public QtxPreferenceMgr { @@ -704,4 +707,31 @@ private: QDateTimeEdit* myDateTime; }; +class QTX_EXPORT QtxPagePrefShortcutBtnsItem : public QtxPageNamedPrefItem +{ +public: + QtxPagePrefShortcutBtnsItem( const QString&, QtxPreferenceItem* = 0, + const QString& = QString(), const QString& = QString() ); + virtual ~QtxPagePrefShortcutBtnsItem(); + virtual void store(); + virtual void retrieve(); + +private: + QtxShortcutEdit* myShortcut; +}; + +class QTX_EXPORT QtxPagePrefShortcutTreeItem : public QtxPageNamedPrefItem +{ +public: + QtxPagePrefShortcutTreeItem( const QString&, QtxPreferenceItem* = 0, + const QString& = QString(), const QString& = QString() ); + virtual ~QtxPagePrefShortcutTreeItem(); + virtual void store(); + virtual void retrieve(); + +private: + QtxShortcutTree* myShortcutTree; + QString mySection; +}; + #endif diff --git a/src/Qtx/QtxShortcutEdit.cxx b/src/Qtx/QtxShortcutEdit.cxx new file mode 100755 index 000000000..c5aa6eaa7 --- /dev/null +++ b/src/Qtx/QtxShortcutEdit.cxx @@ -0,0 +1,331 @@ +// Copyright (C) 2007-2010 CEA/DEN, EDF R&D, OPEN CASCADE +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// + +#include "QtxShortcutEdit.h" + +#include +#include +#include + +#include +#include +#include + +#include +#include + +#define COLUMN_SIZE 500 + +static const char* delete_icon[] = { +"16 16 3 1", +"` c #810000", +" c none", +"# c #ffffff", +" ", +" ", +" ``# ``# ", +" ````# ``# ", +" ````# ``# ", +" ```# `# ", +" `````# ", +" ```# ", +" `````# ", +" ```# ``# ", +" ```# ``# ", +" ```# `# ", +" ```# `# ", +" `# `# ", +" ", +" " +}; + +/*! + \brief Constructor + \param parent parent widget +*/ +QtxShortcutEdit::QtxShortcutEdit( QWidget* parent ) +: QFrame( parent ) +{ + initialize(); + myShortcut->installEventFilter(this); +} + +/*! + \brief Destructor +*/ +QtxShortcutEdit::~QtxShortcutEdit() +{ +} + +/*! + \brief Sets custom shortcut + \param seq a key sequence describes a combination of keys + \sa shortcut() +*/ +void QtxShortcutEdit::setShortcut( const QKeySequence& seq ) +{ + QString txt = seq.toString(); + myPrevShortcutText = txt; + myShortcut->setText( txt ); +} + +/*! + \brief Gets custom shortcut + \return a key sequence describes a combination of keys + \sa setShortcut() +*/ +QKeySequence QtxShortcutEdit::shortcut() +{ + return QKeySequence::fromString( myShortcut->text() ); +} + +/*! + \brief Gets the key sequence from keys that were pressed + \param e a key event + \return a string representation of the key sequence +*/ +QString QtxShortcutEdit::parseEvent( QKeyEvent* e ) +{ + bool isShiftPressed = e->modifiers() & Qt::ShiftModifier; + bool isControlPressed = e->modifiers() & Qt::ControlModifier; + bool isAltPressed = e->modifiers() & Qt::AltModifier; + bool isMetaPressed = e->modifiers() & Qt::MetaModifier; + bool isModifiersPressed = isShiftPressed || isControlPressed || isAltPressed || isMetaPressed; + int result=0; + if( isControlPressed ) + result += Qt::CTRL; + if( isAltPressed ) + result += Qt::ALT; + if( isShiftPressed ) + result += Qt::SHIFT; + if( isMetaPressed ) + result += Qt::META; + + int aKey = e->key(); + if ( ( isValidKey( aKey ) && isModifiersPressed ) || ( ( aKey >= Qt::Key_F1 ) && ( aKey <= Qt::Key_F12 ) ) ) + result += aKey; + + return QKeySequence( result ).toString(); +} + +/*! + \brief Check if the key event contains a 'valid' key + \param aKey the code of the key + \return \c true if the key is 'valid' +*/ + +bool QtxShortcutEdit::isValidKey( int aKey ) +{ + if ( aKey == Qt::Key_Underscore || aKey == Qt::Key_Escape || + ( aKey >= Qt::Key_Backspace && aKey <= Qt::Key_Delete ) || + ( aKey >= Qt::Key_Home && aKey <= Qt::Key_PageDown ) || + ( aKey >= Qt::Key_F1 && aKey <= Qt::Key_F12 ) || + ( aKey >= Qt::Key_Space && aKey <= Qt::Key_Asterisk ) || + ( aKey >= Qt::Key_Comma && aKey <= Qt::Key_Question ) || + ( aKey >= Qt::Key_A && aKey <= Qt::Key_AsciiTilde ) ) + return true; + return false; +} + +/*! + \brief Called when "Clear" button is clicked. +*/ +void QtxShortcutEdit::onCliked() +{ + myShortcut->setText( "" ); +} + +/*! + \brief Called when myShortcut loses focus. +*/ +void QtxShortcutEdit::onEditingFinished() +{ + if ( myShortcut->text().endsWith("+") ) + myShortcut->setText( myPrevShortcutText ); +} + +/*! + \brief Custom event filter. + \param obj event receiver object + \param event event + \return \c true if further event processing should be stopped +*/ +bool QtxShortcutEdit::eventFilter(QObject* obj, QEvent* event) +{ + if ( obj == myShortcut ) { + if (event->type() == QEvent::KeyPress ) { + QKeyEvent* keyEvent = static_cast(event); + QString text = parseEvent( keyEvent ); + if ( keyEvent->key() == Qt::Key_Delete || keyEvent->key() == Qt::Key_Backspace ) + onCliked(); + if ( text != "" ) + myShortcut->setText( text ); + return true; + } + if ( event->type() == QEvent::KeyRelease ) { + if ( myShortcut->text().endsWith("+") ) + myShortcut->setText( myPrevShortcutText ); + else myPrevShortcutText = myShortcut->text(); + + return true; + } + } + return false; +} + +/* + \brief Perform internal intialization. +*/ +void QtxShortcutEdit::initialize() +{ + myPrevShortcutText = QString(); + + QHBoxLayout* base = new QHBoxLayout( this ); + base->setMargin( 0 ); + base->setSpacing( 5 ); + + base->addWidget( myShortcut = new QLineEdit( this ) ); + + QToolButton* deleteBtn = new QToolButton(); + deleteBtn->setIcon( QPixmap( delete_icon ) ); + base->addWidget( deleteBtn ); + + myShortcut->setSizePolicy( QSizePolicy::MinimumExpanding, QSizePolicy::Fixed ); + deleteBtn->setSizePolicy( QSizePolicy::Fixed, QSizePolicy::Fixed ); + + connect( deleteBtn, SIGNAL( clicked() ), this, SLOT( onCliked() ) ); + connect( myShortcut, SIGNAL( editingFinished() ), this, SLOT( onEditingFinished() ) ); +} + +/*! + \brief Constructor + \param parent parent widget +*/ +QtxShortcutTree::QtxShortcutTree( QWidget * parent ) : QTreeWidget( parent ) +{ + setColumnCount( 2 ); + setSelectionMode( QAbstractItemView::SingleSelection ); + setColumnWidth ( 0, COLUMN_SIZE); + setSortingEnabled(false); + headerItem()->setHidden ( true ); + + this->installEventFilter(this); + connect( this, SIGNAL( currentItemChanged ( QTreeWidgetItem*, QTreeWidgetItem* ) ), this, SLOT( onCurrentItemChanged ( QTreeWidgetItem*, QTreeWidgetItem* ) ) ); + +} + +/*! + \brief Destructor +*/ +QtxShortcutTree::~QtxShortcutTree(){} + +/*! + \brief Custom event filter. + \param obj event receiver object + \param event event + \return \c true if further event processing should be stopped +*/ +bool QtxShortcutTree::eventFilter(QObject* obj, QEvent* event) +{ + if ( currentItem() && currentItem()->isSelected() ) { + + if (event->type() == QEvent::KeyPress ) { + QKeyEvent* keyEvent = static_cast(event); + QString text = QtxShortcutEdit::parseEvent( keyEvent ); + if ( keyEvent->key() == Qt::Key_Delete || keyEvent->key() == Qt::Key_Backspace ) + currentItem()->setText( 1, "" ); + if ( text != "" ) { + currentItem()->setText( 1, text ); + } + return true; + } + if ( event->type() == QEvent::KeyRelease ) { + if ( currentItem()->text( 1 ).endsWith( "+" ) ) + currentItem()->setText( 1, myPrevBindings[ currentItem()->parent()->text( 0 ) ][ currentItem()->text( 0 ) ] ); + else myPrevBindings[ currentItem()->parent()->text( 0 ) ][ currentItem()->text( 0 ) ] = currentItem()->text( 1 ); + + return true; + } + } + return false; +} + +/*! + \brief Called when the current item changes. + \param cur the current item + \param prev the previous current item +*/ +void QtxShortcutTree::onCurrentItemChanged( QTreeWidgetItem* cur, QTreeWidgetItem* prev ) +{ + if ( prev && prev->text( 1 ).endsWith( "+" ) ) + prev->setText( 1, myPrevBindings[ prev->parent()->text( 0 ) ][ prev->text( 0 ) ] ); +} + + +/*! + \brief Set key bindings to the tree + \param title the name of top-level item + \param theShortcutMap map of key bindings +*/ +void QtxShortcutTree::setBindings( const QString& title, const ShortcutMap& theShortcutMap ) +{ + QTreeWidgetItem* item= new QTreeWidgetItem(); + if ( findItems( title, Qt::MatchFixedString ).isEmpty() ) { + item->setText( 0, title ); + addTopLevelItem( item ); + item->setFlags( Qt::ItemIsEnabled ); + } else { + item = findItems( title, Qt::MatchFixedString ).first(); + item->takeChildren(); + } + for( ShortcutMap::const_iterator it = theShortcutMap.constBegin(); it != theShortcutMap.constEnd(); ++it ) + item->addChild( new QTreeWidgetItem( QStringList() << it.key() << it.value() ) ); + myPrevBindings.insert( title, theShortcutMap); +} + +/*! + \brief Get all sections names. + \return list of section names +*/ +QStringList QtxShortcutTree::sections() const +{ + QStringList lst; + for( int i = 0; i < topLevelItemCount(); i++ ) + lst << topLevelItem( i )->text( 0 ); + return lst; +} + +ShortcutMap* QtxShortcutTree::bindings( const QString& sec ) const +{ + ShortcutMap* aMap = new ShortcutMap(); + QTreeWidgetItem* item = findItems( sec, Qt::MatchFixedString ).first(); + QList< QTreeWidgetItem* > childLst = item->takeChildren(); + + for( int i = 0; i < childLst.size(); i++ ) + aMap->insert( childLst.at(i)->text( 0 ), childLst.at(i)->text(1) ); + + return aMap; +} + +void QtxShortcutTree::focusOutEvent ( QFocusEvent* event ) +{ + QWidget::focusOutEvent( event ); + if ( currentItem()->isSelected() ) + currentItem()->setText( 1, myPrevBindings[ currentItem()->parent()->text( 0 ) ][ currentItem()->text( 0 ) ] ); +} diff --git a/src/Qtx/QtxShortcutEdit.h b/src/Qtx/QtxShortcutEdit.h new file mode 100755 index 000000000..782402288 --- /dev/null +++ b/src/Qtx/QtxShortcutEdit.h @@ -0,0 +1,84 @@ +// Copyright (C) 2007-2010 CEA/DEN, EDF R&D, OPEN CASCADE +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// + +#ifndef QTXSHORTCUTEDIT_H +#define QTXSHORTCUTEDIT_H + +#include "Qtx.h" + +#include +#include + +class QLineEdit; +class QPushButton; +class QTreeWidgetItem; + +typedef QMap< QString, QString > ShortcutMap; + +class QTX_EXPORT QtxShortcutEdit : public QFrame +{ + Q_OBJECT + +public: + QtxShortcutEdit( QWidget* = 0 ); + virtual ~QtxShortcutEdit(); + void setShortcut( const QKeySequence& ); + QKeySequence shortcut(); + static QString parseEvent( QKeyEvent* ); + static bool isValidKey( int ); + + +private slots: + void onCliked(); + void onEditingFinished(); + +protected: + virtual bool eventFilter( QObject*, QEvent* ); + +private: + void initialize(); + +private: + QLineEdit* myShortcut; + QString myPrevShortcutText; +}; + +class QTX_EXPORT QtxShortcutTree : public QTreeWidget +{ + Q_OBJECT + +public: + QtxShortcutTree( QWidget * parent = 0 ); + virtual ~QtxShortcutTree(); + void setBindings( const QString&, const ShortcutMap& ); + ShortcutMap* bindings( const QString& ) const; + QStringList sections() const; + +protected: + virtual bool eventFilter( QObject*, QEvent* ); + virtual void focusOutEvent( QFocusEvent* ); + +private slots: + void onCurrentItemChanged( QTreeWidgetItem*, QTreeWidgetItem* ); + +private: + QMap< QString, ShortcutMap > myPrevBindings; +}; + +#endif // QTXSHORTCUTEDIT_H diff --git a/src/SUIT/SUIT_PreferenceMgr.cxx b/src/SUIT/SUIT_PreferenceMgr.cxx index 3296f02b0..b3fca9844 100644 --- a/src/SUIT/SUIT_PreferenceMgr.cxx +++ b/src/SUIT/SUIT_PreferenceMgr.cxx @@ -151,6 +151,13 @@ int SUIT_PreferenceMgr::addItem( const QString& title, const int pId, case DirList: item = new QtxPagePrefPathListItem( Qtx::PT_Directory, title, parent, sect, param ); break; + case Shortcut: + item = new QtxPagePrefShortcutBtnsItem( title, parent, sect, param ); + break; + case ShortcutTree: + item = new QtxPagePrefShortcutTreeItem( title, parent, sect, param ); + break; + } return item ? item->id() : -1; diff --git a/src/SUIT/SUIT_PreferenceMgr.h b/src/SUIT/SUIT_PreferenceMgr.h index 37549ae93..eb8edb5e9 100644 --- a/src/SUIT/SUIT_PreferenceMgr.h +++ b/src/SUIT/SUIT_PreferenceMgr.h @@ -37,7 +37,7 @@ class SUIT_EXPORT SUIT_PreferenceMgr : public QtxPagePrefMgr public: typedef enum { Auto, Space, Bool, Color, String, Selector, DblSpin, IntSpin, Double, Integer, - GroupBox, Tab, Frame, Font, DirList, File, Slider } PrefItemType; + GroupBox, Tab, Frame, Font, DirList, File, Slider, Shortcut, ShortcutTree } PrefItemType; public: SUIT_PreferenceMgr( QtxResourceMgr*, QWidget* = 0 );