]> git.lyx.org Git - features.git/blob - src/KeySequence.cpp
c13c41ecdfaf08c81665fafd7323111db7236864
[features.git] / src / KeySequence.cpp
1 /**
2  * \file KeySequence.cpp
3  * This file is part of LyX, the document processor.
4  * Licence details can be found in the file COPYING.
5  *
6  * \author Lars Gullik Bjønnes
7  * \author Jean-Marc Lasgouttes
8  * \author John Levon
9  *
10  * Full author contact details are available in file CREDITS.
11  */
12
13 #include <config.h>
14
15 #include "KeySequence.h"
16
17 #include "gettext.h"
18 #include "KeyMap.h"
19 #include "lfuns.h"
20
21 #include "frontends/LyXKeySym.h"
22 #include "frontends/LyXKeySymFactory.h"
23
24
25 namespace lyx {
26
27 using std::make_pair;
28 using std::string;
29
30
31 FuncRequest const &
32 KeySequence::addkey(LyXKeySymPtr key,
33                     key_modifier::state mod, key_modifier::state nmod)
34 {
35         // adding a key to a deleted sequence
36         // starts a new sequence
37         if (deleted_) {
38                 deleted_ = false;
39                 sequence.clear();
40                 modifiers.clear();
41         }
42
43         modifiers.push_back(make_pair(mod, nmod));
44         sequence.push_back(key);
45
46         if (curmap) {
47                 return curmap->lookup(key, mod, this);
48         }
49
50         static FuncRequest unknown(LFUN_UNKNOWN_ACTION);
51         return unknown;
52 }
53
54
55 size_t KeySequence::parse(string const & s)
56 {
57         if (s.empty())
58                 return 1;
59
60         size_t i = 0;
61         key_modifier::state mod = key_modifier::none;
62         key_modifier::state nmod = key_modifier::none;
63
64         while (i < s.length()) {
65                 if (s[i] == ' ')
66                         ++i;
67                 if (i >= s.length())
68                         break;
69
70                 if (i + 1 < s.length() && s[i + 1] == '-') {
71                         switch (s[i]) {
72                         case 's': case 'S':
73                                 mod |= key_modifier::shift;
74                                 i += 2;
75                                 continue;
76                         case 'c': case 'C':
77                                 mod |= key_modifier::ctrl;
78                                 i += 2;
79                                 continue;
80                         case 'm': case 'M':
81                                 mod |= key_modifier::alt;
82                                 i += 2;
83                                 continue;
84                         default:
85                                 return i + 1;
86                         }
87                 } else if (i + 2 < s.length() && s[i] == '~'
88                            && s[i + 2] == '-') {
89                         switch (s[i + 1]) {
90                         case 's': case 'S':
91                                 nmod |= key_modifier::shift;
92                                 i += 3;
93                                 continue;
94                         case 'c': case 'C':
95                                 nmod |= key_modifier::ctrl;
96                                 i += 3;
97                                 continue;
98                         case 'm': case 'M':
99                                 nmod |= key_modifier::alt;
100                                 i += 3;
101                                 continue;
102                         default:
103                                 return i + 2;
104                         }
105                 } else {
106                         string tbuf;
107                         size_t j = i;
108                         for (; j < s.length() && s[j] != ' '; ++j)
109                                 tbuf += s[j];    // (!!!check bounds :-)
110
111                         LyXKeySymPtr key(LyXKeySymFactory::create());
112                         key->init(tbuf);
113
114                         if (!key->isOK())
115                                 return j;
116
117                         i = j;
118
119                         addkey(key, mod, nmod);
120                         mod = key_modifier::none;
121                 }
122         }
123
124         // empty sequence?
125         if (sequence.size() == 0)
126                 return 0;
127
128         // everything is fine
129         return string::npos;
130 }
131
132
133 docstring const KeySequence::print(bool forgui) const
134 {
135         docstring buf;
136
137         size_t const length = sequence.size();
138
139         for (size_t i = 0; i < length; ++i) {
140                 buf += sequence[i]->print(modifiers[i].first, forgui);
141                 // append a blank
142                 if (i + 1 < length)
143                         buf += ' ';
144         }
145         return buf;
146 }
147
148
149 docstring const KeySequence::printOptions(bool forgui) const
150 {
151         docstring buf;
152
153         buf += print(forgui);
154
155         if (!curmap)
156                 return buf;
157
158         buf += _("   options: ");
159         buf += curmap->print(forgui);
160         return buf;
161 }
162
163
164 void KeySequence::mark_deleted()
165 {
166         deleted_ = true;
167 }
168
169
170 void KeySequence::reset()
171 {
172         mark_deleted();
173         curmap = stdmap;
174 }
175
176 void KeySequence::clear()
177 {
178         sequence.clear();
179         reset();
180 }
181
182
183 } // namespace lyx