summaryrefslogtreecommitdiffstats
path: root/win8/viewer/metro_viewer_process_host.h
blob: 1218a43040fba43fb8491c52bd22a427d52ac0d4 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
// Copyright (c) 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef WIN8_VIEWER_METRO_VIEWER_PROCESS_HOST_H_
#define WIN8_VIEWER_METRO_VIEWER_PROCESS_HOST_H_

#include "base/basictypes.h"
#include "base/callback.h"
#include "base/memory/ref_counted.h"
#include "base/memory/scoped_ptr.h"
#include "base/strings/string16.h"
#include "base/threading/non_thread_safe.h"
#include "ipc/ipc_channel_proxy.h"
#include "ipc/ipc_listener.h"
#include "ipc/ipc_sender.h"
#include "ipc/message_filter.h"
#include "ui/gfx/native_widget_types.h"
#include "win8/viewer/metro_viewer_exports.h"

namespace base {
class SingleThreadTaskRunner;
class WaitableEvent;
}

namespace IPC {
class ChannelProxy;
class Message;
}

namespace win8 {

// Abstract base class for various Metro viewer process host implementations.
class METRO_VIEWER_EXPORT MetroViewerProcessHost : public IPC::Listener,
                                                   public IPC::Sender,
                                                   public base::NonThreadSafe {
 public:
  typedef base::Callback<void(const base::FilePath&, int, void*)>
      OpenFileCompletion;

  typedef base::Callback<void(const std::vector<base::FilePath>&, void*)>
      OpenMultipleFilesCompletion;

  typedef base::Callback<void(const base::FilePath&, int, void*)>
      SaveFileCompletion;

  typedef base::Callback<void(const base::FilePath&, int, void*)>
      SelectFolderCompletion;

  typedef base::Callback<void(void*)> FileSelectionCanceled;

  // Initializes a viewer process host to connect to the Metro viewer process
  // over IPC. The given task runner correspond to a thread on which
  // IPC::Channel is created and used (e.g. IO thread). Instantly connects to
  // the viewer process if one is already connected to |ipc_channel_name|; a
  // viewer can otherwise be launched synchronously via
  // LaunchViewerAndWaitForConnection().
  explicit MetroViewerProcessHost(
      const scoped_refptr<base::SingleThreadTaskRunner>& ipc_task_runner);
  ~MetroViewerProcessHost() override;

  // Returns the process id of the viewer process if one is connected to this
  // host, returns base::kNullProcessId otherwise.
  base::ProcessId GetViewerProcessId();

  // Launches the viewer process associated with the given |app_user_model_id|
  // and blocks until that viewer process connects or until a timeout is
  // reached. Returns true if the viewer process connects before the timeout is
  // reached. NOTE: this assumes that the app referred to by |app_user_model_id|
  // is registered as the default browser.
  bool LaunchViewerAndWaitForConnection(
      const base::string16& app_user_model_id);

  // Handles the activate desktop command for Metro Chrome Ash. The |ash_exit|
  // parameter indicates whether the Ash process would be shutdown after
  // activating the desktop.
  static void HandleActivateDesktop(const base::FilePath& shortcut,
                                    bool ash_exit);

  // Handles the metro exit command.  Notifies the metro viewer to shutdown
  // gracefully.
  static void HandleMetroExit();

  // Handles the open file operation for Metro Chrome Ash. The on_success
  // callback passed in is invoked when we receive the opened file name from
  // the metro viewer. The on failure callback is invoked on failure.
  static void HandleOpenFile(const base::string16& title,
                             const base::FilePath& default_path,
                             const base::string16& filter,
                             const OpenFileCompletion& on_success,
                             const FileSelectionCanceled& on_failure);

  // Handles the open multiple file operation for Metro Chrome Ash. The
  // on_success callback passed in is invoked when we receive the opened file
  // names from the metro viewer. The on failure callback is invoked on failure.
  static void HandleOpenMultipleFiles(
      const base::string16& title,
      const base::FilePath& default_path,
      const base::string16& filter,
      const OpenMultipleFilesCompletion& on_success,
      const FileSelectionCanceled& on_failure);

  // Handles the save file operation for Metro Chrome Ash. The on_success
  // callback passed in is invoked when we receive the saved file name from
  // the metro viewer. The on failure callback is invoked on failure.
  static void HandleSaveFile(const base::string16& title,
                             const base::FilePath& default_path,
                             const base::string16& filter,
                             int filter_index,
                             const base::string16& default_extension,
                             const SaveFileCompletion& on_success,
                             const FileSelectionCanceled& on_failure);

  // Handles the select folder for Metro Chrome Ash. The on_success
  // callback passed in is invoked when we receive the folder name from the
  // metro viewer. The on failure callback is invoked on failure.
  static void HandleSelectFolder(const base::string16& title,
                                 const SelectFolderCompletion& on_success,
                                 const FileSelectionCanceled& on_failure);

 protected:
  // IPC::Sender implementation:
  bool Send(IPC::Message* msg) override;

  // IPC::Listener implementation:
  bool OnMessageReceived(const IPC::Message& message) override;
  void OnChannelError() override = 0;

 private:
  // The following are the implementation for the corresponding static methods
  // above, see them for descriptions.
  void HandleOpenFileImpl(const base::string16& title,
                          const base::FilePath& default_path,
                          const base::string16& filter,
                          const OpenFileCompletion& on_success,
                          const FileSelectionCanceled& on_failure);
  void HandleOpenMultipleFilesImpl(
      const base::string16& title,
      const base::FilePath& default_path,
      const base::string16& filter,
      const OpenMultipleFilesCompletion& on_success,
      const FileSelectionCanceled& on_failure);
  void HandleSaveFileImpl(const base::string16& title,
                          const base::FilePath& default_path,
                          const base::string16& filter,
                          int filter_index,
                          const base::string16& default_extension,
                          const SaveFileCompletion& on_success,
                          const FileSelectionCanceled& on_failure);
  void HandleSelectFolderImpl(const base::string16& title,
                              const SelectFolderCompletion& on_success,
                              const FileSelectionCanceled& on_failure);

  // Called over IPC by the viewer process to tell this host that it should be
  // drawing to |target_surface|.
  virtual void OnSetTargetSurface(gfx::NativeViewId target_surface,
                                  float device_scale) = 0;

  // Called over IPC by the viewer process to request that the url passed in be
  // opened.
  virtual void OnOpenURL(const base::string16& url) = 0;

  // Called over IPC by the viewer process to request that the search string
  // passed in is passed to the default search provider and a URL navigation be
  // performed.
  virtual void OnHandleSearchRequest(const base::string16& search_string) = 0;

  // Called over IPC by the viewer process when the window size has changed.
  virtual void OnWindowSizeChanged(uint32 width, uint32 height) = 0;

  void NotifyChannelConnected();

  // IPC message handing methods:
  void OnFileSaveAsDone(bool success,
                        const base::FilePath& filename,
                        int filter_index);
  void OnFileOpenDone(bool success, const base::FilePath& filename);
  void OnMultiFileOpenDone(bool success,
                           const std::vector<base::FilePath>& files);
  void OnSelectFolderDone(bool success, const base::FilePath& folder);

  // Inner message filter used to handle connection event on the IPC channel
  // proxy's background thread. This prevents consumers of
  // MetroViewerProcessHost from having to pump messages on their own message
  // loop.
  class InternalMessageFilter : public IPC::MessageFilter {
   public:
    InternalMessageFilter(MetroViewerProcessHost* owner);

    // IPC::MessageFilter implementation.
    void OnChannelConnected(int32 peer_pid) override;

   private:
    ~InternalMessageFilter();

    MetroViewerProcessHost* owner_;
    DISALLOW_COPY_AND_ASSIGN(InternalMessageFilter);
  };

  scoped_ptr<IPC::ChannelProxy> channel_;
  scoped_ptr<base::WaitableEvent> channel_connected_event_;
  scoped_refptr<InternalMessageFilter> message_filter_;

  static MetroViewerProcessHost* instance_;

  // Saved callbacks which inform the caller about the result of the open file/
  // save file/select operations.
  OpenFileCompletion file_open_completion_callback_;
  OpenMultipleFilesCompletion multi_file_open_completion_callback_;
  SaveFileCompletion file_saveas_completion_callback_;
  SelectFolderCompletion select_folder_completion_callback_;
  FileSelectionCanceled failure_callback_;

  DISALLOW_COPY_AND_ASSIGN(MetroViewerProcessHost);
};

}  // namespace win8

#endif  // WIN8_VIEWER_METRO_VIEWER_PROCESS_HOST_H_