Add ICU message format support
[chromium-blink-merge.git] / ui / keyboard / keyboard_controller_proxy.cc
blob3671b02e9f24619f62c68683b52c73b491dbfc13
1 // Copyright (c) 2013 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.
5 #include "ui/keyboard/keyboard_controller_proxy.h"
7 #include "base/command_line.h"
8 #include "base/values.h"
9 #include "content/public/browser/site_instance.h"
10 #include "content/public/browser/web_contents.h"
11 #include "content/public/browser/web_contents.h"
12 #include "content/public/browser/web_contents_delegate.h"
13 #include "content/public/browser/web_contents_observer.h"
14 #include "content/public/browser/web_ui.h"
15 #include "content/public/common/bindings_policy.h"
16 #include "ui/aura/layout_manager.h"
17 #include "ui/aura/window.h"
18 #include "ui/base/ime/input_method.h"
19 #include "ui/base/ime/text_input_client.h"
20 #include "ui/keyboard/keyboard_constants.h"
21 #include "ui/keyboard/keyboard_controller.h"
22 #include "ui/keyboard/keyboard_switches.h"
23 #include "ui/keyboard/keyboard_util.h"
24 #include "ui/wm/core/shadow.h"
26 namespace {
28 // The WebContentsDelegate for the keyboard.
29 // The delegate deletes itself when the keyboard is destroyed.
30 class KeyboardContentsDelegate : public content::WebContentsDelegate,
31 public content::WebContentsObserver {
32 public:
33 KeyboardContentsDelegate(keyboard::KeyboardControllerProxy* proxy)
34 : proxy_(proxy) {}
35 ~KeyboardContentsDelegate() override {}
37 private:
38 // Overridden from content::WebContentsDelegate:
39 content::WebContents* OpenURLFromTab(
40 content::WebContents* source,
41 const content::OpenURLParams& params) override {
42 source->GetController().LoadURL(
43 params.url, params.referrer, params.transition, params.extra_headers);
44 Observe(source);
45 return source;
48 bool CanDragEnter(content::WebContents* source,
49 const content::DropData& data,
50 blink::WebDragOperationsMask operations_allowed) override {
51 return false;
54 bool ShouldCreateWebContents(
55 content::WebContents* web_contents,
56 int route_id,
57 int main_frame_route_id,
58 WindowContainerType window_container_type,
59 const std::string& frame_name,
60 const GURL& target_url,
61 const std::string& partition_id,
62 content::SessionStorageNamespace* session_storage_namespace) override {
63 return false;
66 bool IsPopupOrPanel(const content::WebContents* source) const override {
67 return true;
70 void MoveContents(content::WebContents* source,
71 const gfx::Rect& pos) override {
72 aura::Window* keyboard = proxy_->GetKeyboardWindow();
73 // keyboard window must have been added to keyboard container window at this
74 // point. Otherwise, wrong keyboard bounds is used and may cause problem as
75 // described in crbug.com/367788.
76 DCHECK(keyboard->parent());
77 // keyboard window bounds may not set to |pos| after this call. If keyboard
78 // is in FULL_WIDTH mode, only the height of keyboard window will be
79 // changed.
80 keyboard->SetBounds(pos);
83 // Overridden from content::WebContentsDelegate:
84 void RequestMediaAccessPermission(
85 content::WebContents* web_contents,
86 const content::MediaStreamRequest& request,
87 const content::MediaResponseCallback& callback) override {
88 proxy_->RequestAudioInput(web_contents, request, callback);
91 // Overridden from content::WebContentsObserver:
92 void WebContentsDestroyed() override { delete this; }
94 keyboard::KeyboardControllerProxy* proxy_;
96 DISALLOW_COPY_AND_ASSIGN(KeyboardContentsDelegate);
99 } // namespace
101 namespace keyboard {
103 KeyboardControllerProxy::KeyboardControllerProxy(
104 content::BrowserContext* context)
105 : browser_context_(context),
106 default_url_(kKeyboardURL),
107 keyboard_controller_(nullptr) {
110 KeyboardControllerProxy::~KeyboardControllerProxy() {
113 const GURL& KeyboardControllerProxy::GetVirtualKeyboardUrl() {
114 if (keyboard::IsInputViewEnabled()) {
115 const GURL& override_url = GetOverrideContentUrl();
116 return override_url.is_valid() ? override_url : default_url_;
117 } else {
118 return default_url_;
122 void KeyboardControllerProxy::LoadContents(const GURL& url) {
123 if (keyboard_contents_) {
124 content::OpenURLParams params(
125 url,
126 content::Referrer(),
127 SINGLETON_TAB,
128 ui::PAGE_TRANSITION_AUTO_TOPLEVEL,
129 false);
130 keyboard_contents_->OpenURL(params);
134 aura::Window* KeyboardControllerProxy::GetKeyboardWindow() {
135 if (!keyboard_contents_) {
136 content::BrowserContext* context = browser_context();
137 keyboard_contents_.reset(content::WebContents::Create(
138 content::WebContents::CreateParams(context,
139 content::SiteInstance::CreateForURL(context,
140 GetVirtualKeyboardUrl()))));
141 keyboard_contents_->SetDelegate(new KeyboardContentsDelegate(this));
142 SetupWebContents(keyboard_contents_.get());
143 LoadContents(GetVirtualKeyboardUrl());
144 keyboard_contents_->GetNativeView()->AddObserver(this);
147 return keyboard_contents_->GetNativeView();
150 bool KeyboardControllerProxy::HasKeyboardWindow() const {
151 return keyboard_contents_;
154 void KeyboardControllerProxy::ShowKeyboardContainer(aura::Window* container) {
155 GetKeyboardWindow()->Show();
156 container->Show();
159 void KeyboardControllerProxy::HideKeyboardContainer(aura::Window* container) {
160 container->Hide();
161 GetKeyboardWindow()->Hide();
164 void KeyboardControllerProxy::SetUpdateInputType(ui::TextInputType type) {
167 void KeyboardControllerProxy::EnsureCaretInWorkArea() {
168 if (GetInputMethod()->GetTextInputClient()) {
169 aura::Window* keyboard_window = GetKeyboardWindow();
170 aura::Window* root_window = keyboard_window->GetRootWindow();
171 gfx::Rect available_bounds = root_window->bounds();
172 gfx::Rect keyboard_bounds = keyboard_window->bounds();
173 available_bounds.set_height(available_bounds.height() -
174 keyboard_bounds.height());
175 GetInputMethod()->GetTextInputClient()->EnsureCaretInRect(available_bounds);
179 void KeyboardControllerProxy::LoadSystemKeyboard() {
180 DCHECK(keyboard_contents_);
181 if (keyboard_contents_->GetURL() != default_url_) {
182 // TODO(bshe): The height of system virtual keyboard and IME virtual
183 // keyboard may different. The height needs to be restored too.
184 LoadContents(default_url_);
188 void KeyboardControllerProxy::ReloadKeyboardIfNeeded() {
189 DCHECK(keyboard_contents_);
190 if (keyboard_contents_->GetURL() != GetVirtualKeyboardUrl()) {
191 if (keyboard_contents_->GetURL().GetOrigin() !=
192 GetVirtualKeyboardUrl().GetOrigin()) {
193 // Sets keyboard window rectangle to 0 and close current page before
194 // navigate to a keyboard in a different extension. This keeps the UX the
195 // same as Android. Note we need to explicitly close current page as it
196 // might try to resize keyboard window in javascript on a resize event.
197 GetKeyboardWindow()->SetBounds(gfx::Rect());
198 keyboard_contents_->ClosePage();
199 keyboard_controller()->SetKeyboardMode(FULL_WIDTH);
201 LoadContents(GetVirtualKeyboardUrl());
205 void KeyboardControllerProxy::SetController(KeyboardController* controller) {
206 keyboard_controller_ = controller;
209 void KeyboardControllerProxy::SetupWebContents(content::WebContents* contents) {
212 void KeyboardControllerProxy::OnWindowBoundsChanged(
213 aura::Window* window,
214 const gfx::Rect& old_bounds,
215 const gfx::Rect& new_bounds) {
216 if (!shadow_) {
217 shadow_.reset(new wm::Shadow());
218 shadow_->Init(wm::Shadow::STYLE_ACTIVE);
219 shadow_->layer()->SetVisible(true);
220 DCHECK(keyboard_contents_->GetNativeView()->parent());
221 keyboard_contents_->GetNativeView()->parent()->layer()->Add(
222 shadow_->layer());
225 shadow_->SetContentBounds(new_bounds);
228 void KeyboardControllerProxy::OnWindowDestroyed(aura::Window* window) {
229 window->RemoveObserver(this);
232 } // namespace keyboard