Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(267)

Side by Side Diff: ui/base/ime/input_method_auralinux_unittest.cc

Issue 1068093002: Refactoring for InputMethodAuraLinux. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Removes unexpected 229 keydown for non-IME users. Created 5 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright 2015 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "ui/base/ime/input_method_auralinux.h"
6
7 #include "base/strings/string_split.h"
8 #include "base/strings/utf_string_conversions.h"
9 #include "testing/gtest/include/gtest/gtest.h"
10 #include "ui/base/ime/dummy_text_input_client.h"
11 #include "ui/base/ime/input_method_delegate.h"
12 #include "ui/base/ime/input_method_initializer.h"
13 #include "ui/base/ime/linux/fake_input_method_context.h"
14 #include "ui/base/ime/linux/linux_input_method_context_factory.h"
15 #include "ui/events/event.h"
16
17 namespace ui {
18 namespace {
19
20 const base::char16 kActionCommit = L'C';
21 const base::char16 kActionCompositionStart = L'S';
22 const base::char16 kActionCompositionUpdate = L'U';
23 const base::char16 kActionCompositionEnd = L'E';
James Su 2015/04/09 09:11:40 Cover this case in sync mode.
Shu Chen 2015/04/10 05:26:52 Done.
24
25 class LinuxInputMethodContextForTesting : public LinuxInputMethodContext {
26 public:
27 LinuxInputMethodContextForTesting(LinuxInputMethodContextDelegate* delegate,
28 bool is_simple)
29 : delegate_(delegate),
30 is_simple_(is_simple),
31 is_sync_mode_(false),
32 eat_key_(false),
33 focused_(false) {}
34
35 void SetSyncMode(bool is_sync_mode) { is_sync_mode_ = is_sync_mode; }
36 void SetEatKey(bool eat_key) { eat_key_ = eat_key; }
37
38 void AddAction(const std::string& action) {
James Su 2015/04/09 09:11:40 How about introduce separated methods for differen
Shu Chen 2015/04/10 05:26:52 Done.
39 actions_.push_back(base::ASCIIToUTF16(action));
40 }
41
42 protected:
43 bool DispatchKeyEvent(const ui::KeyEvent& key_event) override {
44 if (!is_sync_mode_) {
45 actions_.clear();
46 return eat_key_;
47 }
48
49 for (const auto& action : actions_) {
50 std::vector<base::string16> parts;
51 base::SplitString(action, L':', &parts);
52 base::char16 id = parts[0][0];
53 base::string16 param;
54 if (parts.size() > 1)
55 param = parts[1];
56 if (id == kActionCommit) {
57 delegate_->OnCommit(param);
58 } else if (id == kActionCompositionStart) {
59 delegate_->OnPreeditStart();
60 } else if (id == kActionCompositionUpdate) {
61 CompositionText comp;
62 comp.text = param;
63 delegate_->OnPreeditChanged(comp);
64 } else if (id == kActionCompositionEnd) {
65 delegate_->OnPreeditEnd();
66 }
67 }
68
69 actions_.clear();
70 return eat_key_;
71 }
72
73 void Reset() override {}
74
75 void Focus() override { focused_ = true; }
76
77 void Blur() override { focused_ = false; }
78
79 void SetCursorLocation(const gfx::Rect& rect) override {
80 cursor_position_ = rect;
81 }
82
83 private:
84 LinuxInputMethodContextDelegate* delegate_;
85 std::vector<base::string16> actions_;
86 bool is_simple_;
87 bool is_sync_mode_;
88 bool eat_key_;
89 bool focused_;
90 gfx::Rect cursor_position_;
91
92 DISALLOW_COPY_AND_ASSIGN(LinuxInputMethodContextForTesting);
93 };
94
95 class LinuxInputMethodContextFactoryForTesting
96 : public LinuxInputMethodContextFactory {
97 public:
98 LinuxInputMethodContextFactoryForTesting(){};
99
100 scoped_ptr<LinuxInputMethodContext> CreateInputMethodContext(
101 LinuxInputMethodContextDelegate* delegate,
102 bool is_simple) const override {
103 return scoped_ptr<ui::LinuxInputMethodContext>(
104 new LinuxInputMethodContextForTesting(delegate, is_simple));
105 };
106
107 private:
108 DISALLOW_COPY_AND_ASSIGN(LinuxInputMethodContextFactoryForTesting);
109 };
110
111 class InputMethodDelegateForTesting : public internal::InputMethodDelegate {
112 public:
113 InputMethodDelegateForTesting()
114 : key_type(ET_UNKNOWN), key_code(VKEY_UNKNOWN), key_flags(0){};
115 ~InputMethodDelegateForTesting() override{};
116
117 bool DispatchKeyEventPostIME(const ui::KeyEvent& key_event) override {
118 key_type = key_event.type();
119 key_code = key_event.key_code();
120 key_flags = key_event.flags();
121 return false;
122 }
123
124 void Clear() {
125 key_type = ET_UNKNOWN;
126 key_code = VKEY_UNKNOWN;
127 key_flags = 0;
128 }
129
130 EventType key_type;
131 KeyboardCode key_code;
132 int key_flags;
133
134 private:
135 DISALLOW_COPY_AND_ASSIGN(InputMethodDelegateForTesting);
136 };
137
138 class TextInputClientForTesting : public DummyTextInputClient {
139 public:
140 explicit TextInputClientForTesting(TextInputType text_input_type)
141 : DummyTextInputClient(text_input_type),
142 called_clear_composition(false),
143 called_confirm_composition(false),
144 called_set_composition(false),
145 called_insert_text(false),
146 called_insert_char(false){};
147
148 void Clear() {
149 composition_text.clear();
150 result_text.clear();
151 called_clear_composition = called_confirm_composition =
152 called_set_composition = called_insert_text = called_insert_char =
153 false;
154 }
155
156 base::string16 composition_text;
157 base::string16 result_text;
158 bool called_clear_composition;
159 bool called_confirm_composition;
160 bool called_set_composition;
161 bool called_insert_text;
162 bool called_insert_char;
163
164 protected:
165 void SetCompositionText(const CompositionText& composition) override {
166 composition_text = composition.text;
167 called_set_composition = true;
168 }
169
170 bool HasCompositionText() const override { return !composition_text.empty(); }
171
172 void ConfirmCompositionText() override {
173 composition_text.clear();
174 called_confirm_composition = true;
175 }
176
177 void ClearCompositionText() override {
178 composition_text.clear();
179 called_clear_composition = true;
180 }
181
182 void InsertText(const base::string16& text) override {
183 result_text = text;
184 called_insert_text = true;
185 }
186
187 void InsertChar(base::char16 ch, int flags) override {
188 result_text = ch;
189 called_insert_char = true;
190 }
191 };
192
193 class InputMethodAuraLinuxTest : public testing::Test {
194 protected:
195 InputMethodAuraLinuxTest()
196 : factory_(NULL),
197 input_method_auralinux_(NULL),
198 delegate_(NULL),
199 context_(NULL),
200 context_simple_(NULL) {
201 factory_ = new LinuxInputMethodContextFactoryForTesting();
202 LinuxInputMethodContextFactory::SetInstance(factory_);
203 }
204 ~InputMethodAuraLinuxTest() override {
205 delete factory_;
206 factory_ = NULL;
207 }
208
209 void SetUp() override {
210 delegate_ = new InputMethodDelegateForTesting();
211 input_method_auralinux_ = new InputMethodAuraLinux(delegate_);
212 input_method_auralinux_->OnFocus();
213 context_ = static_cast<LinuxInputMethodContextForTesting*>(
214 input_method_auralinux_->GetContextForTesting(false));
215 context_simple_ = static_cast<LinuxInputMethodContextForTesting*>(
216 input_method_auralinux_->GetContextForTesting(true));
217 }
218
219 void TearDown() override {
220 context_->SetSyncMode(false);
221 context_->SetEatKey(false);
222
223 context_simple_->SetSyncMode(false);
224 context_simple_->SetEatKey(false);
225
226 context_ = NULL;
227 context_simple_ = NULL;
228
229 delete input_method_auralinux_;
230 input_method_auralinux_ = NULL;
231 delete delegate_;
232 delegate_ = NULL;
233 }
234
235 LinuxInputMethodContextFactoryForTesting* factory_;
236 InputMethodAuraLinux* input_method_auralinux_;
237 InputMethodDelegateForTesting* delegate_;
238 LinuxInputMethodContextForTesting* context_;
239 LinuxInputMethodContextForTesting* context_simple_;
240
241 DISALLOW_COPY_AND_ASSIGN(InputMethodAuraLinuxTest);
242 };
243
244 TEST_F(InputMethodAuraLinuxTest, BasicSyncModeTest) {
245 context_->SetSyncMode(true);
246 context_->SetEatKey(true);
247 context_->AddAction("C:a");
248
249 scoped_ptr<TextInputClientForTesting> client(
250 new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
251 input_method_auralinux_->SetFocusedTextInputClient(client.get());
252 input_method_auralinux_->OnTextInputTypeChanged(client.get());
253
254 KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
255 key.set_character(L'a');
256 input_method_auralinux_->DispatchKeyEvent(key);
257
258 EXPECT_EQ(key.type(), delegate_->key_type);
259 EXPECT_EQ(key.key_code(), delegate_->key_code);
260 EXPECT_EQ(key.flags(), delegate_->key_flags);
261 EXPECT_FALSE(client->called_insert_text);
262 EXPECT_TRUE(client->called_insert_char);
263 EXPECT_EQ(1U, client->result_text.size());
264 EXPECT_EQ(key.GetCharacter(), client->result_text[0]);
265
266 input_method_auralinux_->DetachTextInputClient(client.get());
267 client.reset(new TextInputClientForTesting(TEXT_INPUT_TYPE_PASSWORD));
268 context_simple_->SetSyncMode(true);
269 context_simple_->SetEatKey(false);
270
271 input_method_auralinux_->SetFocusedTextInputClient(client.get());
272 input_method_auralinux_->OnTextInputTypeChanged(client.get());
273 input_method_auralinux_->DispatchKeyEvent(key);
274
275 EXPECT_EQ(key.type(), delegate_->key_type);
276 EXPECT_EQ(key.key_code(), delegate_->key_code);
277 EXPECT_EQ(key.flags(), delegate_->key_flags);
278 EXPECT_FALSE(client->called_insert_text);
279 EXPECT_TRUE(client->called_insert_char);
280 EXPECT_EQ(1U, client->result_text.size());
281 EXPECT_EQ(key.GetCharacter(), client->result_text[0]);
282 }
283
284 TEST_F(InputMethodAuraLinuxTest, BasicAsyncModeTest) {
285 context_->SetSyncMode(false);
286 context_->SetEatKey(true);
287
288 scoped_ptr<TextInputClientForTesting> client(
289 new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
290 input_method_auralinux_->SetFocusedTextInputClient(client.get());
291 input_method_auralinux_->OnTextInputTypeChanged(client.get());
292 KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
293 key.set_character(L'a');
294 input_method_auralinux_->DispatchKeyEvent(key);
295 input_method_auralinux_->OnCommit(base::ASCIIToUTF16("a"));
296
297 EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
298 EXPECT_EQ(VKEY_PROCESSKEY, delegate_->key_code);
299 EXPECT_EQ(0, delegate_->key_flags);
300 EXPECT_TRUE(client->called_insert_text);
301 EXPECT_FALSE(client->called_insert_char);
302 EXPECT_EQ(1U, client->result_text.size());
303 EXPECT_EQ(key.GetCharacter(), client->result_text[0]);
304
305 input_method_auralinux_->DetachTextInputClient(client.get());
306 client.reset(new TextInputClientForTesting(TEXT_INPUT_TYPE_PASSWORD));
307 context_simple_->SetSyncMode(false);
308 context_simple_->SetEatKey(false);
309
310 input_method_auralinux_->SetFocusedTextInputClient(client.get());
311 input_method_auralinux_->OnTextInputTypeChanged(client.get());
312 input_method_auralinux_->DispatchKeyEvent(key);
313
314 EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
315 EXPECT_EQ(VKEY_A, delegate_->key_code);
316 EXPECT_EQ(0, delegate_->key_flags);
317 EXPECT_FALSE(client->called_insert_text);
318 EXPECT_TRUE(client->called_insert_char);
319 EXPECT_EQ(1U, client->result_text.size());
320 EXPECT_EQ(key.GetCharacter(), client->result_text[0]);
321 }
322
323 TEST_F(InputMethodAuraLinuxTest, IBusUSTest) {
324 context_->SetSyncMode(false);
325 context_->SetEatKey(true);
326
327 scoped_ptr<TextInputClientForTesting> client(
328 new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
329 input_method_auralinux_->SetFocusedTextInputClient(client.get());
330 input_method_auralinux_->OnTextInputTypeChanged(client.get());
331 KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
332 key.set_character(L'a');
333 input_method_auralinux_->DispatchKeyEvent(key);
334
335 // IBus mutes the key down.
336 EXPECT_EQ(VKEY_UNKNOWN, delegate_->key_code);
337 EXPECT_FALSE(client->called_insert_text);
338 EXPECT_FALSE(client->called_insert_char);
339
340 // IBus simulates a faked key down and handle it in sync mode.
341 context_->SetSyncMode(true);
342 context_->AddAction("C:a");
343 input_method_auralinux_->DispatchKeyEvent(key);
344
345 EXPECT_EQ(VKEY_A, delegate_->key_code);
346 EXPECT_FALSE(client->called_insert_text);
347 EXPECT_TRUE(client->called_insert_char);
348 EXPECT_EQ(1U, client->result_text.size());
349 EXPECT_EQ(key.GetCharacter(), client->result_text[0]);
350
351 // IBus does NOT handle the key up.
352 client->Clear();
353 context_->SetEatKey(false);
354 input_method_auralinux_->DispatchKeyEvent(
355 KeyEvent(ET_KEY_RELEASED, VKEY_A, 0));
356
357 EXPECT_EQ(ET_KEY_RELEASED, delegate_->key_type);
358 EXPECT_EQ(VKEY_A, delegate_->key_code);
359 EXPECT_FALSE(client->called_insert_text);
360 EXPECT_FALSE(client->called_insert_char);
361 }
362
363 TEST_F(InputMethodAuraLinuxTest, IBusPinyinTest) {
364 context_->SetSyncMode(false);
365 context_->SetEatKey(true);
366
367 scoped_ptr<TextInputClientForTesting> client(
368 new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
369 input_method_auralinux_->SetFocusedTextInputClient(client.get());
370 input_method_auralinux_->OnTextInputTypeChanged(client.get());
371 KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
372 key.set_character(L'a');
373 input_method_auralinux_->DispatchKeyEvent(key);
374
375 // IBus mutes the key down.
376 EXPECT_EQ(VKEY_UNKNOWN, delegate_->key_code);
377 EXPECT_FALSE(client->called_insert_text);
378 EXPECT_FALSE(client->called_insert_char);
379 delegate_->Clear();
380
381 // IBus issues a standalone set_composition action.
382 input_method_auralinux_->OnPreeditStart();
383 CompositionText comp;
384 comp.text = base::ASCIIToUTF16("a");
385 input_method_auralinux_->OnPreeditChanged(comp);
386
387 EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
388 EXPECT_EQ(VKEY_PROCESSKEY, delegate_->key_code);
389 EXPECT_TRUE(client->called_set_composition);
390 EXPECT_EQ(1U, client->composition_text.size());
391 EXPECT_EQ(L'a', client->composition_text[0]);
392 delegate_->Clear();
393
394 // IBus issues a commit text with composition after muting the space key down.
395 input_method_auralinux_->DispatchKeyEvent(
396 KeyEvent(ET_KEY_PRESSED, VKEY_SPACE, 0));
397 EXPECT_EQ(VKEY_UNKNOWN, delegate_->key_code);
398 EXPECT_FALSE(client->called_insert_text);
399 EXPECT_FALSE(client->called_insert_char);
400 delegate_->Clear();
401
402 input_method_auralinux_->OnPreeditEnd();
403 input_method_auralinux_->OnCommit(base::ASCIIToUTF16("A"));
404
405 EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
406 EXPECT_EQ(VKEY_PROCESSKEY, delegate_->key_code);
407 EXPECT_TRUE(client->called_clear_composition);
408 EXPECT_TRUE(client->called_insert_text);
409 EXPECT_EQ(1U, client->result_text.size());
410 EXPECT_EQ(L'A', client->result_text[0]);
411 }
412
413 // crbug.com/463491
414 TEST_F(InputMethodAuraLinuxTest, DeadKeyTest) {
415 context_simple_->SetSyncMode(true);
416 context_simple_->SetEatKey(true);
417
418 scoped_ptr<TextInputClientForTesting> client(
419 new TextInputClientForTesting(TEXT_INPUT_TYPE_NONE));
420 input_method_auralinux_->SetFocusedTextInputClient(client.get());
421 input_method_auralinux_->OnTextInputTypeChanged(client.get());
422 KeyEvent dead_key(ET_KEY_PRESSED, VKEY_OEM_7, 0);
423 dead_key.set_character(L'\'');
424 input_method_auralinux_->DispatchKeyEvent(dead_key);
425
426 // The single quote key is muted.
427 EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
428 EXPECT_EQ(VKEY_OEM_7, delegate_->key_code);
429 EXPECT_FALSE(client->called_insert_text);
430 EXPECT_FALSE(client->called_insert_char);
431 delegate_->Clear();
432
433 context_simple_->AddAction("C:X");
434 KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
435 key.set_character(L'a');
436 input_method_auralinux_->DispatchKeyEvent(key);
437
438 // The following A key generates the accent key: รก.
439 EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
440 EXPECT_EQ(VKEY_A, delegate_->key_code);
441 EXPECT_FALSE(client->called_insert_text);
442 EXPECT_TRUE(client->called_insert_char);
443 EXPECT_EQ(1U, client->result_text.size());
444 EXPECT_EQ(L'X', client->result_text[0]);
445 }
446
447 TEST_F(InputMethodAuraLinuxTest, MultiCommitsTest) {
448 context_->SetSyncMode(true);
449 context_->SetEatKey(true);
450 context_->AddAction("C:a");
451 context_->AddAction("C:b");
452 context_->AddAction("C:c");
453
454 scoped_ptr<TextInputClientForTesting> client(
455 new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
456 input_method_auralinux_->SetFocusedTextInputClient(client.get());
457 input_method_auralinux_->OnTextInputTypeChanged(client.get());
458
459 KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
460 key.set_character(L'a');
461 input_method_auralinux_->DispatchKeyEvent(key);
462
463 EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
464 EXPECT_EQ(VKEY_PROCESSKEY, delegate_->key_code);
465 EXPECT_TRUE(client->called_insert_text);
466 EXPECT_FALSE(client->called_insert_char);
467 EXPECT_EQ(base::ASCIIToUTF16("abc"), client->result_text);
468 }
469
470 TEST_F(InputMethodAuraLinuxTest, MixedCompositionAndCommitTest) {
471 context_->SetSyncMode(true);
472 context_->SetEatKey(true);
473 context_->AddAction("C:a");
474 context_->AddAction("S");
475 context_->AddAction("U:b");
476 context_->AddAction("C:c");
477 context_->AddAction("U:d");
James Su 2015/04/09 09:11:40 cover composition end action here?
Shu Chen 2015/04/10 05:26:52 Done.
478
479 scoped_ptr<TextInputClientForTesting> client(
480 new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
481 input_method_auralinux_->SetFocusedTextInputClient(client.get());
482 input_method_auralinux_->OnTextInputTypeChanged(client.get());
483
484 KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
485 key.set_character(L'a');
486 input_method_auralinux_->DispatchKeyEvent(key);
487
488 EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
489 EXPECT_EQ(VKEY_PROCESSKEY, delegate_->key_code);
490 EXPECT_TRUE(client->called_set_composition);
491 EXPECT_TRUE(client->called_insert_text);
492 EXPECT_FALSE(client->called_insert_char);
493 EXPECT_EQ(base::ASCIIToUTF16("d"), client->composition_text);
494 EXPECT_EQ(base::ASCIIToUTF16("ac"), client->result_text);
495 }
496
497 } // namespace
498 } // namespace ui
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698