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

Unified Diff: mojo/services/view_manager/connection_manager.cc

Issue 720883003: Adds a CloneAndAnimate function to WindowManagerInternalClient (Closed) Base URL: https://github.com/domokit/mojo.git@master
Patch Set: tweaks Created 6 years, 1 month 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 side-by-side diff with in-line comments
Download patch
Index: mojo/services/view_manager/connection_manager.cc
diff --git a/mojo/services/view_manager/connection_manager.cc b/mojo/services/view_manager/connection_manager.cc
index c80c1a30ebeef0f55569f07ca0152a33af097a34..846a80c60f3e70211af1ff076769ae92c1863301 100644
--- a/mojo/services/view_manager/connection_manager.cc
+++ b/mojo/services/view_manager/connection_manager.cc
@@ -12,10 +12,86 @@
#include "mojo/services/view_manager/client_connection.h"
#include "mojo/services/view_manager/connection_manager_delegate.h"
#include "mojo/services/view_manager/display_manager.h"
+#include "mojo/services/view_manager/server_view.h"
+#include "mojo/services/view_manager/view_coordinate_conversions.h"
#include "mojo/services/view_manager/view_manager_service_impl.h"
namespace mojo {
namespace service {
+namespace {
+
+// Creates a copy of |view|. The copied view has |delegate| as its delegate.
+// This does not recurse.
+ServerView* CloneView(const ServerView* view, ServerViewDelegate* delegate) {
+ ServerView* clone = new ServerView(delegate, ClonedViewId());
msw 2014/11/18 23:37:42 q: should the clone copy any/all ServerView::prope
sky 2014/11/19 00:49:39 Yes, I missed opacity. No need to visibility as we
msw 2014/11/19 01:27:51 Good catch, but I was wondering about the std::map
sky 2014/11/19 03:28:17 In theory those shouldn't matter as the only possi
msw 2014/11/19 18:18:29 Acknowledged.
+ clone->SetBounds(view->bounds());
+ clone->SetSurfaceId(view->surface_id());
+ return clone;
+}
+
+// Creates copies of all the visible children of |parent|. Newly cloned views
+// are
msw 2014/11/18 23:37:42 nit: fix line break
sky 2014/11/19 00:49:39 Done.
+// added to |cloned_parent| and have |delegate| as their delegate.
+void CloneAllViews(const ServerView* parent,
msw 2014/11/18 23:37:42 nit: CloneViewTree?
sky 2014/11/19 00:49:39 Done.
+ ServerView* cloned_parent,
+ ServerViewDelegate* delegate) {
+ DCHECK(parent->visible());
+ for (const ServerView* to_clone : parent->GetChildren()) {
msw 2014/11/18 23:37:42 q: will cloned views preserve the ordering of the
sky 2014/11/19 00:49:39 Yes. I added a comment indicating this.
+ if (to_clone->visible()) {
+ ServerView* cloned = CloneView(to_clone, delegate);
+ cloned_parent->Add(cloned);
+ CloneAllViews(to_clone, cloned, delegate);
+ }
+ }
+}
+
+// Recurses through all the children of |view| moving any cloned views to
+// |add_to| stacked above |stack_above|. |stack_above| is updated as views are
+// moved.
+void ReparentClonedViews(ServerView* add_to,
msw 2014/11/18 23:37:41 nit: s/add_to/new_parent/?
sky 2014/11/19 00:49:39 Done.
+ ServerView** stack_above,
+ ServerView* view) {
+ if (view->id() == ClonedViewId()) {
+ const gfx::Rect new_bounds(ConvertRectBetweenViews(
+ view, add_to, gfx::Rect(view->bounds().size())));
+ add_to->Add(view);
+ add_to->Reorder(view, *stack_above, ORDER_DIRECTION_ABOVE);
+ view->SetBounds(new_bounds);
+ *stack_above = view;
+ return;
+ }
+
+ for (ServerView* child : view->GetChildren())
+ ReparentClonedViews(add_to, stack_above, child);
+}
+
+// Deletes |view| and all its descendants.
+void DeleteAllViews(ServerView* view) {
msw 2014/11/18 23:37:41 nit: DeleteViewTree?
sky 2014/11/19 00:49:39 Done.
+ for (ServerView* child : view->GetChildren())
+ DeleteAllViews(child);
+
+ delete view;
+}
+
+// TODO(sky): nuke, proof of concept.
+bool DecrementAnimatingViewsOpacity(ServerView* view) {
+ if (view->id() == ClonedViewId()) {
+ const float new_opacity = view->opacity() - .05f;
+ if (new_opacity <= 0)
+ DeleteAllViews(view);
+ else
+ view->SetOpacity(new_opacity);
+ return true;
+ }
+ bool ret_value = false;
+ for (ServerView* child : view->GetChildren()) {
+ if (DecrementAnimatingViewsOpacity(child))
+ ret_value = true;
+ }
+ return ret_value;
+}
+
+} // namespace
ConnectionManager::ScopedChange::ScopedChange(
ViewManagerServiceImpl* connection,
@@ -82,8 +158,8 @@ void ConnectionManager::OnConnectionError(ClientConnection* connection) {
void ConnectionManager::EmbedAtView(
ConnectionSpecificId creator_id,
- const String& url,
- Id transport_view_id,
+ const std::string& url,
+ const ViewId& view_id,
InterfaceRequest<ServiceProvider> service_provider) {
std::string creator_url;
ConnectionMap::const_iterator it = connection_map_.find(creator_id);
@@ -92,8 +168,7 @@ void ConnectionManager::EmbedAtView(
ClientConnection* client_connection =
delegate_->CreateClientConnectionForEmbedAtView(
- this, creator_id, creator_url, url.To<std::string>(),
- ViewIdFromTransportId(transport_view_id));
+ this, creator_id, creator_url, url, view_id);
AddConnection(client_connection);
client_connection->service()->Init(client_connection->client(),
service_provider.Pass());
@@ -142,6 +217,21 @@ void ConnectionManager::SetWindowManagerClientConnection(
InterfaceRequest<ServiceProvider>());
}
+bool ConnectionManager::CloneAndAnimate(const ViewId& view_id) {
+ ServerView* view = GetView(view_id);
+ if (!view || !view->IsDrawn(root_.get()) || view == root_.get())
+ return false;
+ if (!animation_timer_.IsRunning()) {
+ animation_timer_.Start(FROM_HERE, base::TimeDelta::FromMilliseconds(100),
+ this, &ConnectionManager::DoAnimation);
+ }
+ ServerView* clone = CloneView(view, this);
+ CloneAllViews(view, clone, this);
+ view->parent()->Add(clone);
+ view->parent()->Reorder(clone, view, ORDER_DIRECTION_ABOVE);
+ return true;
+}
+
void ConnectionManager::ProcessViewBoundsChanged(const ServerView* view,
const gfx::Rect& old_bounds,
const gfx::Rect& new_bounds) {
@@ -199,22 +289,41 @@ void ConnectionManager::FinishChange() {
current_change_ = NULL;
}
+void ConnectionManager::DoAnimation() {
+ if (!DecrementAnimatingViewsOpacity(root()))
+ animation_timer_.Stop();
+}
+
void ConnectionManager::AddConnection(ClientConnection* connection) {
DCHECK_EQ(0u, connection_map_.count(connection->service()->id()));
connection_map_[connection->service()->id()] = connection;
}
+void ConnectionManager::OnWillDestroyView(ServerView* view) {
+ if (!in_destructor_ && root_->Contains(view) && view != root_.get() &&
msw 2014/11/18 23:37:42 Add a comment here explaining why this is useful,
+ view->id() != ClonedViewId()) {
+ ServerView* parent_above = view;
+ ReparentClonedViews(view->parent(), &parent_above, view);
msw 2014/11/18 23:37:41 Add a comment here explaining why this is useful,
msw 2014/11/18 23:37:42 I worry a bit about potential performance implicat
sky 2014/11/19 00:49:39 The bubbling at most happens for the depth of the
msw 2014/11/19 01:27:51 Acknowledged.
+ }
+}
+
void ConnectionManager::OnViewDestroyed(const ServerView* view) {
if (!in_destructor_)
ProcessViewDeleted(view->id());
}
-void ConnectionManager::OnWillChangeViewHierarchy(
- const ServerView* view,
- const ServerView* new_parent,
- const ServerView* old_parent) {
- if (!in_destructor_)
- ProcessWillChangeViewHierarchy(view, new_parent, old_parent);
+void ConnectionManager::OnWillChangeViewHierarchy(ServerView* view,
+ ServerView* new_parent,
+ ServerView* old_parent) {
+ if (view->id() == ClonedViewId() || in_destructor_)
+ return;
+
+ if (root_->Contains(view) && view != root_.get()) {
+ ServerView* parent_above = view;
+ ReparentClonedViews(view->parent(), &parent_above, view);
msw 2014/11/18 23:37:42 I'm confused; does this reparent cloned views to |
sky 2014/11/19 00:49:39 Added similar comment to above, let me know if sti
msw 2014/11/19 01:27:51 I guess it makes sense, re-parenting an ancestor o
sky 2014/11/19 03:28:17 I think we'll just have to see how this pans out.
msw 2014/11/19 18:18:29 Acknowledged.
+ }
+
+ ProcessWillChangeViewHierarchy(view, new_parent, old_parent);
}
void ConnectionManager::OnViewHierarchyChanged(const ServerView* view,
@@ -263,10 +372,17 @@ void ConnectionManager::OnViewReordered(const ServerView* view,
display_manager_->SchedulePaint(view, gfx::Rect(view->bounds().size()));
}
-void ConnectionManager::OnWillChangeViewVisibility(const ServerView* view) {
+void ConnectionManager::OnWillChangeViewVisibility(ServerView* view) {
if (in_destructor_)
return;
+ if (view != root_.get() && view->id() != ClonedViewId() &&
+ root_->Contains(view) && view->IsDrawn(root_.get())) {
+ // View is going to hide. Promote any cloned views.
+ ServerView* parent_above = view;
+ ReparentClonedViews(view->parent(), &parent_above, view);
+ }
+
for (auto& pair : connection_map_) {
pair.second->service()->ProcessWillChangeViewVisibility(
view, IsChangeSource(pair.first));
@@ -283,9 +399,9 @@ void ConnectionManager::OnViewSharedPropertyChanged(
}
}
-void ConnectionManager::SetViewportSize(SizePtr size) {
- gfx::Size new_size = size.To<gfx::Size>();
- display_manager_->SetViewportSize(new_size);
+void ConnectionManager::OnScheduleViewPaint(const ServerView* view) {
+ if (!in_destructor_)
+ display_manager_->SchedulePaint(view, gfx::Rect(view->bounds().size()));
}
void ConnectionManager::DispatchInputEventToView(Id transport_view_id,
@@ -301,5 +417,15 @@ void ConnectionManager::DispatchInputEventToView(Id transport_view_id,
}
}
+void ConnectionManager::SetViewportSize(SizePtr size) {
+ gfx::Size new_size = size.To<gfx::Size>();
+ display_manager_->SetViewportSize(new_size);
+}
+
+void ConnectionManager::CloneAndAnimate(Id transport_view_id,
+ const Callback<void(bool)>& callback) {
+ callback.Run(CloneAndAnimate(ViewIdFromTransportId(transport_view_id)));
msw 2014/11/18 23:37:42 Add a comment describing the expected lifetime of
msw 2014/11/18 23:37:42 optional nit: it might be more straightforward to
sky 2014/11/19 00:49:39 This code is all going to change drastically (see
msw 2014/11/19 01:27:51 Acknowledged.
+}
+
} // namespace service
} // namespace mojo

Powered by Google App Engine
This is Rietveld 408576698