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

Side by Side Diff: components/view_manager/view_tree_impl.cc

Issue 1344573002: Mandoline: Rename components/view_manager to components/mus (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Rebased Created 5 years, 3 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
« no previous file with comments | « components/view_manager/view_tree_impl.h ('k') | components/view_manager/view_tree_unittest.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright 2014 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 "components/view_manager/view_tree_impl.h"
6
7 #include "base/bind.h"
8 #include "base/stl_util.h"
9 #include "components/view_manager/connection_manager.h"
10 #include "components/view_manager/default_access_policy.h"
11 #include "components/view_manager/display_manager.h"
12 #include "components/view_manager/server_view.h"
13 #include "components/view_manager/view_tree_host_impl.h"
14 #include "components/view_manager/window_manager_access_policy.h"
15 #include "mojo/converters/geometry/geometry_type_converters.h"
16 #include "mojo/converters/ime/ime_type_converters.h"
17 #include "mojo/converters/input_events/input_events_type_converters.h"
18 #include "mojo/converters/surfaces/surfaces_type_converters.h"
19 #include "ui/platform_window/text_input_state.h"
20
21 using mojo::Array;
22 using mojo::Callback;
23 using mojo::Id;
24 using mojo::InterfaceRequest;
25 using mojo::OrderDirection;
26 using mojo::Rect;
27 using mojo::ServiceProvider;
28 using mojo::ServiceProviderPtr;
29 using mojo::String;
30 using mojo::ViewDataPtr;
31
32 namespace view_manager {
33
34 ViewTreeImpl::ViewTreeImpl(
35 ConnectionManager* connection_manager,
36 mojo::ConnectionSpecificId creator_id,
37 const ViewId& root_id)
38 : connection_manager_(connection_manager),
39 id_(connection_manager_->GetAndAdvanceNextConnectionId()),
40 creator_id_(creator_id),
41 client_(nullptr),
42 is_embed_root_(false) {
43 ServerView* view = GetView(root_id);
44 CHECK(view);
45 root_.reset(new ViewId(root_id));
46 if (view->GetRoot() == view) {
47 access_policy_.reset(new WindowManagerAccessPolicy(id_, this));
48 is_embed_root_ = true;
49 } else {
50 access_policy_.reset(new DefaultAccessPolicy(id_, this));
51 is_embed_root_ = (view->get_and_clear_pending_access_policy() &
52 ViewTree::ACCESS_POLICY_EMBED_ROOT) != 0;
53 }
54 }
55
56 ViewTreeImpl::~ViewTreeImpl() {
57 DestroyViews();
58 }
59
60 void ViewTreeImpl::Init(mojo::ViewTreeClient* client, mojo::ViewTreePtr tree) {
61 DCHECK(!client_);
62 client_ = client;
63 std::vector<const ServerView*> to_send;
64 if (root_.get())
65 GetUnknownViewsFrom(GetView(*root_), &to_send);
66
67 // TODO(beng): verify that host can actually be nullptr here.
68 ViewTreeHostImpl* host = GetHost();
69 const ServerView* focused_view = host ? host->GetFocusedView() : nullptr;
70 if (focused_view)
71 focused_view = access_policy_->GetViewForFocusChange(focused_view);
72 const mojo::Id focused_view_transport_id(
73 ViewIdToTransportId(focused_view ? focused_view->id() : ViewId()));
74
75 client->OnEmbed(id_, ViewToViewData(to_send.front()), tree.Pass(),
76 focused_view_transport_id,
77 is_embed_root_ ? ViewTree::ACCESS_POLICY_EMBED_ROOT
78 : ViewTree::ACCESS_POLICY_DEFAULT);
79 }
80
81 const ServerView* ViewTreeImpl::GetView(const ViewId& id) const {
82 if (id_ == id.connection_id) {
83 ViewMap::const_iterator i = view_map_.find(id.view_id);
84 return i == view_map_.end() ? NULL : i->second;
85 }
86 return connection_manager_->GetView(id);
87 }
88
89 bool ViewTreeImpl::IsRoot(const ViewId& id) const {
90 return root_.get() && *root_ == id;
91 }
92
93 ViewTreeHostImpl* ViewTreeImpl::GetHost() {
94 return root_.get() ?
95 connection_manager_->GetViewTreeHostByView(GetView(*root_)) : nullptr;
96 }
97
98 void ViewTreeImpl::OnWillDestroyViewTreeImpl(
99 ViewTreeImpl* connection) {
100 if (creator_id_ == connection->id())
101 creator_id_ = kInvalidConnectionId;
102 const ServerView* connection_root =
103 connection->root_ ? connection->GetView(*connection->root_) : nullptr;
104 if (connection_root &&
105 ((connection_root->id().connection_id == id_ &&
106 view_map_.count(connection_root->id().view_id) > 0) ||
107 (is_embed_root_ && IsViewKnown(connection_root)))) {
108 client()->OnEmbeddedAppDisconnected(
109 ViewIdToTransportId(*connection->root_));
110 }
111 if (root_.get() && root_->connection_id == connection->id())
112 root_.reset();
113 }
114
115 mojo::ErrorCode ViewTreeImpl::CreateView(const ViewId& view_id) {
116 if (view_id.connection_id != id_)
117 return mojo::ERROR_CODE_ILLEGAL_ARGUMENT;
118 if (view_map_.find(view_id.view_id) != view_map_.end())
119 return mojo::ERROR_CODE_VALUE_IN_USE;
120 view_map_[view_id.view_id] = connection_manager_->CreateServerView(view_id);
121 known_views_.insert(ViewIdToTransportId(view_id));
122 return mojo::ERROR_CODE_NONE;
123 }
124
125 bool ViewTreeImpl::AddView(const ViewId& parent_id, const ViewId& child_id) {
126 ServerView* parent = GetView(parent_id);
127 ServerView* child = GetView(child_id);
128 if (parent && child && child->parent() != parent &&
129 !child->Contains(parent) && access_policy_->CanAddView(parent, child)) {
130 ConnectionManager::ScopedChange change(this, connection_manager_, false);
131 parent->Add(child);
132 return true;
133 }
134 return false;
135 }
136
137 std::vector<const ServerView*> ViewTreeImpl::GetViewTree(
138 const ViewId& view_id) const {
139 const ServerView* view = GetView(view_id);
140 std::vector<const ServerView*> views;
141 if (view)
142 GetViewTreeImpl(view, &views);
143 return views;
144 }
145
146 bool ViewTreeImpl::SetViewVisibility(const ViewId& view_id, bool visible) {
147 ServerView* view = GetView(view_id);
148 if (!view || view->visible() == visible ||
149 !access_policy_->CanChangeViewVisibility(view)) {
150 return false;
151 }
152 ConnectionManager::ScopedChange change(this, connection_manager_, false);
153 view->SetVisible(visible);
154 return true;
155 }
156
157 bool ViewTreeImpl::Embed(const ViewId& view_id,
158 mojo::ViewTreeClientPtr client,
159 mojo::ConnectionSpecificId* connection_id) {
160 *connection_id = kInvalidConnectionId;
161 if (!client.get() || !CanEmbed(view_id))
162 return false;
163 PrepareForEmbed(view_id);
164 ViewTreeImpl* new_connection =
165 connection_manager_->EmbedAtView(id_, view_id, client.Pass());
166 if (is_embed_root_)
167 *connection_id = new_connection->id();
168 return true;
169 }
170
171 void ViewTreeImpl::Embed(const ViewId& view_id, mojo::URLRequestPtr request) {
172 if (!CanEmbed(view_id))
173 return;
174 PrepareForEmbed(view_id);
175 connection_manager_->EmbedAtView(id_, view_id, request.Pass());
176 }
177
178 void ViewTreeImpl::ProcessViewBoundsChanged(
179 const ServerView* view,
180 const gfx::Rect& old_bounds,
181 const gfx::Rect& new_bounds,
182 bool originated_change) {
183 if (originated_change || !IsViewKnown(view))
184 return;
185 client()->OnViewBoundsChanged(ViewIdToTransportId(view->id()),
186 Rect::From(old_bounds),
187 Rect::From(new_bounds));
188 }
189
190 void ViewTreeImpl::ProcessViewportMetricsChanged(
191 const mojo::ViewportMetrics& old_metrics,
192 const mojo::ViewportMetrics& new_metrics,
193 bool originated_change) {
194 client()->OnViewViewportMetricsChanged(old_metrics.Clone(),
195 new_metrics.Clone());
196 }
197
198 void ViewTreeImpl::ProcessWillChangeViewHierarchy(
199 const ServerView* view,
200 const ServerView* new_parent,
201 const ServerView* old_parent,
202 bool originated_change) {
203 if (originated_change)
204 return;
205
206 const bool old_drawn = view->IsDrawn();
207 const bool new_drawn = view->visible() && new_parent && new_parent->IsDrawn();
208 if (old_drawn == new_drawn)
209 return;
210
211 NotifyDrawnStateChanged(view, new_drawn);
212 }
213
214 void ViewTreeImpl::ProcessViewPropertyChanged(
215 const ServerView* view,
216 const std::string& name,
217 const std::vector<uint8_t>* new_data,
218 bool originated_change) {
219 if (originated_change)
220 return;
221
222 Array<uint8_t> data;
223 if (new_data)
224 data = Array<uint8_t>::From(*new_data);
225
226 client()->OnViewSharedPropertyChanged(ViewIdToTransportId(view->id()),
227 String(name), data.Pass());
228 }
229
230 void ViewTreeImpl::ProcessViewHierarchyChanged(
231 const ServerView* view,
232 const ServerView* new_parent,
233 const ServerView* old_parent,
234 bool originated_change) {
235 if (originated_change && !IsViewKnown(view) && new_parent &&
236 IsViewKnown(new_parent)) {
237 std::vector<const ServerView*> unused;
238 GetUnknownViewsFrom(view, &unused);
239 }
240 if (originated_change || connection_manager_->is_processing_delete_view() ||
241 connection_manager_->DidConnectionMessageClient(id_)) {
242 return;
243 }
244
245 if (!access_policy_->ShouldNotifyOnHierarchyChange(
246 view, &new_parent, &old_parent)) {
247 return;
248 }
249 // Inform the client of any new views and update the set of views we know
250 // about.
251 std::vector<const ServerView*> to_send;
252 if (!IsViewKnown(view))
253 GetUnknownViewsFrom(view, &to_send);
254 const ViewId new_parent_id(new_parent ? new_parent->id() : ViewId());
255 const ViewId old_parent_id(old_parent ? old_parent->id() : ViewId());
256 client()->OnViewHierarchyChanged(ViewIdToTransportId(view->id()),
257 ViewIdToTransportId(new_parent_id),
258 ViewIdToTransportId(old_parent_id),
259 ViewsToViewDatas(to_send));
260 connection_manager_->OnConnectionMessagedClient(id_);
261 }
262
263 void ViewTreeImpl::ProcessViewReorder(const ServerView* view,
264 const ServerView* relative_view,
265 OrderDirection direction,
266 bool originated_change) {
267 if (originated_change || !IsViewKnown(view) || !IsViewKnown(relative_view))
268 return;
269
270 client()->OnViewReordered(ViewIdToTransportId(view->id()),
271 ViewIdToTransportId(relative_view->id()),
272 direction);
273 }
274
275 void ViewTreeImpl::ProcessViewDeleted(const ViewId& view,
276 bool originated_change) {
277 if (view.connection_id == id_)
278 view_map_.erase(view.view_id);
279
280 const bool in_known = known_views_.erase(ViewIdToTransportId(view)) > 0;
281
282 if (IsRoot(view))
283 root_.reset();
284
285 if (originated_change)
286 return;
287
288 if (in_known) {
289 client()->OnViewDeleted(ViewIdToTransportId(view));
290 connection_manager_->OnConnectionMessagedClient(id_);
291 }
292 }
293
294 void ViewTreeImpl::ProcessWillChangeViewVisibility(
295 const ServerView* view,
296 bool originated_change) {
297 if (originated_change)
298 return;
299
300 if (IsViewKnown(view)) {
301 client()->OnViewVisibilityChanged(ViewIdToTransportId(view->id()),
302 !view->visible());
303 return;
304 }
305
306 bool view_target_drawn_state;
307 if (view->visible()) {
308 // View is being hidden, won't be drawn.
309 view_target_drawn_state = false;
310 } else {
311 // View is being shown. View will be drawn if its parent is drawn.
312 view_target_drawn_state = view->parent() && view->parent()->IsDrawn();
313 }
314
315 NotifyDrawnStateChanged(view, view_target_drawn_state);
316 }
317
318 void ViewTreeImpl::ProcessFocusChanged(
319 const ServerView* old_focused_view,
320 const ServerView* new_focused_view) {
321 const ServerView* view =
322 new_focused_view ? access_policy_->GetViewForFocusChange(new_focused_view)
323 : nullptr;
324 client()->OnViewFocused(view ? ViewIdToTransportId(view->id())
325 : ViewIdToTransportId(ViewId()));
326 }
327
328 bool ViewTreeImpl::IsViewKnown(const ServerView* view) const {
329 return known_views_.count(ViewIdToTransportId(view->id())) > 0;
330 }
331
332 bool ViewTreeImpl::CanReorderView(const ServerView* view,
333 const ServerView* relative_view,
334 OrderDirection direction) const {
335 if (!view || !relative_view)
336 return false;
337
338 if (!view->parent() || view->parent() != relative_view->parent())
339 return false;
340
341 if (!access_policy_->CanReorderView(view, relative_view, direction))
342 return false;
343
344 std::vector<const ServerView*> children = view->parent()->GetChildren();
345 const size_t child_i =
346 std::find(children.begin(), children.end(), view) - children.begin();
347 const size_t target_i =
348 std::find(children.begin(), children.end(), relative_view) -
349 children.begin();
350 if ((direction == mojo::ORDER_DIRECTION_ABOVE && child_i == target_i + 1) ||
351 (direction == mojo::ORDER_DIRECTION_BELOW && child_i + 1 == target_i)) {
352 return false;
353 }
354
355 return true;
356 }
357
358 bool ViewTreeImpl::DeleteViewImpl(ViewTreeImpl* source, ServerView* view) {
359 DCHECK(view);
360 DCHECK_EQ(view->id().connection_id, id_);
361 ConnectionManager::ScopedChange change(source, connection_manager_, true);
362 delete view;
363 return true;
364 }
365
366 void ViewTreeImpl::GetUnknownViewsFrom(
367 const ServerView* view,
368 std::vector<const ServerView*>* views) {
369 if (IsViewKnown(view) || !access_policy_->CanGetViewTree(view))
370 return;
371 views->push_back(view);
372 known_views_.insert(ViewIdToTransportId(view->id()));
373 if (!access_policy_->CanDescendIntoViewForViewTree(view))
374 return;
375 std::vector<const ServerView*> children(view->GetChildren());
376 for (size_t i = 0 ; i < children.size(); ++i)
377 GetUnknownViewsFrom(children[i], views);
378 }
379
380 void ViewTreeImpl::RemoveFromKnown(
381 const ServerView* view,
382 std::vector<ServerView*>* local_views) {
383 if (view->id().connection_id == id_) {
384 if (local_views)
385 local_views->push_back(GetView(view->id()));
386 return;
387 }
388 known_views_.erase(ViewIdToTransportId(view->id()));
389 std::vector<const ServerView*> children = view->GetChildren();
390 for (size_t i = 0; i < children.size(); ++i)
391 RemoveFromKnown(children[i], local_views);
392 }
393
394 void ViewTreeImpl::RemoveRoot() {
395 CHECK(root_.get());
396 const ViewId root_id(*root_);
397 root_.reset();
398 // No need to do anything if we created the view.
399 if (root_id.connection_id == id_)
400 return;
401
402 client()->OnUnembed();
403 client()->OnViewDeleted(ViewIdToTransportId(root_id));
404 connection_manager_->OnConnectionMessagedClient(id_);
405
406 // This connection no longer knows about the view. Unparent any views that
407 // were parented to views in the root.
408 std::vector<ServerView*> local_views;
409 RemoveFromKnown(GetView(root_id), &local_views);
410 for (size_t i = 0; i < local_views.size(); ++i)
411 local_views[i]->parent()->Remove(local_views[i]);
412 }
413
414 Array<ViewDataPtr> ViewTreeImpl::ViewsToViewDatas(
415 const std::vector<const ServerView*>& views) {
416 Array<ViewDataPtr> array(views.size());
417 for (size_t i = 0; i < views.size(); ++i)
418 array[i] = ViewToViewData(views[i]).Pass();
419 return array.Pass();
420 }
421
422 ViewDataPtr ViewTreeImpl::ViewToViewData(const ServerView* view) {
423 DCHECK(IsViewKnown(view));
424 const ServerView* parent = view->parent();
425 // If the parent isn't known, it means the parent is not visible to us (not
426 // in roots), and should not be sent over.
427 if (parent && !IsViewKnown(parent))
428 parent = NULL;
429 ViewDataPtr view_data(mojo::ViewData::New());
430 view_data->parent_id = ViewIdToTransportId(parent ? parent->id() : ViewId());
431 view_data->view_id = ViewIdToTransportId(view->id());
432 view_data->bounds = Rect::From(view->bounds());
433 view_data->properties =
434 mojo::Map<String, Array<uint8_t>>::From(view->properties());
435 view_data->visible = view->visible();
436 view_data->drawn = view->IsDrawn();
437 view_data->viewport_metrics =
438 connection_manager_->GetViewportMetricsForView(view);
439 return view_data.Pass();
440 }
441
442 void ViewTreeImpl::GetViewTreeImpl(
443 const ServerView* view,
444 std::vector<const ServerView*>* views) const {
445 DCHECK(view);
446
447 if (!access_policy_->CanGetViewTree(view))
448 return;
449
450 views->push_back(view);
451
452 if (!access_policy_->CanDescendIntoViewForViewTree(view))
453 return;
454
455 std::vector<const ServerView*> children(view->GetChildren());
456 for (size_t i = 0 ; i < children.size(); ++i)
457 GetViewTreeImpl(children[i], views);
458 }
459
460 void ViewTreeImpl::NotifyDrawnStateChanged(const ServerView* view,
461 bool new_drawn_value) {
462 // Even though we don't know about view, it may be an ancestor of our root, in
463 // which case the change may effect our roots drawn state.
464 if (!root_.get())
465 return;
466
467 const ServerView* root = GetView(*root_);
468 DCHECK(root);
469 if (view->Contains(root) && (new_drawn_value != root->IsDrawn())) {
470 client()->OnViewDrawnStateChanged(ViewIdToTransportId(root->id()),
471 new_drawn_value);
472 }
473 }
474
475 void ViewTreeImpl::DestroyViews() {
476 if (!view_map_.empty()) {
477 ConnectionManager::ScopedChange change(this, connection_manager_, true);
478 // If we get here from the destructor we're not going to get
479 // ProcessViewDeleted(). Copy the map and delete from the copy so that we
480 // don't have to worry about whether |view_map_| changes or not.
481 ViewMap view_map_copy;
482 view_map_.swap(view_map_copy);
483 STLDeleteValues(&view_map_copy);
484 }
485 }
486
487 bool ViewTreeImpl::CanEmbed(const ViewId& view_id) const {
488 const ServerView* view = GetView(view_id);
489 return view && access_policy_->CanEmbed(view);
490 }
491
492 void ViewTreeImpl::PrepareForEmbed(const ViewId& view_id) {
493 const ServerView* view = GetView(view_id);
494 DCHECK(view && access_policy_->CanEmbed(view));
495
496 // Only allow a node to be the root for one connection.
497 ViewTreeImpl* existing_owner =
498 connection_manager_->GetConnectionWithRoot(view_id);
499
500 ConnectionManager::ScopedChange change(this, connection_manager_, true);
501 RemoveChildrenAsPartOfEmbed(view_id);
502 if (existing_owner) {
503 // Never message the originating connection.
504 connection_manager_->OnConnectionMessagedClient(id_);
505 existing_owner->RemoveRoot();
506 }
507 }
508
509 void ViewTreeImpl::RemoveChildrenAsPartOfEmbed(const ViewId& view_id) {
510 ServerView* view = GetView(view_id);
511 CHECK(view);
512 CHECK(view->id().connection_id == view_id.connection_id);
513 std::vector<ServerView*> children = view->GetChildren();
514 for (size_t i = 0; i < children.size(); ++i)
515 view->Remove(children[i]);
516 }
517
518 void ViewTreeImpl::CreateView(
519 Id transport_view_id,
520 const Callback<void(mojo::ErrorCode)>& callback) {
521 callback.Run(CreateView(ViewIdFromTransportId(transport_view_id)));
522 }
523
524 void ViewTreeImpl::DeleteView(
525 Id transport_view_id,
526 const Callback<void(bool)>& callback) {
527 ServerView* view = GetView(ViewIdFromTransportId(transport_view_id));
528 bool success = false;
529 if (view && access_policy_->CanDeleteView(view)) {
530 ViewTreeImpl* connection =
531 connection_manager_->GetConnection(view->id().connection_id);
532 success = connection && connection->DeleteViewImpl(this, view);
533 }
534 callback.Run(success);
535 }
536
537 void ViewTreeImpl::AddView(
538 Id parent_id,
539 Id child_id,
540 const Callback<void(bool)>& callback) {
541 callback.Run(AddView(ViewIdFromTransportId(parent_id),
542 ViewIdFromTransportId(child_id)));
543 }
544
545 void ViewTreeImpl::RemoveViewFromParent(
546 Id view_id,
547 const Callback<void(bool)>& callback) {
548 bool success = false;
549 ServerView* view = GetView(ViewIdFromTransportId(view_id));
550 if (view && view->parent() && access_policy_->CanRemoveViewFromParent(view)) {
551 success = true;
552 ConnectionManager::ScopedChange change(this, connection_manager_, false);
553 view->parent()->Remove(view);
554 }
555 callback.Run(success);
556 }
557
558 void ViewTreeImpl::ReorderView(Id view_id,
559 Id relative_view_id,
560 OrderDirection direction,
561 const Callback<void(bool)>& callback) {
562 bool success = false;
563 ServerView* view = GetView(ViewIdFromTransportId(view_id));
564 ServerView* relative_view = GetView(ViewIdFromTransportId(relative_view_id));
565 if (CanReorderView(view, relative_view, direction)) {
566 success = true;
567 ConnectionManager::ScopedChange change(this, connection_manager_, false);
568 view->parent()->Reorder(view, relative_view, direction);
569 connection_manager_->ProcessViewReorder(view, relative_view, direction);
570 }
571 callback.Run(success);
572 }
573
574 void ViewTreeImpl::GetViewTree(
575 Id view_id,
576 const Callback<void(Array<ViewDataPtr>)>& callback) {
577 std::vector<const ServerView*> views(
578 GetViewTree(ViewIdFromTransportId(view_id)));
579 callback.Run(ViewsToViewDatas(views));
580 }
581
582 void ViewTreeImpl::SetViewBounds(
583 Id view_id,
584 mojo::RectPtr bounds,
585 const Callback<void(bool)>& callback) {
586 ServerView* view = GetView(ViewIdFromTransportId(view_id));
587 const bool success = view && access_policy_->CanSetViewBounds(view);
588 if (success) {
589 ConnectionManager::ScopedChange change(this, connection_manager_, false);
590 view->SetBounds(bounds.To<gfx::Rect>());
591 }
592 callback.Run(success);
593 }
594
595 void ViewTreeImpl::SetViewVisibility(
596 Id transport_view_id,
597 bool visible,
598 const Callback<void(bool)>& callback) {
599 callback.Run(
600 SetViewVisibility(ViewIdFromTransportId(transport_view_id), visible));
601 }
602
603 void ViewTreeImpl::SetViewProperty(
604 uint32_t view_id,
605 const mojo::String& name,
606 mojo::Array<uint8_t> value,
607 const mojo::Callback<void(bool)>& callback) {
608 ServerView* view = GetView(ViewIdFromTransportId(view_id));
609 const bool success = view && access_policy_->CanSetViewProperties(view);
610 if (success) {
611 ConnectionManager::ScopedChange change(this, connection_manager_, false);
612
613 if (value.is_null()) {
614 view->SetProperty(name, nullptr);
615 } else {
616 std::vector<uint8_t> data = value.To<std::vector<uint8_t>>();
617 view->SetProperty(name, &data);
618 }
619 }
620 callback.Run(success);
621 }
622
623 void ViewTreeImpl::RequestSurface(
624 mojo::Id view_id,
625 mojo::InterfaceRequest<mojo::Surface> surface,
626 mojo::SurfaceClientPtr client) {
627 ServerView* view = GetView(ViewIdFromTransportId(view_id));
628 const bool success = view && access_policy_->CanSetViewSurfaceId(view);
629 if (!success)
630 return;
631 view->Bind(surface.Pass(), client.Pass());
632 }
633
634 void ViewTreeImpl::SetViewTextInputState(
635 uint32_t view_id,
636 mojo::TextInputStatePtr state) {
637 ServerView* view = GetView(ViewIdFromTransportId(view_id));
638 bool success = view && access_policy_->CanSetViewTextInputState(view);
639 if (success)
640 view->SetTextInputState(state.To<ui::TextInputState>());
641 }
642
643 void ViewTreeImpl::SetImeVisibility(Id transport_view_id,
644 bool visible,
645 mojo::TextInputStatePtr state) {
646 ServerView* view = GetView(ViewIdFromTransportId(transport_view_id));
647 bool success = view && access_policy_->CanSetViewTextInputState(view);
648 if (success) {
649 if (!state.is_null())
650 view->SetTextInputState(state.To<ui::TextInputState>());
651
652 ViewTreeHostImpl* host = GetHost();
653 if (host)
654 host->SetImeVisibility(view, visible);
655 }
656 }
657
658 void ViewTreeImpl::SetAccessPolicy(Id transport_view_id,
659 uint32 policy_bitmask) {
660 const ViewId view_id(ViewIdFromTransportId(transport_view_id));
661 ServerView* view = GetView(view_id);
662 if (!view)
663 return;
664
665 ViewTreeImpl* existing_owner =
666 connection_manager_->GetConnectionWithRoot(view_id);
667 if (existing_owner)
668 return; // Only allow changing the access policy when nothing is embedded.
669
670 if (access_policy_->CanSetAccessPolicy(view))
671 view->set_pending_access_policy(policy_bitmask);
672 }
673
674 void ViewTreeImpl::Embed(mojo::Id transport_view_id,
675 mojo::ViewTreeClientPtr client,
676 const EmbedCallback& callback) {
677 mojo::ConnectionSpecificId connection_id = kInvalidConnectionId;
678 const bool result = Embed(ViewIdFromTransportId(transport_view_id),
679 client.Pass(), &connection_id);
680 callback.Run(result, connection_id);
681 }
682
683 void ViewTreeImpl::SetFocus(uint32_t view_id) {
684 ServerView* view = GetView(ViewIdFromTransportId(view_id));
685 // TODO(beng): consider shifting non-policy drawn check logic to VTH's
686 // FocusController.
687 if (view && view->IsDrawn() && access_policy_->CanSetFocus(view)) {
688 ConnectionManager::ScopedChange change(this, connection_manager_, false);
689 ViewTreeHostImpl* host = GetHost();
690 if (host)
691 host->SetFocusedView(view);
692 }
693 }
694
695 bool ViewTreeImpl::IsRootForAccessPolicy(const ViewId& id) const {
696 return IsRoot(id);
697 }
698
699 bool ViewTreeImpl::IsViewKnownForAccessPolicy(const ServerView* view) const {
700 return IsViewKnown(view);
701 }
702
703 bool ViewTreeImpl::IsViewRootOfAnotherConnectionForAccessPolicy(
704 const ServerView* view) const {
705 ViewTreeImpl* connection =
706 connection_manager_->GetConnectionWithRoot(view->id());
707 return connection && connection != this;
708 }
709
710 bool ViewTreeImpl::IsDescendantOfEmbedRoot(const ServerView* view) {
711 return is_embed_root_ && root_ && GetView(*root_)->Contains(view);
712 }
713
714 } // namespace view_manager
OLDNEW
« no previous file with comments | « components/view_manager/view_tree_impl.h ('k') | components/view_manager/view_tree_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698