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_aura.h" | 5 #include "content/browser/renderer_host/render_widget_host_view_aura.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/bind_helpers.h" | 8 #include "base/bind_helpers.h" |
9 #include "base/command_line.h" | 9 #include "base/command_line.h" |
10 #include "base/debug/trace_event.h" | 10 #include "base/debug/trace_event.h" |
11 #include "base/logging.h" | 11 #include "base/logging.h" |
12 #include "base/message_loop.h" | 12 #include "base/message_loop.h" |
13 #include "base/string_number_conversions.h" | 13 #include "base/string_number_conversions.h" |
14 #include "cc/output/compositor_frame.h" | 14 #include "cc/output/compositor_frame.h" |
15 #include "cc/output/compositor_frame_ack.h" | 15 #include "cc/output/compositor_frame_ack.h" |
| 16 #include "cc/resources/texture_mailbox.h" |
16 #include "content/browser/accessibility/browser_accessibility_manager.h" | 17 #include "content/browser/accessibility/browser_accessibility_manager.h" |
17 #include "content/browser/accessibility/browser_accessibility_state_impl.h" | 18 #include "content/browser/accessibility/browser_accessibility_state_impl.h" |
18 #include "content/browser/renderer_host/backing_store_aura.h" | 19 #include "content/browser/renderer_host/backing_store_aura.h" |
19 #include "content/browser/renderer_host/dip_util.h" | 20 #include "content/browser/renderer_host/dip_util.h" |
20 #include "content/browser/renderer_host/overscroll_controller.h" | 21 #include "content/browser/renderer_host/overscroll_controller.h" |
21 #include "content/browser/renderer_host/render_view_host_delegate.h" | 22 #include "content/browser/renderer_host/render_view_host_delegate.h" |
22 #include "content/browser/renderer_host/render_widget_host_impl.h" | 23 #include "content/browser/renderer_host/render_widget_host_impl.h" |
23 #include "content/browser/renderer_host/touch_smooth_scroll_gesture_aura.h" | 24 #include "content/browser/renderer_host/touch_smooth_scroll_gesture_aura.h" |
24 #include "content/browser/renderer_host/ui_events_helper.h" | 25 #include "content/browser/renderer_host/ui_events_helper.h" |
25 #include "content/browser/renderer_host/web_input_event_aura.h" | 26 #include "content/browser/renderer_host/web_input_event_aura.h" |
(...skipping 334 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
360 SkAutoLockPixels lock(bitmap); | 361 SkAutoLockPixels lock(bitmap); |
361 media::CopyRGBToVideoFrame( | 362 media::CopyRGBToVideoFrame( |
362 reinterpret_cast<const uint8*>(bitmap.getPixels()), | 363 reinterpret_cast<const uint8*>(bitmap.getPixels()), |
363 bitmap.rowBytes(), | 364 bitmap.rowBytes(), |
364 region_in_frame, | 365 region_in_frame, |
365 target.get()); | 366 target.get()); |
366 } | 367 } |
367 callback.Run(true); | 368 callback.Run(true); |
368 } | 369 } |
369 | 370 |
| 371 void ReleaseMailbox(MessageLoop *msg_loop, base::Callback<void()> callback, |
| 372 unsigned sync_point, bool lost_resource) { |
| 373 if (MessageLoop::current() == msg_loop) { |
| 374 callback.Run(); |
| 375 } else |
| 376 msg_loop->PostTask(FROM_HERE, callback); |
| 377 } |
| 378 |
370 } // namespace | 379 } // namespace |
371 | 380 |
372 // We need to watch for mouse events outside a Web Popup or its parent | 381 // We need to watch for mouse events outside a Web Popup or its parent |
373 // and dismiss the popup for certain events. | 382 // and dismiss the popup for certain events. |
374 class RenderWidgetHostViewAura::EventFilterForPopupExit : | 383 class RenderWidgetHostViewAura::EventFilterForPopupExit : |
375 public ui::EventHandler { | 384 public ui::EventHandler { |
376 public: | 385 public: |
377 explicit EventFilterForPopupExit(RenderWidgetHostViewAura* rwhva) | 386 explicit EventFilterForPopupExit(RenderWidgetHostViewAura* rwhva) |
378 : rwhva_(rwhva) { | 387 : rwhva_(rwhva) { |
379 DCHECK(rwhva_); | 388 DCHECK(rwhva_); |
(...skipping 567 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
947 | 956 |
948 void RenderWidgetHostViewAura::Blur() { | 957 void RenderWidgetHostViewAura::Blur() { |
949 window_->Blur(); | 958 window_->Blur(); |
950 } | 959 } |
951 | 960 |
952 bool RenderWidgetHostViewAura::HasFocus() const { | 961 bool RenderWidgetHostViewAura::HasFocus() const { |
953 return window_->HasFocus(); | 962 return window_->HasFocus(); |
954 } | 963 } |
955 | 964 |
956 bool RenderWidgetHostViewAura::IsSurfaceAvailableForCopy() const { | 965 bool RenderWidgetHostViewAura::IsSurfaceAvailableForCopy() const { |
957 return current_surface_ || current_dib_ || !!host_->GetBackingStore(false); | 966 return current_surface_ || |
| 967 current_frame_.IsValid() || |
| 968 !!host_->GetBackingStore(false); |
958 } | 969 } |
959 | 970 |
960 void RenderWidgetHostViewAura::Show() { | 971 void RenderWidgetHostViewAura::Show() { |
961 window_->Show(); | 972 window_->Show(); |
962 } | 973 } |
963 | 974 |
964 void RenderWidgetHostViewAura::Hide() { | 975 void RenderWidgetHostViewAura::Hide() { |
965 window_->Hide(); | 976 window_->Hide(); |
966 } | 977 } |
967 | 978 |
(...skipping 278 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1246 | 1257 |
1247 CopyFromCompositingSurfaceHelper(src_subrect, | 1258 CopyFromCompositingSurfaceHelper(src_subrect, |
1248 region_in_frame.size(), | 1259 region_in_frame.size(), |
1249 base::Bind(CopySnapshotToVideoFrame, | 1260 base::Bind(CopySnapshotToVideoFrame, |
1250 target, | 1261 target, |
1251 region_in_frame, | 1262 region_in_frame, |
1252 callback)); | 1263 callback)); |
1253 } | 1264 } |
1254 | 1265 |
1255 bool RenderWidgetHostViewAura::CanCopyToVideoFrame() const { | 1266 bool RenderWidgetHostViewAura::CanCopyToVideoFrame() const { |
| 1267 // TODO(skaslev): Implement this path for s/w compositing. |
1256 return current_surface_ != NULL && host_->is_accelerated_compositing_active(); | 1268 return current_surface_ != NULL && host_->is_accelerated_compositing_active(); |
1257 } | 1269 } |
1258 | 1270 |
1259 bool RenderWidgetHostViewAura::CanSubscribeFrame() const { | 1271 bool RenderWidgetHostViewAura::CanSubscribeFrame() const { |
1260 return true; | 1272 return true; |
1261 } | 1273 } |
1262 | 1274 |
1263 void RenderWidgetHostViewAura::BeginFrameSubscription( | 1275 void RenderWidgetHostViewAura::BeginFrameSubscription( |
1264 scoped_ptr<RenderWidgetHostViewFrameSubscriber> subscriber) { | 1276 scoped_ptr<RenderWidgetHostViewFrameSubscriber> subscriber) { |
1265 frame_subscriber_ = subscriber.Pass(); | 1277 frame_subscriber_ = subscriber.Pass(); |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1308 | 1320 |
1309 void RenderWidgetHostViewAura::UpdateExternalTexture() { | 1321 void RenderWidgetHostViewAura::UpdateExternalTexture() { |
1310 // Delay processing accelerated compositing state change till here where we | 1322 // Delay processing accelerated compositing state change till here where we |
1311 // act upon the state change. (Clear the external texture if switching to | 1323 // act upon the state change. (Clear the external texture if switching to |
1312 // software mode or set the external texture if going to accelerated mode). | 1324 // software mode or set the external texture if going to accelerated mode). |
1313 if (accelerated_compositing_state_changed_) | 1325 if (accelerated_compositing_state_changed_) |
1314 accelerated_compositing_state_changed_ = false; | 1326 accelerated_compositing_state_changed_ = false; |
1315 | 1327 |
1316 bool is_compositing_active = host_->is_accelerated_compositing_active(); | 1328 bool is_compositing_active = host_->is_accelerated_compositing_active(); |
1317 if (is_compositing_active && current_surface_) { | 1329 if (is_compositing_active && current_surface_) { |
1318 window_->SetExternalTexture(current_surface_.get()); | 1330 window_->layer()->SetExternalTexture(current_surface_.get()); |
1319 current_frame_size_ = ConvertSizeToDIP(this, current_surface_->size()); | 1331 current_frame_size_ = ConvertSizeToDIP(this, current_surface_->size()); |
1320 CheckResizeLock(); | 1332 CheckResizeLock(); |
1321 } else if (is_compositing_active && current_dib_) { | 1333 } else if (is_compositing_active && current_frame_.IsSharedMemory()) { |
1322 window_->SetExternalTexture(NULL); | 1334 window_->layer()->SetTextureMailbox(current_frame_, |
1323 current_frame_size_ = ConvertSizeToDIP(this, last_swapped_surface_size_); | 1335 current_frame_scale_factor_); |
| 1336 current_frame_size_ = gfx::ToFlooredSize( |
| 1337 gfx::ScaleSize(current_frame_.size(), |
| 1338 1.0f / current_frame_scale_factor_)); |
1324 CheckResizeLock(); | 1339 CheckResizeLock(); |
1325 } else { | 1340 } else { |
1326 window_->SetExternalTexture(NULL); | 1341 window_->layer()->SetExternalTexture(NULL); |
1327 resize_lock_.reset(); | 1342 resize_lock_.reset(); |
1328 host_->WasResized(); | 1343 host_->WasResized(); |
1329 } | 1344 } |
1330 } | 1345 } |
1331 | 1346 |
1332 bool RenderWidgetHostViewAura::SwapBuffersPrepare( | 1347 bool RenderWidgetHostViewAura::SwapBuffersPrepare( |
1333 const gfx::Rect& surface_rect, | 1348 const gfx::Rect& surface_rect, |
1334 const gfx::Rect& damage_rect, | 1349 const gfx::Rect& damage_rect, |
1335 const std::string& mailbox_name, | 1350 const std::string& mailbox_name, |
1336 const BufferPresentedCallback& ack_callback) { | 1351 const BufferPresentedCallback& ack_callback) { |
(...skipping 132 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1469 void RenderWidgetHostViewAura::SendDelegatedFrameAck() { | 1484 void RenderWidgetHostViewAura::SendDelegatedFrameAck() { |
1470 cc::CompositorFrameAck ack; | 1485 cc::CompositorFrameAck ack; |
1471 window_->layer()->TakeUnusedResourcesForChildCompositor(&ack.resources); | 1486 window_->layer()->TakeUnusedResourcesForChildCompositor(&ack.resources); |
1472 RenderWidgetHostImpl::SendSwapCompositorFrameAck( | 1487 RenderWidgetHostImpl::SendSwapCompositorFrameAck( |
1473 host_->GetRoutingID(), host_->GetProcess()->GetID(), ack); | 1488 host_->GetRoutingID(), host_->GetProcess()->GetID(), ack); |
1474 } | 1489 } |
1475 | 1490 |
1476 void RenderWidgetHostViewAura::SwapSoftwareFrame( | 1491 void RenderWidgetHostViewAura::SwapSoftwareFrame( |
1477 scoped_ptr<cc::SoftwareFrameData> frame_data, | 1492 scoped_ptr<cc::SoftwareFrameData> frame_data, |
1478 float frame_device_scale_factor) { | 1493 float frame_device_scale_factor) { |
| 1494 ui::Compositor* compositor = GetCompositor(); |
| 1495 if (!compositor) { |
| 1496 SendSoftwareFrameAck(frame_data->id); |
| 1497 return; |
| 1498 } |
| 1499 |
1479 const gfx::Size& frame_size = frame_data->size; | 1500 const gfx::Size& frame_size = frame_data->size; |
1480 const gfx::Rect& damage_rect = frame_data->damage_rect; | 1501 const gfx::Rect& damage_rect = frame_data->damage_rect; |
1481 const TransportDIB::Id& dib_id = frame_data->dib_id; | 1502 gfx::Size frame_size_in_dip = gfx::ToFlooredSize( |
1482 scoped_ptr<TransportDIB> dib(host_->GetProcess()->MapTransportDIB(dib_id)); | 1503 gfx::ScaleSize(frame_size, 1.0f / frame_device_scale_factor)); |
| 1504 if (ShouldSkipFrame(frame_size_in_dip)) { |
| 1505 SendSoftwareFrameAck(frame_data->id); |
| 1506 return; |
| 1507 } |
1483 | 1508 |
1484 // Validate the received DIB. | 1509 base::SharedMemoryHandle handle = frame_data->handle; |
1485 size_t expected_size = 4 * frame_size.GetArea(); | 1510 #ifdef OS_WIN |
1486 if (!dib || dib->size() < expected_size) { | 1511 BOOL success = ::DuplicateHandle( |
| 1512 host_->GetProcess()->GetHandle(), frame_data->handle, |
| 1513 ::GetCurrentProcess(), &handle, |
| 1514 0, TRUE, DUPLICATE_SAME_ACCESS); |
| 1515 if (!success) { |
1487 host_->GetProcess()->ReceivedBadMessage(); | 1516 host_->GetProcess()->ReceivedBadMessage(); |
1488 return; | 1517 return; |
1489 } | 1518 } |
| 1519 #endif |
1490 | 1520 |
1491 if (last_swapped_surface_size_ != frame_size) { | 1521 if (last_swapped_surface_size_ != frame_size) { |
1492 DLOG_IF(ERROR, damage_rect != gfx::Rect(frame_size)) | 1522 DLOG_IF(ERROR, damage_rect != gfx::Rect(frame_size)) |
1493 << "Expected full damage rect"; | 1523 << "Expected full damage rect"; |
| 1524 last_swapped_surface_size_ = frame_size; |
1494 } | 1525 } |
1495 | 1526 |
1496 TransportDIB::Id last_dib_id = current_dib_id_; | 1527 cc::TextureMailbox::ReleaseCallback callback = |
1497 current_dib_.reset(dib.release()); | 1528 base::Bind(ReleaseMailbox, MessageLoop::current(), |
1498 current_dib_id_ = dib_id; | 1529 base::Bind(&RenderWidgetHostViewAura::SendSoftwareFrameAck, |
1499 last_swapped_surface_size_ = frame_size; | 1530 AsWeakPtr(), |
| 1531 frame_data->id)); |
| 1532 current_frame_ = cc::TextureMailbox(handle, frame_size, callback); |
| 1533 current_frame_scale_factor_ = frame_device_scale_factor; |
| 1534 DCHECK(current_frame_.IsSharedMemory()); |
| 1535 current_frame_size_ = frame_size_in_dip; |
1500 | 1536 |
1501 ui::Compositor* compositor = GetCompositor(); | 1537 released_front_lock_ = NULL; |
1502 if (!compositor) { | 1538 window_->layer()->SetTextureMailbox(current_frame_, |
1503 SendSoftwareFrameAck(last_dib_id); | 1539 current_frame_scale_factor_); |
1504 return; | |
1505 } | |
1506 | |
1507 gfx::Size frame_size_in_dip = gfx::ToFlooredSize( | |
1508 gfx::ScaleSize(frame_size, 1.0f / frame_device_scale_factor)); | |
1509 if (ShouldSkipFrame(frame_size_in_dip)) { | |
1510 can_lock_compositor_ = NO_PENDING_COMMIT; | |
1511 SendSoftwareFrameAck(last_dib_id); | |
1512 } else { | |
1513 AddOnCommitCallbackAndDisableLocks( | |
1514 base::Bind(&RenderWidgetHostViewAura::SendSoftwareFrameAck, | |
1515 AsWeakPtr(), last_dib_id)); | |
1516 } | |
1517 | |
1518 current_frame_size_ = frame_size_in_dip; | |
1519 CheckResizeLock(); | 1540 CheckResizeLock(); |
1520 released_front_lock_ = NULL; | |
1521 window_->SetExternalTexture(NULL); | |
1522 window_->SchedulePaintInRect(ConvertRectToDIP(this, damage_rect)); | 1541 window_->SchedulePaintInRect(ConvertRectToDIP(this, damage_rect)); |
1523 | |
1524 if (paint_observer_) | 1542 if (paint_observer_) |
1525 paint_observer_->OnUpdateCompositorContent(); | 1543 paint_observer_->OnUpdateCompositorContent(); |
1526 } | 1544 } |
1527 | 1545 |
1528 void RenderWidgetHostViewAura::SendSoftwareFrameAck( | 1546 void RenderWidgetHostViewAura::SendSoftwareFrameAck(int id) { |
1529 const TransportDIB::Id& id) { | |
1530 cc::CompositorFrameAck ack; | 1547 cc::CompositorFrameAck ack; |
1531 ack.last_dib_id = id; | 1548 ack.last_frame_id = id; |
1532 RenderWidgetHostImpl::SendSwapCompositorFrameAck( | 1549 RenderWidgetHostImpl::SendSwapCompositorFrameAck( |
1533 host_->GetRoutingID(), host_->GetProcess()->GetID(), ack); | 1550 host_->GetRoutingID(), host_->GetProcess()->GetID(), ack); |
1534 } | 1551 } |
1535 | 1552 |
1536 void RenderWidgetHostViewAura::OnSwapCompositorFrame( | 1553 void RenderWidgetHostViewAura::OnSwapCompositorFrame( |
1537 scoped_ptr<cc::CompositorFrame> frame) { | 1554 scoped_ptr<cc::CompositorFrame> frame) { |
1538 if (frame->delegated_frame_data) { | 1555 if (frame->delegated_frame_data) { |
1539 SwapDelegatedFrame(frame->delegated_frame_data.Pass(), | 1556 SwapDelegatedFrame(frame->delegated_frame_data.Pass(), |
1540 frame->metadata.device_scale_factor); | 1557 frame->metadata.device_scale_factor); |
1541 return; | 1558 return; |
(...skipping 571 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2113 return popup_type_ == WebKit::WebPopupTypeNone; | 2130 return popup_type_ == WebKit::WebPopupTypeNone; |
2114 } | 2131 } |
2115 | 2132 |
2116 void RenderWidgetHostViewAura::OnCaptureLost() { | 2133 void RenderWidgetHostViewAura::OnCaptureLost() { |
2117 host_->LostCapture(); | 2134 host_->LostCapture(); |
2118 if (touch_editing_client_) | 2135 if (touch_editing_client_) |
2119 touch_editing_client_->EndTouchEditing(); | 2136 touch_editing_client_->EndTouchEditing(); |
2120 } | 2137 } |
2121 | 2138 |
2122 void RenderWidgetHostViewAura::OnPaint(gfx::Canvas* canvas) { | 2139 void RenderWidgetHostViewAura::OnPaint(gfx::Canvas* canvas) { |
2123 bool is_compositing_active = host_->is_accelerated_compositing_active(); | |
2124 bool has_backing_store = !!host_->GetBackingStore(false); | 2140 bool has_backing_store = !!host_->GetBackingStore(false); |
2125 if (is_compositing_active && current_dib_) { | 2141 if (has_backing_store) { |
2126 const gfx::Size window_size = window_->bounds().size(); | |
2127 const gfx::Size& frame_size = last_swapped_surface_size_; | |
2128 | |
2129 SkBitmap bitmap; | |
2130 bitmap.setConfig(SkBitmap::kARGB_8888_Config, | |
2131 frame_size.width(), | |
2132 frame_size.height()); | |
2133 bitmap.setPixels(current_dib_->memory()); | |
2134 | |
2135 SkCanvas* sk_canvas = canvas->sk_canvas(); | |
2136 sk_canvas->drawBitmap(bitmap, 0, 0); | |
2137 | |
2138 if (frame_size != window_size) { | |
2139 SkRegion region; | |
2140 region.op(0, 0, window_size.width(), window_size.height(), | |
2141 SkRegion::kUnion_Op); | |
2142 region.op(0, 0, frame_size.width(), frame_size.height(), | |
2143 SkRegion::kDifference_Op); | |
2144 SkPaint paint; | |
2145 paint.setColor(SK_ColorWHITE); | |
2146 for (SkRegion::Iterator it(region); !it.done(); it.next()) | |
2147 sk_canvas->drawIRect(it.rect(), paint); | |
2148 } | |
2149 | |
2150 if (paint_observer_) | |
2151 paint_observer_->OnPaintComplete(); | |
2152 } else if (!is_compositing_active && has_backing_store) { | |
2153 paint_canvas_ = canvas; | 2142 paint_canvas_ = canvas; |
2154 BackingStoreAura* backing_store = static_cast<BackingStoreAura*>( | 2143 BackingStoreAura* backing_store = static_cast<BackingStoreAura*>( |
2155 host_->GetBackingStore(true)); | 2144 host_->GetBackingStore(true)); |
2156 paint_canvas_ = NULL; | 2145 paint_canvas_ = NULL; |
2157 backing_store->SkiaShowRect(gfx::Point(), canvas); | 2146 backing_store->SkiaShowRect(gfx::Point(), canvas); |
2158 | 2147 |
2159 if (paint_observer_) | 2148 if (paint_observer_) |
2160 paint_observer_->OnPaintComplete(); | 2149 paint_observer_->OnPaintComplete(); |
2161 } else if (aura::Env::GetInstance()->render_white_bg()) { | 2150 } else if (aura::Env::GetInstance()->render_white_bg()) { |
2162 canvas->DrawColor(SK_ColorWHITE); | 2151 canvas->DrawColor(SK_ColorWHITE); |
(...skipping 793 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2956 RenderWidgetHost* widget) { | 2945 RenderWidgetHost* widget) { |
2957 return new RenderWidgetHostViewAura(widget); | 2946 return new RenderWidgetHostViewAura(widget); |
2958 } | 2947 } |
2959 | 2948 |
2960 // static | 2949 // static |
2961 void RenderWidgetHostViewPort::GetDefaultScreenInfo(WebScreenInfo* results) { | 2950 void RenderWidgetHostViewPort::GetDefaultScreenInfo(WebScreenInfo* results) { |
2962 GetScreenInfoForWindow(results, NULL); | 2951 GetScreenInfoForWindow(results, NULL); |
2963 } | 2952 } |
2964 | 2953 |
2965 } // namespace content | 2954 } // namespace content |
OLD | NEW |