| OLD | NEW |
| (Empty) |
| 1 // Copyright 2016 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/blimp/compositor_state_deserializer.h" | |
| 6 | |
| 7 #include "base/bind.h" | |
| 8 #include "base/memory/ptr_util.h" | |
| 9 #include "cc/blimp/client_picture_cache.h" | |
| 10 #include "cc/blimp/deserialized_content_layer_client.h" | |
| 11 #include "cc/blimp/layer_factory.h" | |
| 12 #include "cc/blimp/picture_data_conversions.h" | |
| 13 #include "cc/input/layer_selection_bound.h" | |
| 14 #include "cc/layers/layer.h" | |
| 15 #include "cc/layers/picture_layer.h" | |
| 16 #include "cc/layers/solid_color_scrollbar_layer.h" | |
| 17 #include "cc/proto/cc_conversions.h" | |
| 18 #include "cc/proto/client_state_update.pb.h" | |
| 19 #include "cc/proto/gfx_conversions.h" | |
| 20 #include "cc/proto/layer_tree_host.pb.h" | |
| 21 #include "cc/proto/skia_conversions.h" | |
| 22 #include "cc/trees/layer_tree_host_common.h" | |
| 23 #include "cc/trees/layer_tree_host_in_process.h" | |
| 24 | |
| 25 namespace cc { | |
| 26 namespace { | |
| 27 | |
| 28 class DefaultLayerFactory : public LayerFactory { | |
| 29 public: | |
| 30 DefaultLayerFactory() = default; | |
| 31 ~DefaultLayerFactory() override = default; | |
| 32 | |
| 33 // LayerFactory implementation. | |
| 34 scoped_refptr<Layer> CreateLayer(int engine_layer_id) override { | |
| 35 return Layer::Create(); | |
| 36 } | |
| 37 scoped_refptr<PictureLayer> CreatePictureLayer( | |
| 38 int engine_layer_id, | |
| 39 ContentLayerClient* content_layer_client) override { | |
| 40 return PictureLayer::Create(content_layer_client); | |
| 41 } | |
| 42 scoped_refptr<SolidColorScrollbarLayer> CreateSolidColorScrollbarLayer( | |
| 43 int engine_layer_id, | |
| 44 ScrollbarOrientation orientation, | |
| 45 int thumb_thickness, | |
| 46 int track_start, | |
| 47 bool is_left_side_vertical_scrollbar, | |
| 48 int scroll_layer_id) override { | |
| 49 return SolidColorScrollbarLayer::Create( | |
| 50 orientation, thumb_thickness, track_start, | |
| 51 is_left_side_vertical_scrollbar, scroll_layer_id); | |
| 52 } | |
| 53 scoped_refptr<PictureLayer> CreateFakePictureLayer( | |
| 54 int engine_layer_id, | |
| 55 ContentLayerClient* content_layer_client) override { | |
| 56 // We should never create fake layers in production code. | |
| 57 NOTREACHED(); | |
| 58 return PictureLayer::Create(content_layer_client); | |
| 59 } | |
| 60 scoped_refptr<Layer> CreatePushPropertiesCountingLayer( | |
| 61 int engine_layer_id) override { | |
| 62 // We should never create fake layers in production code. | |
| 63 NOTREACHED(); | |
| 64 return Layer::Create(); | |
| 65 } | |
| 66 }; | |
| 67 | |
| 68 } // namespace | |
| 69 | |
| 70 CompositorStateDeserializer::LayerData::LayerData() = default; | |
| 71 | |
| 72 CompositorStateDeserializer::LayerData::~LayerData() = default; | |
| 73 | |
| 74 CompositorStateDeserializer::LayerData::LayerData(LayerData&& other) = default; | |
| 75 | |
| 76 CompositorStateDeserializer::LayerData& CompositorStateDeserializer::LayerData:: | |
| 77 operator=(LayerData&& other) = default; | |
| 78 | |
| 79 CompositorStateDeserializer::CompositorStateDeserializer( | |
| 80 LayerTreeHostInProcess* layer_tree_host, | |
| 81 std::unique_ptr<ClientPictureCache> client_picture_cache, | |
| 82 CompositorStateDeserializerClient* client) | |
| 83 : layer_factory_(base::MakeUnique<DefaultLayerFactory>()), | |
| 84 layer_tree_host_(layer_tree_host), | |
| 85 client_picture_cache_(std::move(client_picture_cache)), | |
| 86 client_(client), | |
| 87 weak_factory_(this) { | |
| 88 DCHECK(layer_tree_host_); | |
| 89 DCHECK(client_); | |
| 90 } | |
| 91 | |
| 92 CompositorStateDeserializer::~CompositorStateDeserializer() = default; | |
| 93 | |
| 94 Layer* CompositorStateDeserializer::GetLayerForEngineId( | |
| 95 int engine_layer_id) const { | |
| 96 EngineIdToLayerMap::const_iterator layer_it = | |
| 97 engine_id_to_layer_.find(engine_layer_id); | |
| 98 return layer_it != engine_id_to_layer_.end() ? layer_it->second.layer.get() | |
| 99 : nullptr; | |
| 100 } | |
| 101 | |
| 102 void CompositorStateDeserializer::DeserializeCompositorUpdate( | |
| 103 const proto::LayerTreeHost& layer_tree_host_proto) { | |
| 104 SychronizeLayerTreeState(layer_tree_host_proto.layer_tree()); | |
| 105 | |
| 106 // Ensure ClientPictureCache contains all the necessary SkPictures before | |
| 107 // deserializing the properties. | |
| 108 proto::SkPictures proto_pictures = layer_tree_host_proto.pictures(); | |
| 109 std::vector<PictureData> pictures = | |
| 110 SkPicturesProtoToPictureDataVector(proto_pictures); | |
| 111 client_picture_cache_->ApplyCacheUpdate(pictures); | |
| 112 | |
| 113 const proto::LayerUpdate& layer_updates = | |
| 114 layer_tree_host_proto.layer_updates(); | |
| 115 for (int i = 0; i < layer_updates.layers_size(); ++i) { | |
| 116 SynchronizeLayerState(layer_updates.layers(i)); | |
| 117 } | |
| 118 | |
| 119 // The deserialization is finished, so now clear the cache. | |
| 120 client_picture_cache_->Flush(); | |
| 121 } | |
| 122 | |
| 123 void CompositorStateDeserializer::SetLayerFactoryForTesting( | |
| 124 std::unique_ptr<LayerFactory> layer_factory) { | |
| 125 layer_factory_ = std::move(layer_factory); | |
| 126 } | |
| 127 | |
| 128 void CompositorStateDeserializer::ApplyViewportDeltas( | |
| 129 const gfx::Vector2dF& inner_delta, | |
| 130 const gfx::Vector2dF& outer_delta, | |
| 131 const gfx::Vector2dF& elastic_overscroll_delta, | |
| 132 float page_scale, | |
| 133 float top_controls_delta) { | |
| 134 DCHECK_EQ(top_controls_delta, 0.0f); | |
| 135 DCHECK(elastic_overscroll_delta == gfx::Vector2dF()); | |
| 136 DCHECK(outer_delta == gfx::Vector2dF()); | |
| 137 | |
| 138 // The inner_delta can be ignored here, since we receive that in the scroll | |
| 139 // callback on the layer itself. | |
| 140 if (page_scale != 1.0f) { | |
| 141 LayerTree* layer_tree = layer_tree_host_->GetLayerTree(); | |
| 142 synced_page_scale_.UpdateDeltaFromImplThread( | |
| 143 layer_tree->page_scale_factor()); | |
| 144 layer_tree->SetPageScaleFactorAndLimits( | |
| 145 synced_page_scale_.EngineMain(), layer_tree->min_page_scale_factor(), | |
| 146 layer_tree->max_page_scale_factor()); | |
| 147 client_->DidUpdateLocalState(); | |
| 148 } | |
| 149 } | |
| 150 | |
| 151 void CompositorStateDeserializer::PullClientStateUpdate( | |
| 152 proto::ClientStateUpdate* client_state_update) { | |
| 153 for (auto& layer_it : engine_id_to_layer_) { | |
| 154 int engine_layer_id = layer_it.first; | |
| 155 auto& synced_scroll_offset = layer_it.second.synced_scroll_offset; | |
| 156 gfx::ScrollOffset scroll_offset_delta = | |
| 157 synced_scroll_offset.PullDeltaForEngineUpdate(); | |
| 158 gfx::Vector2dF scroll_delta_vector = | |
| 159 gfx::ScrollOffsetToVector2dF(scroll_offset_delta); | |
| 160 | |
| 161 if (scroll_delta_vector.IsZero()) { | |
| 162 continue; | |
| 163 } | |
| 164 | |
| 165 proto::ScrollUpdate* scroll_update = | |
| 166 client_state_update->add_scroll_updates(); | |
| 167 scroll_update->set_layer_id(engine_layer_id); | |
| 168 Vector2dFToProto(scroll_delta_vector, | |
| 169 scroll_update->mutable_scroll_delta()); | |
| 170 } | |
| 171 | |
| 172 float page_scale_delta = synced_page_scale_.PullDeltaForEngineUpdate(); | |
| 173 if (page_scale_delta != 1.0f) { | |
| 174 client_state_update->set_page_scale_delta(page_scale_delta); | |
| 175 } | |
| 176 } | |
| 177 | |
| 178 void CompositorStateDeserializer::DidApplyStateUpdatesOnEngine() { | |
| 179 for (auto& layer_it : engine_id_to_layer_) { | |
| 180 Layer* layer = layer_it.second.layer.get(); | |
| 181 auto& synced_scroll_offset = layer_it.second.synced_scroll_offset; | |
| 182 | |
| 183 synced_scroll_offset.DidApplySentDeltaOnEngine(); | |
| 184 layer->SetScrollOffset(synced_scroll_offset.EngineMain()); | |
| 185 } | |
| 186 | |
| 187 synced_page_scale_.DidApplySentDeltaOnEngine(); | |
| 188 LayerTree* layer_tree = layer_tree_host_->GetLayerTree(); | |
| 189 layer_tree->SetPageScaleFactorAndLimits(synced_page_scale_.EngineMain(), | |
| 190 layer_tree->min_page_scale_factor(), | |
| 191 layer_tree->max_page_scale_factor()); | |
| 192 } | |
| 193 | |
| 194 void CompositorStateDeserializer::SendUnappliedDeltasToLayerTreeHost() { | |
| 195 std::unique_ptr<ReflectedMainFrameState> reflected_main_frame_state = | |
| 196 base::MakeUnique<ReflectedMainFrameState>(); | |
| 197 | |
| 198 for (auto& layer_it : engine_id_to_layer_) { | |
| 199 Layer* layer = layer_it.second.layer.get(); | |
| 200 auto& synced_scroll_offset = layer_it.second.synced_scroll_offset; | |
| 201 | |
| 202 gfx::ScrollOffset scroll_offset_delta = | |
| 203 synced_scroll_offset.DeltaNotAppliedOnEngine(); | |
| 204 gfx::Vector2dF scroll_delta_vector = | |
| 205 gfx::ScrollOffsetToVector2dF(scroll_offset_delta); | |
| 206 if (scroll_delta_vector.IsZero()) | |
| 207 continue; | |
| 208 | |
| 209 ReflectedMainFrameState::ScrollUpdate scroll_update; | |
| 210 scroll_update.layer_id = layer->id(); | |
| 211 scroll_update.scroll_delta = scroll_delta_vector; | |
| 212 reflected_main_frame_state->scrolls.push_back(scroll_update); | |
| 213 } | |
| 214 | |
| 215 reflected_main_frame_state->page_scale_delta = | |
| 216 synced_page_scale_.DeltaNotAppliedOnEngine(); | |
| 217 layer_tree_host_->SetReflectedMainFrameState( | |
| 218 std::move(reflected_main_frame_state)); | |
| 219 } | |
| 220 | |
| 221 void CompositorStateDeserializer::SychronizeLayerTreeState( | |
| 222 const proto::LayerTree& layer_tree_proto) { | |
| 223 LayerTree* layer_tree = layer_tree_host_->GetLayerTree(); | |
| 224 | |
| 225 // Synchronize the tree hierarchy first. | |
| 226 // TODO(khushalsagar): Don't do this if the hierarchy didn't change. See | |
| 227 // crbug.com/605170. | |
| 228 EngineIdToLayerMap new_engine_id_to_layer; | |
| 229 ScrollbarLayerToScrollLayerId scrollbar_layer_to_scroll_layer; | |
| 230 if (layer_tree_proto.has_root_layer()) { | |
| 231 const proto::LayerNode& root_layer_node = layer_tree_proto.root_layer(); | |
| 232 layer_tree->SetRootLayer( | |
| 233 GetLayerAndAddToNewMap(root_layer_node, &new_engine_id_to_layer, | |
| 234 &scrollbar_layer_to_scroll_layer)); | |
| 235 SynchronizeLayerHierarchyRecursive(layer_tree->root_layer(), | |
| 236 root_layer_node, &new_engine_id_to_layer, | |
| 237 &scrollbar_layer_to_scroll_layer); | |
| 238 } else { | |
| 239 layer_tree->SetRootLayer(nullptr); | |
| 240 } | |
| 241 engine_id_to_layer_.swap(new_engine_id_to_layer); | |
| 242 | |
| 243 // Now that the tree has been synced, we can set up the scroll layers, since | |
| 244 // the corresponding engine layers have been created. | |
| 245 for (const auto& scrollbar : scrollbar_layer_to_scroll_layer) { | |
| 246 // This corresponds to the id of the Scrollbar Layer. | |
| 247 int scrollbar_layer_id = scrollbar.first; | |
| 248 | |
| 249 // This corresponds to the id of the scroll layer for this scrollbar. | |
| 250 int scroll_layer_id = scrollbar.second; | |
| 251 | |
| 252 SolidColorScrollbarLayer* scrollbar_layer = | |
| 253 static_cast<SolidColorScrollbarLayer*>( | |
| 254 GetLayerForEngineId(scrollbar_layer_id)); | |
| 255 | |
| 256 scrollbar_layer->SetScrollLayer(GetClientIdFromEngineId(scroll_layer_id)); | |
| 257 } | |
| 258 | |
| 259 // Synchronize rest of the tree state. | |
| 260 layer_tree->RegisterViewportLayers( | |
| 261 GetLayer(layer_tree_proto.overscroll_elasticity_layer_id()), | |
| 262 GetLayer(layer_tree_proto.page_scale_layer_id()), | |
| 263 GetLayer(layer_tree_proto.inner_viewport_scroll_layer_id()), | |
| 264 GetLayer(layer_tree_proto.outer_viewport_scroll_layer_id())); | |
| 265 | |
| 266 layer_tree->SetDeviceScaleFactor(layer_tree_proto.device_scale_factor()); | |
| 267 layer_tree->SetPaintedDeviceScaleFactor( | |
| 268 layer_tree_proto.painted_device_scale_factor()); | |
| 269 | |
| 270 float min_page_scale_factor = layer_tree_proto.min_page_scale_factor(); | |
| 271 float max_page_scale_factor = layer_tree_proto.max_page_scale_factor(); | |
| 272 float page_scale_factor = layer_tree_proto.page_scale_factor(); | |
| 273 synced_page_scale_.PushFromEngineMainThread(page_scale_factor); | |
| 274 layer_tree->SetPageScaleFactorAndLimits(synced_page_scale_.EngineMain(), | |
| 275 min_page_scale_factor, | |
| 276 max_page_scale_factor); | |
| 277 | |
| 278 layer_tree->set_background_color(layer_tree_proto.background_color()); | |
| 279 layer_tree->set_has_transparent_background( | |
| 280 layer_tree_proto.has_transparent_background()); | |
| 281 | |
| 282 LayerSelection selection; | |
| 283 LayerSelectionFromProtobuf(&selection, layer_tree_proto.selection()); | |
| 284 layer_tree->RegisterSelection(selection); | |
| 285 layer_tree->SetViewportSize( | |
| 286 ProtoToSize(layer_tree_proto.device_viewport_size())); | |
| 287 | |
| 288 layer_tree->SetHaveScrollEventHandlers( | |
| 289 layer_tree_proto.have_scroll_event_handlers()); | |
| 290 layer_tree->SetEventListenerProperties( | |
| 291 EventListenerClass::kMouseWheel, | |
| 292 static_cast<EventListenerProperties>( | |
| 293 layer_tree_proto.wheel_event_listener_properties())); | |
| 294 layer_tree->SetEventListenerProperties( | |
| 295 EventListenerClass::kTouchStartOrMove, | |
| 296 static_cast<EventListenerProperties>( | |
| 297 layer_tree_proto.touch_start_or_move_event_listener_properties())); | |
| 298 layer_tree->SetEventListenerProperties( | |
| 299 EventListenerClass::kTouchEndOrCancel, | |
| 300 static_cast<EventListenerProperties>( | |
| 301 layer_tree_proto.touch_end_or_cancel_event_listener_properties())); | |
| 302 } | |
| 303 | |
| 304 void CompositorStateDeserializer::SynchronizeLayerState( | |
| 305 const proto::LayerProperties& layer_properties_proto) { | |
| 306 int engine_layer_id = layer_properties_proto.id(); | |
| 307 Layer* layer = GetLayerForEngineId(engine_layer_id); | |
| 308 | |
| 309 // Layer Inputs ----------------------------------------------------- | |
| 310 const proto::BaseLayerProperties& base = layer_properties_proto.base(); | |
| 311 layer->SetNeedsDisplayRect(ProtoToRect(base.update_rect())); | |
| 312 layer->SetBounds(ProtoToSize(base.bounds())); | |
| 313 layer->SetMasksToBounds(base.masks_to_bounds()); | |
| 314 layer->SetOpacity(base.opacity()); | |
| 315 layer->SetBlendMode(SkXfermodeModeFromProto(base.blend_mode())); | |
| 316 layer->SetIsRootForIsolatedGroup(base.is_root_for_isolated_group()); | |
| 317 layer->SetContentsOpaque(base.contents_opaque()); | |
| 318 layer->SetPosition(ProtoToPointF(base.position())); | |
| 319 layer->SetTransform(ProtoToTransform(base.transform())); | |
| 320 layer->SetTransformOrigin(ProtoToPoint3F(base.transform_origin())); | |
| 321 layer->SetIsDrawable(base.is_drawable()); | |
| 322 layer->SetDoubleSided(base.double_sided()); | |
| 323 layer->SetShouldFlattenTransform(base.should_flatten_transform()); | |
| 324 layer->Set3dSortingContextId(base.sorting_context_id()); | |
| 325 layer->SetUseParentBackfaceVisibility(base.use_parent_backface_visibility()); | |
| 326 layer->SetBackgroundColor(base.background_color()); | |
| 327 | |
| 328 gfx::ScrollOffset engine_scroll_offset = | |
| 329 ProtoToScrollOffset(base.scroll_offset()); | |
| 330 SyncedRemoteScrollOffset& synced_scroll_offset = | |
| 331 GetLayerData(engine_layer_id)->synced_scroll_offset; | |
| 332 synced_scroll_offset.PushFromEngineMainThread(engine_scroll_offset); | |
| 333 layer->SetScrollOffset(synced_scroll_offset.EngineMain()); | |
| 334 | |
| 335 layer->SetScrollClipLayerId( | |
| 336 GetClientIdFromEngineId(base.scroll_clip_layer_id())); | |
| 337 layer->SetUserScrollable(base.user_scrollable_horizontal(), | |
| 338 base.user_scrollable_vertical()); | |
| 339 | |
| 340 if (layer->main_thread_scrolling_reasons()) { | |
| 341 layer->ClearMainThreadScrollingReasons( | |
| 342 layer->main_thread_scrolling_reasons()); | |
| 343 } | |
| 344 if (base.main_thread_scrolling_reasons()) { | |
| 345 layer->AddMainThreadScrollingReasons(base.main_thread_scrolling_reasons()); | |
| 346 } | |
| 347 | |
| 348 layer->SetNonFastScrollableRegion( | |
| 349 RegionFromProto(base.non_fast_scrollable_region())); | |
| 350 layer->SetTouchEventHandlerRegion( | |
| 351 RegionFromProto(base.touch_event_handler_region())); | |
| 352 | |
| 353 layer->SetIsContainerForFixedPositionLayers( | |
| 354 base.is_container_for_fixed_position_layers()); | |
| 355 | |
| 356 LayerPositionConstraint position_constraint; | |
| 357 position_constraint.FromProtobuf(base.position_constraint()); | |
| 358 layer->SetPositionConstraint(position_constraint); | |
| 359 | |
| 360 LayerStickyPositionConstraint sticky_position_constraint; | |
| 361 sticky_position_constraint.FromProtobuf(base.sticky_position_constraint()); | |
| 362 layer->SetStickyPositionConstraint(sticky_position_constraint); | |
| 363 layer->SetScrollParent(GetLayerForEngineId(base.scroll_parent_id())); | |
| 364 layer->SetClipParent(GetLayerForEngineId(base.clip_parent_id())); | |
| 365 | |
| 366 layer->SetHasWillChangeTransformHint(base.has_will_change_transform_hint()); | |
| 367 layer->SetHideLayerAndSubtree(base.hide_layer_and_subtree()); | |
| 368 | |
| 369 // ------------------------------------------------------------------ | |
| 370 | |
| 371 // PictureLayer Properties deserialization. | |
| 372 if (layer_properties_proto.has_picture()) { | |
| 373 const proto::PictureLayerProperties& picture_properties = | |
| 374 layer_properties_proto.picture(); | |
| 375 | |
| 376 // Only PictureLayers set picture. | |
| 377 PictureLayer* picture_layer = | |
| 378 static_cast<PictureLayer*>(GetLayerForEngineId(engine_layer_id)); | |
| 379 picture_layer->SetNearestNeighbor(picture_properties.nearest_neighbor()); | |
| 380 | |
| 381 gfx::Rect recorded_viewport = | |
| 382 ProtoToRect(picture_properties.recorded_viewport()); | |
| 383 scoped_refptr<DisplayItemList> display_list; | |
| 384 std::vector<uint32_t> used_engine_picture_ids; | |
| 385 if (picture_properties.has_display_list()) { | |
| 386 display_list = DisplayItemList::CreateFromProto( | |
| 387 picture_properties.display_list(), client_picture_cache_.get(), | |
| 388 &used_engine_picture_ids); | |
| 389 } else { | |
| 390 display_list = nullptr; | |
| 391 } | |
| 392 | |
| 393 // TODO(khushalsagar): The caching here is sub-optimal. If a layer does not | |
| 394 // PushProperties, its pictures won't get counted here even if the layer | |
| 395 // is drawn in the current frame. | |
| 396 for (uint32_t engine_picture_id : used_engine_picture_ids) | |
| 397 client_picture_cache_->MarkUsed(engine_picture_id); | |
| 398 | |
| 399 GetContentLayerClient(engine_layer_id) | |
| 400 ->UpdateDisplayListAndRecordedViewport(display_list, recorded_viewport); | |
| 401 } | |
| 402 } | |
| 403 | |
| 404 void CompositorStateDeserializer::SynchronizeLayerHierarchyRecursive( | |
| 405 Layer* layer, | |
| 406 const proto::LayerNode& layer_node, | |
| 407 EngineIdToLayerMap* new_layer_map, | |
| 408 ScrollbarLayerToScrollLayerId* scrollbar_layer_to_scroll_layer) { | |
| 409 layer->RemoveAllChildren(); | |
| 410 | |
| 411 // Children. | |
| 412 for (int i = 0; i < layer_node.children_size(); i++) { | |
| 413 const proto::LayerNode& child_layer_node = layer_node.children(i); | |
| 414 scoped_refptr<Layer> child_layer = GetLayerAndAddToNewMap( | |
| 415 child_layer_node, new_layer_map, scrollbar_layer_to_scroll_layer); | |
| 416 layer->AddChild(child_layer); | |
| 417 SynchronizeLayerHierarchyRecursive(child_layer.get(), child_layer_node, | |
| 418 new_layer_map, | |
| 419 scrollbar_layer_to_scroll_layer); | |
| 420 } | |
| 421 | |
| 422 // Mask Layer. | |
| 423 if (layer_node.has_mask_layer()) { | |
| 424 const proto::LayerNode& mask_layer_node = layer_node.mask_layer(); | |
| 425 scoped_refptr<Layer> mask_layer = GetLayerAndAddToNewMap( | |
| 426 mask_layer_node, new_layer_map, scrollbar_layer_to_scroll_layer); | |
| 427 layer->SetMaskLayer(mask_layer.get()); | |
| 428 SynchronizeLayerHierarchyRecursive(mask_layer.get(), mask_layer_node, | |
| 429 new_layer_map, | |
| 430 scrollbar_layer_to_scroll_layer); | |
| 431 } else { | |
| 432 layer->SetMaskLayer(nullptr); | |
| 433 } | |
| 434 | |
| 435 // Scroll callback. | |
| 436 layer->set_did_scroll_callback( | |
| 437 base::Bind(&CompositorStateDeserializer::LayerScrolled, | |
| 438 weak_factory_.GetWeakPtr(), layer_node.id())); | |
| 439 } | |
| 440 | |
| 441 scoped_refptr<Layer> CompositorStateDeserializer::GetLayerAndAddToNewMap( | |
| 442 const proto::LayerNode& layer_node, | |
| 443 EngineIdToLayerMap* new_layer_map, | |
| 444 ScrollbarLayerToScrollLayerId* scrollbar_layer_to_scroll_layer) { | |
| 445 DCHECK(new_layer_map->find(layer_node.id()) == new_layer_map->end()) | |
| 446 << "A LayerNode should have been de-serialized only once"; | |
| 447 | |
| 448 scoped_refptr<Layer> layer; | |
| 449 EngineIdToLayerMap::iterator layer_map_it = | |
| 450 engine_id_to_layer_.find(layer_node.id()); | |
| 451 | |
| 452 if (layer_map_it != engine_id_to_layer_.end()) { | |
| 453 // We can re-use the old layer. | |
| 454 layer = layer_map_it->second.layer; | |
| 455 (*new_layer_map)[layer_node.id()] = std::move(layer_map_it->second); | |
| 456 engine_id_to_layer_.erase(layer_map_it); | |
| 457 return layer; | |
| 458 } | |
| 459 | |
| 460 // We need to create a new layer. | |
| 461 auto& layer_data = (*new_layer_map)[layer_node.id()]; | |
| 462 switch (layer_node.type()) { | |
| 463 case proto::LayerNode::UNKNOWN: | |
| 464 NOTREACHED() << "Unknown Layer type"; | |
| 465 case proto::LayerNode::LAYER: | |
| 466 layer_data.layer = layer_factory_->CreateLayer(layer_node.id()); | |
| 467 break; | |
| 468 case proto::LayerNode::PICTURE_LAYER: | |
| 469 layer_data.content_layer_client = | |
| 470 base::MakeUnique<DeserializedContentLayerClient>(); | |
| 471 layer_data.layer = layer_factory_->CreatePictureLayer( | |
| 472 layer_node.id(), layer_data.content_layer_client.get()); | |
| 473 break; | |
| 474 case proto::LayerNode::FAKE_PICTURE_LAYER: | |
| 475 // FAKE_PICTURE_LAYER is for testing only. | |
| 476 layer_data.content_layer_client = | |
| 477 base::MakeUnique<DeserializedContentLayerClient>(); | |
| 478 layer_data.layer = layer_factory_->CreateFakePictureLayer( | |
| 479 layer_node.id(), layer_data.content_layer_client.get()); | |
| 480 break; | |
| 481 case proto::LayerNode::SOLID_COLOR_SCROLLBAR_LAYER: { | |
| 482 // SolidColorScrollbarLayers attach their properties in the LayerNode | |
| 483 // itself. | |
| 484 const proto::SolidColorScrollbarLayerProperties& scrollbar = | |
| 485 layer_node.solid_scrollbar(); | |
| 486 | |
| 487 DCHECK(scrollbar_layer_to_scroll_layer->find(layer_node.id()) == | |
| 488 scrollbar_layer_to_scroll_layer->end()); | |
| 489 int scroll_layer_id = scrollbar.scroll_layer_id(); | |
| 490 (*scrollbar_layer_to_scroll_layer)[layer_node.id()] = scroll_layer_id; | |
| 491 | |
| 492 int thumb_thickness = scrollbar.thumb_thickness(); | |
| 493 int track_start = scrollbar.track_start(); | |
| 494 bool is_left_side_vertical_scrollbar = | |
| 495 scrollbar.is_left_side_vertical_scrollbar(); | |
| 496 ScrollbarOrientation orientation = | |
| 497 ScrollbarOrientationFromProto(scrollbar.orientation()); | |
| 498 | |
| 499 // We use the invalid id for the |scroll_layer_id| because the | |
| 500 // corresponding layer on the client may not have been created yet. | |
| 501 layer_data.layer = layer_factory_->CreateSolidColorScrollbarLayer( | |
| 502 layer_node.id(), orientation, thumb_thickness, track_start, | |
| 503 is_left_side_vertical_scrollbar, Layer::LayerIdLabels::INVALID_ID); | |
| 504 } break; | |
| 505 case proto::LayerNode::PUSH_PROPERTIES_COUNTING_LAYER: | |
| 506 // PUSH_PROPERTIES_COUNTING_LAYER is for testing only. | |
| 507 layer_data.layer = | |
| 508 layer_factory_->CreatePushPropertiesCountingLayer(layer_node.id()); | |
| 509 break; | |
| 510 } | |
| 511 | |
| 512 layer = layer_data.layer; | |
| 513 return layer; | |
| 514 } | |
| 515 | |
| 516 void CompositorStateDeserializer::LayerScrolled(int engine_layer_id) { | |
| 517 LayerData* layer_data = GetLayerData(engine_layer_id); | |
| 518 Layer* layer = layer_data->layer.get(); | |
| 519 SyncedRemoteScrollOffset& synced_scroll_offset = | |
| 520 layer_data->synced_scroll_offset; | |
| 521 synced_scroll_offset.UpdateDeltaFromImplThread(layer->scroll_offset()); | |
| 522 layer->SetScrollOffset(synced_scroll_offset.EngineMain()); | |
| 523 client_->DidUpdateLocalState(); | |
| 524 } | |
| 525 | |
| 526 int CompositorStateDeserializer::GetClientIdFromEngineId( | |
| 527 int engine_layer_id) const { | |
| 528 Layer* layer = GetLayerForEngineId(engine_layer_id); | |
| 529 return layer ? layer->id() : Layer::LayerIdLabels::INVALID_ID; | |
| 530 } | |
| 531 | |
| 532 scoped_refptr<Layer> CompositorStateDeserializer::GetLayer( | |
| 533 int engine_layer_id) const { | |
| 534 EngineIdToLayerMap::const_iterator layer_it = | |
| 535 engine_id_to_layer_.find(engine_layer_id); | |
| 536 return layer_it != engine_id_to_layer_.end() ? layer_it->second.layer | |
| 537 : nullptr; | |
| 538 } | |
| 539 | |
| 540 DeserializedContentLayerClient* | |
| 541 CompositorStateDeserializer::GetContentLayerClient(int engine_layer_id) const { | |
| 542 EngineIdToLayerMap::const_iterator layer_it = | |
| 543 engine_id_to_layer_.find(engine_layer_id); | |
| 544 return layer_it != engine_id_to_layer_.end() | |
| 545 ? layer_it->second.content_layer_client.get() | |
| 546 : nullptr; | |
| 547 } | |
| 548 | |
| 549 CompositorStateDeserializer::LayerData* | |
| 550 CompositorStateDeserializer::GetLayerData(int engine_layer_id) { | |
| 551 EngineIdToLayerMap::iterator layer_it = | |
| 552 engine_id_to_layer_.find(engine_layer_id); | |
| 553 return layer_it != engine_id_to_layer_.end() ? &layer_it->second : nullptr; | |
| 554 } | |
| 555 | |
| 556 } // namespace cc | |
| OLD | NEW |