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/compositor_impl_android.h" | 5 #include "content/browser/renderer_host/compositor_impl_android.h" |
| 6 | 6 |
| 7 #include <android/bitmap.h> | 7 #include <android/bitmap.h> |
| 8 #include <android/native_window_jni.h> | 8 #include <android/native_window_jni.h> |
| 9 | 9 |
| 10 #include "base/android/jni_android.h" | 10 #include "base/android/jni_android.h" |
| (...skipping 176 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 187 | 187 |
| 188 CompositorImpl::CompositorImpl(CompositorClient* client, | 188 CompositorImpl::CompositorImpl(CompositorClient* client, |
| 189 gfx::NativeWindow root_window) | 189 gfx::NativeWindow root_window) |
| 190 : root_layer_(cc::Layer::Create()), | 190 : root_layer_(cc::Layer::Create()), |
| 191 has_transparent_background_(false), | 191 has_transparent_background_(false), |
| 192 device_scale_factor_(1), | 192 device_scale_factor_(1), |
| 193 window_(NULL), | 193 window_(NULL), |
| 194 surface_id_(0), | 194 surface_id_(0), |
| 195 client_(client), | 195 client_(client), |
| 196 root_window_(root_window), | 196 root_window_(root_window), |
| 197 did_post_swapbuffers_(false), | 197 pending_swapbuffers_(0), |
| 198 ignore_schedule_composite_(false), | |
| 199 needs_composite_(false), | |
| 200 needs_animate_(false), | |
| 201 will_composite_immediately_(false), | |
| 202 composite_on_vsync_trigger_(DO_NOT_COMPOSITE), | |
| 203 pending_swapbuffers_(0U), | |
| 204 weak_factory_(this) { | 198 weak_factory_(this) { |
| 205 DCHECK(client); | 199 DCHECK(client); |
| 206 DCHECK(root_window); | 200 DCHECK(root_window); |
| 207 ImageTransportFactoryAndroid::AddObserver(this); | 201 ImageTransportFactoryAndroid::AddObserver(this); |
| 208 root_window->AttachCompositor(this); | 202 root_window->AttachCompositor(this); |
| 209 } | 203 } |
| 210 | 204 |
| 211 CompositorImpl::~CompositorImpl() { | 205 CompositorImpl::~CompositorImpl() { |
| 212 root_window_->DetachCompositor(); | 206 root_window_->DetachCompositor(); |
| 213 ImageTransportFactoryAndroid::RemoveObserver(this); | 207 ImageTransportFactoryAndroid::RemoveObserver(this); |
| 214 // Clean-up any surface references. | 208 // Clean-up any surface references. |
| 215 SetSurface(NULL); | 209 SetSurface(NULL); |
| 216 } | 210 } |
| 217 | 211 |
| 218 void CompositorImpl::PostComposite(CompositingTrigger trigger) { | |
| 219 DCHECK(needs_composite_); | |
| 220 DCHECK(trigger == COMPOSITE_IMMEDIATELY || trigger == COMPOSITE_EVENTUALLY); | |
| 221 | |
| 222 if (will_composite_immediately_ || | |
| 223 (trigger == COMPOSITE_EVENTUALLY && WillComposite())) { | |
| 224 // We will already composite soon enough. | |
| 225 DCHECK(WillComposite()); | |
| 226 return; | |
| 227 } | |
| 228 | |
| 229 if (DidCompositeThisFrame()) { | |
| 230 DCHECK(!WillCompositeThisFrame()); | |
| 231 if (composite_on_vsync_trigger_ != COMPOSITE_IMMEDIATELY) { | |
| 232 composite_on_vsync_trigger_ = trigger; | |
| 233 root_window_->RequestVSyncUpdate(); | |
| 234 } | |
| 235 DCHECK(WillComposite()); | |
| 236 return; | |
| 237 } | |
| 238 | |
| 239 base::TimeDelta delay; | |
| 240 if (trigger == COMPOSITE_IMMEDIATELY) { | |
| 241 will_composite_immediately_ = true; | |
| 242 composite_on_vsync_trigger_ = DO_NOT_COMPOSITE; | |
| 243 } else { | |
| 244 DCHECK(!WillComposite()); | |
| 245 const base::TimeDelta estimated_composite_time = vsync_period_ / 4; | |
| 246 const base::TimeTicks now = base::TimeTicks::Now(); | |
| 247 | |
| 248 if (!last_vsync_.is_null() && (now - last_vsync_) < vsync_period_) { | |
| 249 base::TimeTicks next_composite = | |
| 250 last_vsync_ + vsync_period_ - estimated_composite_time; | |
| 251 if (next_composite < now) { | |
| 252 // It's too late, we will reschedule composite as needed on the next | |
| 253 // vsync. | |
| 254 composite_on_vsync_trigger_ = COMPOSITE_EVENTUALLY; | |
| 255 root_window_->RequestVSyncUpdate(); | |
| 256 DCHECK(WillComposite()); | |
| 257 return; | |
| 258 } | |
| 259 | |
| 260 delay = next_composite - now; | |
| 261 } | |
| 262 } | |
| 263 TRACE_EVENT2("cc", "CompositorImpl::PostComposite", | |
| 264 "trigger", trigger, | |
| 265 "delay", delay.InMillisecondsF()); | |
| 266 | |
| 267 DCHECK(composite_on_vsync_trigger_ == DO_NOT_COMPOSITE); | |
| 268 if (current_composite_task_) | |
| 269 current_composite_task_->Cancel(); | |
| 270 | |
| 271 // Unretained because we cancel the task on shutdown. | |
| 272 current_composite_task_.reset(new base::CancelableClosure( | |
| 273 base::Bind(&CompositorImpl::Composite, base::Unretained(this), trigger))); | |
| 274 base::MessageLoop::current()->PostDelayedTask( | |
| 275 FROM_HERE, current_composite_task_->callback(), delay); | |
| 276 } | |
| 277 | |
| 278 void CompositorImpl::Composite(CompositingTrigger trigger) { | |
| 279 BrowserGpuChannelHostFactory* factory = | |
| 280 BrowserGpuChannelHostFactory::instance(); | |
| 281 if (!factory->GetGpuChannel() || factory->GetGpuChannel()->IsLost()) { | |
| 282 CauseForGpuLaunch cause = | |
| 283 CAUSE_FOR_GPU_LAUNCH_WEBGRAPHICSCONTEXT3DCOMMANDBUFFERIMPL_INITIALIZE; | |
| 284 factory->EstablishGpuChannel( | |
| 285 cause, | |
| 286 base::Bind(&CompositorImpl::OnGpuChannelEstablished, | |
| 287 weak_factory_.GetWeakPtr())); | |
| 288 return; | |
| 289 } | |
| 290 | |
| 291 DCHECK(host_); | |
| 292 DCHECK(trigger == COMPOSITE_IMMEDIATELY || trigger == COMPOSITE_EVENTUALLY); | |
| 293 DCHECK(needs_composite_); | |
| 294 DCHECK(!DidCompositeThisFrame()); | |
| 295 | |
| 296 if (trigger == COMPOSITE_IMMEDIATELY) | |
| 297 will_composite_immediately_ = false; | |
| 298 | |
| 299 DCHECK_LE(pending_swapbuffers_, kMaxSwapBuffers); | |
| 300 if (pending_swapbuffers_ == kMaxSwapBuffers) { | |
| 301 TRACE_EVENT0("compositor", "CompositorImpl_SwapLimit"); | |
| 302 return; | |
| 303 } | |
| 304 | |
| 305 // Reset state before Layout+Composite since that might create more | |
| 306 // requests to Composite that we need to respect. | |
| 307 needs_composite_ = false; | |
| 308 | |
| 309 // Only allow compositing once per vsync. | |
| 310 current_composite_task_->Cancel(); | |
| 311 DCHECK(DidCompositeThisFrame() && !WillComposite()); | |
| 312 | |
| 313 // Ignore ScheduleComposite() from layer tree changes during layout and | |
| 314 // animation updates that will already be reflected in the current frame | |
| 315 // we are about to draw. | |
| 316 ignore_schedule_composite_ = true; | |
| 317 | |
| 318 const base::TimeTicks frame_time = gfx::FrameTime::Now(); | |
| 319 if (needs_animate_) { | |
| 320 needs_animate_ = false; | |
| 321 root_window_->Animate(frame_time); | |
| 322 } | |
| 323 ignore_schedule_composite_ = false; | |
| 324 | |
| 325 did_post_swapbuffers_ = false; | |
| 326 host_->Composite(frame_time); | |
| 327 if (did_post_swapbuffers_) | |
| 328 pending_swapbuffers_++; | |
| 329 | |
| 330 // Need to track vsync to avoid compositing more than once per frame. | |
| 331 root_window_->RequestVSyncUpdate(); | |
| 332 } | |
| 333 | |
| 334 void CompositorImpl::OnGpuChannelEstablished() { | 212 void CompositorImpl::OnGpuChannelEstablished() { |
| 335 ScheduleComposite(); | 213 if (host_) |
| 214 host_->SetNeedsCommit(); | |
|
brianderson
2014/06/24 23:50:12
Should this be SetNeedsRedraw? If this is meant to
danakj
2014/06/25 17:28:54
This should probably just go away?
| |
| 336 } | 215 } |
| 337 | 216 |
| 338 UIResourceProvider& CompositorImpl::GetUIResourceProvider() { | 217 UIResourceProvider& CompositorImpl::GetUIResourceProvider() { |
| 339 return ui_resource_provider_; | 218 return ui_resource_provider_; |
| 340 } | 219 } |
| 341 | 220 |
| 342 void CompositorImpl::SetRootLayer(scoped_refptr<cc::Layer> root_layer) { | 221 void CompositorImpl::SetRootLayer(scoped_refptr<cc::Layer> root_layer) { |
| 343 root_layer_->RemoveAllChildren(); | 222 root_layer_->RemoveAllChildren(); |
| 344 if (root_layer) | 223 if (root_layer) |
| 345 root_layer_->AddChild(root_layer); | 224 root_layer_->AddChild(root_layer); |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 387 } | 266 } |
| 388 if (window) { | 267 if (window) { |
| 389 SetWindowSurface(window); | 268 SetWindowSurface(window); |
| 390 ANativeWindow_release(window); | 269 ANativeWindow_release(window); |
| 391 content::RegisterViewSurface(surface_id_, j_surface.obj()); | 270 content::RegisterViewSurface(surface_id_, j_surface.obj()); |
| 392 } | 271 } |
| 393 } | 272 } |
| 394 | 273 |
| 395 void CompositorImpl::SetVisible(bool visible) { | 274 void CompositorImpl::SetVisible(bool visible) { |
| 396 if (!visible) { | 275 if (!visible) { |
| 397 if (WillComposite()) | |
| 398 CancelComposite(); | |
| 399 ui_resource_provider_.SetLayerTreeHost(NULL); | 276 ui_resource_provider_.SetLayerTreeHost(NULL); |
| 400 host_.reset(); | 277 host_.reset(); |
| 401 } else if (!host_) { | 278 } else if (!host_) { |
| 402 DCHECK(!WillComposite()); | |
| 403 needs_composite_ = false; | |
| 404 needs_animate_ = false; | |
| 405 pending_swapbuffers_ = 0; | 279 pending_swapbuffers_ = 0; |
| 406 cc::LayerTreeSettings settings; | 280 cc::LayerTreeSettings settings; |
| 407 settings.refresh_rate = 60.0; | 281 settings.refresh_rate = 60.0; |
| 408 settings.impl_side_painting = false; | 282 settings.impl_side_painting = false; |
| 409 settings.allow_antialiasing = false; | 283 settings.allow_antialiasing = false; |
| 410 settings.calculate_top_controls_position = false; | 284 settings.calculate_top_controls_position = false; |
| 411 settings.top_controls_height = 0.f; | 285 settings.top_controls_height = 0.f; |
| 412 settings.highp_threshold_min = 2048; | 286 settings.highp_threshold_min = 2048; |
|
no sievers
2014/06/19 17:49:21
If we set...
settings.throttle_frame_production =
brianderson
2014/06/24 23:50:12
+1. I think DirectOutputSurface is now known as Ou
| |
| 413 | 287 |
| 414 CommandLine* command_line = CommandLine::ForCurrentProcess(); | 288 CommandLine* command_line = CommandLine::ForCurrentProcess(); |
| 415 settings.initial_debug_state.SetRecordRenderingStats( | 289 settings.initial_debug_state.SetRecordRenderingStats( |
| 416 command_line->HasSwitch(cc::switches::kEnableGpuBenchmarking)); | 290 command_line->HasSwitch(cc::switches::kEnableGpuBenchmarking)); |
| 417 settings.initial_debug_state.show_fps_counter = | 291 settings.initial_debug_state.show_fps_counter = |
| 418 command_line->HasSwitch(cc::switches::kUIShowFPSCounter); | 292 command_line->HasSwitch(cc::switches::kUIShowFPSCounter); |
| 419 // TODO(enne): Update this this compositor to use the scheduler. | |
| 420 settings.single_thread_proxy_scheduler = false; | |
| 421 | 293 |
| 422 host_ = cc::LayerTreeHost::CreateSingleThreaded( | 294 host_ = cc::LayerTreeHost::CreateSingleThreaded( |
| 423 this, this, HostSharedBitmapManager::current(), settings); | 295 this, this, HostSharedBitmapManager::current(), settings); |
| 424 host_->SetRootLayer(root_layer_); | 296 host_->SetRootLayer(root_layer_); |
| 425 | 297 |
| 426 host_->SetVisible(true); | 298 host_->SetVisible(true); |
| 427 host_->SetLayerTreeHostClientReady(); | 299 host_->SetLayerTreeHostClientReady(); |
| 428 host_->SetViewportSize(size_); | 300 host_->SetViewportSize(size_); |
| 429 host_->set_has_transparent_background(has_transparent_background_); | 301 host_->set_has_transparent_background(has_transparent_background_); |
| 430 host_->SetDeviceScaleFactor(device_scale_factor_); | 302 host_->SetDeviceScaleFactor(device_scale_factor_); |
| 431 ui_resource_provider_.SetLayerTreeHost(host_.get()); | 303 ui_resource_provider_.SetLayerTreeHost(host_.get()); |
| 304 | |
| 305 BrowserGpuChannelHostFactory* factory = | |
| 306 BrowserGpuChannelHostFactory::instance(); | |
| 307 if (!factory->GetGpuChannel() || factory->GetGpuChannel()->IsLost()) { | |
| 308 CauseForGpuLaunch cause = | |
| 309 CAUSE_FOR_GPU_LAUNCH_WEBGRAPHICSCONTEXT3DCOMMANDBUFFERIMPL_INITIALIZE; | |
| 310 factory->EstablishGpuChannel( | |
| 311 cause, | |
| 312 base::Bind(&CompositorImpl::OnGpuChannelEstablished, | |
| 313 weak_factory_.GetWeakPtr())); | |
|
no sievers
2014/06/19 17:13:26
We then need to defer the host_->SetLayerTreeHostC
| |
| 314 } | |
| 432 } | 315 } |
| 433 } | 316 } |
| 434 | 317 |
| 435 void CompositorImpl::setDeviceScaleFactor(float factor) { | 318 void CompositorImpl::setDeviceScaleFactor(float factor) { |
| 436 device_scale_factor_ = factor; | 319 device_scale_factor_ = factor; |
| 437 if (host_) | 320 if (host_) |
| 438 host_->SetDeviceScaleFactor(factor); | 321 host_->SetDeviceScaleFactor(factor); |
| 439 } | 322 } |
| 440 | 323 |
| 441 void CompositorImpl::SetWindowBounds(const gfx::Size& size) { | 324 void CompositorImpl::SetWindowBounds(const gfx::Size& size) { |
| 442 if (size_ == size) | 325 if (size_ == size) |
| 443 return; | 326 return; |
| 444 | 327 |
| 445 size_ = size; | 328 size_ = size; |
| 446 if (host_) | 329 if (host_) |
| 447 host_->SetViewportSize(size); | 330 host_->SetViewportSize(size); |
| 448 root_layer_->SetBounds(size); | 331 root_layer_->SetBounds(size); |
| 449 } | 332 } |
| 450 | 333 |
| 451 void CompositorImpl::SetHasTransparentBackground(bool flag) { | 334 void CompositorImpl::SetHasTransparentBackground(bool flag) { |
| 452 has_transparent_background_ = flag; | 335 has_transparent_background_ = flag; |
| 453 if (host_) | 336 if (host_) |
| 454 host_->set_has_transparent_background(flag); | 337 host_->set_has_transparent_background(flag); |
| 455 } | 338 } |
| 456 | 339 |
| 457 void CompositorImpl::SetNeedsComposite() { | 340 void CompositorImpl::SetNeedsComposite() { |
| 458 if (!host_.get()) | 341 if (!host_.get()) |
| 459 return; | 342 return; |
| 460 DCHECK(!needs_composite_ || WillComposite()); | 343 host_->SetNeedsCommit(); |
| 461 | |
| 462 needs_composite_ = true; | |
| 463 PostComposite(COMPOSITE_IMMEDIATELY); | |
| 464 } | 344 } |
| 465 | 345 |
| 466 static scoped_ptr<WebGraphicsContext3DCommandBufferImpl> | 346 static scoped_ptr<WebGraphicsContext3DCommandBufferImpl> |
| 467 CreateGpuProcessViewContext( | 347 CreateGpuProcessViewContext( |
| 468 const scoped_refptr<GpuChannelHost>& gpu_channel_host, | 348 const scoped_refptr<GpuChannelHost>& gpu_channel_host, |
| 469 const blink::WebGraphicsContext3D::Attributes attributes, | 349 const blink::WebGraphicsContext3D::Attributes attributes, |
| 470 int surface_id) { | 350 int surface_id) { |
| 471 DCHECK(gpu_channel_host); | 351 DCHECK(gpu_channel_host); |
| 472 | 352 |
| 473 GURL url("chrome://gpu/Compositor::createContext3D"); | 353 GURL url("chrome://gpu/Compositor::createContext3D"); |
| (...skipping 15 matching lines...) Expand all Loading... | |
| 489 new WebGraphicsContext3DCommandBufferImpl(surface_id, | 369 new WebGraphicsContext3DCommandBufferImpl(surface_id, |
| 490 url, | 370 url, |
| 491 gpu_channel_host.get(), | 371 gpu_channel_host.get(), |
| 492 attributes, | 372 attributes, |
| 493 lose_context_when_out_of_memory, | 373 lose_context_when_out_of_memory, |
| 494 limits, | 374 limits, |
| 495 NULL)); | 375 NULL)); |
| 496 } | 376 } |
| 497 | 377 |
| 498 void CompositorImpl::Layout() { | 378 void CompositorImpl::Layout() { |
| 499 ignore_schedule_composite_ = true; | 379 host_->SetDeferCommits(true); |
| 500 client_->Layout(); | 380 client_->Layout(); |
| 501 ignore_schedule_composite_ = false; | 381 host_->SetDeferCommits(false); |
| 502 } | 382 } |
| 503 | 383 |
| 504 scoped_ptr<cc::OutputSurface> CompositorImpl::CreateOutputSurface( | 384 scoped_ptr<cc::OutputSurface> CompositorImpl::CreateOutputSurface( |
| 505 bool fallback) { | 385 bool fallback) { |
| 506 blink::WebGraphicsContext3D::Attributes attrs; | 386 blink::WebGraphicsContext3D::Attributes attrs; |
| 507 attrs.shareResources = true; | 387 attrs.shareResources = true; |
| 508 attrs.noAutomaticFlushes = true; | 388 attrs.noAutomaticFlushes = true; |
| 509 pending_swapbuffers_ = 0; | 389 pending_swapbuffers_ = 0; |
| 510 | 390 |
| 511 DCHECK(window_); | 391 DCHECK(window_); |
| (...skipping 15 matching lines...) Expand all Loading... | |
| 527 | 407 |
| 528 return scoped_ptr<cc::OutputSurface>( | 408 return scoped_ptr<cc::OutputSurface>( |
| 529 new OutputSurfaceWithoutParent(context_provider)); | 409 new OutputSurfaceWithoutParent(context_provider)); |
| 530 } | 410 } |
| 531 | 411 |
| 532 void CompositorImpl::OnLostResources() { | 412 void CompositorImpl::OnLostResources() { |
| 533 client_->DidLoseResources(); | 413 client_->DidLoseResources(); |
| 534 ui_resource_provider_.UIResourcesAreInvalid(); | 414 ui_resource_provider_.UIResourcesAreInvalid(); |
| 535 } | 415 } |
| 536 | 416 |
| 537 void CompositorImpl::ScheduleComposite() { | |
| 538 DCHECK(!needs_composite_ || WillComposite()); | |
| 539 if (ignore_schedule_composite_) | |
| 540 return; | |
| 541 | |
| 542 needs_composite_ = true; | |
| 543 // We currently expect layer tree invalidations at most once per frame | |
| 544 // during normal operation and therefore try to composite immediately | |
| 545 // to minimize latency. | |
| 546 PostComposite(COMPOSITE_IMMEDIATELY); | |
| 547 } | |
| 548 | |
| 549 void CompositorImpl::ScheduleAnimation() { | |
| 550 DCHECK(!needs_animate_ || needs_composite_); | |
| 551 DCHECK(!needs_composite_ || WillComposite()); | |
| 552 needs_animate_ = true; | |
| 553 | |
| 554 if (needs_composite_) | |
| 555 return; | |
| 556 | |
| 557 TRACE_EVENT0("cc", "CompositorImpl::ScheduleAnimation"); | |
| 558 needs_composite_ = true; | |
| 559 PostComposite(COMPOSITE_EVENTUALLY); | |
| 560 } | |
| 561 | |
| 562 void CompositorImpl::DidPostSwapBuffers() { | 417 void CompositorImpl::DidPostSwapBuffers() { |
| 563 TRACE_EVENT0("compositor", "CompositorImpl::DidPostSwapBuffers"); | 418 TRACE_EVENT0("compositor", "CompositorImpl::DidPostSwapBuffers"); |
| 564 did_post_swapbuffers_ = true; | 419 pending_swapbuffers_++; |
| 565 } | 420 } |
| 566 | 421 |
| 567 void CompositorImpl::DidCompleteSwapBuffers() { | 422 void CompositorImpl::DidCompleteSwapBuffers() { |
| 568 TRACE_EVENT0("compositor", "CompositorImpl::DidCompleteSwapBuffers"); | 423 TRACE_EVENT0("compositor", "CompositorImpl::DidCompleteSwapBuffers"); |
| 569 DCHECK_GT(pending_swapbuffers_, 0U); | 424 DCHECK_GT(pending_swapbuffers_, 0U); |
| 570 if (pending_swapbuffers_-- == kMaxSwapBuffers && needs_composite_) | 425 pending_swapbuffers_--; |
| 571 PostComposite(COMPOSITE_IMMEDIATELY); | |
| 572 client_->OnSwapBuffersCompleted(pending_swapbuffers_); | 426 client_->OnSwapBuffersCompleted(pending_swapbuffers_); |
|
brianderson
2014/06/24 23:50:12
Can we get rid of pending_swapbuffers_? Implementa
no sievers
2014/06/25 00:03:26
There is one call site in Chrome for Android, wher
| |
| 427 | |
| 428 // TODO(enne): where does this go? | |
| 429 root_window_->RequestVSyncUpdate(); | |
|
enne (OOO)
2014/06/19 01:09:27
This maybe could be in a better place.
no sievers
2014/06/19 17:49:21
...then line 429 can go away here...
| |
| 573 } | 430 } |
| 574 | 431 |
| 575 void CompositorImpl::DidAbortSwapBuffers() { | 432 void CompositorImpl::DidAbortSwapBuffers() { |
| 576 TRACE_EVENT0("compositor", "CompositorImpl::DidAbortSwapBuffers"); | 433 TRACE_EVENT0("compositor", "CompositorImpl::DidAbortSwapBuffers"); |
| 577 // This really gets called only once from | 434 // This really gets called only once from |
| 578 // SingleThreadProxy::DidLoseOutputSurfaceOnImplThread() when the | 435 // SingleThreadProxy::DidLoseOutputSurfaceOnImplThread() when the |
| 579 // context was lost. | 436 // context was lost. |
| 580 ScheduleComposite(); | |
| 581 client_->OnSwapBuffersCompleted(0); | 437 client_->OnSwapBuffersCompleted(0); |
| 582 } | 438 } |
| 583 | 439 |
| 584 void CompositorImpl::DidCommit() { | 440 void CompositorImpl::DidCommit() { |
| 585 root_window_->OnCompositingDidCommit(); | 441 root_window_->OnCompositingDidCommit(); |
| 586 } | 442 } |
| 587 | 443 |
| 588 void CompositorImpl::AttachLayerForReadback(scoped_refptr<cc::Layer> layer) { | 444 void CompositorImpl::AttachLayerForReadback(scoped_refptr<cc::Layer> layer) { |
| 589 root_layer_->AddChild(layer); | 445 root_layer_->AddChild(layer); |
| 590 } | 446 } |
| 591 | 447 |
| 592 void CompositorImpl::RequestCopyOfOutputOnRootLayer( | 448 void CompositorImpl::RequestCopyOfOutputOnRootLayer( |
| 593 scoped_ptr<cc::CopyOutputRequest> request) { | 449 scoped_ptr<cc::CopyOutputRequest> request) { |
| 594 root_layer_->RequestCopyOfOutput(request.Pass()); | 450 root_layer_->RequestCopyOfOutput(request.Pass()); |
| 595 } | 451 } |
| 596 | 452 |
| 597 void CompositorImpl::OnVSync(base::TimeTicks frame_time, | 453 void CompositorImpl::OnVSync(base::TimeTicks frame_time, |
| 598 base::TimeDelta vsync_period) { | 454 base::TimeDelta vsync_period) { |
| 599 vsync_period_ = vsync_period; | 455 // TODO(enne): Does this need to get piped to output surface somehow? |
|
enne (OOO)
2014/06/19 01:09:27
brianderson: I'm a little unclear about vsync para
no sievers
2014/06/19 17:49:21
...and it would take care of the vsync scheduling.
brianderson
2014/06/24 23:50:12
Yes, that makes sense and is how the scheduler exp
| |
| 600 last_vsync_ = frame_time; | |
| 601 | |
| 602 if (WillCompositeThisFrame()) { | |
| 603 // We somehow missed the last vsync interval, so reschedule for deadline. | |
| 604 // We cannot schedule immediately, or will get us out-of-phase with new | |
| 605 // renderer frames. | |
| 606 CancelComposite(); | |
| 607 composite_on_vsync_trigger_ = COMPOSITE_EVENTUALLY; | |
| 608 } else { | |
| 609 current_composite_task_.reset(); | |
| 610 } | |
| 611 | |
| 612 DCHECK(!DidCompositeThisFrame() && !WillCompositeThisFrame()); | |
| 613 if (composite_on_vsync_trigger_ != DO_NOT_COMPOSITE) { | |
| 614 CompositingTrigger trigger = composite_on_vsync_trigger_; | |
| 615 composite_on_vsync_trigger_ = DO_NOT_COMPOSITE; | |
| 616 PostComposite(trigger); | |
| 617 } | |
| 618 } | 456 } |
| 619 | 457 |
| 620 void CompositorImpl::SetNeedsAnimate() { | 458 void CompositorImpl::SetNeedsAnimate() { |
| 621 if (!host_) | 459 if (!host_) |
| 622 return; | 460 return; |
| 623 | 461 |
| 624 host_->SetNeedsAnimate(); | 462 host_->SetNeedsAnimate(); |
| 625 } | 463 } |
| 626 | 464 |
| 627 } // namespace content | 465 } // namespace content |
| OLD | NEW |