display_manager.h revision ca12bfac764ba476d6cd062bf1dde12cc64c3f40
15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifndef ASH_DISPLAY_DISPLAY_MANAGER_H_
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define ASH_DISPLAY_DISPLAY_MANAGER_H_
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <string>
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <vector>
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ash/ash_export.h"
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ash/display/display_info.h"
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ash/display/display_layout.h"
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/compiler_specific.h"
152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/gtest_prod_util.h"
162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/memory/scoped_ptr.h"
172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "ui/gfx/display.h"
182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#if defined(OS_CHROMEOS)
202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chromeos/display/output_configurator.h"
215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace gfx {
242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class Display;
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class Insets;
262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class Rect;
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace ash {
302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class AcceleratorControllerTest;
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class DisplayController;
322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace test {
342a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class DisplayManagerTestApi;
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class SystemGestureEventFilterTest;
362a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)namespace internal {
382a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class DisplayLayoutStore;
392a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// DisplayManager maintains the current display configurations,
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// and notifies observers when configuration changes.
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// TODO(oshima): Make this non internal.
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class ASH_EXPORT DisplayManager
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_CHROMEOS)
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : public chromeos::OutputConfigurator::SoftwareMirroringController
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      {
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  class ASH_EXPORT Delegate {
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)   public:
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    virtual ~Delegate() {}
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Create or updates the mirror window with |display_info|.
552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    virtual void CreateOrUpdateMirrorWindow(
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        const DisplayInfo& display_info) = 0;
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Closes the mirror window if exists.
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    virtual void CloseMirrorWindow() = 0;
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Called before and after the display configuration changes.
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    virtual void PreDisplayConfigurationChange() = 0;
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    virtual void PostDisplayConfigurationChange() = 0;
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  };
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Returns the list of possible UI scales for the display.
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  static std::vector<float> GetScalesForDisplay(const DisplayInfo& info);
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Returns next valid UI scale.
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  static float GetNextUIScale(const DisplayInfo& info, bool up);
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Updates the bounds of the display given by |secondary_display_id|
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // according to |layout|.
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  static void UpdateDisplayBoundsForLayoutById(
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      const DisplayLayout& layout,
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      const gfx::Display& primary_display,
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      int64 secondary_display_id);
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DisplayManager();
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual ~DisplayManager();
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DisplayLayoutStore* layout_store() {
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return layout_store_.get();
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void set_delegate(Delegate* delegate) { delegate_ = delegate; }
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // When set to true, the MonitorManager calls OnDisplayBoundsChanged
895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // even if the display's bounds didn't change. Used to swap primary
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // display.
915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void set_force_bounds_changed(bool force_bounds_changed) {
925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    force_bounds_changed_ = force_bounds_changed;
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Returns the display id of the first display in the outupt list.
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int64 first_display_id() const { return first_display_id_; }
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Initializes displays using command line flag, or uses
995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // defualt if no options are specified.
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void InitFromCommandLine();
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // True if the given |display| is currently connected.
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool IsActiveDisplay(const gfx::Display& display) const;
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // True if there is an internal display.
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool HasInternalDisplay() const;
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool IsInternalDisplayId(int64 id) const;
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Returns display for given |id|;
1115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  const gfx::Display& GetDisplayForId(int64 id) const;
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Finds the display that contains |point| in screeen coordinates.
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Returns invalid display if there is no display that can satisfy
1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // the condition.
1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const gfx::Display& FindDisplayContainingPoint(
1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      const gfx::Point& point_in_screen) const;
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Sets the work area's |insets| to the display given by |display_id|.
1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool UpdateWorkAreaOfDisplay(int64 display_id, const gfx::Insets& insets);
1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Registers the overscan insets for the display of the specified ID. Note
1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // that the insets size should be specified in DIP size. It also triggers the
1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // display's bounds change.
1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void SetOverscanInsets(int64 display_id, const gfx::Insets& insets_in_dip);
1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  // Sets the display's rotation.
1285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  void SetDisplayRotation(int64 display_id, gfx::Display::Rotation rotation);
1295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  // Sets the display's ui scale.
1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void SetDisplayUIScale(int64 display_id, float ui_scale);
1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Register per display properties. |overscan_insets| is NULL if
1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // the display has no custom overscan insets.
1352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  void RegisterDisplayProperty(int64 display_id,
1365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                               gfx::Display::Rotation rotation,
1372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                               float ui_scale,
1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                               const gfx::Insets* overscan_insets);
1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
140  // Tells if display rotation/ui scaling features are enabled.
141  bool IsDisplayRotationEnabled() const;
142  bool IsDisplayUIScalingEnabled() const;
143
144  // Returns the current overscan insets for the specified |display_id|.
145  // Returns an empty insets (0, 0, 0, 0) if no insets are specified for
146  // the display.
147  gfx::Insets GetOverscanInsets(int64 display_id) const;
148
149  // Called when display configuration has changed. The new display
150  // configurations is passed as a vector of Display object, which
151  // contains each display's new infomration.
152  void OnNativeDisplaysChanged(
153      const std::vector<DisplayInfo>& display_info_list);
154
155  // Updates the internal display data and notifies observers about the changes.
156  void UpdateDisplays(const std::vector<DisplayInfo>& display_info_list);
157
158  // Updates current displays using current |display_info_|.
159  void UpdateDisplays();
160
161  // Returns the display at |index|. The display at 0 is
162  // no longer considered "primary".
163  const gfx::Display& GetDisplayAt(size_t index) const;
164
165  const gfx::Display* GetPrimaryDisplayCandidate() const;
166
167  // Returns the logical number of displays. This returns 1
168  // when displays are mirrored.
169  size_t GetNumDisplays() const;
170
171  // Returns the number of connected displays. This returns 2
172  // when displays are mirrored.
173  size_t num_connected_displays() const { return num_connected_displays_; }
174
175  // Returns the mirroring status.
176  bool IsMirrored() const;
177  const gfx::Display& mirrored_display() const { return mirrored_display_; }
178
179  // Retuns the display info associated with |display_id|.
180  const DisplayInfo& GetDisplayInfo(int64 display_id) const;
181
182  // Returns the human-readable name for the display |id|.
183  std::string GetDisplayNameForId(int64 id);
184
185  // Returns the display id that is capable of UI scaling. On device,
186  // this returns internal display's ID if its device scale factor is 2,
187  // or invalid ID if such internal display doesn't exist. On linux
188  // desktop, this returns the first display ID.
189  int64 GetDisplayIdForUIScaling() const;
190
191  // Change the mirror mode.
192  void SetMirrorMode(bool mirrored);
193
194  // Used to emulate display change when run in a desktop environment instead
195  // of on a device.
196  void AddRemoveDisplay();
197  void ToggleDisplayScaleFactor();
198
199  // SoftwareMirroringController override:
200#if defined(OS_CHROMEOS)
201  virtual void SetSoftwareMirroring(bool enabled) OVERRIDE;
202#else
203  void SetSoftwareMirroring(bool enabled);
204#endif
205
206  // Update the bounds of the display given by |display_id|.
207  bool UpdateDisplayBounds(int64 display_id,
208                           const gfx::Rect& new_bounds);
209private:
210  FRIEND_TEST_ALL_PREFIXES(ExtendedDesktopTest, ConvertPoint);
211  FRIEND_TEST_ALL_PREFIXES(DisplayManagerTest, TestNativeDisplaysChanged);
212  FRIEND_TEST_ALL_PREFIXES(DisplayManagerTest,
213                           NativeDisplaysChangedAfterPrimaryChange);
214  FRIEND_TEST_ALL_PREFIXES(DisplayManagerTest, AutomaticOverscanInsets);
215  friend class ash::AcceleratorControllerTest;
216  friend class test::DisplayManagerTestApi;
217  friend class test::SystemGestureEventFilterTest;
218  friend class DisplayManagerTest;
219
220  typedef std::vector<gfx::Display> DisplayList;
221
222  void set_change_display_upon_host_resize(bool value) {
223    change_display_upon_host_resize_ = value;
224  }
225
226  gfx::Display* FindDisplayForId(int64 id);
227
228  // Add the mirror display's display info if the software based
229  // mirroring is in use.
230  void AddMirrorDisplayInfoIfAny(std::vector<DisplayInfo>* display_info_list);
231
232  // Inserts and update the DisplayInfo according to the overscan
233  // state. Note that The DisplayInfo stored in the |internal_display_info_|
234  // can be different from |new_info| (due to overscan state), so
235  // you must use |GetDisplayInfo| to get the correct DisplayInfo for
236  // a display.
237  void InsertAndUpdateDisplayInfo(const DisplayInfo& new_info);
238
239  // Creates a display object from the DisplayInfo for |display_id|.
240  gfx::Display CreateDisplayFromDisplayInfoById(int64 display_id);
241
242  // Updates the bounds of the secondary display in |display_list|
243  // using the layout registered for the display pair and set the
244  // index of display updated to |updated_index|. Returns true
245  // if the secondary display's bounds has been changed from current
246  // value, or false otherwise.
247  bool UpdateSecondaryDisplayBoundsForLayout(DisplayList* display_list,
248                                             size_t* updated_index) const;
249
250  static void UpdateDisplayBoundsForLayout(
251      const DisplayLayout& layout,
252      const gfx::Display& primary_display,
253      gfx::Display* secondary_display);
254
255  Delegate* delegate_;  // not owned.
256
257  scoped_ptr<DisplayLayoutStore> layout_store_;
258
259  int64 first_display_id_;
260
261  gfx::Display mirrored_display_;
262
263  // List of current active dispays.
264  DisplayList displays_;
265
266  int num_connected_displays_;
267
268  bool force_bounds_changed_;
269
270  // The mapping from the display ID to its internal data.
271  std::map<int64, DisplayInfo> display_info_;
272
273  // When set to true, the host window's resize event updates
274  // the display's size. This is set to true when running on
275  // desktop environment (for debugging) so that resizing the host
276  // window wil update the display properly. This is set to false
277  // on device as well as during the unit tests.
278  bool change_display_upon_host_resize_;
279
280  bool software_mirroring_enabled_;
281
282  DISALLOW_COPY_AND_ASSIGN(DisplayManager);
283};
284
285}  // namespace internal
286}  // namespace ash
287
288#endif  // ASH_DISPLAY_DISPLAY_MANAGER_H_
289