Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(308)

Side by Side Diff: services/ui/view_manager/view_registry.cc

Issue 1552043002: Make Mozart view manager use the new compositor. (Closed) Base URL: git@github.com:domokit/mojo.git@moz-12
Patch Set: Created 4 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2015 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 "services/ui/view_manager/view_registry.h"
6
5 #include <algorithm> 7 #include <algorithm>
6 #include <utility> 8 #include <utility>
7 9
8 #include "base/bind.h" 10 #include "base/bind.h"
9 #include "base/bind_helpers.h" 11 #include "base/bind_helpers.h"
10 #include "services/ui/view_manager/surface_manager.h" 12 #include "mojo/services/ui/views/cpp/logging.h"
11 #include "services/ui/view_manager/view_host_impl.h" 13 #include "services/ui/view_manager/view_host_impl.h"
12 #include "services/ui/view_manager/view_registry.h"
13 #include "services/ui/view_manager/view_tree_host_impl.h" 14 #include "services/ui/view_manager/view_tree_host_impl.h"
14 15
15 namespace view_manager { 16 namespace view_manager {
16 17
17 static bool AreViewLayoutParamsValid(const mojo::ui::ViewLayoutParams* params) { 18 static bool AreViewLayoutParamsValid(const mojo::ui::ViewLayoutParams* params) {
18 return params && params->constraints && params->constraints->min_width >= 0 && 19 return params && params->constraints && params->constraints->min_width >= 0 &&
19 params->constraints->max_width >= params->constraints->min_width && 20 params->constraints->max_width >= params->constraints->min_width &&
20 params->constraints->min_height >= 0 && 21 params->constraints->min_height >= 0 &&
21 params->constraints->max_height >= params->constraints->min_height && 22 params->constraints->max_height >= params->constraints->min_height &&
22 params->device_pixel_ratio > 0; 23 params->device_pixel_ratio > 0;
23 } 24 }
24 25
25 static std::ostream& operator<<(std::ostream& os, const mojo::Size* size) { 26 ViewRegistry::ViewRegistry(mojo::gfx::composition::CompositorPtr compositor)
26 return size 27 : compositor_(compositor.Pass()) {}
27 ? os << "{width=" << size->width << ", height=" << size->height
28 << "}"
29 : os << "{null}";
30 }
31
32 static std::ostream& operator<<(std::ostream& os,
33 const mojo::SurfaceId* surface_id) {
34 return surface_id
35 ? os << "{id_namespace=" << surface_id->id_namespace
36 << ", local=" << surface_id->local << "}"
37 : os << "{null}";
38 }
39
40 static std::ostream& operator<<(std::ostream& os,
41 const mojo::ui::ViewToken* token) {
42 return token ? os << "{token=" << token->value << "}" : os << "{null}";
43 }
44
45 static std::ostream& operator<<(std::ostream& os, const ViewState* view_state) {
46 return view_state ? os << "{token=" << view_state->view_token_value() << "}"
47 : os << "{null}";
48 }
49
50 static std::ostream& operator<<(std::ostream& os,
51 const mojo::ui::BoxConstraints* constraints) {
52 return constraints
53 ? os << "{min_width=" << constraints->min_width
54 << ", max_width=" << constraints->max_width
55 << ", min_height=" << constraints->min_height
56 << ", max_height=" << constraints->max_height << "}"
57 : os << "{null}";
58 };
59
60 static std::ostream& operator<<(std::ostream& os,
61 const mojo::ui::ViewLayoutParams* params) {
62 return params
63 ? os << "{constraints=" << params->constraints.get()
64 << ", device_pixel_ratio=" << params->device_pixel_ratio
65 << "}"
66 : os << "{null}";
67 }
68
69 static std::ostream& operator<<(std::ostream& os,
70 const mojo::ui::ViewLayoutInfo* info) {
71 return info
72 ? os << "{size=" << info->size.get()
73 << ", surface_id=" << info->surface_id.get() << "}"
74 : os << "{null}";
75 }
76
77 ViewRegistry::ViewRegistry(SurfaceManager* surface_manager)
78 : surface_manager_(surface_manager), next_view_token_value_(1u) {}
79 28
80 ViewRegistry::~ViewRegistry() {} 29 ViewRegistry::~ViewRegistry() {}
81 30
31 void ViewRegistry::ConnectAssociates(
32 mojo::ApplicationImpl* app_impl,
33 const std::vector<std::string>& urls,
34 const AssociateConnectionErrorCallback& connection_error_callback) {
35 associate_table_.ConnectAssociates(app_impl, this, urls,
36 connection_error_callback);
37 }
38
82 mojo::ui::ViewTokenPtr ViewRegistry::RegisterView( 39 mojo::ui::ViewTokenPtr ViewRegistry::RegisterView(
83 mojo::ui::ViewPtr view, 40 mojo::ui::ViewPtr view,
84 mojo::InterfaceRequest<mojo::ui::ViewHost> view_host_request) { 41 mojo::InterfaceRequest<mojo::ui::ViewHost> view_host_request,
42 const mojo::String& label) {
85 DCHECK(view); 43 DCHECK(view);
86 uint32_t view_token_value = next_view_token_value_++; 44
87 DCHECK(!FindView(view_token_value)); 45 auto view_token = mojo::ui::ViewToken::New();
46 view_token->value = next_view_token_value_++;
47 CHECK(view_token->value);
48 CHECK(!FindView(view_token->value));
88 49
89 // Create the state and bind host to it. 50 // Create the state and bind host to it.
90 ViewState* view_state = new ViewState(view.Pass(), view_token_value); 51 std::string sanitized_label =
52 label.get().substr(0, mojo::ui::kLabelMaxLength);
53 ViewState* view_state =
54 new ViewState(view.Pass(), view_token.Pass(), sanitized_label);
91 ViewHostImpl* view_host = 55 ViewHostImpl* view_host =
92 new ViewHostImpl(this, view_state, view_host_request.Pass()); 56 new ViewHostImpl(this, view_state, view_host_request.Pass());
93 view_state->set_view_host(view_host); 57 view_state->set_view_host(view_host);
94 view_state->set_view_connection_error_handler( 58 view_state->set_view_connection_error_handler(
95 base::Bind(&ViewRegistry::OnViewConnectionError, base::Unretained(this), 59 base::Bind(&ViewRegistry::OnViewConnectionError, base::Unretained(this),
96 view_state)); 60 view_state));
97 view_host->set_view_host_connection_error_handler( 61 view_host->set_view_host_connection_error_handler(
98 base::Bind(&ViewRegistry::OnViewConnectionError, base::Unretained(this), 62 base::Bind(&ViewRegistry::OnViewConnectionError, base::Unretained(this),
99 view_state)); 63 view_state));
100 64
101 // Add to registry and return token. 65 // Add to registry and return token.
102 views_by_token_.insert({view_token_value, view_state}); 66 views_by_token_.insert({view_state->view_token()->value, view_state});
103 mojo::ui::ViewTokenPtr token = mojo::ui::ViewToken::New();
104 token->value = view_state->view_token_value();
105 DVLOG(1) << "RegisterView: view=" << view_state; 67 DVLOG(1) << "RegisterView: view=" << view_state;
106 return token; 68 return view_state->view_token()->Clone();
107 } 69 }
108 70
109 void ViewRegistry::OnViewConnectionError(ViewState* view_state) { 71 void ViewRegistry::OnViewConnectionError(ViewState* view_state) {
110 DCHECK(IsViewStateRegisteredDebug(view_state)); 72 DCHECK(IsViewStateRegisteredDebug(view_state));
111 DVLOG(1) << "OnViewConnectionError: view=" << view_state; 73 DVLOG(1) << "OnViewConnectionError: view=" << view_state;
112 74
113 UnregisterView(view_state); 75 UnregisterView(view_state);
114 } 76 }
115 77
116 void ViewRegistry::UnregisterView(ViewState* view_state) { 78 void ViewRegistry::UnregisterView(ViewState* view_state) {
117 DCHECK(IsViewStateRegisteredDebug(view_state)); 79 DCHECK(IsViewStateRegisteredDebug(view_state));
118 DVLOG(1) << "UnregisterView: view=" << view_state; 80 DVLOG(1) << "UnregisterView: view=" << view_state;
119 81
120 // Remove from parent or roots. 82 // Remove from parent or roots.
121 HijackView(view_state); 83 HijackView(view_state);
122 84
123 // Remove from registry. 85 // Remove from registry.
124 views_by_token_.erase(view_state->view_token_value()); 86 views_by_token_.erase(view_state->view_token()->value);
125 delete view_state; 87 delete view_state;
126 } 88 }
127 89
128 void ViewRegistry::RegisterViewTree( 90 mojo::ui::ViewTreeTokenPtr ViewRegistry::RegisterViewTree(
129 mojo::ui::ViewTreePtr view_tree, 91 mojo::ui::ViewTreePtr view_tree,
130 mojo::InterfaceRequest<mojo::ui::ViewTreeHost> view_tree_host_request) { 92 mojo::InterfaceRequest<mojo::ui::ViewTreeHost> view_tree_host_request,
93 const mojo::String& label) {
131 DCHECK(view_tree); 94 DCHECK(view_tree);
132 95
96 auto view_tree_token = mojo::ui::ViewTreeToken::New();
97 view_tree_token->value = next_view_tree_token_value_++;
98 CHECK(view_tree_token->value);
99 CHECK(!FindViewTree(view_tree_token->value));
100
133 // Create the state and bind host to it. 101 // Create the state and bind host to it.
134 ViewTreeState* tree_state = new ViewTreeState(view_tree.Pass()); 102 std::string sanitized_label =
103 label.get().substr(0, mojo::ui::kLabelMaxLength);
104 ViewTreeState* tree_state = new ViewTreeState(
105 view_tree.Pass(), view_tree_token.Pass(), sanitized_label);
135 ViewTreeHostImpl* tree_host = 106 ViewTreeHostImpl* tree_host =
136 new ViewTreeHostImpl(this, tree_state, view_tree_host_request.Pass()); 107 new ViewTreeHostImpl(this, tree_state, view_tree_host_request.Pass());
137 tree_state->set_view_tree_host(tree_host); 108 tree_state->set_view_tree_host(tree_host);
138 tree_state->set_view_tree_connection_error_handler( 109 tree_state->set_view_tree_connection_error_handler(
139 base::Bind(&ViewRegistry::OnViewTreeConnectionError, 110 base::Bind(&ViewRegistry::OnViewTreeConnectionError,
140 base::Unretained(this), tree_state)); 111 base::Unretained(this), tree_state));
141 tree_host->set_view_tree_host_connection_error_handler( 112 tree_host->set_view_tree_host_connection_error_handler(
142 base::Bind(&ViewRegistry::OnViewTreeConnectionError, 113 base::Bind(&ViewRegistry::OnViewTreeConnectionError,
143 base::Unretained(this), tree_state)); 114 base::Unretained(this), tree_state));
144 115
145 // Add to registry. 116 // Add to registry.
146 view_trees_.push_back(tree_state); 117 view_trees_by_token_.insert(
118 {tree_state->view_tree_token()->value, tree_state});
147 DVLOG(1) << "RegisterViewTree: tree=" << tree_state; 119 DVLOG(1) << "RegisterViewTree: tree=" << tree_state;
120 return tree_state->view_tree_token()->Clone();
148 } 121 }
149 122
150 void ViewRegistry::OnViewTreeConnectionError(ViewTreeState* tree_state) { 123 void ViewRegistry::OnViewTreeConnectionError(ViewTreeState* tree_state) {
151 DCHECK(IsViewTreeStateRegisteredDebug(tree_state)); 124 DCHECK(IsViewTreeStateRegisteredDebug(tree_state));
152 DVLOG(1) << "OnViewTreeConnectionError: tree=" << tree_state; 125 DVLOG(1) << "OnViewTreeConnectionError: tree=" << tree_state;
153 126
154 UnregisterViewTree(tree_state); 127 UnregisterViewTree(tree_state);
155 } 128 }
156 129
157 void ViewRegistry::UnregisterViewTree(ViewTreeState* tree_state) { 130 void ViewRegistry::UnregisterViewTree(ViewTreeState* tree_state) {
158 DCHECK(IsViewTreeStateRegisteredDebug(tree_state)); 131 DCHECK(IsViewTreeStateRegisteredDebug(tree_state));
159 DVLOG(1) << "UnregisterViewTree: tree=" << tree_state; 132 DVLOG(1) << "UnregisterViewTree: tree=" << tree_state;
160 133
161 // Unlink the root if needed. 134 // Unlink the root if needed.
162 if (tree_state->root()) 135 if (tree_state->root())
163 UnlinkRoot(tree_state); 136 UnlinkRoot(tree_state);
164 137
165 // Remove from registry. 138 // Remove from registry.
166 view_trees_.erase(std::find_if( 139 view_trees_by_token_.erase(tree_state->view_tree_token()->value);
167 view_trees_.begin(), view_trees_.end(),
168 [tree_state](ViewTreeState* other) { return tree_state == other; }));
169 delete tree_state; 140 delete tree_state;
170 } 141 }
171 142
143 void ViewRegistry::CreateScene(
144 ViewState* view_state,
145 mojo::InterfaceRequest<mojo::gfx::composition::Scene> scene) {
146 DCHECK(IsViewStateRegisteredDebug(view_state));
147 DVLOG(1) << "CreateScene: view=" << view_state;
148
149 compositor_->CreateScene(
150 scene.Pass(), view_state->label(),
151 base::Bind(&ViewRegistry::OnSceneCreated, base::Unretained(this),
152 view_state->GetWeakPtr()));
153 }
154
155 void ViewRegistry::OnSceneCreated(
156 base::WeakPtr<ViewState> view_state_weak,
157 mojo::gfx::composition::SceneTokenPtr scene_token) {
158 DCHECK(scene_token);
159 ViewState* view_state = view_state_weak.get();
160 if (view_state) {
161 DVLOG(1) << "OnSceneCreated: scene_token=" << scene_token;
162
163 view_state->set_scene_token(scene_token.Pass());
164 view_state->set_scene_changed_since_last_report(true);
165 InvalidateLayout(view_state);
166 }
167 }
168
172 void ViewRegistry::RequestLayout(ViewState* view_state) { 169 void ViewRegistry::RequestLayout(ViewState* view_state) {
173 DCHECK(IsViewStateRegisteredDebug(view_state)); 170 DCHECK(IsViewStateRegisteredDebug(view_state));
174 DVLOG(1) << "RequestLayout: view=" << view_state; 171 DVLOG(1) << "RequestLayout: view=" << view_state;
175 172
176 InvalidateLayout(view_state); 173 InvalidateLayout(view_state);
177 } 174 }
178 175
179 void ViewRegistry::AddChild(ViewState* parent_state, 176 void ViewRegistry::AddChild(ViewState* parent_state,
180 uint32_t child_key, 177 uint32_t child_key,
181 mojo::ui::ViewTokenPtr child_view_token) { 178 mojo::ui::ViewTokenPtr child_view_token) {
182 DCHECK(IsViewStateRegisteredDebug(parent_state)); 179 DCHECK(IsViewStateRegisteredDebug(parent_state));
183 DCHECK(child_view_token); 180 DCHECK(child_view_token);
184 DVLOG(1) << "AddChild: parent=" << parent_state << ", child_key=" << child_key 181 DVLOG(1) << "AddChild: parent=" << parent_state << ", child_key=" << child_key
185 << ", child=" << child_view_token.get(); 182 << ", child=" << child_view_token;
186 183
187 // Check for duplicate children. 184 // Check for duplicate children.
188 if (parent_state->children().find(child_key) != 185 if (parent_state->children().find(child_key) !=
189 parent_state->children().end()) { 186 parent_state->children().end()) {
190 LOG(ERROR) << "View attempted to add a child with a duplicate key: " 187 LOG(ERROR) << "View attempted to add a child with a duplicate key: "
191 << "parent=" << parent_state << ", child_key=" << child_key 188 << "parent=" << parent_state << ", child_key=" << child_key
192 << ", child=" << child_view_token.get(); 189 << ", child=" << child_view_token;
193 UnregisterView(parent_state); 190 UnregisterView(parent_state);
194 return; 191 return;
195 } 192 }
196 193
197 // Check whether the desired child view still exists. 194 // Check whether the desired child view still exists.
198 // Adding a non-existent child still succeeds but the view manager will 195 // Adding a non-existent child still succeeds but the view manager will
199 // immediately report it as being unavailable. 196 // immediately report it as being unavailable.
200 ViewState* child_state = FindView(child_view_token->value); 197 ViewState* child_state = FindView(child_view_token->value);
201 if (!child_state) { 198 if (!child_state) {
202 LinkChildAsUnavailable(parent_state, child_key); 199 LinkChildAsUnavailable(parent_state, child_key);
(...skipping 30 matching lines...) Expand all
233 void ViewRegistry::LayoutChild( 230 void ViewRegistry::LayoutChild(
234 ViewState* parent_state, 231 ViewState* parent_state,
235 uint32_t child_key, 232 uint32_t child_key,
236 mojo::ui::ViewLayoutParamsPtr child_layout_params, 233 mojo::ui::ViewLayoutParamsPtr child_layout_params,
237 const ViewLayoutCallback& callback) { 234 const ViewLayoutCallback& callback) {
238 DCHECK(IsViewStateRegisteredDebug(parent_state)); 235 DCHECK(IsViewStateRegisteredDebug(parent_state));
239 DCHECK(child_layout_params); 236 DCHECK(child_layout_params);
240 DCHECK(child_layout_params->constraints); 237 DCHECK(child_layout_params->constraints);
241 DVLOG(1) << "LayoutChild: parent=" << parent_state 238 DVLOG(1) << "LayoutChild: parent=" << parent_state
242 << ", child_key=" << child_key 239 << ", child_key=" << child_key
243 << ", child_layout_params=" << child_layout_params.get(); 240 << ", child_layout_params=" << child_layout_params;
244 241
245 // Check whether the layout parameters are well-formed. 242 // Check whether the layout parameters are well-formed.
246 if (!AreViewLayoutParamsValid(child_layout_params.get())) { 243 if (!AreViewLayoutParamsValid(child_layout_params.get())) {
247 LOG(ERROR) << "View provided invalid child layout parameters: " 244 LOG(ERROR) << "View provided invalid child layout parameters: "
248 << "parent=" << parent_state << ", child_key=" << child_key 245 << "parent=" << parent_state << ", child_key=" << child_key
249 << ", child_layout_params=" << child_layout_params.get(); 246 << ", child_layout_params=" << child_layout_params;
250 UnregisterView(parent_state); 247 UnregisterView(parent_state);
251 callback.Run(nullptr); 248 callback.Run(nullptr);
252 return; 249 return;
253 } 250 }
254 251
255 // Check whether the child key exists in the parent. 252 // Check whether the child key exists in the parent.
256 auto child_it = parent_state->children().find(child_key); 253 auto child_it = parent_state->children().find(child_key);
257 if (child_it == parent_state->children().end()) { 254 if (child_it == parent_state->children().end()) {
258 LOG(ERROR) << "View attempted to layout a child with an invalid key: " 255 LOG(ERROR) << "View attempted to layout a child with an invalid key: "
259 << "parent=" << parent_state << ", child_key=" << child_key 256 << "parent=" << parent_state << ", child_key=" << child_key
260 << ", child_layout_params=" << child_layout_params.get(); 257 << ", child_layout_params=" << child_layout_params;
261 UnregisterView(parent_state); 258 UnregisterView(parent_state);
262 callback.Run(nullptr); 259 callback.Run(nullptr);
263 return; 260 return;
264 } 261 }
265 262
266 SetLayout(child_it->second, child_layout_params.Pass(), callback); 263 SetLayout(child_it->second, child_layout_params.Pass(), callback);
267 } 264 }
268 265
266 void ViewRegistry::ConnectToViewService(
267 ViewState* view_state,
268 const mojo::String& service_name,
269 mojo::ScopedMessagePipeHandle client_handle) {
270 DCHECK(IsViewStateRegisteredDebug(view_state));
271
272 associate_table_.ConnectToViewService(view_state->view_token()->Clone(),
273 service_name, client_handle.Pass());
274 }
275
269 void ViewRegistry::RequestLayout(ViewTreeState* tree_state) { 276 void ViewRegistry::RequestLayout(ViewTreeState* tree_state) {
270 DCHECK(IsViewTreeStateRegisteredDebug(tree_state)); 277 DCHECK(IsViewTreeStateRegisteredDebug(tree_state));
271 DVLOG(1) << "RequestLayout: tree=" << tree_state; 278 DVLOG(1) << "RequestLayout: tree=" << tree_state;
272 279
273 InvalidateLayoutForRoot(tree_state); 280 InvalidateLayoutForRoot(tree_state);
274 } 281 }
275 282
276 void ViewRegistry::SetRoot(ViewTreeState* tree_state, 283 void ViewRegistry::SetRoot(ViewTreeState* tree_state,
277 uint32_t root_key, 284 uint32_t root_key,
278 mojo::ui::ViewTokenPtr root_view_token) { 285 mojo::ui::ViewTokenPtr root_view_token) {
279 DCHECK(IsViewTreeStateRegisteredDebug(tree_state)); 286 DCHECK(IsViewTreeStateRegisteredDebug(tree_state));
280 DCHECK(root_view_token); 287 DCHECK(root_view_token);
281 DVLOG(1) << "SetRoot: tree=" << tree_state << ", root_key=" << root_key 288 DVLOG(1) << "SetRoot: tree=" << tree_state << ", root_key=" << root_key
282 << ", root=" << root_view_token.get(); 289 << ", root=" << root_view_token;
283 290
284 // Check whether the desired root view still exists. 291 // Check whether the desired root view still exists.
285 // Using a non-existent root view still succeeds but the view manager will 292 // Using a non-existent root view still succeeds but the view manager will
286 // immediately report it as being unavailable. 293 // immediately report it as being unavailable.
287 ViewState* root_state = FindView(root_view_token->value); 294 ViewState* root_state = FindView(root_view_token->value);
288 if (root_state) { 295 if (root_state) {
289 HijackView(root_state); 296 HijackView(root_state);
290 LinkRoot(tree_state, root_state, root_key); 297 LinkRoot(tree_state, root_state, root_key);
291 } else { 298 } else {
292 SendRootUnavailable(tree_state, root_key); 299 SendRootUnavailable(tree_state, root_key);
(...skipping 10 matching lines...) Expand all
303 tree_state->set_explicit_root(false); 310 tree_state->set_explicit_root(false);
304 } 311 }
305 312
306 void ViewRegistry::LayoutRoot(ViewTreeState* tree_state, 313 void ViewRegistry::LayoutRoot(ViewTreeState* tree_state,
307 mojo::ui::ViewLayoutParamsPtr root_layout_params, 314 mojo::ui::ViewLayoutParamsPtr root_layout_params,
308 const ViewLayoutCallback& callback) { 315 const ViewLayoutCallback& callback) {
309 DCHECK(IsViewTreeStateRegisteredDebug(tree_state)); 316 DCHECK(IsViewTreeStateRegisteredDebug(tree_state));
310 DCHECK(root_layout_params); 317 DCHECK(root_layout_params);
311 DCHECK(root_layout_params->constraints); 318 DCHECK(root_layout_params->constraints);
312 DVLOG(1) << "LayoutRoot: tree=" << tree_state 319 DVLOG(1) << "LayoutRoot: tree=" << tree_state
313 << ", root_layout_params=" << root_layout_params.get(); 320 << ", root_layout_params=" << root_layout_params;
314 321
315 // Check whether the layout parameters are well-formed. 322 // Check whether the layout parameters are well-formed.
316 if (!AreViewLayoutParamsValid(root_layout_params.get())) { 323 if (!AreViewLayoutParamsValid(root_layout_params.get())) {
317 LOG(ERROR) << "View tree provided invalid root layout parameters: " 324 LOG(ERROR) << "View tree provided invalid root layout parameters: "
318 << "tree=" << tree_state 325 << "tree=" << tree_state
319 << ", root_layout_params=" << root_layout_params.get(); 326 << ", root_layout_params=" << root_layout_params;
320 UnregisterViewTree(tree_state); 327 UnregisterViewTree(tree_state);
321 callback.Run(nullptr); 328 callback.Run(nullptr);
322 return; 329 return;
323 } 330 }
324 331
325 // Check whether the client called LayoutRoot without first having actually 332 // Check whether the client called LayoutRoot without first having actually
326 // set a root. 333 // set a root.
327 if (!tree_state->explicit_root()) { 334 if (!tree_state->explicit_root()) {
328 LOG(ERROR) << "View tree attempted to layout the rout without having " 335 LOG(ERROR) << "View tree attempted to layout the rout without having "
329 "set one first: tree=" 336 "set one first: tree="
330 << tree_state 337 << tree_state << ", root_layout_params=" << root_layout_params;
331 << ", root_layout_params=" << root_layout_params.get();
332 UnregisterViewTree(tree_state); 338 UnregisterViewTree(tree_state);
333 callback.Run(nullptr); 339 callback.Run(nullptr);
334 return; 340 return;
335 } 341 }
336 342
337 // Check whether the root is unavailable and therefore cannot be laid out. 343 // Check whether the root is unavailable and therefore cannot be laid out.
338 // This is not an error. 344 // This is not an error.
339 if (!tree_state->root()) { 345 if (!tree_state->root()) {
340 callback.Run(nullptr); 346 callback.Run(nullptr);
341 return; 347 return;
342 } 348 }
343 349
344 SetLayout(tree_state->root(), root_layout_params.Pass(), callback); 350 SetLayout(tree_state->root(), root_layout_params.Pass(), callback);
345 } 351 }
346 352
347 ViewState* ViewRegistry::FindView(uint32_t view_token) { 353 void ViewRegistry::ConnectToViewTreeService(
348 auto it = views_by_token_.find(view_token); 354 ViewTreeState* tree_state,
355 const mojo::String& service_name,
356 mojo::ScopedMessagePipeHandle client_handle) {
357 DCHECK(IsViewTreeStateRegisteredDebug(tree_state));
358
359 associate_table_.ConnectToViewTreeService(
360 tree_state->view_tree_token()->Clone(), service_name,
361 client_handle.Pass());
362 }
363
364 ViewState* ViewRegistry::FindView(uint32_t view_token_value) {
365 auto it = views_by_token_.find(view_token_value);
349 return it != views_by_token_.end() ? it->second : nullptr; 366 return it != views_by_token_.end() ? it->second : nullptr;
350 } 367 }
351 368
352 void ViewRegistry::LinkChild(ViewState* parent_state, 369 void ViewRegistry::LinkChild(ViewState* parent_state,
353 uint32_t child_key, 370 uint32_t child_key,
354 ViewState* child_state) { 371 ViewState* child_state) {
355 DCHECK(IsViewStateRegisteredDebug(parent_state)); 372 DCHECK(IsViewStateRegisteredDebug(parent_state));
356 DCHECK(parent_state->children().find(child_key) == 373 DCHECK(parent_state->children().find(child_key) ==
357 parent_state->children().end()); 374 parent_state->children().end());
358 DCHECK(IsViewStateRegisteredDebug(child_state)); 375 DCHECK(IsViewStateRegisteredDebug(child_state));
359 376
360 DVLOG(2) << "Added child " << child_key << " {" 377 DVLOG(2) << "Added child " << child_key << " {" << child_state->label()
361 << child_state->view_token_value() << "} to parent {" 378 << "} to parent {" << parent_state->label() << "}";
362 << parent_state->view_token_value() << "}";
363 379
364 parent_state->children().insert({child_key, child_state}); 380 parent_state->children().insert({child_key, child_state});
365 child_state->SetParent(parent_state, child_key); 381 child_state->SetParent(parent_state, child_key);
366 382
367 // Schedule layout of the parent on behalf of its newly added child. 383 // Schedule layout of the parent on behalf of its newly added child.
368 // We don't need to schedule layout of the child until the parent provides 384 // We don't need to schedule layout of the child until the parent provides
369 // new layout parameters. 385 // new layout parameters.
370 InvalidateLayoutForChild(parent_state, child_key); 386 InvalidateLayoutForChild(parent_state, child_key);
371 } 387 }
372 388
373 void ViewRegistry::LinkChildAsUnavailable(ViewState* parent_state, 389 void ViewRegistry::LinkChildAsUnavailable(ViewState* parent_state,
374 uint32_t child_key) { 390 uint32_t child_key) {
375 DCHECK(IsViewStateRegisteredDebug(parent_state)); 391 DCHECK(IsViewStateRegisteredDebug(parent_state));
376 DCHECK(parent_state->children().find(child_key) == 392 DCHECK(parent_state->children().find(child_key) ==
377 parent_state->children().end()); 393 parent_state->children().end());
378 394
379 DVLOG(2) << "Added unavailable child " << child_key << " to parent {" 395 DVLOG(2) << "Added unavailable child " << child_key << " to parent {"
380 << parent_state->view_token_value() << "}"; 396 << parent_state->label() << "}";
381 397
382 parent_state->children().insert({child_key, nullptr}); 398 parent_state->children().insert({child_key, nullptr});
383 SendChildUnavailable(parent_state, child_key); 399 SendChildUnavailable(parent_state, child_key);
384 400
385 // Don't schedule layout for the parent just yet. Wait for it to 401 // Don't schedule layout for the parent just yet. Wait for it to
386 // remove its child in response to the OnChildUnavailable notification. 402 // remove its child in response to the OnChildUnavailable notification.
387 } 403 }
388 404
389 void ViewRegistry::MarkChildAsUnavailable(ViewState* parent_state, 405 void ViewRegistry::MarkChildAsUnavailable(ViewState* parent_state,
390 uint32_t child_key) { 406 uint32_t child_key) {
391 DCHECK(IsViewStateRegisteredDebug(parent_state)); 407 DCHECK(IsViewStateRegisteredDebug(parent_state));
392 auto child_it = parent_state->children().find(child_key); 408 auto child_it = parent_state->children().find(child_key);
393 DCHECK(child_it != parent_state->children().end()); 409 DCHECK(child_it != parent_state->children().end());
394 DCHECK(child_it->second); 410 DCHECK(child_it->second);
395 411
396 DVLOG(2) << "Marked unavailable child " << child_key << " {" 412 DVLOG(2) << "Marked unavailable child " << child_key << " {"
397 << child_it->second->view_token_value() << "} from parent {" 413 << child_it->second->label() << "} from parent {"
398 << parent_state->view_token_value() << "}"; 414 << parent_state->label() << "}";
399 415
400 ResetStateWhenUnlinking(child_it->second); 416 ResetStateWhenUnlinking(child_it->second);
401 child_it->second->ResetContainer(); 417 child_it->second->ResetContainer();
402 child_it->second = nullptr; 418 child_it->second = nullptr;
403 SendChildUnavailable(parent_state, child_key); 419 SendChildUnavailable(parent_state, child_key);
404 420
405 // Don't schedule layout for the parent just yet. Wait for it to 421 // Don't schedule layout for the parent just yet. Wait for it to
406 // remove its child in response to the OnChildUnavailable notification. 422 // remove its child in response to the OnChildUnavailable notification.
407 // We don't need to schedule layout for the child either since it will 423 // We don't need to schedule layout for the child either since it will
408 // retain its old layout parameters. 424 // retain its old layout parameters.
409 } 425 }
410 426
411 void ViewRegistry::UnlinkChild(ViewState* parent_state, 427 void ViewRegistry::UnlinkChild(ViewState* parent_state,
412 ViewState::ChildrenMap::iterator child_it) { 428 ViewState::ChildrenMap::iterator child_it) {
413 DCHECK(IsViewStateRegisteredDebug(parent_state)); 429 DCHECK(IsViewStateRegisteredDebug(parent_state));
414 DCHECK(child_it != parent_state->children().end()); 430 DCHECK(child_it != parent_state->children().end());
415 431
416 ViewState* child_state = child_it->second; 432 ViewState* child_state = child_it->second;
417 if (child_state) { 433 if (child_state) {
418 DVLOG(2) << "Removed child " << child_state->key() << " {" 434 DVLOG(2) << "Removed child " << child_state->key() << " {"
419 << child_state->view_token_value() << "} from parent {" 435 << child_state->label() << "} from parent {"
420 << parent_state->view_token_value() << "}"; 436 << parent_state->label() << "}";
421 ResetStateWhenUnlinking(child_it->second); 437 ResetStateWhenUnlinking(child_it->second);
422 child_state->ResetContainer(); 438 child_state->ResetContainer();
423 } else { 439 } else {
424 DVLOG(2) << "Removed unavailable child " << child_it->first 440 DVLOG(2) << "Removed unavailable child " << child_it->first
425 << "} from parent {" << parent_state->view_token_value() << "}"; 441 << "} from parent {" << parent_state->label() << "}";
426 } 442 }
427 parent_state->children().erase(child_it); 443 parent_state->children().erase(child_it);
428 444
429 // Schedule layout for the parent now that it has lost its child. 445 // Schedule layout for the parent now that it has lost its child.
430 // We don't need to schedule layout for the child itself since it will 446 // We don't need to schedule layout for the child itself since it will
431 // retain its old layout parameters. 447 // retain its old layout parameters.
432 InvalidateLayout(parent_state); 448 InvalidateLayout(parent_state);
433 } 449 }
434 450
451 ViewTreeState* ViewRegistry::FindViewTree(uint32_t view_tree_token_value) {
452 auto it = view_trees_by_token_.find(view_tree_token_value);
453 return it != view_trees_by_token_.end() ? it->second : nullptr;
454 }
455
435 void ViewRegistry::LinkRoot(ViewTreeState* tree_state, 456 void ViewRegistry::LinkRoot(ViewTreeState* tree_state,
436 ViewState* root_state, 457 ViewState* root_state,
437 uint32_t root_key) { 458 uint32_t root_key) {
438 DCHECK(IsViewTreeStateRegisteredDebug(tree_state)); 459 DCHECK(IsViewTreeStateRegisteredDebug(tree_state));
439 DCHECK(IsViewStateRegisteredDebug(root_state)); 460 DCHECK(IsViewStateRegisteredDebug(root_state));
440 DCHECK(!tree_state->root()); 461 DCHECK(!tree_state->root());
441 DCHECK(!root_state->parent()); 462 DCHECK(!root_state->parent());
442 463
443 DVLOG(2) << "Linked view tree root " << root_key << " {" 464 DVLOG(2) << "Linked view tree root " << root_key << " {"
444 << root_state->view_token_value() << "}"; 465 << root_state->label() << "}";
445 466
446 tree_state->SetRoot(root_state, root_key); 467 tree_state->SetRoot(root_state, root_key);
447 468
448 // Schedule layout of the tree on behalf of its newly added root. 469 // Schedule layout of the tree on behalf of its newly added root.
449 // We don't need to schedule layout of the root until the tree provides 470 // We don't need to schedule layout of the root until the tree provides
450 // new layout parameters. 471 // new layout parameters.
451 InvalidateLayoutForRoot(tree_state); 472 InvalidateLayoutForRoot(tree_state);
452 } 473 }
453 474
454 void ViewRegistry::UnlinkRoot(ViewTreeState* tree_state) { 475 void ViewRegistry::UnlinkRoot(ViewTreeState* tree_state) {
455 DCHECK(IsViewTreeStateRegisteredDebug(tree_state)); 476 DCHECK(IsViewTreeStateRegisteredDebug(tree_state));
456 DCHECK(tree_state->root()); 477 DCHECK(tree_state->root());
457 478
458 DVLOG(2) << "Unlinked view tree root " << tree_state->root()->key() << " {" 479 DVLOG(2) << "Unlinked view tree root " << tree_state->root()->key() << " {"
459 << tree_state->root()->view_token_value() << "}"; 480 << tree_state->root()->label() << "}";
460 481
461 ResetStateWhenUnlinking(tree_state->root()); 482 ResetStateWhenUnlinking(tree_state->root());
462 tree_state->ResetRoot(); 483 tree_state->ResetRoot();
463 484
464 // We don't need to schedule layout for the root since it will retain 485 // We don't need to schedule layout for the root since it will retain
465 // its old layout parameters. 486 // its old layout parameters.
466 } 487 }
467 488
468 void ViewRegistry::HijackView(ViewState* view_state) { 489 void ViewRegistry::HijackView(ViewState* view_state) {
469 if (view_state->parent()) { 490 if (view_state->parent()) {
470 MarkChildAsUnavailable(view_state->parent(), view_state->key()); 491 MarkChildAsUnavailable(view_state->parent(), view_state->key());
471 } else if (view_state->tree()) { 492 } else if (view_state->tree()) {
472 ViewTreeState* tree_state = view_state->tree(); 493 ViewTreeState* tree_state = view_state->tree();
473 uint32_t root_key = tree_state->root()->key(); 494 uint32_t root_key = tree_state->root()->key();
474 UnlinkRoot(tree_state); 495 UnlinkRoot(tree_state);
475 SendRootUnavailable(tree_state, root_key); 496 SendRootUnavailable(tree_state, root_key);
476 } 497 }
477 } 498 }
478 499
479 void ViewRegistry::InvalidateLayout(ViewState* view_state) { 500 void ViewRegistry::InvalidateLayout(ViewState* view_state) {
480 DCHECK(IsViewStateRegisteredDebug(view_state)); 501 DCHECK(IsViewStateRegisteredDebug(view_state));
481 502
482 // We can consider the layout request to have been satisfied if 503 // We can consider the layout request to have been satisfied if
483 // there is already a pending layout request in the queue that has not 504 // there is already a pending layout request in the queue that has not
484 // yet been issued (this is coalescing). Otherwise we must manufacture 505 // yet been issued (this is coalescing). Otherwise we must manufacture
485 // a new one based on the current layout parameters. 506 // a new one based on the current layout parameters.
486 if (view_state->layout_params() && 507 if (view_state->layout_params() &&
487 (view_state->pending_layout_requests().empty() || 508 (view_state->pending_layout_requests().empty() ||
488 view_state->pending_layout_requests().back()->issued())) { 509 view_state->pending_layout_requests().back()->issued())) {
489 EnqueueLayoutRequest(view_state, view_state->layout_params().Clone()); 510 EnqueueLayoutRequest(view_state, view_state->layout_params()->Clone());
490 IssueNextViewLayoutRequest(view_state); 511 IssueNextViewLayoutRequest(view_state);
491 } 512 }
492 } 513 }
493 514
494 void ViewRegistry::InvalidateLayoutForChild(ViewState* parent_state, 515 void ViewRegistry::InvalidateLayoutForChild(ViewState* parent_state,
495 uint32_t child_key) { 516 uint32_t child_key) {
496 DCHECK(IsViewStateRegisteredDebug(parent_state)); 517 DCHECK(IsViewStateRegisteredDebug(parent_state));
497 DCHECK(parent_state->children().find(child_key) != 518 DCHECK(parent_state->children().find(child_key) !=
498 parent_state->children().end()); 519 parent_state->children().end());
499 520
(...skipping 12 matching lines...) Expand all
512 533
513 void ViewRegistry::SetLayout(ViewState* view_state, 534 void ViewRegistry::SetLayout(ViewState* view_state,
514 mojo::ui::ViewLayoutParamsPtr layout_params, 535 mojo::ui::ViewLayoutParamsPtr layout_params,
515 const ViewLayoutCallback& callback) { 536 const ViewLayoutCallback& callback) {
516 DCHECK(IsViewStateRegisteredDebug(view_state)); 537 DCHECK(IsViewStateRegisteredDebug(view_state));
517 DCHECK(AreViewLayoutParamsValid(layout_params.get())); 538 DCHECK(AreViewLayoutParamsValid(layout_params.get()));
518 539
519 // Check whether the currently cached layout parameters are the same 540 // Check whether the currently cached layout parameters are the same
520 // and we already have a result and we have no pending layout requests. 541 // and we already have a result and we have no pending layout requests.
521 if (view_state->pending_layout_requests().empty() && 542 if (view_state->pending_layout_requests().empty() &&
522 view_state->layout_params() && view_state->layout_info() && 543 view_state->layout_params() &&
523 view_state->layout_params()->Equals(*layout_params)) { 544 view_state->layout_params()->Equals(*layout_params)) {
524 DVLOG(2) << "Layout cache hit"; 545 mojo::ui::ViewLayoutInfoPtr info = view_state->CreateLayoutInfo();
525 callback.Run(view_state->layout_info().Clone()); 546 if (info) {
526 return; 547 DVLOG(2) << "Layout cache hit";
548 view_state->set_scene_changed_since_last_report(false);
549 callback.Run(info.Pass());
550 return;
551 }
527 } 552 }
528 553
529 // Check whether the layout parameters are different from the most 554 // Check whether the layout parameters are different from the most
530 // recent pending layout request if we have one. 555 // recent pending layout request if we have one.
531 if (view_state->pending_layout_requests().empty() || 556 if (view_state->pending_layout_requests().empty() ||
532 !view_state->pending_layout_requests().back()->layout_params()->Equals( 557 !view_state->pending_layout_requests().back()->layout_params()->Equals(
533 *layout_params)) { 558 *layout_params)) {
534 // Enqueue a new request for these parameters. 559 // Enqueue a new request for these parameters.
535 EnqueueLayoutRequest(view_state, layout_params.Pass()); 560 EnqueueLayoutRequest(view_state, layout_params.Pass());
536 } 561 }
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
577 tree_state->set_layout_request_issued(true); 602 tree_state->set_layout_request_issued(true);
578 SendViewTreeLayoutRequest(tree_state); 603 SendViewTreeLayoutRequest(tree_state);
579 } 604 }
580 } 605 }
581 606
582 void ViewRegistry::ResetStateWhenUnlinking(ViewState* view_state) { 607 void ViewRegistry::ResetStateWhenUnlinking(ViewState* view_state) {
583 // Clean up parent's recorded state for the child. 608 // Clean up parent's recorded state for the child.
584 if (view_state->parent()) { 609 if (view_state->parent()) {
585 view_state->parent()->children_needing_layout().erase(view_state->key()); 610 view_state->parent()->children_needing_layout().erase(view_state->key());
586 } 611 }
587
588 // Clean up child's recorded state for the parent or tree.
589 if (view_state->wrapped_surface()) {
590 surface_manager_->DestroySurface(view_state->wrapped_surface().Pass());
591 }
592 } 612 }
593 613
594 void ViewRegistry::SendChildUnavailable(ViewState* parent_state, 614 void ViewRegistry::SendChildUnavailable(ViewState* parent_state,
595 uint32_t child_key) { 615 uint32_t child_key) {
596 DCHECK(IsViewStateRegisteredDebug(parent_state)); 616 DCHECK(IsViewStateRegisteredDebug(parent_state));
597 617
598 // TODO: Detect ANRs 618 // TODO: Detect ANRs
599 DVLOG(1) << "SendChildUnavailable: child_key=" << child_key; 619 DVLOG(1) << "SendChildUnavailable: child_key=" << child_key;
600 parent_state->view()->OnChildUnavailable(child_key, 620 parent_state->view()->OnChildUnavailable(child_key,
601 base::Bind(&base::DoNothing)); 621 base::Bind(&base::DoNothing));
602 } 622 }
603 623
604 void ViewRegistry::SendRootUnavailable(ViewTreeState* tree_state, 624 void ViewRegistry::SendRootUnavailable(ViewTreeState* tree_state,
605 uint32_t root_key) { 625 uint32_t root_key) {
606 DCHECK(IsViewTreeStateRegisteredDebug(tree_state)); 626 DCHECK(IsViewTreeStateRegisteredDebug(tree_state));
607 627
608 // TODO: Detect ANRs 628 // TODO: Detect ANRs
609 DVLOG(1) << "SendRootUnavailable: root_key=" << root_key; 629 DVLOG(1) << "SendRootUnavailable: root_key=" << root_key;
610 tree_state->view_tree()->OnRootUnavailable(root_key, 630 tree_state->view_tree()->OnRootUnavailable(root_key,
611 base::Bind(&base::DoNothing)); 631 base::Bind(&base::DoNothing));
612 } 632 }
613 633
614 void ViewRegistry::SendViewLayoutRequest(ViewState* view_state) { 634 void ViewRegistry::SendViewLayoutRequest(ViewState* view_state) {
615 DCHECK(IsViewStateRegisteredDebug(view_state)); 635 DCHECK(IsViewStateRegisteredDebug(view_state));
616 DCHECK(!view_state->pending_layout_requests().empty()); 636 DCHECK(!view_state->pending_layout_requests().empty());
617 DCHECK(view_state->pending_layout_requests().front()->issued()); 637 DCHECK(view_state->pending_layout_requests().front()->issued());
618 638
619 // TODO: Detect ANRs 639 // TODO: Detect ANRs
620 DVLOG(1) << "SendViewLayoutRequest: view.token=" 640 DVLOG(1) << "SendViewLayoutRequest: view.token=" << view_state->label();
621 << view_state->view_token_value();
622 view_state->view()->OnLayout( 641 view_state->view()->OnLayout(
623 view_state->pending_layout_requests().front()->layout_params()->Clone(), 642 view_state->pending_layout_requests().front()->layout_params()->Clone(),
624 mojo::Array<uint32_t>::From(view_state->children_needing_layout()), 643 mojo::Array<uint32_t>::From(view_state->children_needing_layout()),
625 base::Bind(&ViewRegistry::OnViewLayoutResult, base::Unretained(this), 644 base::Bind(&ViewRegistry::OnViewLayoutResult, base::Unretained(this),
626 view_state->GetWeakPtr())); 645 view_state->GetWeakPtr()));
627 view_state->children_needing_layout().clear(); 646 view_state->children_needing_layout().clear();
628 } 647 }
629 648
630 void ViewRegistry::SendViewTreeLayoutRequest(ViewTreeState* tree_state) { 649 void ViewRegistry::SendViewTreeLayoutRequest(ViewTreeState* tree_state) {
631 DCHECK(IsViewTreeStateRegisteredDebug(tree_state)); 650 DCHECK(IsViewTreeStateRegisteredDebug(tree_state));
632 DCHECK(tree_state->layout_request_issued()); 651 DCHECK(tree_state->layout_request_issued());
633 652
634 // TODO: Detect ANRs 653 // TODO: Detect ANRs
635 DVLOG(1) << "SendViewTreeLayoutRequest"; 654 DVLOG(1) << "SendViewTreeLayoutRequest";
636 tree_state->view_tree()->OnLayout( 655 tree_state->view_tree()->OnLayout(
637 base::Bind(&ViewRegistry::OnViewTreeLayoutResult, base::Unretained(this), 656 base::Bind(&ViewRegistry::OnViewTreeLayoutResult, base::Unretained(this),
638 tree_state->GetWeakPtr())); 657 tree_state->GetWeakPtr()));
639 } 658 }
640 659
641 static bool IsSizeInBounds(mojo::ui::BoxConstraints* constraints, 660 static bool IsSizeInBounds(mojo::ui::BoxConstraints* constraints,
642 mojo::Size* size) { 661 mojo::Size* size) {
643 return size && size->width >= constraints->min_width && 662 return size && size->width >= constraints->min_width &&
644 size->width <= constraints->max_width && 663 size->width <= constraints->max_width &&
645 size->height >= constraints->min_height && 664 size->height >= constraints->min_height &&
646 size->height <= constraints->max_height; 665 size->height <= constraints->max_height;
647 } 666 }
648 667
649 void ViewRegistry::OnViewLayoutResult(base::WeakPtr<ViewState> view_state_weak, 668 void ViewRegistry::OnViewLayoutResult(base::WeakPtr<ViewState> view_state_weak,
650 mojo::ui::ViewLayoutInfoPtr info) { 669 mojo::ui::ViewLayoutResultPtr result) {
651 DCHECK(info); 670 DCHECK(result);
652 DCHECK(info->surface_id); // checked by mojom
653 671
654 ViewState* view_state = view_state_weak.get(); 672 ViewState* view_state = view_state_weak.get();
655 if (!view_state) 673 if (!view_state)
656 return; 674 return;
657 675
658 DCHECK(!view_state->pending_layout_requests().empty()); 676 DCHECK(!view_state->pending_layout_requests().empty());
659 DCHECK(view_state->pending_layout_requests().front()->issued()); 677 DCHECK(view_state->pending_layout_requests().front()->issued());
660 678
661 std::unique_ptr<ViewLayoutRequest> request( 679 std::unique_ptr<ViewLayoutRequest> request(
662 std::move(view_state->pending_layout_requests().front())); 680 std::move(view_state->pending_layout_requests().front()));
663 view_state->pending_layout_requests().erase( 681 view_state->pending_layout_requests().erase(
664 view_state->pending_layout_requests().begin()); 682 view_state->pending_layout_requests().begin());
665 683
666 DVLOG(1) << "OnViewLayoutResult: view=" << view_state 684 DVLOG(1) << "OnViewLayoutResult: view=" << view_state
667 << ", params=" << request->layout_params() 685 << ", params=" << request->layout_params() << ", result=" << result;
668 << ", info=" << info.get();
669 686
670 // Validate the layout info. 687 // Validate the layout info.
671 if (!IsSizeInBounds(request->layout_params()->constraints.get(), 688 if (!IsSizeInBounds(request->layout_params()->constraints.get(),
672 info->size.get())) { 689 result->size.get())) {
673 LOG(ERROR) << "View returned invalid size in its layout info: " 690 LOG(ERROR) << "View returned invalid size in its layout info: "
674 << "view=" << view_state 691 << "view=" << view_state
675 << ", params=" << request->layout_params() 692 << ", params=" << request->layout_params()
676 << ", info=" << info.get(); 693 << ", result=" << result;
677 UnregisterView(view_state); 694 UnregisterView(view_state);
678 return; 695 return;
679 } 696 }
680 697
681 // Assume the parent or root will not see the new layout information if 698 // Assume the parent or root will not see the new layout information if
682 // there are no callbacks so we need to inform it when things change. 699 // there are no callbacks so we need to inform it when things change.
683 const bool size_changed = 700 const bool size_changed =
684 !view_state->layout_info() || 701 !view_state->layout_result() ||
685 !view_state->layout_info()->size->Equals(*info->size); 702 !view_state->layout_result()->size->Equals(*result->size);
686 const bool surface_changed =
687 !view_state->layout_info() ||
688 !view_state->layout_info()->surface_id->Equals(*info->surface_id);
689 const bool recurse = 703 const bool recurse =
690 !request->has_callbacks() && (surface_changed || size_changed); 704 !request->has_callbacks() &&
705 (size_changed || view_state->scene_changed_since_last_report());
691 706
692 view_state->layout_params() = request->TakeLayoutParams().Pass(); 707 view_state->set_layout_params(request->TakeLayoutParams().Pass());
693 view_state->layout_info() = info.Pass(); 708 view_state->set_layout_result(result.Pass());
694 709
695 if (surface_changed) { 710 mojo::ui::ViewLayoutInfoPtr info = view_state->CreateLayoutInfo();
696 if (view_state->wrapped_surface()) 711 if (info) {
697 surface_manager_->DestroySurface(view_state->wrapped_surface().Pass()); 712 view_state->set_scene_changed_since_last_report(false);
698 view_state->wrapped_surface() = surface_manager_->CreateWrappedSurface( 713 request->DispatchLayoutInfo(info.Pass());
699 view_state->layout_info()->surface_id.get());
700 } 714 }
701 715
702 request->DispatchLayoutInfo(view_state->layout_info().get());
703
704 if (recurse) { 716 if (recurse) {
705 if (view_state->parent()) { 717 if (view_state->parent()) {
706 InvalidateLayoutForChild(view_state->parent(), view_state->key()); 718 InvalidateLayoutForChild(view_state->parent(), view_state->key());
707 } else if (view_state->tree()) { 719 } else if (view_state->tree()) {
708 InvalidateLayoutForRoot(view_state->tree()); 720 InvalidateLayoutForRoot(view_state->tree());
709 } 721 }
710 } 722 }
711 723
712 IssueNextViewLayoutRequest(view_state); 724 IssueNextViewLayoutRequest(view_state);
713 } 725 }
714 726
715 void ViewRegistry::OnViewTreeLayoutResult( 727 void ViewRegistry::OnViewTreeLayoutResult(
716 base::WeakPtr<ViewTreeState> tree_state_weak) { 728 base::WeakPtr<ViewTreeState> tree_state_weak) {
717 ViewTreeState* tree_state = tree_state_weak.get(); 729 ViewTreeState* tree_state = tree_state_weak.get();
718 if (tree_state) { 730 if (tree_state) {
719 DCHECK(tree_state->layout_request_issued()); 731 DCHECK(tree_state->layout_request_issued());
720 732
721 DVLOG(1) << "OnViewTreeLayoutResult"; 733 DVLOG(1) << "OnViewTreeLayoutResult";
722 734
723 tree_state->set_layout_request_issued(false); 735 tree_state->set_layout_request_issued(false);
724 IssueNextViewTreeLayoutRequest(tree_state); 736 IssueNextViewTreeLayoutRequest(tree_state);
725 } 737 }
726 } 738 }
727 739
728 } // namespace view_manager 740 } // namespace view_manager
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698