1 /***************************************************************************
2 *                                                                         *
3 *   This program is free software; you can redistribute it and/or modify  *
4 *   it under the terms of the GNU General Public License as published by  *
5 *   the Free Software Foundation; either version 3 of the License, or     *
6 *   (at your option) any later version.                                   *
7 *                                                                         *
8 ***************************************************************************/
9 
10 #include "ShortcutEdit.h"
11 
12 #include <QKeySequence>
13 
translateModifiers(Qt::KeyboardModifiers state,const QString & text)14 static int translateModifiers(Qt::KeyboardModifiers state, const QString &text) {
15     int result = 0;
16     if ((state & Qt::ShiftModifier) && (text.isEmpty()
17                                         || !text.at(0).isPrint()
18                                         || text.at(0).isLetter()
19                                         || text.at(0).isSpace()))
20         result |= Qt::SHIFT;
21     if (state & Qt::ControlModifier)
22         result |= Qt::CTRL;
23     if (state & Qt::MetaModifier)
24         result |= Qt::META;
25     if (state & Qt::AltModifier)
26         result |= Qt::ALT;
27 
28     return result;
29 }
30 
ShortcutEdit(QWidget * parent)31 ShortcutEdit::ShortcutEdit(QWidget *parent) :
32         LineEdit(parent), keyNumber(0)
33 {
34     installEventFilter(this);
35 
36     keys[0] = keys[1] = keys[2] = keys[3] = 0;
37 }
38 
eventFilter(QObject * obj,QEvent * e)39 bool ShortcutEdit::eventFilter(QObject *obj, QEvent *e){
40     if (e->type() == QEvent::KeyRelease || e->type() == QEvent::Shortcut){
41         if (keyNumber < 3){
42             for (int i = keyNumber; i < 3; i++)
43                 keys[i] = 0;
44         }
45 
46         keyNumber = 0;
47         return true;
48     }
49     else if (e->type() == QEvent::ShortcutOverride){
50         e->accept();
51 
52         return true;
53     }
54 
55     if (e->type() != QEvent::KeyPress)
56         return LineEdit::eventFilter(obj, e);
57 
58     QKeyEvent *k_e = reinterpret_cast<QKeyEvent* >(e);
59 
60     if (!k_e)
61         return true;
62 
63     int nextKey = k_e->key();
64     if ( keyNumber > 3 ||
65          nextKey == Qt::Key_Control ||
66          nextKey == Qt::Key_Shift ||
67          nextKey == Qt::Key_Meta ||
68          nextKey == Qt::Key_Alt )
69         return true;
70 
71     nextKey |= translateModifiers(k_e->modifiers(), k_e->text());
72     switch (keyNumber) {
73     case 0:
74         keys[0] = nextKey;
75         break;
76     case 1:
77         keys[1] = nextKey;
78         break;
79     case 2:
80         keys[2] = nextKey;
81         break;
82     case 3:
83         keys[3] = nextKey;
84         break;
85     default:
86         break;
87     }
88     keyNumber++;
89     QKeySequence ks(keys[0], keys[1], keys[2], keys[3]);
90 
91     setText(ks.toString());
92 
93     return true;
94 }
95