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 "base/basictypes.h"
6#include "base/bind.h"
7#include "base/logging.h"
8#include "base/message_loop/message_loop.h"
9#include "base/strings/string_number_conversions.h"
10#include "mojo/application/application_runner_chromium.h"
11#include "mojo/public/c/system/main.h"
12#include "mojo/public/cpp/application/application_connection.h"
13#include "mojo/public/cpp/application/application_delegate.h"
14#include "mojo/public/cpp/application/application_impl.h"
15#include "mojo/public/cpp/application/connect.h"
16#include "mojo/public/cpp/application/interface_factory_impl.h"
17#include "mojo/services/public/cpp/view_manager/view.h"
18#include "mojo/services/public/cpp/view_manager/view_manager.h"
19#include "mojo/services/public/cpp/view_manager/view_manager_client_factory.h"
20#include "mojo/services/public/cpp/view_manager/view_manager_delegate.h"
21#include "mojo/services/public/cpp/view_manager/view_observer.h"
22#include "mojo/services/public/interfaces/navigation/navigation.mojom.h"
23#include "ui/events/event_constants.h"
24#include "url/gurl.h"
25#include "url/url_util.h"
26
27namespace mojo {
28namespace examples {
29
30const SkColor kColors[] = {SK_ColorYELLOW, SK_ColorRED, SK_ColorGREEN,
31                           SK_ColorMAGENTA};
32
33struct Window {
34  Window(View* root, scoped_ptr<ServiceProvider> embedder_service_provider)
35      : root(root),
36        embedder_service_provider(embedder_service_provider.Pass()) {}
37  View* root;
38  scoped_ptr<ServiceProvider> embedder_service_provider;
39};
40
41class EmbeddedApp
42    : public ApplicationDelegate,
43      public ViewManagerDelegate,
44      public ViewObserver {
45 public:
46  EmbeddedApp() { url::AddStandardScheme("mojo"); }
47  virtual ~EmbeddedApp() {}
48
49 private:
50
51  // Overridden from ApplicationDelegate:
52  virtual void Initialize(ApplicationImpl* app) MOJO_OVERRIDE {
53    view_manager_client_factory_.reset(
54        new ViewManagerClientFactory(app->shell(), this));
55  }
56
57  virtual bool ConfigureIncomingConnection(ApplicationConnection* connection)
58      MOJO_OVERRIDE {
59    connection->AddService(view_manager_client_factory_.get());
60    return true;
61  }
62
63  // Overridden from ViewManagerDelegate:
64  virtual void OnEmbed(ViewManager* view_manager,
65                       View* root,
66                       ServiceProviderImpl* exported_services,
67                       scoped_ptr<ServiceProvider> imported_services) OVERRIDE {
68    root->AddObserver(this);
69    windows_[root->id()] = new Window(root, imported_services.Pass());
70    root->SetColor(kColors[next_color_++ % arraysize(kColors)]);
71  }
72  virtual void OnViewManagerDisconnected(ViewManager* view_manager) OVERRIDE {
73    base::MessageLoop::current()->Quit();
74  }
75
76  // Overridden from ViewObserver:
77  virtual void OnViewDestroyed(View* view) OVERRIDE {
78    DCHECK(windows_.find(view->id()) != windows_.end());
79    windows_.erase(view->id());
80  }
81  virtual void OnViewInputEvent(View* view, const EventPtr& event) OVERRIDE {
82    if (event->action == EVENT_TYPE_MOUSE_RELEASED) {
83      if (event->flags & EVENT_FLAGS_LEFT_MOUSE_BUTTON) {
84        URLRequestPtr request(URLRequest::New());
85        request->url = "http://www.aaronboodman.com/z_dropbox/test.html";
86        NavigatorHostPtr navigator_host;
87        ConnectToService(windows_[view->id()]->embedder_service_provider.get(),
88                         &navigator_host);
89        navigator_host->RequestNavigate(TARGET_SOURCE_NODE, request.Pass());
90      }
91    }
92  }
93
94  scoped_ptr<ViewManagerClientFactory> view_manager_client_factory_;
95
96  typedef std::map<Id, Window*> WindowMap;
97  WindowMap windows_;
98
99  int next_color_;
100
101  DISALLOW_COPY_AND_ASSIGN(EmbeddedApp);
102};
103
104}  // namespace examples
105}  // namespace mojo
106
107MojoResult MojoMain(MojoHandle shell_handle) {
108  mojo::ApplicationRunnerChromium runner(new mojo::examples::EmbeddedApp);
109  return runner.Run(shell_handle);
110}
111