OLD | NEW |
| (Empty) |
1 // Copyright 2011 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 "cc/trees/layer_tree_host.h" | |
6 | |
7 #include <stddef.h> | |
8 #include <stdint.h> | |
9 | |
10 #include <algorithm> | |
11 #include <memory> | |
12 #include <stack> | |
13 #include <string> | |
14 #include <unordered_map> | |
15 | |
16 #include "base/atomic_sequence_num.h" | |
17 #include "base/bind.h" | |
18 #include "base/command_line.h" | |
19 #include "base/location.h" | |
20 #include "base/memory/ptr_util.h" | |
21 #include "base/metrics/histogram_macros.h" | |
22 #include "base/numerics/safe_math.h" | |
23 #include "base/single_thread_task_runner.h" | |
24 #include "base/stl_util.h" | |
25 #include "base/strings/string_number_conversions.h" | |
26 #include "base/threading/thread_task_runner_handle.h" | |
27 #include "base/trace_event/trace_event.h" | |
28 #include "base/trace_event/trace_event_argument.h" | |
29 #include "cc/animation/animation_events.h" | |
30 #include "cc/animation/animation_host.h" | |
31 #include "cc/base/math_util.h" | |
32 #include "cc/blimp/client_picture_cache.h" | |
33 #include "cc/blimp/engine_picture_cache.h" | |
34 #include "cc/blimp/image_serialization_processor.h" | |
35 #include "cc/blimp/picture_data.h" | |
36 #include "cc/blimp/picture_data_conversions.h" | |
37 #include "cc/debug/devtools_instrumentation.h" | |
38 #include "cc/debug/frame_viewer_instrumentation.h" | |
39 #include "cc/debug/rendering_stats_instrumentation.h" | |
40 #include "cc/input/layer_selection_bound.h" | |
41 #include "cc/input/page_scale_animation.h" | |
42 #include "cc/layers/heads_up_display_layer.h" | |
43 #include "cc/layers/heads_up_display_layer_impl.h" | |
44 #include "cc/layers/layer.h" | |
45 #include "cc/layers/layer_iterator.h" | |
46 #include "cc/layers/layer_proto_converter.h" | |
47 #include "cc/layers/painted_scrollbar_layer.h" | |
48 #include "cc/proto/gfx_conversions.h" | |
49 #include "cc/proto/layer_tree.pb.h" | |
50 #include "cc/proto/layer_tree_host.pb.h" | |
51 #include "cc/resources/ui_resource_manager.h" | |
52 #include "cc/scheduler/begin_frame_source.h" | |
53 #include "cc/trees/draw_property_utils.h" | |
54 #include "cc/trees/layer_tree_host_client.h" | |
55 #include "cc/trees/layer_tree_host_common.h" | |
56 #include "cc/trees/layer_tree_host_impl.h" | |
57 #include "cc/trees/layer_tree_impl.h" | |
58 #include "cc/trees/property_tree_builder.h" | |
59 #include "cc/trees/proxy_main.h" | |
60 #include "cc/trees/remote_channel_impl.h" | |
61 #include "cc/trees/single_thread_proxy.h" | |
62 #include "cc/trees/swap_promise_manager.h" | |
63 #include "cc/trees/tree_synchronizer.h" | |
64 #include "ui/gfx/geometry/size_conversions.h" | |
65 #include "ui/gfx/geometry/vector2d_conversions.h" | |
66 | |
67 namespace { | |
68 static base::StaticAtomicSequenceNumber s_layer_tree_host_sequence_number; | |
69 } | |
70 | |
71 namespace cc { | |
72 namespace { | |
73 | |
74 std::unique_ptr<base::trace_event::TracedValue> | |
75 ComputeLayerTreeHostProtoSizeSplitAsValue(proto::LayerTreeHost* proto) { | |
76 std::unique_ptr<base::trace_event::TracedValue> value( | |
77 new base::trace_event::TracedValue()); | |
78 base::CheckedNumeric<int> base_layer_properties_size = 0; | |
79 base::CheckedNumeric<int> picture_layer_properties_size = 0; | |
80 base::CheckedNumeric<int> display_item_list_size = 0; | |
81 base::CheckedNumeric<int> drawing_display_items_size = 0; | |
82 | |
83 const proto::LayerUpdate& layer_update_proto = proto->layer_updates(); | |
84 for (int i = 0; i < layer_update_proto.layers_size(); ++i) { | |
85 const proto::LayerProperties layer_properties_proto = | |
86 layer_update_proto.layers(i); | |
87 base_layer_properties_size += layer_properties_proto.base().ByteSize(); | |
88 | |
89 if (layer_properties_proto.has_picture()) { | |
90 const proto::PictureLayerProperties& picture_proto = | |
91 layer_properties_proto.picture(); | |
92 picture_layer_properties_size += picture_proto.ByteSize(); | |
93 | |
94 const proto::DisplayItemList& display_list_proto = | |
95 picture_proto.display_list(); | |
96 display_item_list_size += display_list_proto.ByteSize(); | |
97 | |
98 for (int j = 0; j < display_list_proto.items_size(); ++j) { | |
99 const proto::DisplayItem& display_item = display_list_proto.items(j); | |
100 if (display_item.type() == proto::DisplayItem::Type_Drawing) | |
101 drawing_display_items_size += display_item.ByteSize(); | |
102 } | |
103 } | |
104 } | |
105 | |
106 value->SetInteger("TotalLayerTreeHostProtoSize", proto->ByteSize()); | |
107 value->SetInteger("LayerTreeHierarchySize", | |
108 proto->layer_tree().root_layer().ByteSize()); | |
109 value->SetInteger("LayerUpdatesSize", proto->layer_updates().ByteSize()); | |
110 value->SetInteger("PropertyTreesSize", | |
111 proto->layer_tree().property_trees().ByteSize()); | |
112 | |
113 // LayerUpdate size breakdown. | |
114 value->SetInteger("TotalBasePropertiesSize", | |
115 base_layer_properties_size.ValueOrDefault(-1)); | |
116 value->SetInteger("PictureLayerPropertiesSize", | |
117 picture_layer_properties_size.ValueOrDefault(-1)); | |
118 value->SetInteger("DisplayItemListSize", | |
119 display_item_list_size.ValueOrDefault(-1)); | |
120 value->SetInteger("DrawingDisplayItemsSize", | |
121 drawing_display_items_size.ValueOrDefault(-1)); | |
122 return value; | |
123 } | |
124 | |
125 } // namespace | |
126 | |
127 LayerTreeHost::InitParams::InitParams() { | |
128 } | |
129 | |
130 LayerTreeHost::InitParams::~InitParams() { | |
131 } | |
132 | |
133 std::unique_ptr<LayerTreeHostInterface> LayerTreeHost::CreateThreaded( | |
134 scoped_refptr<base::SingleThreadTaskRunner> impl_task_runner, | |
135 InitParams* params) { | |
136 DCHECK(params->main_task_runner.get()); | |
137 DCHECK(impl_task_runner.get()); | |
138 DCHECK(params->settings); | |
139 std::unique_ptr<LayerTreeHost> layer_tree_host( | |
140 new LayerTreeHost(params, CompositorMode::THREADED)); | |
141 layer_tree_host->InitializeThreaded( | |
142 params->main_task_runner, impl_task_runner, | |
143 std::move(params->external_begin_frame_source)); | |
144 return std::move(layer_tree_host); | |
145 } | |
146 | |
147 std::unique_ptr<LayerTreeHost> LayerTreeHost::CreateSingleThreaded( | |
148 LayerTreeHostSingleThreadClient* single_thread_client, | |
149 InitParams* params) { | |
150 DCHECK(params->settings); | |
151 std::unique_ptr<LayerTreeHost> layer_tree_host( | |
152 new LayerTreeHost(params, CompositorMode::SINGLE_THREADED)); | |
153 layer_tree_host->InitializeSingleThreaded( | |
154 single_thread_client, params->main_task_runner, | |
155 std::move(params->external_begin_frame_source)); | |
156 return layer_tree_host; | |
157 } | |
158 | |
159 std::unique_ptr<LayerTreeHostInterface> LayerTreeHost::CreateRemoteServer( | |
160 RemoteProtoChannel* remote_proto_channel, | |
161 InitParams* params) { | |
162 DCHECK(params->main_task_runner.get()); | |
163 DCHECK(params->settings); | |
164 DCHECK(remote_proto_channel); | |
165 TRACE_EVENT0("cc.remote", "LayerTreeHost::CreateRemoteServer"); | |
166 | |
167 // Using an external begin frame source is not supported on the server in | |
168 // remote mode. | |
169 DCHECK(!params->settings->use_external_begin_frame_source); | |
170 DCHECK(!params->external_begin_frame_source); | |
171 DCHECK(params->image_serialization_processor); | |
172 | |
173 std::unique_ptr<LayerTreeHost> layer_tree_host( | |
174 new LayerTreeHost(params, CompositorMode::REMOTE)); | |
175 layer_tree_host->InitializeRemoteServer(remote_proto_channel, | |
176 params->main_task_runner); | |
177 return std::move(layer_tree_host); | |
178 } | |
179 | |
180 std::unique_ptr<LayerTreeHostInterface> LayerTreeHost::CreateRemoteClient( | |
181 RemoteProtoChannel* remote_proto_channel, | |
182 scoped_refptr<base::SingleThreadTaskRunner> impl_task_runner, | |
183 InitParams* params) { | |
184 DCHECK(params->main_task_runner.get()); | |
185 DCHECK(params->settings); | |
186 DCHECK(remote_proto_channel); | |
187 | |
188 // Using an external begin frame source is not supported in remote mode. | |
189 // TODO(khushalsagar): Add support for providing an external begin frame | |
190 // source on the client LayerTreeHost. crbug/576962 | |
191 DCHECK(!params->settings->use_external_begin_frame_source); | |
192 DCHECK(!params->external_begin_frame_source); | |
193 DCHECK(params->image_serialization_processor); | |
194 | |
195 std::unique_ptr<LayerTreeHost> layer_tree_host( | |
196 new LayerTreeHost(params, CompositorMode::REMOTE)); | |
197 layer_tree_host->InitializeRemoteClient( | |
198 remote_proto_channel, params->main_task_runner, impl_task_runner); | |
199 return std::move(layer_tree_host); | |
200 } | |
201 | |
202 LayerTreeHost::LayerTreeHost(InitParams* params, CompositorMode mode) | |
203 : LayerTreeHost( | |
204 params, | |
205 mode, | |
206 base::MakeUnique<LayerTree>(std::move(params->animation_host), | |
207 this)) {} | |
208 | |
209 LayerTreeHost::LayerTreeHost(InitParams* params, | |
210 CompositorMode mode, | |
211 std::unique_ptr<LayerTree> layer_tree) | |
212 : micro_benchmark_controller_(this), | |
213 layer_tree_(std::move(layer_tree)), | |
214 compositor_mode_(mode), | |
215 ui_resource_manager_(base::MakeUnique<UIResourceManager>()), | |
216 client_(params->client), | |
217 source_frame_number_(0), | |
218 rendering_stats_instrumentation_(RenderingStatsInstrumentation::Create()), | |
219 settings_(*params->settings), | |
220 debug_state_(settings_.initial_debug_state), | |
221 visible_(false), | |
222 has_gpu_rasterization_trigger_(false), | |
223 content_is_suitable_for_gpu_rasterization_(true), | |
224 gpu_rasterization_histogram_recorded_(false), | |
225 did_complete_scale_animation_(false), | |
226 id_(s_layer_tree_host_sequence_number.GetNext() + 1), | |
227 next_commit_forces_redraw_(false), | |
228 shared_bitmap_manager_(params->shared_bitmap_manager), | |
229 gpu_memory_buffer_manager_(params->gpu_memory_buffer_manager), | |
230 task_graph_runner_(params->task_graph_runner), | |
231 image_serialization_processor_(params->image_serialization_processor) { | |
232 DCHECK(task_graph_runner_); | |
233 DCHECK(layer_tree_); | |
234 | |
235 rendering_stats_instrumentation_->set_record_rendering_stats( | |
236 debug_state_.RecordRenderingStats()); | |
237 } | |
238 | |
239 void LayerTreeHost::InitializeThreaded( | |
240 scoped_refptr<base::SingleThreadTaskRunner> main_task_runner, | |
241 scoped_refptr<base::SingleThreadTaskRunner> impl_task_runner, | |
242 std::unique_ptr<BeginFrameSource> external_begin_frame_source) { | |
243 task_runner_provider_ = | |
244 TaskRunnerProvider::Create(main_task_runner, impl_task_runner); | |
245 std::unique_ptr<ProxyMain> proxy_main = | |
246 ProxyMain::CreateThreaded(this, task_runner_provider_.get()); | |
247 InitializeProxy(std::move(proxy_main), | |
248 std::move(external_begin_frame_source)); | |
249 } | |
250 | |
251 void LayerTreeHost::InitializeSingleThreaded( | |
252 LayerTreeHostSingleThreadClient* single_thread_client, | |
253 scoped_refptr<base::SingleThreadTaskRunner> main_task_runner, | |
254 std::unique_ptr<BeginFrameSource> external_begin_frame_source) { | |
255 task_runner_provider_ = TaskRunnerProvider::Create(main_task_runner, nullptr); | |
256 InitializeProxy(SingleThreadProxy::Create(this, single_thread_client, | |
257 task_runner_provider_.get()), | |
258 std::move(external_begin_frame_source)); | |
259 } | |
260 | |
261 void LayerTreeHost::InitializeRemoteServer( | |
262 RemoteProtoChannel* remote_proto_channel, | |
263 scoped_refptr<base::SingleThreadTaskRunner> main_task_runner) { | |
264 task_runner_provider_ = TaskRunnerProvider::Create(main_task_runner, nullptr); | |
265 | |
266 if (image_serialization_processor_) { | |
267 engine_picture_cache_ = | |
268 image_serialization_processor_->CreateEnginePictureCache(); | |
269 } | |
270 InitializeProxy(ProxyMain::CreateRemote(remote_proto_channel, this, | |
271 task_runner_provider_.get()), | |
272 nullptr); | |
273 } | |
274 | |
275 void LayerTreeHost::InitializeRemoteClient( | |
276 RemoteProtoChannel* remote_proto_channel, | |
277 scoped_refptr<base::SingleThreadTaskRunner> main_task_runner, | |
278 scoped_refptr<base::SingleThreadTaskRunner> impl_task_runner) { | |
279 task_runner_provider_ = | |
280 TaskRunnerProvider::Create(main_task_runner, impl_task_runner); | |
281 | |
282 if (image_serialization_processor_) { | |
283 client_picture_cache_ = | |
284 image_serialization_processor_->CreateClientPictureCache(); | |
285 } | |
286 | |
287 // For the remote mode, the RemoteChannelImpl implements the Proxy, which is | |
288 // owned by the LayerTreeHost. The RemoteChannelImpl pipes requests which need | |
289 // to handled locally, for instance the Output Surface creation to the | |
290 // LayerTreeHost on the client, while the other requests are sent to the | |
291 // RemoteChannelMain on the server which directs them to ProxyMain and the | |
292 // remote server LayerTreeHost. | |
293 InitializeProxy(base::MakeUnique<RemoteChannelImpl>( | |
294 this, remote_proto_channel, task_runner_provider_.get()), | |
295 nullptr); | |
296 } | |
297 | |
298 void LayerTreeHost::InitializeForTesting( | |
299 std::unique_ptr<TaskRunnerProvider> task_runner_provider, | |
300 std::unique_ptr<Proxy> proxy_for_testing, | |
301 std::unique_ptr<BeginFrameSource> external_begin_frame_source) { | |
302 task_runner_provider_ = std::move(task_runner_provider); | |
303 | |
304 InitializePictureCacheForTesting(); | |
305 | |
306 InitializeProxy(std::move(proxy_for_testing), | |
307 std::move(external_begin_frame_source)); | |
308 } | |
309 | |
310 void LayerTreeHost::InitializePictureCacheForTesting() { | |
311 if (!image_serialization_processor_) | |
312 return; | |
313 | |
314 // Initialize both engine and client cache to ensure serialization tests | |
315 // with a single LayerTreeHost can work correctly. | |
316 engine_picture_cache_ = | |
317 image_serialization_processor_->CreateEnginePictureCache(); | |
318 client_picture_cache_ = | |
319 image_serialization_processor_->CreateClientPictureCache(); | |
320 } | |
321 | |
322 void LayerTreeHost::SetTaskRunnerProviderForTesting( | |
323 std::unique_ptr<TaskRunnerProvider> task_runner_provider) { | |
324 DCHECK(!task_runner_provider_); | |
325 task_runner_provider_ = std::move(task_runner_provider); | |
326 } | |
327 | |
328 void LayerTreeHost::SetUIResourceManagerForTesting( | |
329 std::unique_ptr<UIResourceManager> ui_resource_manager) { | |
330 ui_resource_manager_ = std::move(ui_resource_manager); | |
331 } | |
332 | |
333 void LayerTreeHost::InitializeProxy( | |
334 std::unique_ptr<Proxy> proxy, | |
335 std::unique_ptr<BeginFrameSource> external_begin_frame_source) { | |
336 TRACE_EVENT0("cc", "LayerTreeHost::InitializeForReal"); | |
337 DCHECK(task_runner_provider_); | |
338 | |
339 proxy_ = std::move(proxy); | |
340 proxy_->Start(std::move(external_begin_frame_source)); | |
341 | |
342 layer_tree_->animation_host()->SetSupportsScrollAnimations( | |
343 proxy_->SupportsImplScrolling()); | |
344 } | |
345 | |
346 LayerTreeHost::~LayerTreeHost() { | |
347 TRACE_EVENT0("cc", "LayerTreeHost::~LayerTreeHost"); | |
348 | |
349 // Clear any references into the LayerTreeHost. | |
350 layer_tree_.reset(); | |
351 | |
352 if (proxy_) { | |
353 DCHECK(task_runner_provider_->IsMainThread()); | |
354 proxy_->Stop(); | |
355 | |
356 // Proxy must be destroyed before the Task Runner Provider. | |
357 proxy_ = nullptr; | |
358 } | |
359 } | |
360 | |
361 int LayerTreeHost::GetId() const { | |
362 return id_; | |
363 } | |
364 | |
365 int LayerTreeHost::SourceFrameNumber() const { | |
366 return source_frame_number_; | |
367 } | |
368 | |
369 LayerTree* LayerTreeHost::GetLayerTree() { | |
370 return layer_tree_.get(); | |
371 } | |
372 | |
373 const LayerTree* LayerTreeHost::GetLayerTree() const { | |
374 return layer_tree_.get(); | |
375 } | |
376 | |
377 UIResourceManager* LayerTreeHost::GetUIResourceManager() const { | |
378 return ui_resource_manager_.get(); | |
379 } | |
380 | |
381 TaskRunnerProvider* LayerTreeHost::GetTaskRunnerProvider() const { | |
382 return task_runner_provider_.get(); | |
383 } | |
384 | |
385 SwapPromiseManager* LayerTreeHost::GetSwapPromiseManager() { | |
386 return &swap_promise_manager_; | |
387 } | |
388 | |
389 const LayerTreeSettings& LayerTreeHost::GetSettings() const { | |
390 return settings_; | |
391 } | |
392 | |
393 void LayerTreeHost::SetSurfaceClientId(uint32_t client_id) { | |
394 surface_sequence_generator_.set_surface_client_id(client_id); | |
395 } | |
396 | |
397 void LayerTreeHost::QueueSwapPromise( | |
398 std::unique_ptr<SwapPromise> swap_promise) { | |
399 swap_promise_manager_.QueueSwapPromise(std::move(swap_promise)); | |
400 } | |
401 | |
402 SurfaceSequenceGenerator* LayerTreeHost::GetSurfaceSequenceGenerator() { | |
403 return &surface_sequence_generator_; | |
404 } | |
405 | |
406 void LayerTreeHost::WillBeginMainFrame() { | |
407 devtools_instrumentation::WillBeginMainThreadFrame(GetId(), | |
408 SourceFrameNumber()); | |
409 client_->WillBeginMainFrame(); | |
410 } | |
411 | |
412 void LayerTreeHost::DidBeginMainFrame() { | |
413 client_->DidBeginMainFrame(); | |
414 } | |
415 | |
416 void LayerTreeHost::BeginMainFrameNotExpectedSoon() { | |
417 client_->BeginMainFrameNotExpectedSoon(); | |
418 } | |
419 | |
420 void LayerTreeHost::BeginMainFrame(const BeginFrameArgs& args) { | |
421 client_->BeginMainFrame(args); | |
422 } | |
423 | |
424 void LayerTreeHost::DidStopFlinging() { | |
425 proxy_->MainThreadHasStoppedFlinging(); | |
426 } | |
427 | |
428 const LayerTreeDebugState& LayerTreeHost::GetDebugState() const { | |
429 return debug_state_; | |
430 } | |
431 | |
432 void LayerTreeHost::RequestMainFrameUpdate() { | |
433 client_->UpdateLayerTreeHost(); | |
434 } | |
435 | |
436 // This function commits the LayerTreeHost to an impl tree. When modifying | |
437 // this function, keep in mind that the function *runs* on the impl thread! Any | |
438 // code that is logically a main thread operation, e.g. deletion of a Layer, | |
439 // should be delayed until the LayerTreeHost::CommitComplete, which will run | |
440 // after the commit, but on the main thread. | |
441 void LayerTreeHost::FinishCommitOnImplThread(LayerTreeHostImpl* host_impl) { | |
442 DCHECK(!IsRemoteServer()); | |
443 DCHECK(task_runner_provider_->IsImplThread()); | |
444 | |
445 bool is_new_trace; | |
446 TRACE_EVENT_IS_NEW_TRACE(&is_new_trace); | |
447 if (is_new_trace && | |
448 frame_viewer_instrumentation::IsTracingLayerTreeSnapshots() && | |
449 layer_tree_->root_layer()) { | |
450 LayerTreeHostCommon::CallFunctionForEveryLayer( | |
451 layer_tree_.get(), [](Layer* layer) { layer->DidBeginTracing(); }); | |
452 } | |
453 | |
454 LayerTreeImpl* sync_tree = host_impl->sync_tree(); | |
455 | |
456 if (next_commit_forces_redraw_) { | |
457 sync_tree->ForceRedrawNextActivation(); | |
458 next_commit_forces_redraw_ = false; | |
459 } | |
460 | |
461 sync_tree->set_source_frame_number(SourceFrameNumber()); | |
462 | |
463 if (layer_tree_->needs_full_tree_sync()) | |
464 TreeSynchronizer::SynchronizeTrees(layer_tree_->root_layer(), sync_tree); | |
465 | |
466 layer_tree_->PushPropertiesTo(sync_tree); | |
467 | |
468 sync_tree->PassSwapPromises(swap_promise_manager_.TakeSwapPromises()); | |
469 | |
470 host_impl->SetHasGpuRasterizationTrigger(has_gpu_rasterization_trigger_); | |
471 host_impl->SetContentIsSuitableForGpuRasterization( | |
472 content_is_suitable_for_gpu_rasterization_); | |
473 RecordGpuRasterizationHistogram(); | |
474 | |
475 host_impl->SetViewportSize(layer_tree_->device_viewport_size()); | |
476 // TODO(senorblanco): Move this to LayerTree::PushPropertiesTo so that it | |
477 // happens before GPU rasterization properties are set, since those trigger an | |
478 // update of GPU rasterization status, which depends on the device scale | |
479 // factor. (crbug.com/535700) | |
480 sync_tree->SetDeviceScaleFactor(layer_tree_->device_scale_factor()); | |
481 host_impl->SetDebugState(debug_state_); | |
482 | |
483 sync_tree->set_ui_resource_request_queue( | |
484 ui_resource_manager_->TakeUIResourcesRequests()); | |
485 | |
486 { | |
487 TRACE_EVENT0("cc", "LayerTreeHost::PushProperties"); | |
488 | |
489 TreeSynchronizer::PushLayerProperties(layer_tree_.get(), sync_tree); | |
490 | |
491 // This must happen after synchronizing property trees and after push | |
492 // properties, which updates property tree indices, but before animation | |
493 // host pushes properties as animation host push properties can change | |
494 // Animation::InEffect and we want the old InEffect value for updating | |
495 // property tree scrolling and animation. | |
496 sync_tree->UpdatePropertyTreeScrollingAndAnimationFromMainThread(); | |
497 | |
498 TRACE_EVENT0("cc", "LayerTreeHost::AnimationHost::PushProperties"); | |
499 DCHECK(host_impl->animation_host()); | |
500 layer_tree_->animation_host()->PushPropertiesTo( | |
501 host_impl->animation_host()); | |
502 } | |
503 | |
504 // This must happen after synchronizing property trees and after pushing | |
505 // properties, which updates the clobber_active_value flag. | |
506 sync_tree->UpdatePropertyTreeScrollOffset(layer_tree_->property_trees()); | |
507 | |
508 micro_benchmark_controller_.ScheduleImplBenchmarks(host_impl); | |
509 layer_tree_->property_trees()->ResetAllChangeTracking(); | |
510 } | |
511 | |
512 void LayerTreeHost::WillCommit() { | |
513 swap_promise_manager_.WillCommit(); | |
514 client_->WillCommit(); | |
515 } | |
516 | |
517 void LayerTreeHost::UpdateHudLayer() { | |
518 } | |
519 | |
520 void LayerTreeHost::CommitComplete() { | |
521 source_frame_number_++; | |
522 client_->DidCommit(); | |
523 if (did_complete_scale_animation_) { | |
524 client_->DidCompletePageScaleAnimation(); | |
525 did_complete_scale_animation_ = false; | |
526 } | |
527 } | |
528 | |
529 void LayerTreeHost::SetOutputSurface(std::unique_ptr<OutputSurface> surface) { | |
530 TRACE_EVENT0("cc", "LayerTreeHost::SetOutputSurface"); | |
531 DCHECK(surface); | |
532 | |
533 DCHECK(!new_output_surface_); | |
534 new_output_surface_ = std::move(surface); | |
535 proxy_->SetOutputSurface(new_output_surface_.get()); | |
536 } | |
537 | |
538 std::unique_ptr<OutputSurface> LayerTreeHost::ReleaseOutputSurface() { | |
539 DCHECK(!visible_); | |
540 | |
541 DidLoseOutputSurface(); | |
542 proxy_->ReleaseOutputSurface(); | |
543 return std::move(current_output_surface_); | |
544 } | |
545 | |
546 void LayerTreeHost::RequestNewOutputSurface() { | |
547 client_->RequestNewOutputSurface(); | |
548 } | |
549 | |
550 void LayerTreeHost::DidInitializeOutputSurface() { | |
551 DCHECK(new_output_surface_); | |
552 current_output_surface_ = std::move(new_output_surface_); | |
553 client_->DidInitializeOutputSurface(); | |
554 } | |
555 | |
556 void LayerTreeHost::DidFailToInitializeOutputSurface() { | |
557 DCHECK(new_output_surface_); | |
558 // Note: It is safe to drop all output surface references here as | |
559 // LayerTreeHostImpl will not keep a pointer to either the old or | |
560 // new output surface after failing to initialize the new one. | |
561 current_output_surface_ = nullptr; | |
562 new_output_surface_ = nullptr; | |
563 client_->DidFailToInitializeOutputSurface(); | |
564 } | |
565 | |
566 std::unique_ptr<LayerTreeHostImpl> LayerTreeHost::CreateLayerTreeHostImpl( | |
567 LayerTreeHostImplClient* client) { | |
568 DCHECK(!IsRemoteServer()); | |
569 DCHECK(task_runner_provider_->IsImplThread()); | |
570 | |
571 const bool supports_impl_scrolling = task_runner_provider_->HasImplThread(); | |
572 std::unique_ptr<AnimationHost> animation_host_impl = | |
573 layer_tree_->animation_host()->CreateImplInstance( | |
574 supports_impl_scrolling); | |
575 | |
576 std::unique_ptr<LayerTreeHostImpl> host_impl = LayerTreeHostImpl::Create( | |
577 settings_, client, task_runner_provider_.get(), | |
578 rendering_stats_instrumentation_.get(), shared_bitmap_manager_, | |
579 gpu_memory_buffer_manager_, task_graph_runner_, | |
580 std::move(animation_host_impl), id_); | |
581 host_impl->SetHasGpuRasterizationTrigger(has_gpu_rasterization_trigger_); | |
582 host_impl->SetContentIsSuitableForGpuRasterization( | |
583 content_is_suitable_for_gpu_rasterization_); | |
584 shared_bitmap_manager_ = NULL; | |
585 gpu_memory_buffer_manager_ = NULL; | |
586 task_graph_runner_ = NULL; | |
587 input_handler_weak_ptr_ = host_impl->AsWeakPtr(); | |
588 return host_impl; | |
589 } | |
590 | |
591 void LayerTreeHost::DidLoseOutputSurface() { | |
592 TRACE_EVENT0("cc", "LayerTreeHost::DidLoseOutputSurface"); | |
593 DCHECK(task_runner_provider_->IsMainThread()); | |
594 SetNeedsCommit(); | |
595 } | |
596 | |
597 void LayerTreeHost::SetDeferCommits(bool defer_commits) { | |
598 proxy_->SetDeferCommits(defer_commits); | |
599 } | |
600 | |
601 DISABLE_CFI_PERF | |
602 void LayerTreeHost::SetNeedsAnimate() { | |
603 proxy_->SetNeedsAnimate(); | |
604 swap_promise_manager_.NotifySwapPromiseMonitorsOfSetNeedsCommit(); | |
605 } | |
606 | |
607 DISABLE_CFI_PERF | |
608 void LayerTreeHost::SetNeedsUpdateLayers() { | |
609 proxy_->SetNeedsUpdateLayers(); | |
610 swap_promise_manager_.NotifySwapPromiseMonitorsOfSetNeedsCommit(); | |
611 } | |
612 | |
613 void LayerTreeHost::SetNeedsCommit() { | |
614 proxy_->SetNeedsCommit(); | |
615 swap_promise_manager_.NotifySwapPromiseMonitorsOfSetNeedsCommit(); | |
616 } | |
617 | |
618 void LayerTreeHost::SetNeedsRedraw() { | |
619 SetNeedsRedrawRect(gfx::Rect(layer_tree_->device_viewport_size())); | |
620 } | |
621 | |
622 void LayerTreeHost::SetNeedsRedrawRect(const gfx::Rect& damage_rect) { | |
623 proxy_->SetNeedsRedraw(damage_rect); | |
624 } | |
625 | |
626 bool LayerTreeHost::CommitRequested() const { | |
627 return proxy_->CommitRequested(); | |
628 } | |
629 | |
630 bool LayerTreeHost::BeginMainFrameRequested() const { | |
631 return proxy_->BeginMainFrameRequested(); | |
632 } | |
633 | |
634 void LayerTreeHost::SetNextCommitWaitsForActivation() { | |
635 proxy_->SetNextCommitWaitsForActivation(); | |
636 } | |
637 | |
638 void LayerTreeHost::SetNextCommitForcesRedraw() { | |
639 next_commit_forces_redraw_ = true; | |
640 proxy_->SetNeedsUpdateLayers(); | |
641 } | |
642 | |
643 void LayerTreeHost::SetAnimationEvents( | |
644 std::unique_ptr<AnimationEvents> events) { | |
645 DCHECK(task_runner_provider_->IsMainThread()); | |
646 layer_tree_->animation_host()->SetAnimationEvents(std::move(events)); | |
647 } | |
648 | |
649 void LayerTreeHost::SetDebugState(const LayerTreeDebugState& debug_state) { | |
650 LayerTreeDebugState new_debug_state = | |
651 LayerTreeDebugState::Unite(settings_.initial_debug_state, debug_state); | |
652 | |
653 if (LayerTreeDebugState::Equal(debug_state_, new_debug_state)) | |
654 return; | |
655 | |
656 debug_state_ = new_debug_state; | |
657 | |
658 rendering_stats_instrumentation_->set_record_rendering_stats( | |
659 debug_state_.RecordRenderingStats()); | |
660 | |
661 SetNeedsCommit(); | |
662 } | |
663 | |
664 void LayerTreeHost::ResetGpuRasterizationTracking() { | |
665 content_is_suitable_for_gpu_rasterization_ = true; | |
666 gpu_rasterization_histogram_recorded_ = false; | |
667 } | |
668 | |
669 void LayerTreeHost::SetHasGpuRasterizationTrigger(bool has_trigger) { | |
670 if (has_trigger == has_gpu_rasterization_trigger_) | |
671 return; | |
672 | |
673 has_gpu_rasterization_trigger_ = has_trigger; | |
674 TRACE_EVENT_INSTANT1("cc", | |
675 "LayerTreeHost::SetHasGpuRasterizationTrigger", | |
676 TRACE_EVENT_SCOPE_THREAD, | |
677 "has_trigger", | |
678 has_gpu_rasterization_trigger_); | |
679 } | |
680 | |
681 void LayerTreeHost::ApplyPageScaleDeltaFromImplSide(float page_scale_delta) { | |
682 DCHECK(CommitRequested()); | |
683 if (page_scale_delta == 1.f) | |
684 return; | |
685 float page_scale = layer_tree_->page_scale_factor() * page_scale_delta; | |
686 layer_tree_->SetPageScaleFromImplSide(page_scale); | |
687 } | |
688 | |
689 void LayerTreeHost::SetVisible(bool visible) { | |
690 if (visible_ == visible) | |
691 return; | |
692 visible_ = visible; | |
693 proxy_->SetVisible(visible); | |
694 } | |
695 | |
696 bool LayerTreeHost::IsVisible() const { | |
697 return visible_; | |
698 } | |
699 | |
700 void LayerTreeHost::NotifyInputThrottledUntilCommit() { | |
701 proxy_->NotifyInputThrottledUntilCommit(); | |
702 } | |
703 | |
704 void LayerTreeHost::LayoutAndUpdateLayers() { | |
705 DCHECK(IsSingleThreaded()); | |
706 // This function is only valid when not using the scheduler. | |
707 DCHECK(!settings_.single_thread_proxy_scheduler); | |
708 RequestMainFrameUpdate(); | |
709 UpdateLayers(); | |
710 } | |
711 | |
712 void LayerTreeHost::Composite(base::TimeTicks frame_begin_time) { | |
713 DCHECK(IsSingleThreaded()); | |
714 // This function is only valid when not using the scheduler. | |
715 DCHECK(!settings_.single_thread_proxy_scheduler); | |
716 SingleThreadProxy* proxy = static_cast<SingleThreadProxy*>(proxy_.get()); | |
717 | |
718 proxy->CompositeImmediately(frame_begin_time); | |
719 } | |
720 | |
721 bool LayerTreeHost::UpdateLayers() { | |
722 if (!layer_tree_->root_layer()) | |
723 return false; | |
724 DCHECK(!layer_tree_->root_layer()->parent()); | |
725 bool result = DoUpdateLayers(layer_tree_->root_layer()); | |
726 micro_benchmark_controller_.DidUpdateLayers(); | |
727 return result || next_commit_forces_redraw_; | |
728 } | |
729 | |
730 void LayerTreeHost::DidCompletePageScaleAnimation() { | |
731 did_complete_scale_animation_ = true; | |
732 } | |
733 | |
734 void LayerTreeHost::RecordGpuRasterizationHistogram() { | |
735 // Gpu rasterization is only supported for Renderer compositors. | |
736 // Checking for IsSingleThreaded() to exclude Browser compositors. | |
737 if (gpu_rasterization_histogram_recorded_ || IsSingleThreaded()) | |
738 return; | |
739 | |
740 // Record how widely gpu rasterization is enabled. | |
741 // This number takes device/gpu whitelisting/backlisting into account. | |
742 // Note that we do not consider the forced gpu rasterization mode, which is | |
743 // mostly used for debugging purposes. | |
744 UMA_HISTOGRAM_BOOLEAN("Renderer4.GpuRasterizationEnabled", | |
745 settings_.gpu_rasterization_enabled); | |
746 if (settings_.gpu_rasterization_enabled) { | |
747 UMA_HISTOGRAM_BOOLEAN("Renderer4.GpuRasterizationTriggered", | |
748 has_gpu_rasterization_trigger_); | |
749 UMA_HISTOGRAM_BOOLEAN("Renderer4.GpuRasterizationSuitableContent", | |
750 content_is_suitable_for_gpu_rasterization_); | |
751 // Record how many pages actually get gpu rasterization when enabled. | |
752 UMA_HISTOGRAM_BOOLEAN("Renderer4.GpuRasterizationUsed", | |
753 (has_gpu_rasterization_trigger_ && | |
754 content_is_suitable_for_gpu_rasterization_)); | |
755 } | |
756 | |
757 gpu_rasterization_histogram_recorded_ = true; | |
758 } | |
759 | |
760 bool LayerTreeHost::DoUpdateLayers(Layer* root_layer) { | |
761 TRACE_EVENT1("cc", "LayerTreeHost::DoUpdateLayers", "source_frame_number", | |
762 SourceFrameNumber()); | |
763 | |
764 layer_tree_->UpdateHudLayer(debug_state_.ShowHudInfo()); | |
765 UpdateHudLayer(); | |
766 | |
767 Layer* root_scroll = | |
768 PropertyTreeBuilder::FindFirstScrollableLayer(root_layer); | |
769 Layer* page_scale_layer = layer_tree_->page_scale_layer(); | |
770 if (!page_scale_layer && root_scroll) | |
771 page_scale_layer = root_scroll->parent(); | |
772 | |
773 if (layer_tree_->hud_layer()) { | |
774 layer_tree_->hud_layer()->PrepareForCalculateDrawProperties( | |
775 layer_tree_->device_viewport_size(), | |
776 layer_tree_->device_scale_factor()); | |
777 } | |
778 | |
779 gfx::Transform identity_transform; | |
780 LayerList update_layer_list; | |
781 | |
782 { | |
783 TRACE_EVENT0("cc", "LayerTreeHost::UpdateLayers::BuildPropertyTrees"); | |
784 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("cc.debug.cdp-perf"), | |
785 "LayerTreeHostCommon::ComputeVisibleRectsWithPropertyTrees"); | |
786 PropertyTreeBuilder::PreCalculateMetaInformation(root_layer); | |
787 bool can_render_to_separate_surface = true; | |
788 PropertyTrees* property_trees = layer_tree_->property_trees(); | |
789 if (!settings_.use_layer_lists) { | |
790 // If use_layer_lists is set, then the property trees should have been | |
791 // built by the client already. | |
792 PropertyTreeBuilder::BuildPropertyTrees( | |
793 root_layer, page_scale_layer, | |
794 layer_tree_->inner_viewport_scroll_layer(), | |
795 layer_tree_->outer_viewport_scroll_layer(), | |
796 layer_tree_->overscroll_elasticity_layer(), | |
797 layer_tree_->elastic_overscroll(), layer_tree_->page_scale_factor(), | |
798 layer_tree_->device_scale_factor(), | |
799 gfx::Rect(layer_tree_->device_viewport_size()), identity_transform, | |
800 property_trees); | |
801 TRACE_EVENT_INSTANT1("cc", | |
802 "LayerTreeHost::UpdateLayers_BuiltPropertyTrees", | |
803 TRACE_EVENT_SCOPE_THREAD, "property_trees", | |
804 property_trees->AsTracedValue()); | |
805 } else { | |
806 TRACE_EVENT_INSTANT1("cc", | |
807 "LayerTreeHost::UpdateLayers_ReceivedPropertyTrees", | |
808 TRACE_EVENT_SCOPE_THREAD, "property_trees", | |
809 property_trees->AsTracedValue()); | |
810 } | |
811 draw_property_utils::UpdatePropertyTrees(property_trees, | |
812 can_render_to_separate_surface); | |
813 draw_property_utils::FindLayersThatNeedUpdates( | |
814 layer_tree_.get(), property_trees->transform_tree, | |
815 property_trees->effect_tree, &update_layer_list); | |
816 } | |
817 | |
818 for (const auto& layer : update_layer_list) | |
819 layer->SavePaintProperties(); | |
820 | |
821 bool content_is_suitable_for_gpu = true; | |
822 bool did_paint_content = layer_tree_->UpdateLayers( | |
823 update_layer_list, &content_is_suitable_for_gpu); | |
824 | |
825 if (content_is_suitable_for_gpu) { | |
826 ++num_consecutive_frames_suitable_for_gpu_; | |
827 if (num_consecutive_frames_suitable_for_gpu_ >= | |
828 kNumFramesToConsiderBeforeGpuRasterization) { | |
829 content_is_suitable_for_gpu_rasterization_ = true; | |
830 } | |
831 } else { | |
832 num_consecutive_frames_suitable_for_gpu_ = 0; | |
833 content_is_suitable_for_gpu_rasterization_ = false; | |
834 } | |
835 return did_paint_content; | |
836 } | |
837 | |
838 void LayerTreeHost::ApplyViewportDeltas(ScrollAndScaleSet* info) { | |
839 gfx::Vector2dF inner_viewport_scroll_delta; | |
840 if (info->inner_viewport_scroll.layer_id != Layer::INVALID_ID) | |
841 inner_viewport_scroll_delta = info->inner_viewport_scroll.scroll_delta; | |
842 | |
843 if (inner_viewport_scroll_delta.IsZero() && info->page_scale_delta == 1.f && | |
844 info->elastic_overscroll_delta.IsZero() && !info->top_controls_delta) | |
845 return; | |
846 | |
847 // Preemptively apply the scroll offset and scale delta here before sending | |
848 // it to the client. If the client comes back and sets it to the same | |
849 // value, then the layer can early out without needing a full commit. | |
850 if (layer_tree_->inner_viewport_scroll_layer()) { | |
851 layer_tree_->inner_viewport_scroll_layer()->SetScrollOffsetFromImplSide( | |
852 gfx::ScrollOffsetWithDelta( | |
853 layer_tree_->inner_viewport_scroll_layer()->scroll_offset(), | |
854 inner_viewport_scroll_delta)); | |
855 } | |
856 | |
857 ApplyPageScaleDeltaFromImplSide(info->page_scale_delta); | |
858 layer_tree_->SetElasticOverscrollFromImplSide( | |
859 layer_tree_->elastic_overscroll() + info->elastic_overscroll_delta); | |
860 // TODO(ccameron): pass the elastic overscroll here so that input events | |
861 // may be translated appropriately. | |
862 client_->ApplyViewportDeltas(inner_viewport_scroll_delta, gfx::Vector2dF(), | |
863 info->elastic_overscroll_delta, | |
864 info->page_scale_delta, | |
865 info->top_controls_delta); | |
866 SetNeedsUpdateLayers(); | |
867 } | |
868 | |
869 void LayerTreeHost::ApplyScrollAndScale(ScrollAndScaleSet* info) { | |
870 for (auto& swap_promise : info->swap_promises) { | |
871 TRACE_EVENT_WITH_FLOW1("input,benchmark", | |
872 "LatencyInfo.Flow", | |
873 TRACE_ID_DONT_MANGLE(swap_promise->TraceId()), | |
874 TRACE_EVENT_FLAG_FLOW_IN | TRACE_EVENT_FLAG_FLOW_OUT, | |
875 "step", "Main thread scroll update"); | |
876 swap_promise_manager_.QueueSwapPromise(std::move(swap_promise)); | |
877 } | |
878 | |
879 if (layer_tree_->root_layer()) { | |
880 for (size_t i = 0; i < info->scrolls.size(); ++i) { | |
881 Layer* layer = layer_tree_->LayerById(info->scrolls[i].layer_id); | |
882 if (!layer) | |
883 continue; | |
884 layer->SetScrollOffsetFromImplSide(gfx::ScrollOffsetWithDelta( | |
885 layer->scroll_offset(), info->scrolls[i].scroll_delta)); | |
886 SetNeedsUpdateLayers(); | |
887 } | |
888 } | |
889 | |
890 // This needs to happen after scroll deltas have been sent to prevent top | |
891 // controls from clamping the layout viewport both on the compositor and | |
892 // on the main thread. | |
893 ApplyViewportDeltas(info); | |
894 } | |
895 | |
896 const base::WeakPtr<InputHandler>& LayerTreeHost::GetInputHandler() const { | |
897 return input_handler_weak_ptr_; | |
898 } | |
899 | |
900 void LayerTreeHost::UpdateTopControlsState(TopControlsState constraints, | |
901 TopControlsState current, | |
902 bool animate) { | |
903 // Top controls are only used in threaded or remote mode. | |
904 DCHECK(IsThreaded() || IsRemoteServer()); | |
905 proxy_->UpdateTopControlsState(constraints, current, animate); | |
906 } | |
907 | |
908 void LayerTreeHost::AnimateLayers(base::TimeTicks monotonic_time) { | |
909 AnimationHost* animation_host = layer_tree_->animation_host(); | |
910 std::unique_ptr<AnimationEvents> events = animation_host->CreateEvents(); | |
911 | |
912 if (animation_host->AnimateLayers(monotonic_time)) | |
913 animation_host->UpdateAnimationState(true, events.get()); | |
914 | |
915 if (!events->events_.empty()) | |
916 layer_tree_->property_trees()->needs_rebuild = true; | |
917 } | |
918 | |
919 int LayerTreeHost::ScheduleMicroBenchmark( | |
920 const std::string& benchmark_name, | |
921 std::unique_ptr<base::Value> value, | |
922 const MicroBenchmark::DoneCallback& callback) { | |
923 return micro_benchmark_controller_.ScheduleRun(benchmark_name, | |
924 std::move(value), callback); | |
925 } | |
926 | |
927 bool LayerTreeHost::SendMessageToMicroBenchmark( | |
928 int id, | |
929 std::unique_ptr<base::Value> value) { | |
930 return micro_benchmark_controller_.SendMessage(id, std::move(value)); | |
931 } | |
932 | |
933 void LayerTreeHost::SetLayerTreeMutator( | |
934 std::unique_ptr<LayerTreeMutator> mutator) { | |
935 proxy_->SetMutator(std::move(mutator)); | |
936 } | |
937 | |
938 bool LayerTreeHost::IsSingleThreaded() const { | |
939 DCHECK(compositor_mode_ != CompositorMode::SINGLE_THREADED || | |
940 !task_runner_provider_->HasImplThread()); | |
941 return compositor_mode_ == CompositorMode::SINGLE_THREADED; | |
942 } | |
943 | |
944 bool LayerTreeHost::IsThreaded() const { | |
945 DCHECK(compositor_mode_ != CompositorMode::THREADED || | |
946 task_runner_provider_->HasImplThread()); | |
947 return compositor_mode_ == CompositorMode::THREADED; | |
948 } | |
949 | |
950 bool LayerTreeHost::IsRemoteServer() const { | |
951 // The LayerTreeHost on the server does not have an impl task runner. | |
952 return compositor_mode_ == CompositorMode::REMOTE && | |
953 !task_runner_provider_->HasImplThread(); | |
954 } | |
955 | |
956 bool LayerTreeHost::IsRemoteClient() const { | |
957 return compositor_mode_ == CompositorMode::REMOTE && | |
958 task_runner_provider_->HasImplThread(); | |
959 } | |
960 | |
961 void LayerTreeHost::ToProtobufForCommit( | |
962 proto::LayerTreeHost* proto, | |
963 std::vector<std::unique_ptr<SwapPromise>>* swap_promises) { | |
964 DCHECK(engine_picture_cache_); | |
965 // Not all fields are serialized, as they are either not needed for a commit, | |
966 // or implementation isn't ready yet. | |
967 // Unsupported items: | |
968 // - animations | |
969 // - UI resources | |
970 // - instrumentation of stats | |
971 // - histograms | |
972 // Skipped items: | |
973 // - SwapPromise as they are mostly used for perf measurements. | |
974 // - The bitmap and GPU memory related items. | |
975 // Other notes: | |
976 // - The output surfaces are only valid on the client-side so they are | |
977 // therefore not serialized. | |
978 // - LayerTreeSettings are needed only during construction of the | |
979 // LayerTreeHost, so they are serialized outside of the LayerTreeHost | |
980 // serialization. | |
981 // - The |visible_| flag will be controlled from the client separately and | |
982 // will need special handling outside of the serialization of the | |
983 // LayerTreeHost. | |
984 // TODO(nyquist): Figure out how to support animations. See crbug.com/570376. | |
985 TRACE_EVENT0("cc.remote", "LayerTreeHost::ToProtobufForCommit"); | |
986 *swap_promises = swap_promise_manager_.TakeSwapPromises(); | |
987 | |
988 proto->set_source_frame_number(source_frame_number_); | |
989 | |
990 // Serialize the LayerTree before serializing the properties. During layer | |
991 // property serialization, we clear the list |layer_that_should_properties_| | |
992 // from the LayerTree. | |
993 layer_tree_->ToProtobuf(proto->mutable_layer_tree()); | |
994 | |
995 LayerProtoConverter::SerializeLayerProperties(this, | |
996 proto->mutable_layer_updates()); | |
997 | |
998 std::vector<PictureData> pictures = | |
999 engine_picture_cache_->CalculateCacheUpdateAndFlush(); | |
1000 proto::PictureDataVectorToSkPicturesProto(pictures, | |
1001 proto->mutable_pictures()); | |
1002 | |
1003 debug_state_.ToProtobuf(proto->mutable_debug_state()); | |
1004 proto->set_has_gpu_rasterization_trigger(has_gpu_rasterization_trigger_); | |
1005 proto->set_content_is_suitable_for_gpu_rasterization( | |
1006 content_is_suitable_for_gpu_rasterization_); | |
1007 proto->set_id(id_); | |
1008 proto->set_next_commit_forces_redraw(next_commit_forces_redraw_); | |
1009 | |
1010 TRACE_EVENT_OBJECT_SNAPSHOT_WITH_ID( | |
1011 "cc.remote", "LayerTreeHostProto", source_frame_number_, | |
1012 ComputeLayerTreeHostProtoSizeSplitAsValue(proto)); | |
1013 } | |
1014 | |
1015 void LayerTreeHost::FromProtobufForCommit(const proto::LayerTreeHost& proto) { | |
1016 DCHECK(client_picture_cache_); | |
1017 source_frame_number_ = proto.source_frame_number(); | |
1018 | |
1019 layer_tree_->FromProtobuf(proto.layer_tree()); | |
1020 | |
1021 // Ensure ClientPictureCache contains all the necessary SkPictures before | |
1022 // deserializing the properties. | |
1023 proto::SkPictures proto_pictures = proto.pictures(); | |
1024 std::vector<PictureData> pictures = | |
1025 SkPicturesProtoToPictureDataVector(proto_pictures); | |
1026 client_picture_cache_->ApplyCacheUpdate(pictures); | |
1027 | |
1028 LayerProtoConverter::DeserializeLayerProperties(layer_tree_->root_layer(), | |
1029 proto.layer_updates()); | |
1030 | |
1031 // The deserialization is finished, so now clear the cache. | |
1032 client_picture_cache_->Flush(); | |
1033 | |
1034 debug_state_.FromProtobuf(proto.debug_state()); | |
1035 has_gpu_rasterization_trigger_ = proto.has_gpu_rasterization_trigger(); | |
1036 content_is_suitable_for_gpu_rasterization_ = | |
1037 proto.content_is_suitable_for_gpu_rasterization(); | |
1038 id_ = proto.id(); | |
1039 next_commit_forces_redraw_ = proto.next_commit_forces_redraw(); | |
1040 } | |
1041 | |
1042 } // namespace cc | |
OLD | NEW |