Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "content/browser/renderer_host/render_widget_host_view_android.h" | 5 #include "content/browser/renderer_host/render_widget_host_view_android.h" |
| 6 | 6 |
| 7 #include <android/bitmap.h> | 7 #include <android/bitmap.h> |
| 8 | 8 |
| 9 #include "base/bind.h" | 9 #include "base/bind.h" |
| 10 #include "base/bind_helpers.h" | 10 #include "base/bind_helpers.h" |
| 11 #include "base/command_line.h" | 11 #include "base/command_line.h" |
| 12 #include "base/logging.h" | 12 #include "base/logging.h" |
| 13 #include "base/message_loop/message_loop.h" | 13 #include "base/message_loop/message_loop.h" |
| 14 #include "base/strings/utf_string_conversions.h" | 14 #include "base/strings/utf_string_conversions.h" |
| 15 #include "base/threading/worker_pool.h" | 15 #include "base/threading/worker_pool.h" |
| 16 #include "cc/layers/delegated_renderer_layer.h" | 16 #include "cc/layers/delegated_renderer_layer.h" |
| 17 #include "cc/layers/layer.h" | 17 #include "cc/layers/layer.h" |
| 18 #include "cc/layers/texture_layer.h" | 18 #include "cc/layers/texture_layer.h" |
| 19 #include "cc/output/compositor_frame.h" | 19 #include "cc/output/compositor_frame.h" |
| 20 #include "cc/output/compositor_frame_ack.h" | 20 #include "cc/output/compositor_frame_ack.h" |
| 21 #include "cc/output/copy_output_request.h" | |
| 22 #include "cc/output/copy_output_result.h" | |
| 21 #include "cc/trees/layer_tree_host.h" | 23 #include "cc/trees/layer_tree_host.h" |
| 22 #include "content/browser/accessibility/browser_accessibility_manager_android.h" | 24 #include "content/browser/accessibility/browser_accessibility_manager_android.h" |
| 23 #include "content/browser/android/content_view_core_impl.h" | 25 #include "content/browser/android/content_view_core_impl.h" |
| 24 #include "content/browser/android/in_process/synchronous_compositor_impl.h" | 26 #include "content/browser/android/in_process/synchronous_compositor_impl.h" |
| 25 #include "content/browser/android/overscroll_glow.h" | 27 #include "content/browser/android/overscroll_glow.h" |
| 26 #include "content/browser/gpu/gpu_surface_tracker.h" | 28 #include "content/browser/gpu/gpu_surface_tracker.h" |
| 27 #include "content/browser/renderer_host/compositor_impl_android.h" | 29 #include "content/browser/renderer_host/compositor_impl_android.h" |
| 30 #include "content/browser/renderer_host/dip_util.h" | |
| 28 #include "content/browser/renderer_host/image_transport_factory_android.h" | 31 #include "content/browser/renderer_host/image_transport_factory_android.h" |
| 29 #include "content/browser/renderer_host/render_widget_host_impl.h" | 32 #include "content/browser/renderer_host/render_widget_host_impl.h" |
| 30 #include "content/browser/renderer_host/surface_texture_transport_client_android .h" | 33 #include "content/browser/renderer_host/surface_texture_transport_client_android .h" |
| 31 #include "content/browser/renderer_host/touch_smooth_scroll_gesture_android.h" | 34 #include "content/browser/renderer_host/touch_smooth_scroll_gesture_android.h" |
| 32 #include "content/common/gpu/client/gl_helper.h" | 35 #include "content/common/gpu/client/gl_helper.h" |
| 33 #include "content/common/gpu/gpu_messages.h" | 36 #include "content/common/gpu/gpu_messages.h" |
| 34 #include "content/common/input_messages.h" | 37 #include "content/common/input_messages.h" |
| 35 #include "content/common/view_messages.h" | 38 #include "content/common/view_messages.h" |
| 36 #include "content/public/common/content_switches.h" | 39 #include "content/public/common/content_switches.h" |
| 40 #include "skia/ext/image_operations.h" | |
| 37 #include "third_party/khronos/GLES2/gl2.h" | 41 #include "third_party/khronos/GLES2/gl2.h" |
| 38 #include "third_party/khronos/GLES2/gl2ext.h" | 42 #include "third_party/khronos/GLES2/gl2ext.h" |
| 39 #include "ui/gfx/android/device_display_info.h" | 43 #include "ui/gfx/android/device_display_info.h" |
| 40 #include "ui/gfx/android/java_bitmap.h" | 44 #include "ui/gfx/android/java_bitmap.h" |
| 41 #include "ui/gfx/display.h" | 45 #include "ui/gfx/display.h" |
| 42 #include "ui/gfx/screen.h" | 46 #include "ui/gfx/screen.h" |
| 43 #include "ui/gfx/size_conversions.h" | 47 #include "ui/gfx/size_conversions.h" |
| 44 | 48 |
| 45 namespace content { | 49 namespace content { |
| 46 | 50 |
| (...skipping 275 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 322 } | 326 } |
| 323 | 327 |
| 324 bool RenderWidgetHostViewAndroid::HasFocus() const { | 328 bool RenderWidgetHostViewAndroid::HasFocus() const { |
| 325 if (!content_view_core_) | 329 if (!content_view_core_) |
| 326 return false; // ContentViewCore not created yet. | 330 return false; // ContentViewCore not created yet. |
| 327 | 331 |
| 328 return content_view_core_->HasFocus(); | 332 return content_view_core_->HasFocus(); |
| 329 } | 333 } |
| 330 | 334 |
| 331 bool RenderWidgetHostViewAndroid::IsSurfaceAvailableForCopy() const { | 335 bool RenderWidgetHostViewAndroid::IsSurfaceAvailableForCopy() const { |
| 332 NOTIMPLEMENTED(); | 336 return HasValidFrame(); |
| 333 return false; | |
| 334 } | 337 } |
| 335 | 338 |
| 336 void RenderWidgetHostViewAndroid::Show() { | 339 void RenderWidgetHostViewAndroid::Show() { |
| 337 if (are_layers_attached_) | 340 if (are_layers_attached_) |
| 338 return; | 341 return; |
| 339 | 342 |
| 340 are_layers_attached_ = true; | 343 are_layers_attached_ = true; |
| 341 AttachLayers(); | 344 AttachLayers(); |
| 342 } | 345 } |
| 343 | 346 |
| (...skipping 189 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 533 | 536 |
| 534 void RenderWidgetHostViewAndroid::SetBackground(const SkBitmap& background) { | 537 void RenderWidgetHostViewAndroid::SetBackground(const SkBitmap& background) { |
| 535 RenderWidgetHostViewBase::SetBackground(background); | 538 RenderWidgetHostViewBase::SetBackground(background); |
| 536 host_->Send(new ViewMsg_SetBackground(host_->GetRoutingID(), background)); | 539 host_->Send(new ViewMsg_SetBackground(host_->GetRoutingID(), background)); |
| 537 } | 540 } |
| 538 | 541 |
| 539 void RenderWidgetHostViewAndroid::CopyFromCompositingSurface( | 542 void RenderWidgetHostViewAndroid::CopyFromCompositingSurface( |
| 540 const gfx::Rect& src_subrect, | 543 const gfx::Rect& src_subrect, |
| 541 const gfx::Size& dst_size, | 544 const gfx::Size& dst_size, |
| 542 const base::Callback<void(bool, const SkBitmap&)>& callback) { | 545 const base::Callback<void(bool, const SkBitmap&)>& callback) { |
| 543 NOTIMPLEMENTED(); | 546 if (!IsSurfaceAvailableForCopy()) { |
| 544 callback.Run(false, SkBitmap()); | 547 callback.Run(false, SkBitmap()); |
| 548 return; | |
| 549 } | |
| 550 | |
| 551 const gfx::Display& display = | |
| 552 gfx::Screen::GetNativeScreen()->GetPrimaryDisplay(); | |
| 553 float device_scale_factor = display.device_scale_factor(); | |
| 554 | |
| 555 const gfx::Size& dst_size_in_pixel = ConvertViewSizeToPixel(this, dst_size); | |
|
no sievers
2013/08/09 20:54:03
Ok, I guess it makes sense that we use DIP here, s
pfeldman
2013/08/12 10:17:36
Done.
| |
| 556 gfx::Rect src_subrect_in_pixel = | |
| 557 ConvertRectToPixel(device_scale_factor, src_subrect); | |
| 558 | |
| 559 scoped_ptr<cc::CopyOutputRequest> request; | |
| 560 if (src_subrect_in_pixel.size() == dst_size_in_pixel) { | |
| 561 request = cc::CopyOutputRequest::CreateBitmapRequest(base::Bind( | |
| 562 &RenderWidgetHostViewAndroid::CopyFromCompositingSurfaceHasResult, | |
| 563 dst_size_in_pixel, | |
| 564 callback)); | |
| 565 } else { | |
| 566 request = cc::CopyOutputRequest::CreateRequest(base::Bind( | |
| 567 &RenderWidgetHostViewAndroid::CopyFromCompositingSurfaceHasResult, | |
| 568 dst_size_in_pixel, | |
| 569 callback)); | |
| 570 } | |
| 571 request->set_area(src_subrect_in_pixel); | |
| 572 layer_->RequestCopyOfOutput(request.Pass()); | |
| 545 } | 573 } |
| 546 | 574 |
| 547 void RenderWidgetHostViewAndroid::CopyFromCompositingSurfaceToVideoFrame( | 575 void RenderWidgetHostViewAndroid::CopyFromCompositingSurfaceToVideoFrame( |
| 548 const gfx::Rect& src_subrect, | 576 const gfx::Rect& src_subrect, |
| 549 const scoped_refptr<media::VideoFrame>& target, | 577 const scoped_refptr<media::VideoFrame>& target, |
| 550 const base::Callback<void(bool)>& callback) { | 578 const base::Callback<void(bool)>& callback) { |
| 551 NOTIMPLEMENTED(); | 579 NOTIMPLEMENTED(); |
| 552 callback.Run(false); | 580 callback.Run(false); |
| 553 } | 581 } |
| 554 | 582 |
| (...skipping 591 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1146 } | 1174 } |
| 1147 | 1175 |
| 1148 void RenderWidgetHostViewAndroid::OnLostResources() { | 1176 void RenderWidgetHostViewAndroid::OnLostResources() { |
| 1149 if (texture_layer_) | 1177 if (texture_layer_) |
| 1150 texture_layer_->SetIsDrawable(false); | 1178 texture_layer_->SetIsDrawable(false); |
| 1151 texture_id_in_layer_ = 0; | 1179 texture_id_in_layer_ = 0; |
| 1152 RunAckCallbacks(); | 1180 RunAckCallbacks(); |
| 1153 } | 1181 } |
| 1154 | 1182 |
| 1155 // static | 1183 // static |
| 1184 void RenderWidgetHostViewAndroid::CopyFromCompositingSurfaceHasResult( | |
|
no sievers
2013/08/09 20:54:03
nit: Do we even need this function now that we hav
pfeldman
2013/08/12 10:17:36
Done. Branches now call respective callbacks.
| |
| 1185 const gfx::Size& dst_size_in_pixel, | |
| 1186 const base::Callback<void(bool, const SkBitmap&)>& callback, | |
| 1187 scoped_ptr<cc::CopyOutputResult> result) { | |
| 1188 if (result->IsEmpty() || result->size().IsEmpty()) { | |
| 1189 callback.Run(false, SkBitmap()); | |
| 1190 return; | |
| 1191 } | |
| 1192 | |
| 1193 if (result->HasTexture()) { | |
| 1194 PrepareTextureCopyOutputResult(dst_size_in_pixel, callback, result.Pass()); | |
| 1195 return; | |
| 1196 } | |
| 1197 | |
| 1198 DCHECK(result->HasBitmap()); | |
| 1199 PrepareBitmapCopyOutputResult(dst_size_in_pixel, callback, result.Pass()); | |
| 1200 } | |
| 1201 | |
| 1202 static void CopyFromCompositingSurfaceFinished( | |
| 1203 const base::Callback<void(bool, const SkBitmap&)>& callback, | |
|
no sievers
2013/08/09 20:54:03
can you put this function inside the anonymous nam
pfeldman
2013/08/12 10:17:36
Done.
| |
| 1204 const cc::TextureMailbox::ReleaseCallback& release_callback, | |
| 1205 scoped_ptr<SkBitmap> bitmap, | |
| 1206 scoped_ptr<SkAutoLockPixels> bitmap_pixels_lock, | |
| 1207 bool result) { | |
| 1208 bitmap_pixels_lock.reset(); | |
| 1209 release_callback.Run(0, false); | |
| 1210 callback.Run(result, *bitmap); | |
| 1211 } | |
| 1212 | |
| 1213 // static | |
| 1214 void RenderWidgetHostViewAndroid::PrepareTextureCopyOutputResult( | |
| 1215 const gfx::Size& dst_size_in_pixel, | |
| 1216 const base::Callback<void(bool, const SkBitmap&)>& callback, | |
| 1217 scoped_ptr<cc::CopyOutputResult> result) { | |
| 1218 base::ScopedClosureRunner scoped_callback_runner( | |
| 1219 base::Bind(callback, false, SkBitmap())); | |
| 1220 | |
| 1221 DCHECK(result->HasTexture()); | |
| 1222 if (!result->HasTexture()) | |
| 1223 return; | |
| 1224 | |
| 1225 scoped_ptr<SkBitmap> bitmap(new SkBitmap); | |
| 1226 bitmap->setConfig(SkBitmap::kARGB_8888_Config, | |
| 1227 dst_size_in_pixel.width(), dst_size_in_pixel.height()); | |
| 1228 if (!bitmap->allocPixels()) | |
| 1229 return; | |
| 1230 bitmap->setIsOpaque(true); | |
| 1231 | |
| 1232 ImageTransportFactoryAndroid* factory = | |
| 1233 ImageTransportFactoryAndroid::GetInstance(); | |
| 1234 GLHelper* gl_helper = factory->GetGLHelper(); | |
| 1235 if (!gl_helper) | |
| 1236 return; | |
| 1237 | |
| 1238 scoped_ptr<SkAutoLockPixels> bitmap_pixels_lock( | |
| 1239 new SkAutoLockPixels(*bitmap)); | |
| 1240 uint8* pixels = static_cast<uint8*>(bitmap->getPixels()); | |
| 1241 | |
| 1242 scoped_ptr<cc::TextureMailbox> texture_mailbox = result->TakeTexture(); | |
| 1243 DCHECK(texture_mailbox->IsTexture()); | |
| 1244 if (!texture_mailbox->IsTexture()) | |
| 1245 return; | |
| 1246 | |
| 1247 scoped_callback_runner.Release(); | |
| 1248 | |
| 1249 gl_helper->CropScaleReadbackAndCleanMailbox( | |
| 1250 texture_mailbox->name(), | |
| 1251 texture_mailbox->sync_point(), | |
| 1252 result->size(), | |
| 1253 gfx::Rect(result->size()), | |
| 1254 dst_size_in_pixel, | |
| 1255 pixels, | |
| 1256 base::Bind(&CopyFromCompositingSurfaceFinished, | |
| 1257 callback, | |
| 1258 texture_mailbox->callback(), | |
| 1259 base::Passed(&bitmap), | |
| 1260 base::Passed(&bitmap_pixels_lock))); | |
| 1261 } | |
| 1262 | |
| 1263 // static | |
| 1264 void RenderWidgetHostViewAndroid::PrepareBitmapCopyOutputResult( | |
| 1265 const gfx::Size& dst_size_in_pixel, | |
| 1266 const base::Callback<void(bool, const SkBitmap&)>& callback, | |
| 1267 scoped_ptr<cc::CopyOutputResult> result) { | |
| 1268 DCHECK(result->HasBitmap()); | |
| 1269 | |
| 1270 base::ScopedClosureRunner scoped_callback_runner( | |
| 1271 base::Bind(callback, false, SkBitmap())); | |
| 1272 if (!result->HasBitmap()) | |
| 1273 return; | |
| 1274 | |
| 1275 scoped_ptr<SkBitmap> source = result->TakeBitmap(); | |
| 1276 DCHECK(source); | |
| 1277 if (!source) | |
| 1278 return; | |
| 1279 | |
| 1280 DCHECK_EQ(source->width(), dst_size_in_pixel.width()); | |
| 1281 DCHECK_EQ(source->height(), dst_size_in_pixel.height()); | |
| 1282 | |
| 1283 scoped_callback_runner.Release(); | |
| 1284 callback.Run(true, *source); | |
| 1285 } | |
| 1286 | |
| 1287 // static | |
| 1156 void RenderWidgetHostViewPort::GetDefaultScreenInfo( | 1288 void RenderWidgetHostViewPort::GetDefaultScreenInfo( |
| 1157 WebKit::WebScreenInfo* results) { | 1289 WebKit::WebScreenInfo* results) { |
| 1158 const gfx::Display& display = | 1290 const gfx::Display& display = |
| 1159 gfx::Screen::GetNativeScreen()->GetPrimaryDisplay(); | 1291 gfx::Screen::GetNativeScreen()->GetPrimaryDisplay(); |
| 1160 results->rect = display.bounds(); | 1292 results->rect = display.bounds(); |
| 1161 // TODO(husky): Remove any system controls from availableRect. | 1293 // TODO(husky): Remove any system controls from availableRect. |
| 1162 results->availableRect = display.work_area(); | 1294 results->availableRect = display.work_area(); |
| 1163 results->deviceScaleFactor = display.device_scale_factor(); | 1295 results->deviceScaleFactor = display.device_scale_factor(); |
| 1164 gfx::DeviceDisplayInfo info; | 1296 gfx::DeviceDisplayInfo info; |
| 1165 results->depth = info.GetBitsPerPixel(); | 1297 results->depth = info.GetBitsPerPixel(); |
| 1166 results->depthPerComponent = info.GetBitsPerComponent(); | 1298 results->depthPerComponent = info.GetBitsPerComponent(); |
| 1167 results->isMonochrome = (results->depthPerComponent == 0); | 1299 results->isMonochrome = (results->depthPerComponent == 0); |
| 1168 } | 1300 } |
| 1169 | 1301 |
| 1170 //////////////////////////////////////////////////////////////////////////////// | 1302 //////////////////////////////////////////////////////////////////////////////// |
| 1171 // RenderWidgetHostView, public: | 1303 // RenderWidgetHostView, public: |
| 1172 | 1304 |
| 1173 // static | 1305 // static |
| 1174 RenderWidgetHostView* | 1306 RenderWidgetHostView* |
| 1175 RenderWidgetHostView::CreateViewForWidget(RenderWidgetHost* widget) { | 1307 RenderWidgetHostView::CreateViewForWidget(RenderWidgetHost* widget) { |
| 1176 RenderWidgetHostImpl* rwhi = RenderWidgetHostImpl::From(widget); | 1308 RenderWidgetHostImpl* rwhi = RenderWidgetHostImpl::From(widget); |
| 1177 return new RenderWidgetHostViewAndroid(rwhi, NULL); | 1309 return new RenderWidgetHostViewAndroid(rwhi, NULL); |
| 1178 } | 1310 } |
| 1179 | 1311 |
| 1180 } // namespace content | 1312 } // namespace content |
| OLD | NEW |