-
Notifications
You must be signed in to change notification settings - Fork 1.7k
/
DualScreenService.uwp.cs
143 lines (113 loc) · 3.91 KB
/
DualScreenService.uwp.cs
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
using System;
using System.ComponentModel;
using System.Threading.Tasks;
using Windows.Foundation.Metadata;
using Windows.Graphics.Display;
using Windows.UI.ViewManagement;
#if UWP_18362
using Windows.UI.WindowManagement;
#endif
using Windows.UI.Xaml;
using Windows.UI.Xaml.Hosting;
using Xamarin.Forms;
using Xamarin.Forms.DualScreen;
using Xamarin.Forms.Internals;
using Xamarin.Forms.Platform.UWP;
[assembly: Dependency(typeof(DualScreenService))]
namespace Xamarin.Forms.DualScreen
{
internal partial class DualScreenService : IDualScreenService, Platform.UWP.DualScreen.IDualScreenService
{
public event EventHandler OnScreenChanged;
public DualScreenService()
{
if(Window.Current != null)
Window.Current.SizeChanged += OnCurrentSizeChanged;
}
public Task<int> GetHingeAngleAsync() => Task.FromResult(0);
void OnCurrentSizeChanged(object sender, Windows.UI.Core.WindowSizeChangedEventArgs e)
{
OnScreenChanged?.Invoke(this, EventArgs.Empty);
}
bool IsDualScreenDevice => ApiInformation.IsMethodPresent("Windows.UI.ViewManagement.ApplicationView", "GetSpanningRects");
public bool IsSpanned
{
get
{
if (!IsDualScreenDevice)
return false;
var visibleBounds = Window.Current.Bounds;
if (visibleBounds.Height > 1200 || visibleBounds.Width > 1200)
return true;
return false;
}
}
public DeviceInfo DeviceInfo => Device.info;
public bool IsLandscape
{
get
{
if (IsSpanned)
return ApplicationView.GetForCurrentView().Orientation == ApplicationViewOrientation.Portrait;
else
return ApplicationView.GetForCurrentView().Orientation == ApplicationViewOrientation.Landscape;
}
}
public Size ScaledScreenSize
{
get
{
Windows.Foundation.Rect windowSize = Window.Current.Bounds;
return new Size(windowSize.Width, windowSize.Height);
}
}
public Rectangle GetHinge()
{
if (!IsDualScreenDevice)
return Rectangle.Zero;
var screen = DisplayInformation.GetForCurrentView();
if (IsLandscape)
{
if (IsSpanned)
return new Rectangle(0, 664 + 24, ScaledPixels(screen.ScreenWidthInRawPixels), 0);
else
return new Rectangle(0, 664, ScaledPixels(screen.ScreenWidthInRawPixels), 0);
}
else
return new Rectangle(720, 0, 0, ScaledPixels(screen.ScreenHeightInRawPixels));
}
double ScaledPixels(double n)
=> n / DisplayInformation.GetForCurrentView().RawPixelsPerViewPixel;
public Point? GetLocationOnScreen(VisualElement visualElement)
{
var view = Platform.UWP.Platform.GetRenderer(visualElement);
if (view?.ContainerElement == null)
return null;
var ttv = view.ContainerElement.TransformToVisual(Window.Current.Content);
Windows.Foundation.Point screenCoords = ttv.TransformPoint(new Windows.Foundation.Point(0, 0));
return new Point(screenCoords.X, screenCoords.Y);
}
public object WatchForChangesOnLayout(VisualElement visualElement, Action action)
{
var view = Platform.UWP.Platform.GetRenderer(visualElement);
if (view?.ContainerElement == null)
return null;
EventHandler<object> layoutUpdated = (_, __) =>
{
action();
};
view.ContainerElement.LayoutUpdated += layoutUpdated;
return layoutUpdated;
}
public void StopWatchingForChangesOnLayout(VisualElement visualElement, object handle)
{
if (handle == null)
return;
var view = Platform.UWP.Platform.GetRenderer(visualElement);
if (view?.ContainerElement == null)
return;
if(handle is EventHandler<object> handler)
view.ContainerElement.LayoutUpdated -= handler;
}
}
}