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

Unified 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 side-by-side diff with in-line comments
Download patch
Index: ui/base/ime/input_method_auralinux_unittest.cc
diff --git a/ui/base/ime/input_method_auralinux_unittest.cc b/ui/base/ime/input_method_auralinux_unittest.cc
new file mode 100644
index 0000000000000000000000000000000000000000..4d8da24a3fe1651dd3e191f3bea4096e8a9ed105
--- /dev/null
+++ b/ui/base/ime/input_method_auralinux_unittest.cc
@@ -0,0 +1,498 @@
+// Copyright 2015 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/ime/input_method_auralinux.h"
+
+#include "base/strings/string_split.h"
+#include "base/strings/utf_string_conversions.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "ui/base/ime/dummy_text_input_client.h"
+#include "ui/base/ime/input_method_delegate.h"
+#include "ui/base/ime/input_method_initializer.h"
+#include "ui/base/ime/linux/fake_input_method_context.h"
+#include "ui/base/ime/linux/linux_input_method_context_factory.h"
+#include "ui/events/event.h"
+
+namespace ui {
+namespace {
+
+const base::char16 kActionCommit = L'C';
+const base::char16 kActionCompositionStart = L'S';
+const base::char16 kActionCompositionUpdate = L'U';
+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.
+
+class LinuxInputMethodContextForTesting : public LinuxInputMethodContext {
+ public:
+ LinuxInputMethodContextForTesting(LinuxInputMethodContextDelegate* delegate,
+ bool is_simple)
+ : delegate_(delegate),
+ is_simple_(is_simple),
+ is_sync_mode_(false),
+ eat_key_(false),
+ focused_(false) {}
+
+ void SetSyncMode(bool is_sync_mode) { is_sync_mode_ = is_sync_mode; }
+ void SetEatKey(bool eat_key) { eat_key_ = eat_key; }
+
+ 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.
+ actions_.push_back(base::ASCIIToUTF16(action));
+ }
+
+ protected:
+ bool DispatchKeyEvent(const ui::KeyEvent& key_event) override {
+ if (!is_sync_mode_) {
+ actions_.clear();
+ return eat_key_;
+ }
+
+ for (const auto& action : actions_) {
+ std::vector<base::string16> parts;
+ base::SplitString(action, L':', &parts);
+ base::char16 id = parts[0][0];
+ base::string16 param;
+ if (parts.size() > 1)
+ param = parts[1];
+ if (id == kActionCommit) {
+ delegate_->OnCommit(param);
+ } else if (id == kActionCompositionStart) {
+ delegate_->OnPreeditStart();
+ } else if (id == kActionCompositionUpdate) {
+ CompositionText comp;
+ comp.text = param;
+ delegate_->OnPreeditChanged(comp);
+ } else if (id == kActionCompositionEnd) {
+ delegate_->OnPreeditEnd();
+ }
+ }
+
+ actions_.clear();
+ return eat_key_;
+ }
+
+ void Reset() override {}
+
+ void Focus() override { focused_ = true; }
+
+ void Blur() override { focused_ = false; }
+
+ void SetCursorLocation(const gfx::Rect& rect) override {
+ cursor_position_ = rect;
+ }
+
+ private:
+ LinuxInputMethodContextDelegate* delegate_;
+ std::vector<base::string16> actions_;
+ bool is_simple_;
+ bool is_sync_mode_;
+ bool eat_key_;
+ bool focused_;
+ gfx::Rect cursor_position_;
+
+ DISALLOW_COPY_AND_ASSIGN(LinuxInputMethodContextForTesting);
+};
+
+class LinuxInputMethodContextFactoryForTesting
+ : public LinuxInputMethodContextFactory {
+ public:
+ LinuxInputMethodContextFactoryForTesting(){};
+
+ scoped_ptr<LinuxInputMethodContext> CreateInputMethodContext(
+ LinuxInputMethodContextDelegate* delegate,
+ bool is_simple) const override {
+ return scoped_ptr<ui::LinuxInputMethodContext>(
+ new LinuxInputMethodContextForTesting(delegate, is_simple));
+ };
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(LinuxInputMethodContextFactoryForTesting);
+};
+
+class InputMethodDelegateForTesting : public internal::InputMethodDelegate {
+ public:
+ InputMethodDelegateForTesting()
+ : key_type(ET_UNKNOWN), key_code(VKEY_UNKNOWN), key_flags(0){};
+ ~InputMethodDelegateForTesting() override{};
+
+ bool DispatchKeyEventPostIME(const ui::KeyEvent& key_event) override {
+ key_type = key_event.type();
+ key_code = key_event.key_code();
+ key_flags = key_event.flags();
+ return false;
+ }
+
+ void Clear() {
+ key_type = ET_UNKNOWN;
+ key_code = VKEY_UNKNOWN;
+ key_flags = 0;
+ }
+
+ EventType key_type;
+ KeyboardCode key_code;
+ int key_flags;
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(InputMethodDelegateForTesting);
+};
+
+class TextInputClientForTesting : public DummyTextInputClient {
+ public:
+ explicit TextInputClientForTesting(TextInputType text_input_type)
+ : DummyTextInputClient(text_input_type),
+ called_clear_composition(false),
+ called_confirm_composition(false),
+ called_set_composition(false),
+ called_insert_text(false),
+ called_insert_char(false){};
+
+ void Clear() {
+ composition_text.clear();
+ result_text.clear();
+ called_clear_composition = called_confirm_composition =
+ called_set_composition = called_insert_text = called_insert_char =
+ false;
+ }
+
+ base::string16 composition_text;
+ base::string16 result_text;
+ bool called_clear_composition;
+ bool called_confirm_composition;
+ bool called_set_composition;
+ bool called_insert_text;
+ bool called_insert_char;
+
+ protected:
+ void SetCompositionText(const CompositionText& composition) override {
+ composition_text = composition.text;
+ called_set_composition = true;
+ }
+
+ bool HasCompositionText() const override { return !composition_text.empty(); }
+
+ void ConfirmCompositionText() override {
+ composition_text.clear();
+ called_confirm_composition = true;
+ }
+
+ void ClearCompositionText() override {
+ composition_text.clear();
+ called_clear_composition = true;
+ }
+
+ void InsertText(const base::string16& text) override {
+ result_text = text;
+ called_insert_text = true;
+ }
+
+ void InsertChar(base::char16 ch, int flags) override {
+ result_text = ch;
+ called_insert_char = true;
+ }
+};
+
+class InputMethodAuraLinuxTest : public testing::Test {
+ protected:
+ InputMethodAuraLinuxTest()
+ : factory_(NULL),
+ input_method_auralinux_(NULL),
+ delegate_(NULL),
+ context_(NULL),
+ context_simple_(NULL) {
+ factory_ = new LinuxInputMethodContextFactoryForTesting();
+ LinuxInputMethodContextFactory::SetInstance(factory_);
+ }
+ ~InputMethodAuraLinuxTest() override {
+ delete factory_;
+ factory_ = NULL;
+ }
+
+ void SetUp() override {
+ delegate_ = new InputMethodDelegateForTesting();
+ input_method_auralinux_ = new InputMethodAuraLinux(delegate_);
+ input_method_auralinux_->OnFocus();
+ context_ = static_cast<LinuxInputMethodContextForTesting*>(
+ input_method_auralinux_->GetContextForTesting(false));
+ context_simple_ = static_cast<LinuxInputMethodContextForTesting*>(
+ input_method_auralinux_->GetContextForTesting(true));
+ }
+
+ void TearDown() override {
+ context_->SetSyncMode(false);
+ context_->SetEatKey(false);
+
+ context_simple_->SetSyncMode(false);
+ context_simple_->SetEatKey(false);
+
+ context_ = NULL;
+ context_simple_ = NULL;
+
+ delete input_method_auralinux_;
+ input_method_auralinux_ = NULL;
+ delete delegate_;
+ delegate_ = NULL;
+ }
+
+ LinuxInputMethodContextFactoryForTesting* factory_;
+ InputMethodAuraLinux* input_method_auralinux_;
+ InputMethodDelegateForTesting* delegate_;
+ LinuxInputMethodContextForTesting* context_;
+ LinuxInputMethodContextForTesting* context_simple_;
+
+ DISALLOW_COPY_AND_ASSIGN(InputMethodAuraLinuxTest);
+};
+
+TEST_F(InputMethodAuraLinuxTest, BasicSyncModeTest) {
+ context_->SetSyncMode(true);
+ context_->SetEatKey(true);
+ context_->AddAction("C:a");
+
+ scoped_ptr<TextInputClientForTesting> client(
+ new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
+ input_method_auralinux_->SetFocusedTextInputClient(client.get());
+ input_method_auralinux_->OnTextInputTypeChanged(client.get());
+
+ KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
+ key.set_character(L'a');
+ input_method_auralinux_->DispatchKeyEvent(key);
+
+ EXPECT_EQ(key.type(), delegate_->key_type);
+ EXPECT_EQ(key.key_code(), delegate_->key_code);
+ EXPECT_EQ(key.flags(), delegate_->key_flags);
+ EXPECT_FALSE(client->called_insert_text);
+ EXPECT_TRUE(client->called_insert_char);
+ EXPECT_EQ(1U, client->result_text.size());
+ EXPECT_EQ(key.GetCharacter(), client->result_text[0]);
+
+ input_method_auralinux_->DetachTextInputClient(client.get());
+ client.reset(new TextInputClientForTesting(TEXT_INPUT_TYPE_PASSWORD));
+ context_simple_->SetSyncMode(true);
+ context_simple_->SetEatKey(false);
+
+ input_method_auralinux_->SetFocusedTextInputClient(client.get());
+ input_method_auralinux_->OnTextInputTypeChanged(client.get());
+ input_method_auralinux_->DispatchKeyEvent(key);
+
+ EXPECT_EQ(key.type(), delegate_->key_type);
+ EXPECT_EQ(key.key_code(), delegate_->key_code);
+ EXPECT_EQ(key.flags(), delegate_->key_flags);
+ EXPECT_FALSE(client->called_insert_text);
+ EXPECT_TRUE(client->called_insert_char);
+ EXPECT_EQ(1U, client->result_text.size());
+ EXPECT_EQ(key.GetCharacter(), client->result_text[0]);
+}
+
+TEST_F(InputMethodAuraLinuxTest, BasicAsyncModeTest) {
+ context_->SetSyncMode(false);
+ context_->SetEatKey(true);
+
+ scoped_ptr<TextInputClientForTesting> client(
+ new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
+ input_method_auralinux_->SetFocusedTextInputClient(client.get());
+ input_method_auralinux_->OnTextInputTypeChanged(client.get());
+ KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
+ key.set_character(L'a');
+ input_method_auralinux_->DispatchKeyEvent(key);
+ input_method_auralinux_->OnCommit(base::ASCIIToUTF16("a"));
+
+ EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
+ EXPECT_EQ(VKEY_PROCESSKEY, delegate_->key_code);
+ EXPECT_EQ(0, delegate_->key_flags);
+ EXPECT_TRUE(client->called_insert_text);
+ EXPECT_FALSE(client->called_insert_char);
+ EXPECT_EQ(1U, client->result_text.size());
+ EXPECT_EQ(key.GetCharacter(), client->result_text[0]);
+
+ input_method_auralinux_->DetachTextInputClient(client.get());
+ client.reset(new TextInputClientForTesting(TEXT_INPUT_TYPE_PASSWORD));
+ context_simple_->SetSyncMode(false);
+ context_simple_->SetEatKey(false);
+
+ input_method_auralinux_->SetFocusedTextInputClient(client.get());
+ input_method_auralinux_->OnTextInputTypeChanged(client.get());
+ input_method_auralinux_->DispatchKeyEvent(key);
+
+ EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
+ EXPECT_EQ(VKEY_A, delegate_->key_code);
+ EXPECT_EQ(0, delegate_->key_flags);
+ EXPECT_FALSE(client->called_insert_text);
+ EXPECT_TRUE(client->called_insert_char);
+ EXPECT_EQ(1U, client->result_text.size());
+ EXPECT_EQ(key.GetCharacter(), client->result_text[0]);
+}
+
+TEST_F(InputMethodAuraLinuxTest, IBusUSTest) {
+ context_->SetSyncMode(false);
+ context_->SetEatKey(true);
+
+ scoped_ptr<TextInputClientForTesting> client(
+ new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
+ input_method_auralinux_->SetFocusedTextInputClient(client.get());
+ input_method_auralinux_->OnTextInputTypeChanged(client.get());
+ KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
+ key.set_character(L'a');
+ input_method_auralinux_->DispatchKeyEvent(key);
+
+ // IBus mutes the key down.
+ EXPECT_EQ(VKEY_UNKNOWN, delegate_->key_code);
+ EXPECT_FALSE(client->called_insert_text);
+ EXPECT_FALSE(client->called_insert_char);
+
+ // IBus simulates a faked key down and handle it in sync mode.
+ context_->SetSyncMode(true);
+ context_->AddAction("C:a");
+ input_method_auralinux_->DispatchKeyEvent(key);
+
+ EXPECT_EQ(VKEY_A, delegate_->key_code);
+ EXPECT_FALSE(client->called_insert_text);
+ EXPECT_TRUE(client->called_insert_char);
+ EXPECT_EQ(1U, client->result_text.size());
+ EXPECT_EQ(key.GetCharacter(), client->result_text[0]);
+
+ // IBus does NOT handle the key up.
+ client->Clear();
+ context_->SetEatKey(false);
+ input_method_auralinux_->DispatchKeyEvent(
+ KeyEvent(ET_KEY_RELEASED, VKEY_A, 0));
+
+ EXPECT_EQ(ET_KEY_RELEASED, delegate_->key_type);
+ EXPECT_EQ(VKEY_A, delegate_->key_code);
+ EXPECT_FALSE(client->called_insert_text);
+ EXPECT_FALSE(client->called_insert_char);
+}
+
+TEST_F(InputMethodAuraLinuxTest, IBusPinyinTest) {
+ context_->SetSyncMode(false);
+ context_->SetEatKey(true);
+
+ scoped_ptr<TextInputClientForTesting> client(
+ new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
+ input_method_auralinux_->SetFocusedTextInputClient(client.get());
+ input_method_auralinux_->OnTextInputTypeChanged(client.get());
+ KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
+ key.set_character(L'a');
+ input_method_auralinux_->DispatchKeyEvent(key);
+
+ // IBus mutes the key down.
+ EXPECT_EQ(VKEY_UNKNOWN, delegate_->key_code);
+ EXPECT_FALSE(client->called_insert_text);
+ EXPECT_FALSE(client->called_insert_char);
+ delegate_->Clear();
+
+ // IBus issues a standalone set_composition action.
+ input_method_auralinux_->OnPreeditStart();
+ CompositionText comp;
+ comp.text = base::ASCIIToUTF16("a");
+ input_method_auralinux_->OnPreeditChanged(comp);
+
+ EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
+ EXPECT_EQ(VKEY_PROCESSKEY, delegate_->key_code);
+ EXPECT_TRUE(client->called_set_composition);
+ EXPECT_EQ(1U, client->composition_text.size());
+ EXPECT_EQ(L'a', client->composition_text[0]);
+ delegate_->Clear();
+
+ // IBus issues a commit text with composition after muting the space key down.
+ input_method_auralinux_->DispatchKeyEvent(
+ KeyEvent(ET_KEY_PRESSED, VKEY_SPACE, 0));
+ EXPECT_EQ(VKEY_UNKNOWN, delegate_->key_code);
+ EXPECT_FALSE(client->called_insert_text);
+ EXPECT_FALSE(client->called_insert_char);
+ delegate_->Clear();
+
+ input_method_auralinux_->OnPreeditEnd();
+ input_method_auralinux_->OnCommit(base::ASCIIToUTF16("A"));
+
+ EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
+ EXPECT_EQ(VKEY_PROCESSKEY, delegate_->key_code);
+ EXPECT_TRUE(client->called_clear_composition);
+ EXPECT_TRUE(client->called_insert_text);
+ EXPECT_EQ(1U, client->result_text.size());
+ EXPECT_EQ(L'A', client->result_text[0]);
+}
+
+// crbug.com/463491
+TEST_F(InputMethodAuraLinuxTest, DeadKeyTest) {
+ context_simple_->SetSyncMode(true);
+ context_simple_->SetEatKey(true);
+
+ scoped_ptr<TextInputClientForTesting> client(
+ new TextInputClientForTesting(TEXT_INPUT_TYPE_NONE));
+ input_method_auralinux_->SetFocusedTextInputClient(client.get());
+ input_method_auralinux_->OnTextInputTypeChanged(client.get());
+ KeyEvent dead_key(ET_KEY_PRESSED, VKEY_OEM_7, 0);
+ dead_key.set_character(L'\'');
+ input_method_auralinux_->DispatchKeyEvent(dead_key);
+
+ // The single quote key is muted.
+ EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
+ EXPECT_EQ(VKEY_OEM_7, delegate_->key_code);
+ EXPECT_FALSE(client->called_insert_text);
+ EXPECT_FALSE(client->called_insert_char);
+ delegate_->Clear();
+
+ context_simple_->AddAction("C:X");
+ KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
+ key.set_character(L'a');
+ input_method_auralinux_->DispatchKeyEvent(key);
+
+ // The following A key generates the accent key: รก.
+ EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
+ EXPECT_EQ(VKEY_A, delegate_->key_code);
+ EXPECT_FALSE(client->called_insert_text);
+ EXPECT_TRUE(client->called_insert_char);
+ EXPECT_EQ(1U, client->result_text.size());
+ EXPECT_EQ(L'X', client->result_text[0]);
+}
+
+TEST_F(InputMethodAuraLinuxTest, MultiCommitsTest) {
+ context_->SetSyncMode(true);
+ context_->SetEatKey(true);
+ context_->AddAction("C:a");
+ context_->AddAction("C:b");
+ context_->AddAction("C:c");
+
+ scoped_ptr<TextInputClientForTesting> client(
+ new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
+ input_method_auralinux_->SetFocusedTextInputClient(client.get());
+ input_method_auralinux_->OnTextInputTypeChanged(client.get());
+
+ KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
+ key.set_character(L'a');
+ input_method_auralinux_->DispatchKeyEvent(key);
+
+ EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
+ EXPECT_EQ(VKEY_PROCESSKEY, delegate_->key_code);
+ EXPECT_TRUE(client->called_insert_text);
+ EXPECT_FALSE(client->called_insert_char);
+ EXPECT_EQ(base::ASCIIToUTF16("abc"), client->result_text);
+}
+
+TEST_F(InputMethodAuraLinuxTest, MixedCompositionAndCommitTest) {
+ context_->SetSyncMode(true);
+ context_->SetEatKey(true);
+ context_->AddAction("C:a");
+ context_->AddAction("S");
+ context_->AddAction("U:b");
+ context_->AddAction("C:c");
+ 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.
+
+ scoped_ptr<TextInputClientForTesting> client(
+ new TextInputClientForTesting(TEXT_INPUT_TYPE_TEXT));
+ input_method_auralinux_->SetFocusedTextInputClient(client.get());
+ input_method_auralinux_->OnTextInputTypeChanged(client.get());
+
+ KeyEvent key(ET_KEY_PRESSED, VKEY_A, 0);
+ key.set_character(L'a');
+ input_method_auralinux_->DispatchKeyEvent(key);
+
+ EXPECT_EQ(ET_KEY_PRESSED, delegate_->key_type);
+ EXPECT_EQ(VKEY_PROCESSKEY, delegate_->key_code);
+ EXPECT_TRUE(client->called_set_composition);
+ EXPECT_TRUE(client->called_insert_text);
+ EXPECT_FALSE(client->called_insert_char);
+ EXPECT_EQ(base::ASCIIToUTF16("d"), client->composition_text);
+ EXPECT_EQ(base::ASCIIToUTF16("ac"), client->result_text);
+}
+
+} // namespace
+} // namespace ui

Powered by Google App Engine
This is Rietveld 408576698