Check the existence of RootWindow in ui::GetScaleFactorForNativeView.
[chromium-blink-merge.git] / ui / base / layout.cc
bloba7e6d46bdef7d72749537291208d05698bae9e81
1 // Copyright (c) 2012 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.
5 #include "ui/base/layout.h"
7 #include <algorithm>
8 #include <cmath>
9 #include <limits>
11 #include "base/basictypes.h"
12 #include "base/command_line.h"
13 #include "base/logging.h"
14 #include "build/build_config.h"
15 #include "ui/base/ui_base_switches.h"
17 #if defined(USE_AURA) && !defined(OS_WIN)
18 #include "ui/aura/root_window.h"
19 #include "ui/compositor/compositor.h"
20 #endif // defined(USE_AURA) && !defined(OS_WIN)
22 #if defined(OS_MACOSX)
23 #include "base/mac/mac_util.h"
24 #endif
26 #if defined(OS_WIN)
27 #include "base/win/metro.h"
28 #include <Windows.h>
29 #endif // defined(OS_WIN)
31 namespace {
33 // Helper function that determines whether we want to optimize the UI for touch.
34 bool UseTouchOptimizedUI() {
35 // If --touch-optimized-ui is specified and not set to "auto", then override
36 // the hardware-determined setting (eg. for testing purposes).
37 static bool has_touch_optimized_ui = CommandLine::ForCurrentProcess()->
38 HasSwitch(switches::kTouchOptimizedUI);
39 if (has_touch_optimized_ui) {
40 const std::string switch_value = CommandLine::ForCurrentProcess()->
41 GetSwitchValueASCII(switches::kTouchOptimizedUI);
43 // Note that simply specifying the switch is the same as enabled.
44 if (switch_value.empty() ||
45 switch_value == switches::kTouchOptimizedUIEnabled) {
46 return true;
47 } else if (switch_value == switches::kTouchOptimizedUIDisabled) {
48 return false;
49 } else if (switch_value != switches::kTouchOptimizedUIAuto) {
50 LOG(ERROR) << "Invalid --touch-optimized-ui option: " << switch_value;
54 #if defined(OS_WIN)
55 // On Windows, we use the touch layout only when we are running in
56 // Metro mode.
57 return base::win::IsMetroProcess() && base::win::IsTouchEnabled();
58 #else
59 return false;
60 #endif
63 const float kScaleFactorScales[] = {1.0, 2.0};
64 const size_t kScaleFactorScalesLength = arraysize(kScaleFactorScales);
66 std::vector<ui::ScaleFactor>& GetSupportedScaleFactorsInternal() {
67 static std::vector<ui::ScaleFactor>* supported_scale_factors =
68 new std::vector<ui::ScaleFactor>();
69 if (supported_scale_factors->empty()) {
70 supported_scale_factors->push_back(ui::SCALE_FACTOR_100P);
71 #if defined(OS_MACOSX) && defined(ENABLE_HIDPI)
72 if (base::mac::IsOSLionOrLater())
73 supported_scale_factors->push_back(ui::SCALE_FACTOR_200P);
74 #elif defined(USE_ASH)
75 supported_scale_factors->push_back(ui::SCALE_FACTOR_200P);
76 #endif
78 return *supported_scale_factors;
81 } // namespace
83 namespace ui {
85 // Note that this function should be extended to select
86 // LAYOUT_TOUCH when appropriate on more platforms than just
87 // Windows and Ash.
88 DisplayLayout GetDisplayLayout() {
89 #if defined(USE_ASH)
90 if (UseTouchOptimizedUI())
91 return LAYOUT_TOUCH;
92 return LAYOUT_ASH;
93 #elif defined(OS_WIN)
94 if (UseTouchOptimizedUI())
95 return LAYOUT_TOUCH;
96 return LAYOUT_DESKTOP;
97 #else
98 return LAYOUT_DESKTOP;
99 #endif
102 ScaleFactor GetScaleFactorFromScale(float scale) {
103 size_t closest_match = 0;
104 float smallest_diff = std::numeric_limits<float>::max();
105 for (size_t i = 0; i < kScaleFactorScalesLength; ++i) {
106 float diff = std::abs(kScaleFactorScales[i] - scale);
107 if (diff < smallest_diff) {
108 closest_match = i;
109 smallest_diff = diff;
112 return static_cast<ui::ScaleFactor>(closest_match);
115 float GetScaleFactorScale(ScaleFactor scale_factor) {
116 return kScaleFactorScales[scale_factor];
119 std::vector<ScaleFactor> GetSupportedScaleFactors() {
120 return GetSupportedScaleFactorsInternal();
123 bool IsScaleFactorSupported(ScaleFactor scale_factor) {
124 const std::vector<ScaleFactor>& supported =
125 GetSupportedScaleFactorsInternal();
126 return std::find(supported.begin(), supported.end(), scale_factor) !=
127 supported.end();
130 namespace test {
132 void SetSupportedScaleFactors(
133 const std::vector<ui::ScaleFactor>& scale_factors) {
134 std::vector<ui::ScaleFactor>& supported_scale_factors =
135 GetSupportedScaleFactorsInternal();
136 supported_scale_factors = scale_factors;
139 } // namespace test
141 #if !defined(OS_MACOSX)
142 ScaleFactor GetScaleFactorForNativeView(gfx::NativeView view) {
143 #if defined(USE_AURA) && !defined(OS_WIN)
144 aura::RootWindow* root_window = view->GetRootWindow();
145 if (!root_window)
146 return SCALE_FACTOR_NONE;
147 return GetScaleFactorFromScale(
148 root_window->compositor()->device_scale_factor());
149 #else
150 NOTIMPLEMENTED();
151 return SCALE_FACTOR_NONE;
152 #endif
154 #endif // !defined(OS_MACOSX)
156 } // namespace ui