OLD | NEW |
| (Empty) |
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. | |
4 | |
5 #include "content/components/web_contents_delegate_android/web_contents_delegate
_android.h" | |
6 | |
7 #include <android/keycodes.h> | |
8 | |
9 #include "base/android/jni_android.h" | |
10 #include "base/android/jni_string.h" | |
11 #include "content/components/web_contents_delegate_android/color_chooser_android
.h" | |
12 #include "content/public/browser/android/content_view_core.h" | |
13 #include "content/public/browser/render_widget_host_view.h" | |
14 #include "content/public/browser/invalidate_type.h" | |
15 #include "content/public/browser/page_navigator.h" | |
16 #include "content/public/browser/navigation_controller.h" | |
17 #include "content/public/browser/navigation_entry.h" | |
18 #include "content/public/browser/web_contents.h" | |
19 #include "content/public/common/page_transition_types.h" | |
20 #include "content/public/common/referrer.h" | |
21 #include "jni/WebContentsDelegateAndroid_jni.h" | |
22 #include "ui/gfx/rect.h" | |
23 #include "webkit/glue/window_open_disposition.h" | |
24 | |
25 using base::android::AttachCurrentThread; | |
26 using base::android::ConvertUTF8ToJavaString; | |
27 using base::android::ConvertUTF16ToJavaString; | |
28 using base::android::HasClass; | |
29 using base::android::ScopedJavaLocalRef; | |
30 | |
31 namespace content { | |
32 | |
33 WebContentsDelegateAndroid::WebContentsDelegateAndroid(JNIEnv* env, jobject obj) | |
34 : weak_java_delegate_(env, obj) { | |
35 } | |
36 | |
37 WebContentsDelegateAndroid::~WebContentsDelegateAndroid() { | |
38 } | |
39 | |
40 ScopedJavaLocalRef<jobject> | |
41 WebContentsDelegateAndroid::GetJavaDelegate(JNIEnv* env) const { | |
42 return weak_java_delegate_.get(env); | |
43 } | |
44 | |
45 // ---------------------------------------------------------------------------- | |
46 // WebContentsDelegate methods | |
47 // ---------------------------------------------------------------------------- | |
48 | |
49 ColorChooser* WebContentsDelegateAndroid::OpenColorChooser( | |
50 WebContents* source, | |
51 int color_chooser_id, | |
52 SkColor color) { | |
53 return ColorChooser::Create(color_chooser_id, source, color); | |
54 } | |
55 | |
56 // OpenURLFromTab() will be called when we're performing a browser-intiated | |
57 // navigation. The most common scenario for this is opening new tabs (see | |
58 // RenderViewImpl::decidePolicyForNavigation for more details). | |
59 WebContents* WebContentsDelegateAndroid::OpenURLFromTab( | |
60 WebContents* source, | |
61 const OpenURLParams& params) { | |
62 const GURL& url = params.url; | |
63 WindowOpenDisposition disposition = params.disposition; | |
64 PageTransition transition( | |
65 PageTransitionFromInt(params.transition)); | |
66 | |
67 if (!source || (disposition != CURRENT_TAB && | |
68 disposition != NEW_FOREGROUND_TAB && | |
69 disposition != NEW_BACKGROUND_TAB && | |
70 disposition != OFF_THE_RECORD)) { | |
71 NOTIMPLEMENTED(); | |
72 return NULL; | |
73 } | |
74 | |
75 JNIEnv* env = AttachCurrentThread(); | |
76 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
77 if (obj.is_null()) | |
78 return WebContentsDelegate::OpenURLFromTab(source, params); | |
79 | |
80 if (disposition == NEW_FOREGROUND_TAB || | |
81 disposition == NEW_BACKGROUND_TAB || | |
82 disposition == OFF_THE_RECORD) { | |
83 JNIEnv* env = AttachCurrentThread(); | |
84 ScopedJavaLocalRef<jstring> java_url = | |
85 ConvertUTF8ToJavaString(env, url.spec()); | |
86 Java_WebContentsDelegateAndroid_openNewTab(env, | |
87 obj.obj(), | |
88 java_url.obj(), | |
89 disposition == OFF_THE_RECORD); | |
90 return NULL; | |
91 } | |
92 | |
93 source->GetController().LoadURL(url, params.referrer, transition, | |
94 std::string()); | |
95 return source; | |
96 } | |
97 | |
98 void WebContentsDelegateAndroid::NavigationStateChanged( | |
99 const WebContents* source, unsigned changed_flags) { | |
100 if (changed_flags & INVALIDATE_TYPE_TITLE) { | |
101 JNIEnv* env = AttachCurrentThread(); | |
102 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
103 if (obj.is_null()) | |
104 return; | |
105 Java_WebContentsDelegateAndroid_onTitleUpdated( | |
106 env, obj.obj()); | |
107 } | |
108 } | |
109 | |
110 void WebContentsDelegateAndroid::AddNewContents( | |
111 WebContents* source, | |
112 WebContents* new_contents, | |
113 WindowOpenDisposition disposition, | |
114 const gfx::Rect& initial_pos, | |
115 bool user_gesture, | |
116 bool* was_blocked) { | |
117 JNIEnv* env = AttachCurrentThread(); | |
118 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
119 bool handled = false; | |
120 if (!obj.is_null()) { | |
121 handled = Java_WebContentsDelegateAndroid_addNewContents( | |
122 env, | |
123 obj.obj(), | |
124 reinterpret_cast<jint>(source), | |
125 reinterpret_cast<jint>(new_contents), | |
126 static_cast<jint>(disposition), | |
127 NULL, | |
128 user_gesture); | |
129 } | |
130 if (!handled) | |
131 delete new_contents; | |
132 } | |
133 | |
134 void WebContentsDelegateAndroid::ActivateContents(WebContents* contents) { | |
135 // TODO(dtrainor) When doing the merge I came across this. Should we be | |
136 // activating this tab here? | |
137 } | |
138 | |
139 void WebContentsDelegateAndroid::DeactivateContents(WebContents* contents) { | |
140 // Do nothing. | |
141 } | |
142 | |
143 void WebContentsDelegateAndroid::LoadingStateChanged(WebContents* source) { | |
144 JNIEnv* env = AttachCurrentThread(); | |
145 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
146 if (obj.is_null()) | |
147 return; | |
148 bool has_stopped = source == NULL || !source->IsLoading(); | |
149 | |
150 if (has_stopped) | |
151 Java_WebContentsDelegateAndroid_onLoadStopped(env, obj.obj()); | |
152 else | |
153 Java_WebContentsDelegateAndroid_onLoadStarted(env, obj.obj()); | |
154 } | |
155 | |
156 void WebContentsDelegateAndroid::LoadProgressChanged(WebContents* source, | |
157 double progress) { | |
158 JNIEnv* env = AttachCurrentThread(); | |
159 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
160 if (obj.is_null()) | |
161 return; | |
162 Java_WebContentsDelegateAndroid_notifyLoadProgressChanged( | |
163 env, | |
164 obj.obj(), | |
165 progress); | |
166 } | |
167 | |
168 void WebContentsDelegateAndroid::CloseContents(WebContents* source) { | |
169 JNIEnv* env = AttachCurrentThread(); | |
170 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
171 if (obj.is_null()) | |
172 return; | |
173 Java_WebContentsDelegateAndroid_closeContents(env, obj.obj()); | |
174 } | |
175 | |
176 void WebContentsDelegateAndroid::MoveContents(WebContents* source, | |
177 const gfx::Rect& pos) { | |
178 // Do nothing. | |
179 } | |
180 | |
181 bool WebContentsDelegateAndroid::AddMessageToConsole( | |
182 WebContents* source, | |
183 int32 level, | |
184 const string16& message, | |
185 int32 line_no, | |
186 const string16& source_id) { | |
187 JNIEnv* env = AttachCurrentThread(); | |
188 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
189 if (obj.is_null()) | |
190 return WebContentsDelegate::AddMessageToConsole(source, level, message, | |
191 line_no, source_id); | |
192 ScopedJavaLocalRef<jstring> jmessage(ConvertUTF16ToJavaString(env, message)); | |
193 ScopedJavaLocalRef<jstring> jsource_id( | |
194 ConvertUTF16ToJavaString(env, source_id)); | |
195 int jlevel = WEB_CONTENTS_DELEGATE_LOG_LEVEL_TIP; | |
196 switch (level) { | |
197 case logging::LOG_VERBOSE: | |
198 jlevel = WEB_CONTENTS_DELEGATE_LOG_LEVEL_TIP; | |
199 break; | |
200 case logging::LOG_INFO: | |
201 jlevel = WEB_CONTENTS_DELEGATE_LOG_LEVEL_LOG; | |
202 break; | |
203 case logging::LOG_WARNING: | |
204 jlevel = WEB_CONTENTS_DELEGATE_LOG_LEVEL_WARNING; | |
205 break; | |
206 case logging::LOG_ERROR: | |
207 jlevel = WEB_CONTENTS_DELEGATE_LOG_LEVEL_ERROR; | |
208 break; | |
209 default: | |
210 NOTREACHED(); | |
211 } | |
212 return Java_WebContentsDelegateAndroid_addMessageToConsole( | |
213 env, | |
214 GetJavaDelegate(env).obj(), | |
215 jlevel, | |
216 jmessage.obj(), | |
217 line_no, | |
218 jsource_id.obj()); | |
219 } | |
220 | |
221 // This is either called from TabContents::DidNavigateMainFramePostCommit() with | |
222 // an empty GURL or responding to RenderViewHost::OnMsgUpateTargetURL(). In | |
223 // Chrome, the latter is not always called, especially not during history | |
224 // navigation. So we only handle the first case and pass the source TabContents' | |
225 // url to Java to update the UI. | |
226 void WebContentsDelegateAndroid::UpdateTargetURL(WebContents* source, | |
227 int32 page_id, | |
228 const GURL& url) { | |
229 if (!url.is_empty()) | |
230 return; | |
231 JNIEnv* env = AttachCurrentThread(); | |
232 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
233 if (obj.is_null()) | |
234 return; | |
235 ScopedJavaLocalRef<jstring> java_url = | |
236 ConvertUTF8ToJavaString(env, source->GetURL().spec()); | |
237 Java_WebContentsDelegateAndroid_onUpdateUrl(env, | |
238 obj.obj(), | |
239 java_url.obj()); | |
240 } | |
241 | |
242 void WebContentsDelegateAndroid::HandleKeyboardEvent( | |
243 WebContents* source, | |
244 const NativeWebKeyboardEvent& event) { | |
245 jobject key_event = event.os_event; | |
246 if (key_event) { | |
247 JNIEnv* env = AttachCurrentThread(); | |
248 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
249 if (obj.is_null()) | |
250 return; | |
251 Java_WebContentsDelegateAndroid_handleKeyboardEvent( | |
252 env, obj.obj(), key_event); | |
253 } | |
254 } | |
255 | |
256 bool WebContentsDelegateAndroid::TakeFocus(WebContents* source, bool reverse) { | |
257 JNIEnv* env = AttachCurrentThread(); | |
258 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
259 if (obj.is_null()) | |
260 return WebContentsDelegate::TakeFocus(source, reverse); | |
261 return Java_WebContentsDelegateAndroid_takeFocus( | |
262 env, obj.obj(), reverse); | |
263 } | |
264 | |
265 void WebContentsDelegateAndroid::ShowRepostFormWarningDialog( | |
266 WebContents* source) { | |
267 JNIEnv* env = AttachCurrentThread(); | |
268 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
269 if (obj.is_null()) | |
270 return; | |
271 ScopedJavaLocalRef<jobject> content_view_core = | |
272 ContentViewCore::FromWebContents(source)->GetJavaObject(); | |
273 if (content_view_core.is_null()) | |
274 return; | |
275 Java_WebContentsDelegateAndroid_showRepostFormWarningDialog(env, obj.obj(), | |
276 content_view_core.obj()); | |
277 } | |
278 | |
279 void WebContentsDelegateAndroid::ToggleFullscreenModeForTab( | |
280 WebContents* web_contents, | |
281 bool enter_fullscreen) { | |
282 JNIEnv* env = AttachCurrentThread(); | |
283 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
284 if (obj.is_null()) | |
285 return; | |
286 Java_WebContentsDelegateAndroid_toggleFullscreenModeForTab( | |
287 env, obj.obj(), enter_fullscreen); | |
288 } | |
289 | |
290 bool WebContentsDelegateAndroid::IsFullscreenForTabOrPending( | |
291 const WebContents* web_contents) const { | |
292 JNIEnv* env = AttachCurrentThread(); | |
293 ScopedJavaLocalRef<jobject> obj = GetJavaDelegate(env); | |
294 if (obj.is_null()) | |
295 return false; | |
296 return Java_WebContentsDelegateAndroid_isFullscreenForTabOrPending( | |
297 env, obj.obj()); | |
298 } | |
299 | |
300 // ---------------------------------------------------------------------------- | |
301 // Native JNI methods | |
302 // ---------------------------------------------------------------------------- | |
303 | |
304 // Register native methods | |
305 | |
306 bool RegisterWebContentsDelegateAndroid(JNIEnv* env) { | |
307 if (!HasClass(env, kWebContentsDelegateAndroidClassPath)) { | |
308 DLOG(ERROR) << "Unable to find class WebContentsDelegateAndroid!"; | |
309 return false; | |
310 } | |
311 return RegisterNativesImpl(env); | |
312 } | |
313 | |
314 } // namespace content | |
OLD | NEW |