Extract code handling PrinterProviderAPI from PrintPreviewHandler
[chromium-blink-merge.git] / chrome / browser / android / chrome_web_contents_delegate_android.cc
blob6a71f28f9a70d52f9cceb22683c4fa8c11182a7e
1 // Copyright (c) 2012 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 "chrome/browser/android/chrome_web_contents_delegate_android.h"
7 #include "base/android/jni_android.h"
8 #include "base/android/jni_string.h"
9 #include "base/command_line.h"
10 #include "chrome/browser/chrome_notification_types.h"
11 #include "chrome/browser/file_select_helper.h"
12 #include "chrome/browser/media/media_capture_devices_dispatcher.h"
13 #include "chrome/browser/media/protected_media_identifier_permission_context.h"
14 #include "chrome/browser/media/protected_media_identifier_permission_context_factory.h"
15 #include "chrome/browser/prerender/prerender_manager.h"
16 #include "chrome/browser/prerender/prerender_manager_factory.h"
17 #include "chrome/browser/profiles/profile.h"
18 #include "chrome/browser/ui/blocked_content/popup_blocker_tab_helper.h"
19 #include "chrome/browser/ui/browser_navigator.h"
20 #include "chrome/browser/ui/find_bar/find_notification_details.h"
21 #include "chrome/browser/ui/find_bar/find_tab_helper.h"
22 #include "chrome/browser/ui/tab_helpers.h"
23 #include "chrome/common/chrome_switches.h"
24 #include "components/app_modal/javascript_dialog_manager.h"
25 #include "content/public/browser/notification_details.h"
26 #include "content/public/browser/notification_service.h"
27 #include "content/public/browser/notification_source.h"
28 #include "content/public/browser/render_process_host.h"
29 #include "content/public/browser/render_view_host.h"
30 #include "content/public/browser/web_contents.h"
31 #include "content/public/common/file_chooser_params.h"
32 #include "jni/ChromeWebContentsDelegateAndroid_jni.h"
33 #include "third_party/WebKit/public/web/WebWindowFeatures.h"
34 #include "ui/gfx/geometry/rect.h"
35 #include "ui/gfx/geometry/rect_f.h"
37 #if defined(ENABLE_PLUGINS)
38 #include "chrome/browser/pepper_broker_infobar_delegate.h"
39 #endif
41 using base::android::AttachCurrentThread;
42 using base::android::ScopedJavaLocalRef;
43 using content::FileChooserParams;
44 using content::WebContents;
46 namespace {
48 ScopedJavaLocalRef<jobject> CreateJavaRectF(
49 JNIEnv* env,
50 const gfx::RectF& rect) {
51 return ScopedJavaLocalRef<jobject>(
52 Java_ChromeWebContentsDelegateAndroid_createRectF(env,
53 rect.x(),
54 rect.y(),
55 rect.right(),
56 rect.bottom()));
59 ScopedJavaLocalRef<jobject> CreateJavaRect(
60 JNIEnv* env,
61 const gfx::Rect& rect) {
62 return ScopedJavaLocalRef<jobject>(
63 Java_ChromeWebContentsDelegateAndroid_createRect(
64 env,
65 static_cast<int>(rect.x()),
66 static_cast<int>(rect.y()),
67 static_cast<int>(rect.right()),
68 static_cast<int>(rect.bottom())));
71 } // anonymous namespace
73 namespace chrome {
74 namespace android {
76 ChromeWebContentsDelegateAndroid::ChromeWebContentsDelegateAndroid(JNIEnv* env,
77 jobject obj)
78 : WebContentsDelegateAndroid(env, obj) {
81 ChromeWebContentsDelegateAndroid::~ChromeWebContentsDelegateAndroid() {
82 notification_registrar_.RemoveAll();
85 // Register native methods.
86 bool RegisterChromeWebContentsDelegateAndroid(JNIEnv* env) {
87 return RegisterNativesImpl(env);
90 void ChromeWebContentsDelegateAndroid::LoadingStateChanged(
91 WebContents* source, bool to_different_document) {
92 bool has_stopped = source == NULL || !source->IsLoading();
93 WebContentsDelegateAndroid::LoadingStateChanged(
94 source, to_different_document);
95 LoadProgressChanged(source, has_stopped ? 1 : 0);
98 void ChromeWebContentsDelegateAndroid::RunFileChooser(
99 WebContents* web_contents,
100 const FileChooserParams& params) {
101 FileSelectHelper::RunFileChooser(web_contents, params);
104 void ChromeWebContentsDelegateAndroid::CloseContents(
105 WebContents* web_contents) {
106 // Prevent dangling registrations assigned to closed web contents.
107 if (notification_registrar_.IsRegistered(this,
108 chrome::NOTIFICATION_FIND_RESULT_AVAILABLE,
109 content::Source<WebContents>(web_contents))) {
110 notification_registrar_.Remove(this,
111 chrome::NOTIFICATION_FIND_RESULT_AVAILABLE,
112 content::Source<WebContents>(web_contents));
115 WebContentsDelegateAndroid::CloseContents(web_contents);
118 void ChromeWebContentsDelegateAndroid::Observe(
119 int type,
120 const content::NotificationSource& source,
121 const content::NotificationDetails& details) {
122 switch (type) {
123 case chrome::NOTIFICATION_FIND_RESULT_AVAILABLE:
124 OnFindResultAvailable(
125 content::Source<WebContents>(source).ptr(),
126 content::Details<FindNotificationDetails>(details).ptr());
127 break;
128 default:
129 NOTREACHED() << "Unexpected notification: " << type;
130 break;
134 void ChromeWebContentsDelegateAndroid::FindReply(
135 WebContents* web_contents,
136 int request_id,
137 int number_of_matches,
138 const gfx::Rect& selection_rect,
139 int active_match_ordinal,
140 bool final_update) {
141 if (!notification_registrar_.IsRegistered(this,
142 chrome::NOTIFICATION_FIND_RESULT_AVAILABLE,
143 content::Source<WebContents>(web_contents))) {
144 notification_registrar_.Add(this,
145 chrome::NOTIFICATION_FIND_RESULT_AVAILABLE,
146 content::Source<WebContents>(web_contents));
149 FindTabHelper* find_tab_helper = FindTabHelper::FromWebContents(web_contents);
150 find_tab_helper->HandleFindReply(request_id,
151 number_of_matches,
152 selection_rect,
153 active_match_ordinal,
154 final_update);
157 void ChromeWebContentsDelegateAndroid::OnFindResultAvailable(
158 WebContents* web_contents,
159 const FindNotificationDetails* find_result) {
160 JNIEnv* env = base::android::AttachCurrentThread();
161 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env);
162 if (obj.is_null())
163 return;
165 ScopedJavaLocalRef<jobject> selection_rect = CreateJavaRect(
166 env, find_result->selection_rect());
168 // Create the details object.
169 ScopedJavaLocalRef<jobject> details_object =
170 Java_ChromeWebContentsDelegateAndroid_createFindNotificationDetails(
171 env,
172 find_result->number_of_matches(),
173 selection_rect.obj(),
174 find_result->active_match_ordinal(),
175 find_result->final_update());
177 Java_ChromeWebContentsDelegateAndroid_onFindResultAvailable(
178 env,
179 obj.obj(),
180 details_object.obj());
183 void ChromeWebContentsDelegateAndroid::FindMatchRectsReply(
184 WebContents* web_contents,
185 int version,
186 const std::vector<gfx::RectF>& rects,
187 const gfx::RectF& active_rect) {
188 JNIEnv* env = base::android::AttachCurrentThread();
189 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env);
190 if (obj.is_null())
191 return;
193 // Create the details object.
194 ScopedJavaLocalRef<jobject> details_object =
195 Java_ChromeWebContentsDelegateAndroid_createFindMatchRectsDetails(
196 env,
197 version,
198 rects.size(),
199 CreateJavaRectF(env, active_rect).obj());
201 // Add the rects
202 for (size_t i = 0; i < rects.size(); ++i) {
203 Java_ChromeWebContentsDelegateAndroid_setMatchRectByIndex(
204 env,
205 details_object.obj(),
207 CreateJavaRectF(env, rects[i]).obj());
210 Java_ChromeWebContentsDelegateAndroid_onFindMatchRectsAvailable(
211 env,
212 obj.obj(),
213 details_object.obj());
216 content::JavaScriptDialogManager*
217 ChromeWebContentsDelegateAndroid::GetJavaScriptDialogManager(
218 WebContents* source) {
219 return app_modal::JavaScriptDialogManager::GetInstance();
222 void ChromeWebContentsDelegateAndroid::RequestMediaAccessPermission(
223 content::WebContents* web_contents,
224 const content::MediaStreamRequest& request,
225 const content::MediaResponseCallback& callback) {
226 MediaCaptureDevicesDispatcher::GetInstance()->ProcessMediaAccessRequest(
227 web_contents, request, callback, NULL);
230 bool ChromeWebContentsDelegateAndroid::CheckMediaAccessPermission(
231 content::WebContents* web_contents,
232 const GURL& security_origin,
233 content::MediaStreamType type) {
234 return MediaCaptureDevicesDispatcher::GetInstance()
235 ->CheckMediaAccessPermission(web_contents, security_origin, type);
238 bool ChromeWebContentsDelegateAndroid::RequestPpapiBrokerPermission(
239 WebContents* web_contents,
240 const GURL& url,
241 const base::FilePath& plugin_path,
242 const base::Callback<void(bool)>& callback) {
243 #if defined(ENABLE_PLUGINS)
244 PepperBrokerInfoBarDelegate::Create(
245 web_contents, url, plugin_path, callback);
246 return true;
247 #else
248 return false;
249 #endif
252 WebContents* ChromeWebContentsDelegateAndroid::OpenURLFromTab(
253 WebContents* source,
254 const content::OpenURLParams& params) {
255 WindowOpenDisposition disposition = params.disposition;
256 if (!source || (disposition != CURRENT_TAB &&
257 disposition != NEW_FOREGROUND_TAB &&
258 disposition != NEW_BACKGROUND_TAB &&
259 disposition != OFF_THE_RECORD &&
260 disposition != NEW_POPUP &&
261 disposition != NEW_WINDOW)) {
262 // We can't handle this here. Give the parent a chance.
263 return WebContentsDelegateAndroid::OpenURLFromTab(source, params);
266 Profile* profile = Profile::FromBrowserContext(source->GetBrowserContext());
267 chrome::NavigateParams nav_params(profile,
268 params.url,
269 params.transition);
270 FillNavigateParamsFromOpenURLParams(&nav_params, params);
271 nav_params.source_contents = source;
272 nav_params.window_action = chrome::NavigateParams::SHOW_WINDOW;
273 nav_params.user_gesture = params.user_gesture;
275 PopupBlockerTabHelper* popup_blocker_helper =
276 PopupBlockerTabHelper::FromWebContents(source);
277 DCHECK(popup_blocker_helper);
279 if ((params.disposition == NEW_POPUP ||
280 params.disposition == NEW_FOREGROUND_TAB ||
281 params.disposition == NEW_BACKGROUND_TAB ||
282 params.disposition == NEW_WINDOW) &&
283 !params.user_gesture &&
284 !base::CommandLine::ForCurrentProcess()->HasSwitch(
285 switches::kDisablePopupBlocking)) {
286 if (popup_blocker_helper->MaybeBlockPopup(nav_params,
287 blink::WebWindowFeatures())) {
288 return NULL;
292 if (disposition == CURRENT_TAB) {
293 // Only prerender for a current-tab navigation to avoid session storage
294 // namespace issues.
295 nav_params.target_contents = source;
296 prerender::PrerenderManager* prerender_manager =
297 prerender::PrerenderManagerFactory::GetForProfile(profile);
298 if (prerender_manager &&
299 prerender_manager->MaybeUsePrerenderedPage(params.url, &nav_params)) {
300 return nav_params.target_contents;
304 return WebContentsDelegateAndroid::OpenURLFromTab(source, params);
307 void ChromeWebContentsDelegateAndroid::AddNewContents(
308 WebContents* source,
309 WebContents* new_contents,
310 WindowOpenDisposition disposition,
311 const gfx::Rect& initial_rect,
312 bool user_gesture,
313 bool* was_blocked) {
314 // No code for this yet.
315 DCHECK_NE(disposition, SAVE_TO_DISK);
316 // Can't create a new contents for the current tab - invalid case.
317 DCHECK_NE(disposition, CURRENT_TAB);
319 TabHelpers::AttachTabHelpers(new_contents);
321 JNIEnv* env = AttachCurrentThread();
322 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env);
323 bool handled = false;
324 if (!obj.is_null()) {
325 ScopedJavaLocalRef<jobject> jsource;
326 if (source)
327 jsource = source->GetJavaWebContents();
328 ScopedJavaLocalRef<jobject> jnew_contents;
329 if (new_contents)
330 jnew_contents = new_contents->GetJavaWebContents();
332 handled = Java_ChromeWebContentsDelegateAndroid_addNewContents(
333 env,
334 obj.obj(),
335 jsource.obj(),
336 jnew_contents.obj(),
337 static_cast<jint>(disposition),
338 NULL,
339 user_gesture);
342 if (was_blocked)
343 *was_blocked = !handled;
344 if (!handled)
345 delete new_contents;
348 } // namespace android
349 } // namespace chrome