Commit 4e72e787 authored by ben@chromium.org's avatar ben@chromium.org

Attempt at cleaning up a bunch of shutdown issues.

1. Defers command buffer destruction until after the native viewport client has had a chance to cleanup.
2. Destroy the compositor before quitting the view manager message loop.
3. Make various NodeObservers properly unhook themselves as node/view observers during destruction and view swapping.
4. Adds a "ViewManagerDisconnected" method to ViewManagerDelegate to allow the application to exit when the connection to the view manager is closed. This is necessary in addition to root monitoring because for some connections (e.g. the root node->window manager) the root node is not destroyed. I'm not entirely happy with imposing this burden on application developers but I will try and tidy this up later.
5. Instantiate nested AtExitManagers only in a static build. In the component build we can use the shell's.
6. Adds a callback to notify the ViewManagerInitServiceImpl when the NativeViewport is destroyed. The VMISI uses this callback to close its connection to the view manager, which triggers the view manager to shut down.

Since this still crashes, I can't test this yet.

R=sky@chromium.org
http://crbug.com/325901

Review URL: https://codereview.chromium.org/372273004

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@282683 0039d316-1c4b-4281-b951-d872f2087c98
parent 782a8e94
...@@ -152,6 +152,10 @@ class AuraDemo : public ApplicationDelegate, ...@@ -152,6 +152,10 @@ class AuraDemo : public ApplicationDelegate,
window_tree_host_->Show(); window_tree_host_->Show();
} }
virtual void OnViewManagerDisconnected(
view_manager::ViewManager* view_manager) OVERRIDE {
base::MessageLoop::current()->Quit();
}
// WindowTreeHostMojoDelegate: // WindowTreeHostMojoDelegate:
virtual void CompositorContentsChanged(const SkBitmap& bitmap) OVERRIDE { virtual void CompositorContentsChanged(const SkBitmap& bitmap) OVERRIDE {
......
...@@ -205,6 +205,12 @@ class Browser : public ApplicationDelegate, ...@@ -205,6 +205,12 @@ class Browser : public ApplicationDelegate,
root_->SetFocus(); root_->SetFocus();
CreateWidget(root_); CreateWidget(root_);
} }
virtual void OnViewManagerDisconnected(
view_manager::ViewManager* view_manager) OVERRIDE {
DCHECK_EQ(view_manager_, view_manager);
view_manager_ = NULL;
base::MessageLoop::current()->Quit();
}
// views::TextfieldController: // views::TextfieldController:
virtual bool HandleKeyEvent(views::Textfield* sender, virtual bool HandleKeyEvent(views::Textfield* sender,
...@@ -232,6 +238,10 @@ class Browser : public ApplicationDelegate, ...@@ -232,6 +238,10 @@ class Browser : public ApplicationDelegate,
else if (gained_focus == root_) else if (gained_focus == root_)
focus_client->FocusWindow(widget_->GetNativeView()); focus_client->FocusWindow(widget_->GetNativeView());
} }
virtual void OnNodeDestroyed(view_manager::Node* node) OVERRIDE {
DCHECK_EQ(root_, node);
node->RemoveObserver(this);
}
scoped_ptr<ViewsInit> views_init_; scoped_ptr<ViewsInit> views_init_;
......
...@@ -39,8 +39,9 @@ class SampleApp : public ApplicationDelegate, public NativeViewportClient { ...@@ -39,8 +39,9 @@ class SampleApp : public ApplicationDelegate, public NativeViewportClient {
virtual void OnCreated() OVERRIDE { virtual void OnCreated() OVERRIDE {
} }
virtual void OnDestroyed() OVERRIDE { virtual void OnDestroyed(const mojo::Callback<void()>& callback) OVERRIDE {
base::MessageLoop::current()->Quit(); base::MessageLoop::current()->Quit();
callback.Run();
} }
virtual void OnBoundsChanged(RectPtr bounds) OVERRIDE { virtual void OnBoundsChanged(RectPtr bounds) OVERRIDE {
......
...@@ -5,6 +5,7 @@ ...@@ -5,6 +5,7 @@
#include "base/basictypes.h" #include "base/basictypes.h"
#include "base/bind.h" #include "base/bind.h"
#include "base/logging.h" #include "base/logging.h"
#include "base/message_loop/message_loop.h"
#include "base/strings/string_number_conversions.h" #include "base/strings/string_number_conversions.h"
#include "mojo/public/cpp/application/application_connection.h" #include "mojo/public/cpp/application/application_connection.h"
#include "mojo/public/cpp/application/application_delegate.h" #include "mojo/public/cpp/application/application_delegate.h"
...@@ -97,6 +98,9 @@ class EmbeddedApp : public ApplicationDelegate, ...@@ -97,6 +98,9 @@ class EmbeddedApp : public ApplicationDelegate,
roots_[root->id()] = root; roots_[root->id()] = root;
ProcessPendingNodeColor(root->id()); ProcessPendingNodeColor(root->id());
} }
virtual void OnViewManagerDisconnected(ViewManager* view_manager) OVERRIDE {
base::MessageLoop::current()->Quit();
}
// Overridden from ViewObserver: // Overridden from ViewObserver:
virtual void OnViewInputEvent(View* view, const EventPtr& event) OVERRIDE { virtual void OnViewInputEvent(View* view, const EventPtr& event) OVERRIDE {
......
...@@ -2,6 +2,7 @@ ...@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be // Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file. // found in the LICENSE file.
#include "base/message_loop/message_loop.h"
#include "mojo/examples/html_viewer/blink_platform_impl.h" #include "mojo/examples/html_viewer/blink_platform_impl.h"
#include "mojo/examples/html_viewer/html_document_view.h" #include "mojo/examples/html_viewer/html_document_view.h"
#include "mojo/public/cpp/application/application_connection.h" #include "mojo/public/cpp/application/application_connection.h"
...@@ -77,6 +78,10 @@ class HTMLViewer : public ApplicationDelegate, ...@@ -77,6 +78,10 @@ class HTMLViewer : public ApplicationDelegate,
document_view_->AttachToNode(root); document_view_->AttachToNode(root);
MaybeLoad(); MaybeLoad();
} }
virtual void OnViewManagerDisconnected(
view_manager::ViewManager* view_manager) OVERRIDE {
base::MessageLoop::current()->Quit();
}
void MaybeLoad() { void MaybeLoad() {
if (document_view_ && response_.get()) if (document_view_ && response_.get())
......
...@@ -93,6 +93,12 @@ class Keyboard : public ApplicationDelegate, ...@@ -93,6 +93,12 @@ class Keyboard : public ApplicationDelegate,
root->SetActiveView(view_manager::View::Create(view_manager)); root->SetActiveView(view_manager::View::Create(view_manager));
CreateWidget(root); CreateWidget(root);
} }
virtual void OnViewManagerDisconnected(
view_manager::ViewManager* view_manager) OVERRIDE {
DCHECK_EQ(view_manager_, view_manager);
view_manager_ = NULL;
base::MessageLoop::current()->Quit();
}
// KeyboardDelegate: // KeyboardDelegate:
virtual void OnKeyPressed(int key_code, int event_flags) OVERRIDE { virtual void OnKeyPressed(int key_code, int event_flags) OVERRIDE {
......
...@@ -297,6 +297,12 @@ class MediaViewer : public ApplicationDelegate, ...@@ -297,6 +297,12 @@ class MediaViewer : public ApplicationDelegate,
request->response_details.Pass()); request->response_details.Pass());
} }
} }
virtual void OnViewManagerDisconnected(
view_manager::ViewManager* view_manager) OVERRIDE {
DCHECK_EQ(view_manager_, view_manager);
view_manager_ = NULL;
base::MessageLoop::current()->Quit();
}
// Overridden from ControlPanel::Delegate: // Overridden from ControlPanel::Delegate:
virtual void ButtonPressed(ControlPanel::ControlType type) OVERRIDE { virtual void ButtonPressed(ControlPanel::ControlType type) OVERRIDE {
......
...@@ -4,6 +4,7 @@ ...@@ -4,6 +4,7 @@
#include "base/basictypes.h" #include "base/basictypes.h"
#include "base/bind.h" #include "base/bind.h"
#include "base/message_loop/message_loop.h"
#include "base/strings/stringprintf.h" #include "base/strings/stringprintf.h"
#include "mojo/examples/window_manager/window_manager.mojom.h" #include "mojo/examples/window_manager/window_manager.mojom.h"
#include "mojo/public/cpp/application/application_connection.h" #include "mojo/public/cpp/application/application_connection.h"
...@@ -94,6 +95,9 @@ class NestingApp : public ApplicationDelegate, ...@@ -94,6 +95,9 @@ class NestingApp : public ApplicationDelegate,
NavigateChild(); NavigateChild();
} }
virtual void OnViewManagerDisconnected(ViewManager* view_manager) OVERRIDE {
base::MessageLoop::current()->Quit();
}
// Overridden from ViewObserver: // Overridden from ViewObserver:
virtual void OnViewInputEvent(View* view, const EventPtr& event) OVERRIDE { virtual void OnViewInputEvent(View* view, const EventPtr& event) OVERRIDE {
......
...@@ -55,7 +55,7 @@ class PepperContainerApp: public ApplicationDelegate, ...@@ -55,7 +55,7 @@ class PepperContainerApp: public ApplicationDelegate,
plugin_instance_.reset(); plugin_instance_.reset();
} }
virtual void OnDestroyed() OVERRIDE { virtual void OnDestroyed(const mojo::Callback<void()>& callback) OVERRIDE {
ppapi::ProxyAutoLock lock; ppapi::ProxyAutoLock lock;
if (plugin_instance_) { if (plugin_instance_) {
...@@ -64,6 +64,7 @@ class PepperContainerApp: public ApplicationDelegate, ...@@ -64,6 +64,7 @@ class PepperContainerApp: public ApplicationDelegate,
} }
base::MessageLoop::current()->Quit(); base::MessageLoop::current()->Quit();
callback.Run();
} }
virtual void OnBoundsChanged(RectPtr bounds) OVERRIDE { virtual void OnBoundsChanged(RectPtr bounds) OVERRIDE {
......
...@@ -4,6 +4,7 @@ ...@@ -4,6 +4,7 @@
#include <algorithm> #include <algorithm>
#include "base/message_loop/message_loop.h"
#include "base/strings/string_tokenizer.h" #include "base/strings/string_tokenizer.h"
#include "mojo/examples/media_viewer/media_viewer.mojom.h" #include "mojo/examples/media_viewer/media_viewer.mojom.h"
#include "mojo/public/cpp/application/application_connection.h" #include "mojo/public/cpp/application/application_connection.h"
...@@ -166,6 +167,10 @@ class PNGViewer : public ApplicationDelegate, ...@@ -166,6 +167,10 @@ class PNGViewer : public ApplicationDelegate,
if (!bitmap_.isNull()) if (!bitmap_.isNull())
DrawBitmap(); DrawBitmap();
} }
virtual void OnViewManagerDisconnected(
view_manager::ViewManager* view_manager) OVERRIDE {
base::MessageLoop::current()->Quit();
}
void DrawBitmap() { void DrawBitmap() {
if (!content_view_) if (!content_view_)
......
...@@ -48,8 +48,10 @@ class SampleApp : public ApplicationDelegate, public NativeViewportClient { ...@@ -48,8 +48,10 @@ class SampleApp : public ApplicationDelegate, public NativeViewportClient {
virtual void OnCreated() MOJO_OVERRIDE { virtual void OnCreated() MOJO_OVERRIDE {
} }
virtual void OnDestroyed() MOJO_OVERRIDE { virtual void OnDestroyed(
const mojo::Callback<void()>& callback) MOJO_OVERRIDE {
RunLoop::current()->Quit(); RunLoop::current()->Quit();
callback.Run();
} }
virtual void OnBoundsChanged(RectPtr bounds) MOJO_OVERRIDE { virtual void OnBoundsChanged(RectPtr bounds) MOJO_OVERRIDE {
......
...@@ -18,7 +18,6 @@ ...@@ -18,7 +18,6 @@
#include "mojo/services/public/cpp/view_manager/view_event_dispatcher.h" #include "mojo/services/public/cpp/view_manager/view_event_dispatcher.h"
#include "mojo/services/public/cpp/view_manager/view_manager.h" #include "mojo/services/public/cpp/view_manager/view_manager.h"
#include "mojo/services/public/cpp/view_manager/view_manager_delegate.h" #include "mojo/services/public/cpp/view_manager/view_manager_delegate.h"
#include "mojo/services/public/cpp/view_manager/view_observer.h"
#include "mojo/services/public/interfaces/input_events/input_events.mojom.h" #include "mojo/services/public/interfaces/input_events/input_events.mojom.h"
#include "mojo/services/public/interfaces/launcher/launcher.mojom.h" #include "mojo/services/public/interfaces/launcher/launcher.mojom.h"
#include "mojo/services/public/interfaces/navigation/navigation.mojom.h" #include "mojo/services/public/interfaces/navigation/navigation.mojom.h"
...@@ -189,7 +188,6 @@ class RootLayoutManager : public NodeObserver { ...@@ -189,7 +188,6 @@ class RootLayoutManager : public NodeObserver {
class WindowManager : public ApplicationDelegate, class WindowManager : public ApplicationDelegate,
public DebugPanel::Delegate, public DebugPanel::Delegate,
public ViewObserver,
public ViewManagerDelegate, public ViewManagerDelegate,
public ViewEventDispatcher { public ViewEventDispatcher {
public: public:
...@@ -280,23 +278,27 @@ class WindowManager : public ApplicationDelegate, ...@@ -280,23 +278,27 @@ class WindowManager : public ApplicationDelegate,
view_manager_ = view_manager; view_manager_ = view_manager;
view_manager_->SetEventDispatcher(this); view_manager_->SetEventDispatcher(this);
Node* node = Node::Create(view_manager); Node* node = Node::Create(view_manager_);
root->AddChild(node); root->AddChild(node);
node->SetBounds(gfx::Rect(root->bounds().size())); node->SetBounds(gfx::Rect(root->bounds().size()));
content_node_id_ = node->id(); content_node_id_ = node->id();
root_layout_manager_.reset( root_layout_manager_.reset(
new RootLayoutManager(view_manager, root, content_node_id_)); new RootLayoutManager(view_manager_, root, content_node_id_));
root->AddObserver(root_layout_manager_.get()); root->AddObserver(root_layout_manager_.get());
View* view = View::Create(view_manager); View* view = View::Create(view_manager_);
node->SetActiveView(view); node->SetActiveView(view);
view->SetColor(SK_ColorBLUE); view->SetColor(SK_ColorBLUE);
view->AddObserver(this);
CreateLauncherUI(); CreateLauncherUI();
CreateControlPanel(node); CreateControlPanel(node);
} }
virtual void OnViewManagerDisconnected(ViewManager* view_manager) OVERRIDE {
DCHECK_EQ(view_manager_, view_manager);
view_manager_ = NULL;
base::MessageLoop::current()->Quit();
}
// Overridden from ViewEventDispatcher: // Overridden from ViewEventDispatcher:
virtual void DispatchEvent(View* target, EventPtr event) OVERRIDE { virtual void DispatchEvent(View* target, EventPtr event) OVERRIDE {
......
...@@ -11,7 +11,9 @@ ...@@ -11,7 +11,9 @@
extern "C" APPLICATION_EXPORT MojoResult CDECL MojoMain( extern "C" APPLICATION_EXPORT MojoResult CDECL MojoMain(
MojoHandle shell_handle) { MojoHandle shell_handle) {
base::CommandLine::Init(0, NULL); base::CommandLine::Init(0, NULL);
#if !defined(COMPONENT_BUILD)
base::AtExitManager at_exit; base::AtExitManager at_exit;
#endif
base::MessageLoop loop; base::MessageLoop loop;
scoped_ptr<mojo::ApplicationDelegate> delegate( scoped_ptr<mojo::ApplicationDelegate> delegate(
mojo::ApplicationDelegate::Create()); mojo::ApplicationDelegate::Create());
......
...@@ -137,12 +137,15 @@ class NativeViewportImpl ...@@ -137,12 +137,15 @@ class NativeViewportImpl
} }
virtual void OnDestroyed() OVERRIDE { virtual void OnDestroyed() OVERRIDE {
command_buffer_.reset(); client()->OnDestroyed(base::Bind(&NativeViewportImpl::AckDestroyed,
client()->OnDestroyed(); base::Unretained(this)));
base::MessageLoop::current()->Quit();
} }
private: private:
void AckDestroyed() {
command_buffer_.reset();
}
shell::Context* context_; shell::Context* context_;
gfx::AcceleratedWidget widget_; gfx::AcceleratedWidget widget_;
scoped_ptr<services::NativeViewport> native_viewport_; scoped_ptr<services::NativeViewport> native_viewport_;
......
...@@ -62,7 +62,9 @@ class Delegate : public mojo::ApplicationDelegate { ...@@ -62,7 +62,9 @@ class Delegate : public mojo::ApplicationDelegate {
extern "C" APPLICATION_EXPORT MojoResult CDECL MojoMain( extern "C" APPLICATION_EXPORT MojoResult CDECL MojoMain(
MojoHandle shell_handle) { MojoHandle shell_handle) {
base::CommandLine::Init(0, NULL); base::CommandLine::Init(0, NULL);
#if !defined(COMPONENT_BUILD)
base::AtExitManager at_exit; base::AtExitManager at_exit;
#endif
// The IO message loop allows us to use net::URLRequest on this thread. // The IO message loop allows us to use net::URLRequest on this thread.
base::MessageLoopForIO loop; base::MessageLoopForIO loop;
......
...@@ -194,26 +194,6 @@ class ScopedSetBoundsNotifier { ...@@ -194,26 +194,6 @@ class ScopedSetBoundsNotifier {
DISALLOW_COPY_AND_ASSIGN(ScopedSetBoundsNotifier); DISALLOW_COPY_AND_ASSIGN(ScopedSetBoundsNotifier);
}; };
class ScopedDestructionNotifier {
public:
explicit ScopedDestructionNotifier(Node* node)
: node_(node) {
FOR_EACH_OBSERVER(NodeObserver,
*NodePrivate(node_).observers(),
OnNodeDestroying(node_));
}
~ScopedDestructionNotifier() {
FOR_EACH_OBSERVER(NodeObserver,
*NodePrivate(node_).observers(),
OnNodeDestroyed(node_));
}
private:
Node* node_;
DISALLOW_COPY_AND_ASSIGN(ScopedDestructionNotifier);
};
// Some operations are only permitted in the connection that created the node. // Some operations are only permitted in the connection that created the node.
bool OwnsNode(ViewManager* manager, Node* node) { bool OwnsNode(ViewManager* manager, Node* node) {
return !manager || return !manager ||
...@@ -359,13 +339,14 @@ Node::Node() ...@@ -359,13 +339,14 @@ Node::Node()
active_view_(NULL) {} active_view_(NULL) {}
Node::~Node() { Node::~Node() {
ScopedDestructionNotifier notifier(this); FOR_EACH_OBSERVER(NodeObserver, observers_, OnNodeDestroying(this));
if (parent_) if (parent_)
parent_->LocalRemoveChild(this); parent_->LocalRemoveChild(this);
// TODO(beng): It'd be better to do this via a destruction observer in the // TODO(beng): It'd be better to do this via a destruction observer in the
// ViewManagerClientImpl. // ViewManagerClientImpl.
if (manager_) if (manager_)
static_cast<ViewManagerClientImpl*>(manager_)->RemoveNode(id_); static_cast<ViewManagerClientImpl*>(manager_)->RemoveNode(id_);
FOR_EACH_OBSERVER(NodeObserver, observers_, OnNodeDestroyed(this));
} }
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
......
...@@ -13,28 +13,6 @@ ...@@ -13,28 +13,6 @@
namespace mojo { namespace mojo {
namespace view_manager { namespace view_manager {
namespace {
class ScopedDestructionNotifier {
public:
explicit ScopedDestructionNotifier(View* view)
: view_(view) {
FOR_EACH_OBSERVER(ViewObserver,
*ViewPrivate(view_).observers(),
OnViewDestroying(view_));
}
~ScopedDestructionNotifier() {
FOR_EACH_OBSERVER(ViewObserver,
*ViewPrivate(view_).observers(),
OnViewDestroyed(view_));
}
private:
View* view_;
DISALLOW_COPY_AND_ASSIGN(ScopedDestructionNotifier);
};
} // namespace
// static // static
View* View::Create(ViewManager* manager) { View* View::Create(ViewManager* manager) {
View* view = new View(manager); View* view = new View(manager);
...@@ -80,11 +58,13 @@ View::View() ...@@ -80,11 +58,13 @@ View::View()
manager_(NULL) {} manager_(NULL) {}
View::~View() { View::~View() {
ScopedDestructionNotifier notifier(this); FOR_EACH_OBSERVER(ViewObserver, observers_, OnViewDestroying(this));
// TODO(beng): It'd be better to do this via a destruction observer in the // TODO(beng): It'd be better to do this via a destruction observer in the
// ViewManagerClientImpl. // ViewManagerClientImpl.
if (manager_) if (manager_)
static_cast<ViewManagerClientImpl*>(manager_)->RemoveView(id_); static_cast<ViewManagerClientImpl*>(manager_)->RemoveView(id_);
FOR_EACH_OBSERVER(ViewObserver, observers_, OnViewDestroyed(this));
} }
void View::LocalDestroy() { void View::LocalDestroy() {
......
...@@ -97,6 +97,7 @@ class RootObserver : public NodeObserver { ...@@ -97,6 +97,7 @@ class RootObserver : public NodeObserver {
DCHECK_EQ(node, root_); DCHECK_EQ(node, root_);
static_cast<ViewManagerClientImpl*>( static_cast<ViewManagerClientImpl*>(
NodePrivate(root_).view_manager())->RemoveRoot(root_); NodePrivate(root_).view_manager())->RemoveRoot(root_);
node->RemoveObserver(this);
delete this; delete this;
} }
...@@ -535,6 +536,7 @@ ViewManagerClientImpl::ViewManagerClientImpl(ApplicationConnection* connection, ...@@ -535,6 +536,7 @@ ViewManagerClientImpl::ViewManagerClientImpl(ApplicationConnection* connection,
dispatcher_(NULL) {} dispatcher_(NULL) {}
ViewManagerClientImpl::~ViewManagerClientImpl() { ViewManagerClientImpl::~ViewManagerClientImpl() {
delegate_->OnViewManagerDisconnected(this);
while (!nodes_.empty()) { while (!nodes_.empty()) {
IdToNodeMap::iterator it = nodes_.begin(); IdToNodeMap::iterator it = nodes_.begin();
if (OwnsNode(it->second->id())) if (OwnsNode(it->second->id()))
......
...@@ -83,6 +83,7 @@ class ConnectServiceLoader : public ServiceLoader, ...@@ -83,6 +83,7 @@ class ConnectServiceLoader : public ServiceLoader,
Node* root) OVERRIDE { Node* root) OVERRIDE {
callback_.Run(view_manager, root); callback_.Run(view_manager, root);
} }
virtual void OnViewManagerDisconnected(ViewManager* view_manager) OVERRIDE {}
ScopedVector<ApplicationImpl> apps_; ScopedVector<ApplicationImpl> apps_;
LoadedCallback callback_; LoadedCallback callback_;
......
...@@ -13,7 +13,8 @@ class ViewManager; ...@@ -13,7 +13,8 @@ class ViewManager;
class ViewManagerDelegate { class ViewManagerDelegate {
public: public:
virtual void OnRootAdded(ViewManager* view_manager, Node* root) {} virtual void OnRootAdded(ViewManager* view_manager, Node* root) = 0;
virtual void OnViewManagerDisconnected(ViewManager* view_manager) = 0;
protected: protected:
virtual ~ViewManagerDelegate() {} virtual ~ViewManagerDelegate() {}
......
...@@ -21,7 +21,7 @@ interface NativeViewport { ...@@ -21,7 +21,7 @@ interface NativeViewport {
interface NativeViewportClient { interface NativeViewportClient {
OnCreated(); OnCreated();
OnBoundsChanged(Rect bounds); OnBoundsChanged(Rect bounds);
OnDestroyed(); OnDestroyed() => ();
OnEvent(Event event) => (); OnEvent(Event event) => ();
}; };
......
...@@ -42,12 +42,17 @@ RootNodeManager::Context::~Context() { ...@@ -42,12 +42,17 @@ RootNodeManager::Context::~Context() {
aura::Env::DeleteInstance(); aura::Env::DeleteInstance();
} }
RootNodeManager::RootNodeManager(ApplicationConnection* app_connection, RootNodeManager::RootNodeManager(
RootViewManagerDelegate* view_manager_delegate) ApplicationConnection* app_connection,
RootViewManagerDelegate* view_manager_delegate,
const Callback<void()>& native_viewport_closed_callback)
: app_connection_(app_connection), : app_connection_(app_connection),
next_connection_id_(1), next_connection_id_(1),
next_server_change_id_(1), next_server_change_id_(1),
root_view_manager_(app_connection, this, view_manager_delegate), root_view_manager_(app_connection,
this,
view_manager_delegate,
native_viewport_closed_callback),
root_(new Node(this, RootNodeId())), root_(new Node(this, RootNodeId())),
current_change_(NULL) { current_change_(NULL) {
} }
......
...@@ -82,7 +82,8 @@ class MOJO_VIEW_MANAGER_EXPORT RootNodeManager ...@@ -82,7 +82,8 @@ class MOJO_VIEW_MANAGER_EXPORT RootNodeManager
}; };
RootNodeManager(ApplicationConnection* app_connection, RootNodeManager(ApplicationConnection* app_connection,
RootViewManagerDelegate* view_manager_delegate); RootViewManagerDelegate* view_manager_delegate,
const Callback<void()>& native_viewport_closed_callback);
virtual ~RootNodeManager(); virtual ~RootNodeManager();
// Returns the id for the next ViewManagerServiceImpl. // Returns the id for the next ViewManagerServiceImpl.
......
...@@ -116,9 +116,11 @@ class WindowTreeClientImpl : public aura::client::WindowTreeClient { ...@@ -116,9 +116,11 @@ class WindowTreeClientImpl : public aura::client::WindowTreeClient {
DISALLOW_COPY_AND_ASSIGN(WindowTreeClientImpl); DISALLOW_COPY_AND_ASSIGN(WindowTreeClientImpl);
}; };
RootViewManager::RootViewManager(ApplicationConnection* app_connection, RootViewManager::RootViewManager(
RootNodeManager* root_node, ApplicationConnection* app_connection,
RootViewManagerDelegate* delegate) RootNodeManager* root_node,
RootViewManagerDelegate* delegate,
const Callback<void()>& native_viewport_closed_callback)
: delegate_(delegate), : delegate_(delegate),
root_node_manager_(root_node), root_node_manager_(root_node),
in_setup_(false) { in_setup_(false) {
...@@ -131,7 +133,8 @@ RootViewManager::RootViewManager(ApplicationConnection* app_connection, ...@@ -131,7 +133,8 @@ RootViewManager::RootViewManager(ApplicationConnection* app_connection,
viewport.Pass(), viewport.Pass(),
gfx::Rect(800, 600), gfx::Rect(800, 600),
base::Bind(&RootViewManager::OnCompositorCreated, base::Bind(&RootViewManager::OnCompositorCreated,
base::Unretained(this)))); base::Unretained(this)),
native_viewport_closed_callback));
} }
RootViewManager::~RootViewManager() { RootViewManager::~RootViewManager() {
......
...@@ -9,6 +9,7 @@ ...@@ -9,6 +9,7 @@
#include "base/basictypes.h" #include "base/basictypes.h"
#include "base/memory/scoped_ptr.h" #include "base/memory/scoped_ptr.h"
#include "mojo/public/cpp/bindings/callback.h"
#include "mojo/public/cpp/gles2/gles2.h" #include "mojo/public/cpp/gles2/gles2.h"
#include "mojo/services/view_manager/view_manager_export.h" #include "mojo/services/view_manager/view_manager_export.h"
...@@ -39,7 +40,8 @@ class MOJO_VIEW_MANAGER_EXPORT RootViewManager { ...@@ -39,7 +40,8 @@ class MOJO_VIEW_MANAGER_EXPORT RootViewManager {
public: public:
RootViewManager(ApplicationConnection* app_connection, RootViewManager(ApplicationConnection* app_connection,
RootNodeManager* root_node, RootNodeManager* root_node,
RootViewManagerDelegate* delegate); RootViewManagerDelegate* delegate,
const Callback<void()>& native_viewport_closed_callback);
virtual ~RootViewManager(); virtual ~RootViewManager();
// See description above field for details. // See description above field for details.
......
...@@ -4,6 +4,7 @@ ...@@ -4,6 +4,7 @@
#include "mojo/services/view_manager/view_manager_init_service_impl.h" #include "mojo/services/view_manager/view_manager_init_service_impl.h"
#include "base/bind.h"
#include "mojo/public/interfaces/service_provider/service_provider.mojom.h" #include "mojo/public/interfaces/service_provider/service_provider.mojom.h"
#include "mojo/services/view_manager/ids.h" #include "mojo/services/view_manager/ids.h"
#include "mojo/services/view_manager/view_manager_service_impl.h" #include "mojo/services/view_manager/view_manager_service_impl.h"
...@@ -19,7 +20,11 @@ ViewManagerInitServiceImpl::ConnectParams::~ConnectParams() {} ...@@ -19,7 +20,11 @@ ViewManagerInitServiceImpl::ConnectParams::~ConnectParams() {}
ViewManagerInitServiceImpl::ViewManagerInitServiceImpl( ViewManagerInitServiceImpl::ViewManagerInitServiceImpl(
ApplicationConnection* connection) ApplicationConnection* connection)
: root_node_manager_(connection, this), : root_node_manager_(
connection,
this,
base::Bind(&ViewManagerInitServiceImpl::OnNativeViewportDeleted,
base::Unretained(this))),
is_tree_host_ready_(false) { is_tree_host_ready_(false) {
} }
...@@ -57,6 +62,13 @@ void ViewManagerInitServiceImpl::OnRootViewManagerWindowTreeHostCreated() { ...@@ -57,6 +62,13 @@ void ViewManagerInitServiceImpl::OnRootViewManagerWindowTreeHostCreated() {
MaybeEmbedRoot(connect_params_->url, connect_params_->callback); MaybeEmbedRoot(connect_params_->url, connect_params_->callback);
} }
void ViewManagerInitServiceImpl::OnNativeViewportDeleted() {
// TODO(beng): Should not have to rely on implementation detail of
// InterfaceImpl to close the connection. Instead should simply
// be able to delete this object.
internal_state()->router()->CloseMessagePipe();
}
} // namespace service } // namespace service
} // namespace view_manager } // namespace view_manager
} // namespace mojo } // namespace mojo
...@@ -57,6 +57,8 @@ class MOJO_VIEW_MANAGER_EXPORT ViewManagerInitServiceImpl ...@@ -57,6 +57,8 @@ class MOJO_VIEW_MANAGER_EXPORT ViewManagerInitServiceImpl
// RootViewManagerDelegate overrides: // RootViewManagerDelegate overrides:
virtual void OnRootViewManagerWindowTreeHostCreated() OVERRIDE; virtual void OnRootViewManagerWindowTreeHostCreated() OVERRIDE;
void OnNativeViewportDeleted();
ServiceProvider* service_provider_; ServiceProvider* service_provider_;
RootNodeManager root_node_manager_; RootNodeManager root_node_manager_;
......
...@@ -68,9 +68,11 @@ void RootLayoutManager::SetChildBounds(aura::Window* child, ...@@ -68,9 +68,11 @@ void RootLayoutManager::SetChildBounds(aura::Window* child,
WindowTreeHostImpl::WindowTreeHostImpl( WindowTreeHostImpl::WindowTreeHostImpl(
NativeViewportPtr viewport, NativeViewportPtr viewport,
const gfx::Rect& bounds, const gfx::Rect& bounds,
const base::Callback<void()>& compositor_created_callback) const Callback<void()>& compositor_created_callback,
const Callback<void()>& native_viewport_closed_callback)
: native_viewport_(viewport.Pass()), : native_viewport_(viewport.Pass()),
compositor_created_callback_(compositor_created_callback), compositor_created_callback_(compositor_created_callback),
native_viewport_closed_callback_(native_viewport_closed_callback),
bounds_(bounds) { bounds_(bounds) {
native_viewport_.set_client(this); native_viewport_.set_client(this);
native_viewport_->Create(Rect::From(bounds)); native_viewport_->Create(Rect::From(bounds));
...@@ -178,8 +180,11 @@ void WindowTreeHostImpl::OnBoundsChanged(RectPtr bounds) { ...@@ -178,8 +180,11 @@ void WindowTreeHostImpl::OnBoundsChanged(RectPtr bounds) {
OnHostResized(bounds_.size()); OnHostResized(bounds_.size());
} }
void WindowTreeHostImpl::OnDestroyed() { void WindowTreeHostImpl::OnDestroyed(const mojo::Callback<void()>& callback) {
base::MessageLoop::current()->Quit(); DestroyCompositor();
native_viewport_closed_callback_.Run();
// TODO(beng): quit the message loop once we are on our own thread.
callback.Run();
} }
void WindowTreeHostImpl::OnEvent(EventPtr event, void WindowTreeHostImpl::OnEvent(EventPtr event,
......
...@@ -25,9 +25,11 @@ class WindowTreeHostImpl : public aura::WindowTreeHost, ...@@ -25,9 +25,11 @@ class WindowTreeHostImpl : public aura::WindowTreeHost,
public ui::EventSource, public ui::EventSource,
public NativeViewportClient { public NativeViewportClient {
public: public:
WindowTreeHostImpl(NativeViewportPtr viewport, WindowTreeHostImpl(
const gfx::Rect& bounds, NativeViewportPtr viewport,
const base::Callback<void()>& compositor_created_callback); const gfx::Rect& bounds,
const Callback<void()>& compositor_created_callback,
const Callback<void()>& native_viewport_closed_callback);
virtual ~WindowTreeHostImpl(); virtual ~WindowTreeHostImpl();
gfx::Rect bounds() const { return bounds_; } gfx::Rect bounds() const { return bounds_; }
...@@ -54,7 +56,7 @@ class WindowTreeHostImpl : public aura::WindowTreeHost, ...@@ -54,7 +56,7 @@ class WindowTreeHostImpl : public aura::WindowTreeHost,
// Overridden from NativeViewportClient: // Overridden from NativeViewportClient:
virtual void OnCreated() OVERRIDE; virtual void OnCreated() OVERRIDE;
virtual void OnDestroyed() OVERRIDE; virtual void OnDestroyed(const mojo::Callback<void()>& callback) OVERRIDE;
virtual void OnBoundsChanged(RectPtr bounds) OVERRIDE; virtual void OnBoundsChanged(RectPtr bounds) OVERRIDE;
virtual void OnEvent(EventPtr event, virtual void OnEvent(EventPtr event,
const mojo::Callback<void()>& callback) OVERRIDE; const mojo::Callback<void()>& callback) OVERRIDE;
...@@ -62,7 +64,8 @@ class WindowTreeHostImpl : public aura::WindowTreeHost, ...@@ -62,7 +64,8 @@ class WindowTreeHostImpl : public aura::WindowTreeHost,
static ContextFactoryImpl* context_factory_; static ContextFactoryImpl* context_factory_;
NativeViewportPtr native_viewport_; NativeViewportPtr native_viewport_;
base::Callback<void()> compositor_created_callback_; Callback<void()> compositor_created_callback_;
Callback<void()> native_viewport_closed_callback_;
gfx::Rect bounds_; gfx::Rect bounds_;
......
...@@ -91,6 +91,7 @@ NativeWidgetViewManager::NativeWidgetViewManager( ...@@ -91,6 +91,7 @@ NativeWidgetViewManager::NativeWidgetViewManager(
views::internal::NativeWidgetDelegate* delegate, view_manager::Node* node) views::internal::NativeWidgetDelegate* delegate, view_manager::Node* node)
: NativeWidgetAura(delegate), : NativeWidgetAura(delegate),
node_(node) { node_(node) {
node_->AddObserver(this);
node_->active_view()->AddObserver(this); node_->active_view()->AddObserver(this);
window_tree_host_.reset(new WindowTreeHostMojo(node_, this)); window_tree_host_.reset(new WindowTreeHostMojo(node_, this));
window_tree_host_->InitHost(); window_tree_host_->InitHost();
...@@ -112,7 +113,9 @@ NativeWidgetViewManager::NativeWidgetViewManager( ...@@ -112,7 +113,9 @@ NativeWidgetViewManager::NativeWidgetViewManager(
} }
NativeWidgetViewManager::~NativeWidgetViewManager() { NativeWidgetViewManager::~NativeWidgetViewManager() {
node_->active_view()->RemoveObserver(this); if (node_->active_view())
node_->active_view()->RemoveObserver(this);
node_->RemoveObserver(this);
} }
void NativeWidgetViewManager::InitNativeWidget( void NativeWidgetViewManager::InitNativeWidget(
...@@ -129,6 +132,20 @@ void NativeWidgetViewManager::CompositorContentsChanged( ...@@ -129,6 +132,20 @@ void NativeWidgetViewManager::CompositorContentsChanged(
node_->active_view()->SetContents(bitmap); node_->active_view()->SetContents(bitmap);
} }
void NativeWidgetViewManager::OnNodeDestroyed(view_manager::Node* node) {
window_tree_host_.reset();
}
void NativeWidgetViewManager::OnNodeActiveViewChanged(
view_manager::Node* node,
view_manager::View* old_view,
view_manager::View* new_view) {
if (old_view)
old_view->RemoveObserver(this);
if (new_view)
new_view->AddObserver(this);
}
void NativeWidgetViewManager::OnViewInputEvent(view_manager::View* view, void NativeWidgetViewManager::OnViewInputEvent(view_manager::View* view,
const EventPtr& event) { const EventPtr& event) {
scoped_ptr<ui::Event> ui_event(event.To<scoped_ptr<ui::Event> >()); scoped_ptr<ui::Event> ui_event(event.To<scoped_ptr<ui::Event> >());
......
...@@ -42,6 +42,12 @@ class NativeWidgetViewManager : public views::NativeWidgetAura, ...@@ -42,6 +42,12 @@ class NativeWidgetViewManager : public views::NativeWidgetAura,
// WindowTreeHostMojoDelegate: // WindowTreeHostMojoDelegate:
virtual void CompositorContentsChanged(const SkBitmap& bitmap) OVERRIDE; virtual void CompositorContentsChanged(const SkBitmap& bitmap) OVERRIDE;
// view_manager::NodeObserver:
virtual void OnNodeDestroyed(view_manager::Node* node) OVERRIDE;
virtual void OnNodeActiveViewChanged(view_manager::Node* node,
view_manager::View* old_view,
view_manager::View* new_view) OVERRIDE;
// view_manager::ViewObserver // view_manager::ViewObserver
virtual void OnViewInputEvent(view_manager::View* view, virtual void OnViewInputEvent(view_manager::View* view,
const EventPtr& event) OVERRIDE; const EventPtr& event) OVERRIDE;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment