Thu, 22 Jan 2015 13:21:57 +0100
Incorporate requested changes from Mozilla in review:
https://bugzilla.mozilla.org/show_bug.cgi?id=1123480#c6
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* This Source Code Form is subject to the terms of the Mozilla Public
3 * License, v. 2.0. If a copy of the MPL was not distributed with this
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 #include "MetroUtils.h"
7 #include <windows.h>
8 #include "nsICommandLineRunner.h"
9 #include "nsNetUtil.h"
10 #include "nsIBrowserDOMWindow.h"
11 #include "nsIWebNavigation.h"
12 #include "nsIDocShellTreeItem.h"
13 #include "nsIDOMWindow.h"
14 #include "nsIDOMChromeWindow.h"
15 #include "nsIWindowMediator.h"
16 #include "nsIURI.h"
17 #include "prlog.h"
18 #include "nsIObserverService.h"
19 #include "nsRect.h"
21 #include <wrl/wrappers/corewrappers.h>
22 #include <windows.ui.applicationsettings.h>
23 #include <windows.graphics.display.h>
24 #include "DisplayInfo_sdk81.h"
26 using namespace ABI::Windows::UI::ApplicationSettings;
28 using namespace mozilla;
30 using namespace ABI::Windows::Foundation;
31 using namespace Microsoft::WRL;
32 using namespace Microsoft::WRL::Wrappers;
33 using namespace ABI::Windows::UI::ViewManagement;
34 using namespace ABI::Windows::Graphics::Display;
36 // Conversion between logical and physical coordinates
38 double
39 MetroUtils::LogToPhysFactor()
40 {
41 ComPtr<IDisplayInformationStatics> dispInfoStatics;
42 if (SUCCEEDED(GetActivationFactory(HStringReference(RuntimeClass_Windows_Graphics_Display_DisplayInformation).Get(),
43 dispInfoStatics.GetAddressOf()))) {
44 ComPtr<IDisplayInformation> dispInfo;
45 if (SUCCEEDED(dispInfoStatics->GetForCurrentView(&dispInfo))) {
46 FLOAT dpi;
47 if (SUCCEEDED(dispInfo->get_LogicalDpi(&dpi))) {
48 return (double)dpi / 96.0f;
49 }
50 }
51 }
53 ComPtr<IDisplayPropertiesStatics> dispProps;
54 if (SUCCEEDED(GetActivationFactory(HStringReference(RuntimeClass_Windows_Graphics_Display_DisplayProperties).Get(),
55 dispProps.GetAddressOf()))) {
56 FLOAT dpi;
57 if (SUCCEEDED(dispProps->get_LogicalDpi(&dpi))) {
58 return (double)dpi / 96.0f;
59 }
60 }
62 return 1.0;
63 }
65 double
66 MetroUtils::PhysToLogFactor()
67 {
68 return 1.0 / LogToPhysFactor();
69 }
71 double
72 MetroUtils::ScaleFactor()
73 {
74 // Return the resolution scale factor reported by the metro environment.
75 // XXX TODO: also consider the desktop resolution setting, as IE appears to do?
76 ComPtr<IDisplayInformationStatics> dispInfoStatics;
77 if (SUCCEEDED(GetActivationFactory(HStringReference(RuntimeClass_Windows_Graphics_Display_DisplayInformation).Get(),
78 dispInfoStatics.GetAddressOf()))) {
79 ComPtr<IDisplayInformation> dispInfo;
80 if (SUCCEEDED(dispInfoStatics->GetForCurrentView(&dispInfo))) {
81 ResolutionScale scale;
82 if (SUCCEEDED(dispInfo->get_ResolutionScale(&scale))) {
83 return (double)scale / 100.0;
84 }
85 }
86 }
88 ComPtr<IDisplayPropertiesStatics> dispProps;
89 if (SUCCEEDED(GetActivationFactory(HStringReference(RuntimeClass_Windows_Graphics_Display_DisplayProperties).Get(),
90 dispProps.GetAddressOf()))) {
91 ResolutionScale scale;
92 if (SUCCEEDED(dispProps->get_ResolutionScale(&scale))) {
93 return (double)scale / 100.0;
94 }
95 }
97 return 1.0;
98 }
100 nsIntPoint
101 MetroUtils::LogToPhys(const Point& aPt)
102 {
103 double factor = LogToPhysFactor();
104 return nsIntPoint(int32_t(NS_round(aPt.X * factor)), int32_t(NS_round(aPt.Y * factor)));
105 }
107 nsIntRect
108 MetroUtils::LogToPhys(const Rect& aRect)
109 {
110 double factor = LogToPhysFactor();
111 return nsIntRect(int32_t(NS_round(aRect.X * factor)),
112 int32_t(NS_round(aRect.Y * factor)),
113 int32_t(NS_round(aRect.Width * factor)),
114 int32_t(NS_round(aRect.Height * factor)));
115 }
117 Point
118 MetroUtils::PhysToLog(const nsIntPoint& aPt)
119 {
120 // Points contain FLOATs
121 FLOAT factor = (FLOAT)PhysToLogFactor();
122 Point p = { FLOAT(aPt.x) * factor, FLOAT(aPt.y) * factor };
123 return p;
124 }
126 nsresult
127 MetroUtils::FireObserver(const char* aMessage, const char16_t* aData)
128 {
129 nsCOMPtr<nsIObserverService> observerService =
130 mozilla::services::GetObserverService();
131 if (observerService) {
132 return observerService->NotifyObservers(nullptr, aMessage, aData);
133 }
134 return NS_ERROR_FAILURE;
135 }
137 HRESULT MetroUtils::CreateUri(HSTRING aUriStr, ComPtr<IUriRuntimeClass>& aUriOut)
138 {
139 HRESULT hr;
140 ComPtr<IUriRuntimeClassFactory> uriFactory;
141 hr = GetActivationFactory(HStringReference(RuntimeClass_Windows_Foundation_Uri).Get(), &uriFactory);
142 AssertRetHRESULT(hr, hr);
143 ComPtr<IUriRuntimeClass> uri;
144 return uriFactory->CreateUri(aUriStr, &aUriOut);
145 }
147 HRESULT MetroUtils::CreateUri(HString& aHString, ComPtr<IUriRuntimeClass>& aUriOut)
148 {
149 return MetroUtils::CreateUri(aHString.Get(), aUriOut);
150 }
152 HRESULT
153 MetroUtils::GetViewState(ApplicationViewState& aState)
154 {
155 HRESULT hr;
156 ComPtr<IApplicationViewStatics> appViewStatics;
157 hr = GetActivationFactory(HStringReference(RuntimeClass_Windows_UI_ViewManagement_ApplicationView).Get(),
158 appViewStatics.GetAddressOf());
159 AssertRetHRESULT(hr, hr);
160 hr = appViewStatics->get_Value(&aState);
161 return hr;
162 }
164 HRESULT
165 MetroUtils::TryUnsnap(bool* aResult)
166 {
167 HRESULT hr;
168 ComPtr<IApplicationViewStatics> appViewStatics;
169 hr = GetActivationFactory(HStringReference(RuntimeClass_Windows_UI_ViewManagement_ApplicationView).Get(),
170 appViewStatics.GetAddressOf());
171 AssertRetHRESULT(hr, hr);
172 boolean success = false;
173 hr = appViewStatics->TryUnsnap(&success);
174 if (aResult)
175 *aResult = success;
176 return hr;
177 }
179 HRESULT
180 MetroUtils::ShowSettingsFlyout()
181 {
182 ComPtr<ISettingsPaneStatics> settingsPaneStatics;
183 HRESULT hr = GetActivationFactory(HStringReference(RuntimeClass_Windows_UI_ApplicationSettings_SettingsPane).Get(),
184 settingsPaneStatics.GetAddressOf());
185 if (SUCCEEDED(hr)) {
186 settingsPaneStatics->Show();
187 }
189 return hr;
190 }