PageRenderTime 137ms CodeModel.GetById 13ms RepoModel.GetById 0ms app.codeStats 0ms

/InvUwa/InvUwaShell.cs

https://gitlab.com/chunseoklee/Invention
C# | 1372 lines | 1110 code | 225 blank | 37 comment | 126 complexity | b58909e23aa64e5e4eb1553ec64e13b6 MD5 | raw file
  1. /*! 13 !*/
  2. using System;
  3. using System.Collections.Generic;
  4. using System.Diagnostics;
  5. using System.Linq;
  6. using System.IO;
  7. using System.Text;
  8. using System.Threading.Tasks;
  9. using Inv.Support;
  10. namespace Inv
  11. {
  12. public static class UwaShell
  13. {
  14. static UwaShell()
  15. {
  16. }
  17. public static void Attach(Windows.UI.Xaml.Controls.Page UwaPage, Func<Inv.Application> ApplicationFunction)
  18. {
  19. try
  20. {
  21. var InvApplication = ApplicationFunction();
  22. var UwaEngine = new UwaEngine(UwaPage, InvApplication);
  23. UwaEngine.Start();
  24. #if DEBUG
  25. //throw new Exception("I'm a fail");
  26. #endif
  27. }
  28. catch (Exception Exception)
  29. {
  30. var Grid = new Windows.UI.Xaml.Controls.Grid();
  31. UwaPage.Content = Grid;
  32. Grid.HorizontalAlignment = Windows.UI.Xaml.HorizontalAlignment.Stretch;
  33. Grid.VerticalAlignment = Windows.UI.Xaml.VerticalAlignment.Stretch;
  34. var Scroll = new Windows.UI.Xaml.Controls.ScrollViewer();
  35. Grid.Children.Add(Scroll);
  36. Scroll.Margin = new Windows.UI.Xaml.Thickness(0, 100, 0, 0);
  37. Scroll.VerticalScrollBarVisibility = Windows.UI.Xaml.Controls.ScrollBarVisibility.Auto;
  38. Scroll.HorizontalScrollBarVisibility = Windows.UI.Xaml.Controls.ScrollBarVisibility.Auto;
  39. var TextBox = new Windows.UI.Xaml.Controls.TextBox();
  40. Scroll.Content = TextBox;
  41. TextBox.IsReadOnly = true;
  42. TextBox.TextWrapping = Windows.UI.Xaml.TextWrapping.Wrap;
  43. var Message = Environment.NewLine + Exception.Message + Environment.NewLine + Environment.NewLine + Exception.StackTrace;
  44. TextBox.Text = Message;
  45. var Button = new Windows.UI.Xaml.Controls.Button();
  46. Grid.Children.Add(Button);
  47. Button.HorizontalAlignment = Windows.UI.Xaml.HorizontalAlignment.Center;
  48. Button.VerticalAlignment = Windows.UI.Xaml.VerticalAlignment.Top;
  49. Button.Margin = new Windows.UI.Xaml.Thickness(0, 30, 0, 0);
  50. Button.Content = "Send this start up fault to the author";
  51. Button.Click += (Sender, Event) => MailTo("hodgskin.callan@gmail.com", "Start Up Fault", Message);
  52. }
  53. }
  54. internal static void MailTo(string To, string Subject, string Body)
  55. {
  56. var MailUri = new Uri(string.Format("mailto:{0}?subject={1}&body={2}", To, Uri.EscapeDataString(Subject), Uri.EscapeDataString(Body)));
  57. // TODO: attachments not supported by mailto protocol.
  58. var MailTask = Windows.System.Launcher.LaunchUriAsync(MailUri).AsTask();
  59. MailTask.Wait();
  60. }
  61. }
  62. internal sealed class UwaPlatform : Inv.Platform
  63. {
  64. public UwaPlatform(UwaEngine Engine)
  65. {
  66. this.Engine = Engine;
  67. this.Vault = new UwaVault();
  68. this.LocalFolder = Windows.Storage.ApplicationData.Current.LocalFolder;
  69. }
  70. int Platform.ThreadAffinity()
  71. {
  72. return Environment.CurrentManagedThreadId;
  73. }
  74. string Platform.CalendarTimeZoneName()
  75. {
  76. return TimeZoneInfo.Local.DisplayName;
  77. }
  78. void Platform.CalendarShowPicker(CalendarPicker CalendarPicker)
  79. {
  80. // TODO: Uwa date/time picker.
  81. }
  82. bool Platform.EmailSendMessage(EmailMessage EmailMessage)
  83. {
  84. // TODO: Windows.ApplicationModel.Email.EmailMessage in Windows 10 only?
  85. //var em = new Windows.ApplicationModel.Email.EmailMessage() ;
  86. //em.To.Add(new EmailRecipient("yourname@yourdomain.com"));
  87. //em.Subject = "Your Subject...";
  88. //em.Body = "Your email body...";
  89. //em.Attachments.Add(new EmailAttachment(...);
  90. //EmailManager.ShowComposeNewEmailAsync(em).AsTask().Wait();
  91. UwaShell.MailTo(EmailMessage.GetTos().Select(T => T.Address).AsSeparatedText(","), EmailMessage.Subject ?? "", EmailMessage.Body ?? "");
  92. return true;
  93. }
  94. bool Platform.PhoneIsSupported
  95. {
  96. get { return false; }
  97. }
  98. bool Platform.PhoneDial(string PhoneNumber)
  99. {
  100. return false;
  101. }
  102. bool Platform.PhoneSMS(string PhoneNumber)
  103. {
  104. return false;
  105. }
  106. long Platform.DirectoryGetLengthFile(File File)
  107. {
  108. var StorageFolder = SelectStorageFolder(File.Folder);
  109. var FileTask = StorageFolder.GetBasicPropertiesAsync().AsTask();
  110. FileTask.Wait();
  111. return (long)FileTask.Result.Size;
  112. }
  113. DateTime Platform.DirectoryGetLastWriteTimeUtcFile(File File)
  114. {
  115. var StorageFolder = SelectStorageFolder(File.Folder);
  116. var FileTask = StorageFolder.GetFileAsync(File.Name).AsTask();
  117. FileTask.Wait();
  118. var PropertiesTask = FileTask.Result.GetBasicPropertiesAsync().AsTask();
  119. PropertiesTask.Wait();
  120. return PropertiesTask.Result.DateModified.UtcDateTime;
  121. }
  122. void Platform.DirectorySetLastWriteTimeUtcFile(File File, DateTime Timestamp)
  123. {
  124. var StorageFolder = SelectStorageFolder(File.Folder);
  125. var FileTask = StorageFolder.GetFileAsync(File.Name).AsTask();
  126. FileTask.Wait();
  127. // TODO: System.IO.File.SetLastWriteTimeUtc(SelectFilePath(File), Timestamp);
  128. }
  129. System.IO.Stream Platform.DirectoryCreateFile(File File)
  130. {
  131. var StorageFolder = SelectStorageFolder(File.Folder);
  132. var WriteTask = System.IO.WindowsRuntimeStorageExtensions.OpenStreamForWriteAsync(StorageFolder, File.Name, Windows.Storage.CreationCollisionOption.ReplaceExisting);
  133. WriteTask.Wait();
  134. return WriteTask.Result;
  135. }
  136. System.IO.Stream Platform.DirectoryAppendFile(File File)
  137. {
  138. var StorageFolder = SelectStorageFolder(File.Folder);
  139. var WriteTask = System.IO.WindowsRuntimeStorageExtensions.OpenStreamForWriteAsync(StorageFolder, File.Name, Windows.Storage.CreationCollisionOption.OpenIfExists);
  140. WriteTask.Wait();
  141. WriteTask.Result.Seek(0, System.IO.SeekOrigin.End);
  142. return WriteTask.Result;
  143. }
  144. System.IO.Stream Platform.DirectoryOpenFile(File File)
  145. {
  146. var StorageFolder = SelectStorageFolder(File.Folder);
  147. var ReadTask = System.IO.WindowsRuntimeStorageExtensions.OpenStreamForReadAsync(StorageFolder, File.Name);
  148. ReadTask.Wait();
  149. return ReadTask.Result;
  150. }
  151. bool Platform.DirectoryExistsFile(File File)
  152. {
  153. var StorageFolder = SelectStorageFolder(File.Folder);
  154. var FileTask = StorageFolder.TryGetItemAsync(File.Name).AsTask();
  155. FileTask.Wait();
  156. return FileTask.Result != null;
  157. }
  158. void Platform.DirectoryDeleteFile(File File)
  159. {
  160. var StorageFolder = SelectStorageFolder(File.Folder);
  161. var FileTask = StorageFolder.GetFileAsync(File.Name).AsTask();
  162. FileTask.Wait();
  163. var DeleteTask = FileTask.Result.DeleteAsync().AsTask();
  164. DeleteTask.Wait();
  165. }
  166. void Platform.DirectoryCopyFile(File SourceFile, File TargetFile)
  167. {
  168. var SourceFolder = SelectStorageFolder(SourceFile.Folder);
  169. var TargetFolder = SelectStorageFolder(TargetFile.Folder);
  170. var SourceFileTask = SourceFolder.GetFileAsync(SourceFile.Name).AsTask();
  171. SourceFileTask.Wait();
  172. var CopyTask = SourceFileTask.Result.CopyAsync(TargetFolder, TargetFile.Name).AsTask();
  173. CopyTask.Wait();
  174. }
  175. void Platform.DirectoryMoveFile(File SourceFile, File TargetFile)
  176. {
  177. var SourceFolder = SelectStorageFolder(SourceFile.Folder);
  178. var TargetFolder = SelectStorageFolder(TargetFile.Folder);
  179. var SourceFileTask = SourceFolder.GetFileAsync(SourceFile.Name).AsTask();
  180. SourceFileTask.Wait();
  181. var MoveTask = SourceFileTask.Result.MoveAsync(TargetFolder, TargetFile.Name).AsTask();
  182. MoveTask.Wait();
  183. }
  184. IEnumerable<File> Platform.DirectoryGetFolderFiles(Folder Folder, string FileMask)
  185. {
  186. var StorageFolder = SelectStorageFolder(Folder);
  187. var FilesTask = StorageFolder.GetFilesAsync(Windows.Storage.Search.CommonFileQuery.OrderByName).AsTask();
  188. FilesTask.Wait();
  189. var Regex = new System.Text.RegularExpressions.Regex("^" + System.Text.RegularExpressions.Regex.Escape(FileMask).Replace(@"\*", ".*").Replace(@"\?", ".") + "$");
  190. foreach (var StorageFile in FilesTask.Result)
  191. {
  192. if (Regex.IsMatch(StorageFile.Name))
  193. yield return new File(Folder, StorageFile.Name);
  194. }
  195. }
  196. System.IO.Stream Platform.DirectoryOpenAsset(Asset Asset)
  197. {
  198. var InstallFolder = Windows.ApplicationModel.Package.Current.InstalledLocation;
  199. var FileTask = InstallFolder.GetFileAsync(System.IO.Path.Combine("Assets", Asset.Name)).AsTask();
  200. FileTask.Wait();
  201. var StreamTask = FileTask.Result.OpenStreamForReadAsync();
  202. StreamTask.Wait();
  203. return StreamTask.Result;
  204. }
  205. bool Platform.DirectoryExistsAsset(Asset Asset)
  206. {
  207. var InstallFolder = Windows.ApplicationModel.Package.Current.InstalledLocation;
  208. var FileTask = InstallFolder.TryGetItemAsync(System.IO.Path.Combine("Assets", Asset.Name)).AsTask();
  209. FileTask.Wait();
  210. return FileTask.Result != null;
  211. }
  212. bool Platform.LocationIsSupported
  213. {
  214. get { return false; }
  215. }
  216. void Platform.LocationLookup(LocationLookup LocationLookup)
  217. {
  218. // TODO: implement windows 8 app location services.
  219. LocationLookup.SetPlacemarks(new Placemark[] { });
  220. }
  221. void Platform.AudioPlaySound(Sound Sound, float Volume)
  222. {
  223. MediaUtilities.Play(Sound, Volume);
  224. }
  225. void Platform.WindowAsynchronise(Action Action)
  226. {
  227. Engine.CoreWindow.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () => Action()).AsTask().Forget();
  228. }
  229. Modifier Platform.WindowGetModifier()
  230. {
  231. return Engine.GetModifier();
  232. }
  233. long Platform.ProcessMemoryBytes()
  234. {
  235. return GC.GetTotalMemory(false);
  236. }
  237. void Platform.WebSocketConnect(WebSocket Socket)
  238. {
  239. var TcpClient = new Inv.Tcp.Client(Socket.Host, Socket.Port);
  240. TcpClient.Connect();
  241. Socket.Node = TcpClient;
  242. Socket.SetStreams(TcpClient.InputStream, TcpClient.OutputStream);
  243. }
  244. void Platform.WebSocketDisconnect(WebSocket Socket)
  245. {
  246. var TcpClient = (Inv.Tcp.Client)Socket.Node;
  247. if (TcpClient != null)
  248. {
  249. Socket.Node = null;
  250. Socket.SetStreams(null, null);
  251. TcpClient.Disconnect();
  252. }
  253. }
  254. void Platform.WebLaunchUri(Uri Uri)
  255. {
  256. Windows.System.Launcher.LaunchUriAsync(Uri).AsTask().Wait();
  257. }
  258. void Platform.MarketBrowse(string AppleiTunesID, string GooglePlayID, string WindowsStoreID)
  259. {
  260. Windows.System.Launcher.LaunchUriAsync(new Uri("ms-windows-store:REVIEW?PFN=" + WindowsStoreID)).AsTask().Wait();
  261. }
  262. void Platform.VaultLoadSecret(Secret Secret)
  263. {
  264. Vault.Load(Secret);
  265. }
  266. void Platform.VaultSaveSecret(Secret Secret)
  267. {
  268. Vault.Save(Secret);
  269. }
  270. void Platform.VaultDeleteSecret(Secret Secret)
  271. {
  272. Vault.Delete(Secret);
  273. }
  274. private Windows.Storage.StorageFolder SelectStorageFolder(Folder Folder)
  275. {
  276. if (Folder.Name == null)
  277. return LocalFolder;
  278. var FolderTask = LocalFolder.TryGetItemAsync(Folder.Name).AsTask();
  279. FolderTask.Wait();
  280. if (FolderTask.Result != null)
  281. return FolderTask.Result as Windows.Storage.StorageFolder;
  282. var CreateTask = LocalFolder.CreateFolderAsync(Folder.Name).AsTask();
  283. CreateTask.Wait();
  284. return CreateTask.Result;
  285. }
  286. private UwaEngine Engine;
  287. private UwaVault Vault;
  288. private Windows.Storage.StorageFolder LocalFolder;
  289. }
  290. public static class MediaUtilities
  291. {
  292. static MediaUtilities()
  293. {
  294. SoundIdDictionary = new Dictionary<Sound, Windows.UI.Xaml.Controls.MediaElement>();
  295. }
  296. public static void Play(Inv.Sound InvSound, float VolumeScale)
  297. {
  298. Windows.UI.Xaml.Controls.MediaElement MediaElement;
  299. if (VolumeScale == 1.0F)
  300. {
  301. MediaElement = SoundIdDictionary.GetOrAdd(InvSound, S => ProduceMediaElement(S, VolumeScale));
  302. // can only overlap the same sound effect by having two media elements.
  303. if (MediaElement.CurrentState == Windows.UI.Xaml.Media.MediaElementState.Playing)
  304. MediaElement = ProduceMediaElement(InvSound, VolumeScale);
  305. }
  306. else
  307. {
  308. MediaElement = ProduceMediaElement(InvSound, VolumeScale);
  309. }
  310. MediaElement.Play();
  311. }
  312. private static Windows.UI.Xaml.Controls.MediaElement ProduceMediaElement(Inv.Sound Sound, float Volume)
  313. {
  314. var Result = new Windows.UI.Xaml.Controls.MediaElement();
  315. var MemoryStream = new Windows.Storage.Streams.InMemoryRandomAccessStream();
  316. using (var DataWriter = new Windows.Storage.Streams.DataWriter(MemoryStream))
  317. {
  318. // Write the bytes to the stream
  319. DataWriter.WriteBytes(Sound.GetBuffer());
  320. // Store the bytes to the MemoryStream
  321. DataWriter.StoreAsync().AsTask().Wait();
  322. // Not necessary, but do it anyway
  323. DataWriter.FlushAsync().AsTask().Wait();
  324. // Detach from the Memory stream so we don't close it
  325. DataWriter.DetachStream();
  326. }
  327. Result.Volume = Volume;
  328. Result.SetSource(MemoryStream, "mp3");
  329. Result.MediaEnded += (Sender, Event) => Result.Stop();
  330. return Result;
  331. }
  332. private static Dictionary<Inv.Sound, Windows.UI.Xaml.Controls.MediaElement> SoundIdDictionary;
  333. }
  334. internal sealed class UwaEngine
  335. {
  336. public UwaEngine(Windows.UI.Xaml.Controls.Page UwaPage, Inv.Application Application)
  337. {
  338. this.UwaPage = UwaPage;
  339. this.InvApplication = Application;
  340. this.UwaMaster = new Windows.UI.Xaml.Controls.Grid();
  341. UwaPage.Content = UwaMaster;
  342. this.ColourBrushDictionary = new Dictionary<Inv.Colour, Windows.UI.Xaml.Media.Brush>();
  343. this.MediaImageDictionary = new Dictionary<Inv.Image, Windows.UI.Xaml.Media.Imaging.BitmapSource>();
  344. this.CanvasBitmapDictionary = new Dictionary<Inv.Image, Microsoft.Graphics.Canvas.ICanvasImage>();
  345. #region Key mapping.
  346. this.KeyDictionary = new Dictionary<Windows.System.VirtualKey, Inv.Key>()
  347. {
  348. { Windows.System.VirtualKey.Number0, Key.n0 },
  349. { Windows.System.VirtualKey.Number1, Key.n1 },
  350. { Windows.System.VirtualKey.Number2, Key.n2 },
  351. { Windows.System.VirtualKey.Number3, Key.n3 },
  352. { Windows.System.VirtualKey.Number4, Key.n4 },
  353. { Windows.System.VirtualKey.Number5, Key.n5 },
  354. { Windows.System.VirtualKey.Number6, Key.n6 },
  355. { Windows.System.VirtualKey.Number7, Key.n7 },
  356. { Windows.System.VirtualKey.Number8, Key.n8 },
  357. { Windows.System.VirtualKey.Number9, Key.n9 },
  358. { Windows.System.VirtualKey.A, Key.A },
  359. { Windows.System.VirtualKey.B, Key.B },
  360. { Windows.System.VirtualKey.C, Key.C },
  361. { Windows.System.VirtualKey.D, Key.D },
  362. { Windows.System.VirtualKey.E, Key.E },
  363. { Windows.System.VirtualKey.F, Key.F },
  364. { Windows.System.VirtualKey.G, Key.G },
  365. { Windows.System.VirtualKey.H, Key.H },
  366. { Windows.System.VirtualKey.I, Key.I },
  367. { Windows.System.VirtualKey.J, Key.J },
  368. { Windows.System.VirtualKey.K, Key.K },
  369. { Windows.System.VirtualKey.L, Key.L },
  370. { Windows.System.VirtualKey.M, Key.M },
  371. { Windows.System.VirtualKey.N, Key.N },
  372. { Windows.System.VirtualKey.O, Key.O },
  373. { Windows.System.VirtualKey.P, Key.P },
  374. { Windows.System.VirtualKey.Q, Key.Q },
  375. { Windows.System.VirtualKey.R, Key.R },
  376. { Windows.System.VirtualKey.S, Key.S },
  377. { Windows.System.VirtualKey.T, Key.T },
  378. { Windows.System.VirtualKey.U, Key.U },
  379. { Windows.System.VirtualKey.V, Key.V },
  380. { Windows.System.VirtualKey.W, Key.W },
  381. { Windows.System.VirtualKey.X, Key.X },
  382. { Windows.System.VirtualKey.Y, Key.Y },
  383. { Windows.System.VirtualKey.Z, Key.Z },
  384. { Windows.System.VirtualKey.F1, Key.F1 },
  385. { Windows.System.VirtualKey.F2, Key.F2 },
  386. { Windows.System.VirtualKey.F3, Key.F3 },
  387. { Windows.System.VirtualKey.F4, Key.F4 },
  388. { Windows.System.VirtualKey.F5, Key.F5 },
  389. { Windows.System.VirtualKey.F6, Key.F6 },
  390. { Windows.System.VirtualKey.F7, Key.F7 },
  391. { Windows.System.VirtualKey.F8, Key.F8 },
  392. { Windows.System.VirtualKey.F9, Key.F9 },
  393. { Windows.System.VirtualKey.F10, Key.F10 },
  394. { Windows.System.VirtualKey.F11, Key.F11 },
  395. { Windows.System.VirtualKey.F12, Key.F12 },
  396. { Windows.System.VirtualKey.Escape, Key.Escape },
  397. { Windows.System.VirtualKey.Enter, Key.Enter },
  398. { Windows.System.VirtualKey.Tab, Key.Tab },
  399. { Windows.System.VirtualKey.Space, Key.Space },
  400. { Windows.System.VirtualKey.Decimal, Key.Period },
  401. { (Windows.System.VirtualKey)188, Key.Comma },
  402. { (Windows.System.VirtualKey)192, Key.BackQuote },
  403. { Windows.System.VirtualKey.Add, Key.Plus },
  404. { Windows.System.VirtualKey.Subtract, Key.Minus },
  405. { Windows.System.VirtualKey.Up, Key.Up },
  406. { Windows.System.VirtualKey.Down, Key.Down },
  407. { Windows.System.VirtualKey.Left, Key.Left },
  408. { Windows.System.VirtualKey.Right, Key.Right },
  409. { Windows.System.VirtualKey.Home, Key.Home },
  410. { Windows.System.VirtualKey.End, Key.End },
  411. { Windows.System.VirtualKey.PageUp, Key.PageUp },
  412. { Windows.System.VirtualKey.PageDown, Key.PageDown },
  413. { Windows.System.VirtualKey.Clear, Key.Clear },
  414. { Windows.System.VirtualKey.Insert, Key.Insert },
  415. { Windows.System.VirtualKey.Delete, Key.Delete },
  416. { Windows.System.VirtualKey.Divide, Key.Slash },
  417. { Windows.System.VirtualKey.Multiply, Key.Asterisk },
  418. { (Windows.System.VirtualKey)190, Key.Period },
  419. { (Windows.System.VirtualKey)191, Key.Slash },
  420. { (Windows.System.VirtualKey)220, Key.Backslash },
  421. //{ (Windows.System.VirtualKey)255, }, // Happens when F10 key is spammed?
  422. };
  423. #endregion
  424. this.RouteDictionary = new Dictionary<Type, Func<Inv.Panel, Windows.UI.Xaml.FrameworkElement>>()
  425. {
  426. { typeof(Inv.Button), TranslateButton },
  427. { typeof(Inv.Canvas), TranslateCanvas },
  428. { typeof(Inv.Dock), TranslateDock },
  429. { typeof(Inv.Edit), TranslateEdit },
  430. { typeof(Inv.Graphic), TranslateGraphic },
  431. { typeof(Inv.Label), TranslateLabel },
  432. { typeof(Inv.Memo), TranslateMemo },
  433. { typeof(Inv.Overlay), TranslateOverlay },
  434. { typeof(Inv.Render), TranslateRender },
  435. { typeof(Inv.Scroll), TranslateScroll },
  436. { typeof(Inv.Frame), TranslateFrame },
  437. { typeof(Inv.Stack), TranslateStack },
  438. { typeof(Inv.Table), TranslateTable },
  439. };
  440. InvApplication.SetPlatform(new UwaPlatform(this));
  441. }
  442. private void KeyDown(Windows.UI.Core.CoreWindow Sender, Windows.UI.Core.KeyEventArgs Event)
  443. {
  444. // ignore keystrokes while transitioning.
  445. if (UwaMaster.Children.Count == 1)
  446. KeyPress(Event.VirtualKey);
  447. Event.Handled = true;
  448. }
  449. private void AcceleratorKeyActivated(Windows.UI.Core.CoreDispatcher Sender, Windows.UI.Core.AcceleratorKeyEventArgs Event)
  450. {
  451. var IsSystemKey = (Event.VirtualKey == Windows.System.VirtualKey.Tab ||
  452. Event.VirtualKey == Windows.System.VirtualKey.Menu ||
  453. Event.VirtualKey == Windows.System.VirtualKey.LeftMenu ||
  454. Event.VirtualKey == Windows.System.VirtualKey.RightMenu) && Event.EventType == Windows.UI.Core.CoreAcceleratorKeyEventType.KeyDown;
  455. var IsFunctionKey = !Event.KeyStatus.IsMenuKeyDown && Event.VirtualKey >= Windows.System.VirtualKey.F1 && Event.VirtualKey <= Windows.System.VirtualKey.F12 && Event.EventType == Windows.UI.Core.CoreAcceleratorKeyEventType.SystemKeyDown;
  456. if (IsSystemKey || IsFunctionKey)
  457. {
  458. // ignore keystrokes while transitioning.
  459. if (UwaMaster.Children.Count == 1)
  460. KeyPress(Event.VirtualKey);
  461. Event.Handled = true;
  462. }
  463. else if (Event.KeyStatus.IsMenuKeyDown && Event.EventType == Windows.UI.Core.CoreAcceleratorKeyEventType.SystemKeyDown && Event.VirtualKey >= Windows.System.VirtualKey.F4)
  464. {
  465. // we can prevent the closing of the app from Alt+F4.
  466. Event.Handled = !InvApplication.ExitQueryInvoke();
  467. }
  468. }
  469. private void KeyPress(Windows.System.VirtualKey VirtualKey)
  470. {
  471. var InvSurface = InvApplication.Window.ActiveSurface;
  472. if (InvSurface != null)
  473. {
  474. var InvKey = TranslateKey(VirtualKey);
  475. if (InvKey != null)
  476. {
  477. var Keystroke = new Keystroke()
  478. {
  479. Key = InvKey.Value,
  480. Modifier = GetModifier()
  481. };
  482. InvSurface.KeystrokeInvoke(Keystroke);
  483. Process();
  484. }
  485. }
  486. }
  487. public void Start()
  488. {
  489. Resize();
  490. // TODO: unique hardware identifier: Windows.System.Profile.HardwareIdentification.GetPackageSpecificToken(null);
  491. InvApplication.Device.Name = ""; // TODO: is this hanging? UwaSystem.GetMachineName();
  492. InvApplication.Device.Model = ""; // TODO: is this hanging? UwaSystem.GetDeviceModel();
  493. InvApplication.Device.System = "";// TODO: this is hanging? UwaSystem.GetWindowsVersion();
  494. InvApplication.StartInvoke();
  495. Process();
  496. Windows.ApplicationModel.Core.CoreApplication.UnhandledErrorDetected += UnhandledErrorDetected;
  497. Windows.ApplicationModel.Core.CoreApplication.Exiting += Exiting;
  498. Windows.ApplicationModel.Core.CoreApplication.Suspending += Suspending;
  499. Windows.ApplicationModel.Core.CoreApplication.Resuming += Resuming;
  500. Windows.UI.Xaml.Media.CompositionTarget.Rendering += Rendering;
  501. this.CoreWindow = Windows.UI.Core.CoreWindow.GetForCurrentThread();
  502. CoreWindow.KeyDown += KeyDown;
  503. CoreWindow.Dispatcher.AcceleratorKeyActivated += AcceleratorKeyActivated;
  504. CoreWindow.SizeChanged += SizeChanged;
  505. CoreWindow.PointerPressed += PointerPressed;
  506. CoreWindow.PointerReleased += PointerReleased;
  507. CoreWindow.PointerMoved += PointerMoved;
  508. }
  509. public void Stop()
  510. {
  511. // NOTE: InvApplication.StopInvoke() is called by Exiting.
  512. if (CoreWindow != null)
  513. {
  514. CoreWindow.Dispatcher.AcceleratorKeyActivated -= AcceleratorKeyActivated;
  515. CoreWindow.KeyDown -= KeyDown;
  516. CoreWindow.SizeChanged -= SizeChanged;
  517. CoreWindow.PointerPressed -= PointerPressed;
  518. CoreWindow.PointerReleased -= PointerReleased;
  519. CoreWindow.PointerMoved -= PointerMoved;
  520. }
  521. Windows.UI.Xaml.Media.CompositionTarget.Rendering -= Rendering;
  522. Windows.ApplicationModel.Core.CoreApplication.Suspending -= Suspending;
  523. Windows.ApplicationModel.Core.CoreApplication.Resuming -= Resuming;
  524. Windows.ApplicationModel.Core.CoreApplication.Exiting -= Exiting;
  525. Windows.ApplicationModel.Core.CoreApplication.UnhandledErrorDetected -= UnhandledErrorDetected;
  526. }
  527. internal Windows.UI.Core.CoreWindow CoreWindow { get; private set; }
  528. internal Modifier GetModifier()
  529. {
  530. return new Modifier()
  531. {
  532. IsLeftShift = (CoreWindow.GetKeyState(Windows.System.VirtualKey.LeftShift) & Windows.UI.Core.CoreVirtualKeyStates.Down) == Windows.UI.Core.CoreVirtualKeyStates.Down,
  533. IsRightShift = (CoreWindow.GetKeyState(Windows.System.VirtualKey.RightShift) & Windows.UI.Core.CoreVirtualKeyStates.Down) == Windows.UI.Core.CoreVirtualKeyStates.Down,
  534. IsLeftAlt = (CoreWindow.GetKeyState(Windows.System.VirtualKey.LeftMenu) & Windows.UI.Core.CoreVirtualKeyStates.Down) == Windows.UI.Core.CoreVirtualKeyStates.Down,
  535. IsRightAlt = (CoreWindow.GetKeyState(Windows.System.VirtualKey.RightMenu) & Windows.UI.Core.CoreVirtualKeyStates.Down) == Windows.UI.Core.CoreVirtualKeyStates.Down,
  536. IsLeftCtrl = (CoreWindow.GetKeyState(Windows.System.VirtualKey.LeftControl) & Windows.UI.Core.CoreVirtualKeyStates.Down) == Windows.UI.Core.CoreVirtualKeyStates.Down,
  537. IsRightCtrl = (CoreWindow.GetKeyState(Windows.System.VirtualKey.RightControl) & Windows.UI.Core.CoreVirtualKeyStates.Down) == Windows.UI.Core.CoreVirtualKeyStates.Down
  538. };
  539. }
  540. private void Resize()
  541. {
  542. var Display = Windows.Graphics.Display.DisplayInformation.GetForCurrentView();
  543. var ResolutionWidthPixels = (int)Windows.UI.Xaml.Window.Current.Bounds.Width;
  544. var ResolutionHeightPixels = (int)Windows.UI.Xaml.Window.Current.Bounds.Height;
  545. InvApplication.Window.Width = ResolutionWidthPixels;
  546. InvApplication.Window.Height = ResolutionHeightPixels;
  547. }
  548. private void Process()
  549. {
  550. if (InvApplication.IsExit)
  551. {
  552. Windows.ApplicationModel.Core.CoreApplication.Exit();
  553. Stop();
  554. }
  555. else
  556. {
  557. var InvWindow = InvApplication.Window;
  558. if (InvWindow.ActiveTimerSet.Count > 0)
  559. {
  560. foreach (var InvTimer in InvWindow.ActiveTimerSet)
  561. {
  562. var UwaTimer = AccessTimer(InvTimer, S =>
  563. {
  564. var Result = new Windows.UI.Xaml.DispatcherTimer();
  565. Result.Tick += (Sender, Event) => InvTimer.IntervalInvoke();
  566. return Result;
  567. });
  568. if (UwaTimer.Interval != InvTimer.IntervalTime)
  569. UwaTimer.Interval = InvTimer.IntervalTime;
  570. if (InvTimer.IsEnabled && !UwaTimer.IsEnabled)
  571. UwaTimer.Start();
  572. else if (!InvTimer.IsEnabled && UwaTimer.IsEnabled)
  573. UwaTimer.Stop();
  574. }
  575. InvWindow.ActiveTimerSet.RemoveWhere(T => !T.IsEnabled);
  576. }
  577. var InvSurface = InvWindow.ActiveSurface;
  578. if (InvSurface != null)
  579. {
  580. var UwaSurface = AccessSurface(InvSurface, S =>
  581. {
  582. var Result = new UwaSurface();
  583. return Result;
  584. });
  585. if (!UwaMaster.Children.Contains(UwaSurface))
  586. InvSurface.ArrangeInvoke();
  587. ProcessTransition(UwaSurface);
  588. InvSurface.ComposeInvoke();
  589. if (InvSurface.Render())
  590. {
  591. UwaSurface.Border.Background = TranslateMediaBrush(InvSurface.Background.Colour);
  592. UwaSurface.Border.Child = TranslatePanel(InvSurface.Content);
  593. }
  594. InvSurface.ProcessChanges(P => TranslatePanel(P));
  595. if (InvSurface.Focus != null)
  596. {
  597. var UwaOverrideFocus = InvSurface.Focus.Node as UwaOverrideFocusContract;
  598. InvSurface.Focus = null;
  599. if (UwaOverrideFocus != null)
  600. UwaMaster.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () => UwaOverrideFocus.OverrideFocus()).AsTask().Forget();
  601. }
  602. }
  603. else
  604. {
  605. UwaPage.Content = null;
  606. }
  607. if (InvWindow.Render())
  608. {
  609. //UwaWindow.Title = InvApplication.Title ?? "";
  610. //UwaMaster.Background = TranslateBrush(InvWindow.Background.Colour);
  611. }
  612. if (InvSurface != null)
  613. ProcessAnimation(InvSurface);
  614. InvWindow.DisplayRate.Calculate();
  615. }
  616. }
  617. private void ProcessTransition(UwaSurface UwaSurface)
  618. {
  619. var InvWindow = InvApplication.Window;
  620. var InvTransition = InvWindow.ActiveTransition;
  621. if (InvTransition == null)
  622. {
  623. Debug.Assert(UwaMaster.Children.Contains(UwaSurface));
  624. }
  625. else if (UwaMaster.Children.Count <= 1) // don't transition while animating a previous transition.
  626. {
  627. var UwaFromSurface = UwaMaster.Children.Count == 0 ? null : (UwaSurface)UwaMaster.Children[0];
  628. var UwaToSurface = UwaSurface;
  629. if (UwaFromSurface == UwaToSurface)
  630. {
  631. Debug.WriteLine("Transition to self");
  632. }
  633. else
  634. {
  635. switch (InvTransition.Animation)
  636. {
  637. case TransitionAnimation.None:
  638. UwaMaster.Children.Clear();
  639. UwaMaster.Children.Add(UwaToSurface);
  640. break;
  641. case TransitionAnimation.Fade:
  642. UwaMaster.Children.Add(UwaToSurface);
  643. UwaToSurface.IsHitTestVisible = false;
  644. UwaToSurface.Opacity = 0.0;
  645. var UwaFadeDuration = new Windows.UI.Xaml.Duration(TimeSpan.FromMilliseconds(InvTransition.Duration.TotalMilliseconds / 2));
  646. var UwaFadeOutStoryboard = new Windows.UI.Xaml.Media.Animation.Storyboard();
  647. var UwaFadeInStoryboard = new Windows.UI.Xaml.Media.Animation.Storyboard();
  648. var UwaFadeInAnimation = new Windows.UI.Xaml.Media.Animation.DoubleAnimation()
  649. {
  650. FillBehavior = Windows.UI.Xaml.Media.Animation.FillBehavior.HoldEnd,
  651. From = 0.0,
  652. To = 1.0,
  653. Duration = UwaFadeDuration
  654. };
  655. Windows.UI.Xaml.Media.Animation.Storyboard.SetTarget(UwaFadeInAnimation, UwaToSurface);
  656. Windows.UI.Xaml.Media.Animation.Storyboard.SetTargetProperty(UwaFadeInAnimation, "Opacity");
  657. UwaFadeInStoryboard.Children.Add(UwaFadeInAnimation);
  658. UwaFadeInAnimation.Completed += (Sender, Event) =>
  659. {
  660. UwaToSurface.IsHitTestVisible = true;
  661. UwaToSurface.Opacity = 1.0;
  662. };
  663. if (UwaFromSurface == null)
  664. {
  665. UwaFadeInStoryboard.Begin();
  666. }
  667. else
  668. {
  669. UwaFromSurface.IsHitTestVisible = false;
  670. var UwaFadeOutAnimation = new Windows.UI.Xaml.Media.Animation.DoubleAnimation()
  671. {
  672. FillBehavior = Windows.UI.Xaml.Media.Animation.FillBehavior.HoldEnd,
  673. From = 1.0,
  674. To = 0.0,
  675. Duration = UwaFadeDuration
  676. };
  677. Windows.UI.Xaml.Media.Animation.Storyboard.SetTarget(UwaFadeOutAnimation, UwaFromSurface);
  678. Windows.UI.Xaml.Media.Animation.Storyboard.SetTargetProperty(UwaFadeOutAnimation, "Opacity");
  679. UwaFadeOutStoryboard.Children.Add(UwaFadeOutAnimation);
  680. UwaFadeOutAnimation.Completed += (Sender, Event) =>
  681. {
  682. UwaFromSurface.IsHitTestVisible = true;
  683. UwaFromSurface.Opacity = 1.0;
  684. UwaMaster.Children.Remove(UwaFromSurface);
  685. UwaFadeInStoryboard.Begin();
  686. };
  687. UwaFadeOutStoryboard.Begin();
  688. }
  689. break;
  690. case TransitionAnimation.CarouselBack:
  691. case TransitionAnimation.CarouselNext:
  692. var CarouselForward = InvTransition.Animation == TransitionAnimation.CarouselNext;
  693. var UwaCarouselDuration = new Windows.UI.Xaml.Duration(InvTransition.Duration);
  694. var UwaCarouselStoryboard = new Windows.UI.Xaml.Media.Animation.Storyboard();
  695. if (UwaFromSurface != null)
  696. {
  697. var FromCarouselTransform = new Windows.UI.Xaml.Media.TranslateTransform() { X = 0, Y = 0 };
  698. UwaFromSurface.RenderTransform = FromCarouselTransform;
  699. UwaFromSurface.IsHitTestVisible = false;
  700. var UwaFromAnimation = new Windows.UI.Xaml.Media.Animation.DoubleAnimation()
  701. {
  702. //AccelerationRatio = 0.5,
  703. //DecelerationRatio = 0.5,
  704. Duration = UwaCarouselDuration,
  705. From = 0,
  706. To = CarouselForward ? -UwaMaster.ActualWidth : UwaMaster.ActualWidth
  707. };
  708. Windows.UI.Xaml.Media.Animation.Storyboard.SetTarget(UwaFromAnimation, FromCarouselTransform);
  709. Windows.UI.Xaml.Media.Animation.Storyboard.SetTargetProperty(UwaFromAnimation, "X");
  710. UwaCarouselStoryboard.Children.Add(UwaFromAnimation);
  711. }
  712. if (UwaToSurface != null)
  713. {
  714. var ToCarouselTransform = new Windows.UI.Xaml.Media.TranslateTransform() { X = 0, Y = 0 };
  715. UwaToSurface.RenderTransform = ToCarouselTransform;
  716. UwaToSurface.IsHitTestVisible = false;
  717. UwaMaster.Children.Add(UwaToSurface);
  718. var UwaToAnimation = new Windows.UI.Xaml.Media.Animation.DoubleAnimation()
  719. {
  720. //AccelerationRatio = 0.5,
  721. //DecelerationRatio = 0.5,
  722. Duration = UwaCarouselDuration,
  723. From = CarouselForward ? UwaMaster.ActualWidth : -UwaMaster.ActualWidth,
  724. To = 0
  725. };
  726. Windows.UI.Xaml.Media.Animation.Storyboard.SetTarget(UwaToAnimation, ToCarouselTransform);
  727. Windows.UI.Xaml.Media.Animation.Storyboard.SetTargetProperty(UwaToAnimation, "X");
  728. UwaCarouselStoryboard.Children.Add(UwaToAnimation);
  729. }
  730. UwaCarouselStoryboard.Completed += (Sender, Event) =>
  731. {
  732. if (UwaFromSurface != null)
  733. {
  734. UwaFromSurface.IsHitTestVisible = true;
  735. UwaMaster.Children.Remove(UwaFromSurface);
  736. UwaFromSurface.RenderTransform = null;
  737. }
  738. if (UwaToSurface != null)
  739. {
  740. UwaToSurface.IsHitTestVisible = true;
  741. UwaToSurface.RenderTransform = null;
  742. }
  743. };
  744. UwaCarouselStoryboard.Begin();
  745. break;
  746. default:
  747. throw new Exception("TransitionAnimation not handled: " + InvTransition.Animation);
  748. }
  749. }
  750. InvWindow.ActiveTransition = null;
  751. }
  752. }
  753. private void ProcessAnimation(Inv.Surface InvSurfaceActive)
  754. {
  755. if (InvSurfaceActive.StopAnimationSet.Count > 0)
  756. {
  757. foreach (var InvAnimation in InvSurfaceActive.StopAnimationSet)
  758. {
  759. if (InvAnimation.Node != null)
  760. {
  761. var WpfStoryboard = (Windows.UI.Xaml.Media.Animation.Storyboard)InvAnimation.Node;
  762. foreach (var InvTarget in InvAnimation.GetTargets())
  763. {
  764. var WpfPanel = TranslatePanel(InvTarget.Panel);
  765. if (WpfPanel != null)
  766. {
  767. WpfPanel.Opacity = (float)WpfPanel.Opacity;
  768. InvTarget.Panel.Opacity.BypassSet((float)WpfPanel.Opacity);
  769. }
  770. }
  771. WpfStoryboard.Stop();
  772. }
  773. }
  774. InvSurfaceActive.StopAnimationSet.Clear();
  775. }
  776. else if (InvSurfaceActive.StartAnimationSet.Count > 0)
  777. {
  778. foreach (var InvAnimation in InvSurfaceActive.StartAnimationSet)
  779. {
  780. var WpfStoryboard = new Windows.UI.Xaml.Media.Animation.Storyboard();
  781. InvAnimation.Node = WpfStoryboard;
  782. WpfStoryboard.Completed += (Sender, Event) =>
  783. {
  784. InvAnimation.Complete();
  785. InvAnimation.Node = null;
  786. };
  787. foreach (var InvTarget in InvAnimation.GetTargets())
  788. {
  789. var InvPanel = InvTarget.Panel;
  790. var WpfPanel = TranslatePanel(InvPanel);
  791. foreach (var InvCommand in InvTarget.GetCommands())
  792. WpfStoryboard.Children.Add(TranslateAnimationCommand(InvPanel, WpfPanel, InvCommand));
  793. }
  794. WpfStoryboard.Begin();
  795. }
  796. InvSurfaceActive.StartAnimationSet.Clear();
  797. }
  798. }
  799. private Windows.UI.Xaml.Media.Animation.Timeline TranslateAnimationCommand(Inv.Panel InvPanel, Windows.UI.Xaml.FrameworkElement WpfPanel, AnimationCommand InvCommand)
  800. {
  801. // TODO: more types of animation commands.
  802. var Result = TranslateAnimationOpacityCommand(InvPanel, WpfPanel, InvCommand);
  803. Result.Completed += (Sender, Event) => InvCommand.Complete();
  804. return Result;
  805. }
  806. private Windows.UI.Xaml.Media.Animation.Timeline TranslateAnimationOpacityCommand(Inv.Panel InvPanel, Windows.UI.Xaml.FrameworkElement WpfPanel, AnimationCommand InvCommand)
  807. {
  808. var InvOpacityCommand = (Inv.AnimationOpacityCommand)InvCommand;
  809. var Result = new Windows.UI.Xaml.Media.Animation.DoubleAnimation()
  810. {
  811. From = InvOpacityCommand.From,
  812. To = InvOpacityCommand.To,
  813. Duration = InvOpacityCommand.Duration,
  814. FillBehavior = Windows.UI.Xaml.Media.Animation.FillBehavior.HoldEnd
  815. };
  816. // NOTE: if you set BeginTime to null, the animation will not run!
  817. if (InvOpacityCommand.Offset != null)
  818. Result.BeginTime = InvOpacityCommand.Offset;
  819. Windows.UI.Xaml.Media.Animation.Storyboard.SetTarget(Result, WpfPanel);
  820. Windows.UI.Xaml.Media.Animation.Storyboard.SetTargetProperty(Result, "Opacity");
  821. WpfPanel.Opacity = InvOpacityCommand.From;
  822. InvPanel.Opacity.BypassSet(InvOpacityCommand.To);
  823. Result.Completed += (Sender, Event) =>
  824. {
  825. WpfPanel.Opacity = InvPanel.Opacity.Get();
  826. };
  827. return Result;
  828. }
  829. private Windows.UI.Xaml.FrameworkElement TranslateButton(Inv.Panel InvPanel)
  830. {
  831. var InvButton = (Inv.Button)InvPanel;
  832. var UwaButton = AccessPanel(InvButton, P =>
  833. {
  834. var Result = new UwaButton();
  835. Result.PointerEntered += (Sender, Event) =>
  836. {
  837. Result.Border.Background = TranslateMediaBrush(P.Background.Colour != null ? P.Background.Colour.Value.Lighten(0.25F) : (Inv.Colour?)null);
  838. };
  839. Result.PointerExited += (Sender, Event) =>
  840. {
  841. Result.Border.Background = TranslateMediaBrush(P.Background.Colour != null ? P.Background.Colour : null);
  842. };
  843. Result.AddHandler(Windows.UI.Xaml.Controls.Primitives.ButtonBase.PointerPressedEvent, new Windows.UI.Xaml.Input.PointerEventHandler((S, E) =>
  844. {
  845. // NOTE: .PointerPressed += doesn't fire for buttons.
  846. Result.Border.Background = TranslateMediaBrush(P.Background.Colour != null ? P.Background.Colour.Value.Darken(0.25F) : (Inv.Colour?)null);
  847. }), true);
  848. Result.AddHandler(Windows.UI.Xaml.Controls.Primitives.ButtonBase.PointerReleasedEvent, new Windows.UI.Xaml.Input.PointerEventHandler((S, E) =>
  849. {
  850. // NOTE: .PointerReleased += doesn't fire for buttons.
  851. Result.Border.Background = TranslateMediaBrush(P.Background.Colour);
  852. }), true);
  853. Result.Tapped += (Sender, Event) =>
  854. {
  855. if (InvApplication.Window.IsActiveSurface(P.Surface))
  856. P.SingleTapInvoke();
  857. Event.Handled = true;
  858. };
  859. Result.RightTapped += (Sender, Event) =>
  860. {
  861. if (InvApplication.Window.IsActiveSurface(P.Surface))
  862. P.ContextTapInvoke();
  863. Event.Handled = true;
  864. };
  865. return Result;
  866. });
  867. RenderPanel(InvButton, UwaButton, () =>
  868. {
  869. TranslateLayout(InvButton, UwaButton, UwaButton.Border);
  870. UwaButton.IsEnabled = InvButton.IsEnabled;
  871. //UwaButton.Button.Focusable = InvButton.IsFocused;
  872. if (InvButton.ContentSingleton.Render())
  873. {
  874. UwaButton.Border.Child = null; // detach previous content in case it has moved.
  875. UwaButton.Border.Child = TranslatePanel(InvButton.ContentSingleton.Data);
  876. }
  877. });
  878. return UwaButton;
  879. }
  880. private Windows.UI.Xaml.FrameworkElement TranslateCanvas(Inv.Panel InvPanel)
  881. {
  882. var InvCanvas = (Inv.Canvas)InvPanel;
  883. var UwaCanvas = AccessPanel(InvCanvas, P =>
  884. {
  885. return new UwaCanvas();
  886. });
  887. RenderPanel(InvCanvas, UwaCanvas, () =>
  888. {
  889. TranslateLayout(InvCanvas, UwaCanvas.Border, UwaCanvas.Border);
  890. if (InvCanvas.PieceCollection.Render())
  891. {
  892. UwaCanvas.Canvas.Children.Clear();
  893. foreach (var InvElement in InvCanvas.PieceCollection)
  894. {
  895. var UwaElement = new Windows.UI.Xaml.Controls.Border();
  896. UwaCanvas.Canvas.Children.Add(UwaElement);
  897. Windows.UI.Xaml.Controls.Canvas.SetLeft(UwaElement, InvElement.Rect.Left);
  898. Windows.UI.Xaml.Controls.Canvas.SetTop(UwaElement, InvElement.Rect.Top);
  899. UwaElement.Width = InvElement.Rect.Width;
  900. UwaElement.Height = InvElement.Rect.Height;
  901. var UwaPanel = TranslatePanel(InvElement.Panel);
  902. UwaElement.Child = UwaPanel;
  903. }
  904. }
  905. });
  906. return UwaCanvas;
  907. }
  908. private Windows.UI.Xaml.FrameworkElement TranslateDock(Inv.Panel InvPanel)
  909. {
  910. var InvDock = (Inv.Dock)InvPanel;
  911. var IsHorizontal = InvDock.Orientation == DockOrientation.Horizontal;
  912. var UwaDock = AccessPanel(InvDock, P =>
  913. {
  914. var Result = new UwaDock();
  915. return Result;
  916. });
  917. RenderPanel(InvDock, UwaDock, () =>
  918. {
  919. TranslateLayout(InvDock, UwaDock.Border, UwaDock.Border);
  920. if (InvDock.CollectionRender())
  921. {
  922. UwaDock.Grid.Children.Clear();
  923. UwaDock.Grid.RowDefinitions.Clear();
  924. UwaDock.Grid.ColumnDefinitions.Clear();
  925. var Position = 0;
  926. foreach (var InvHeader in InvDock.HeaderCollection)
  927. {
  928. var UwaPanel = TranslatePanel(InvHeader);
  929. UwaDock.Grid.Children.Add(UwaPanel);
  930. if (IsHorizontal)
  931. {
  932. UwaDock.Grid.ColumnDefinitions.Add(new Windows.UI.Xaml.Controls.ColumnDefinition() { Width = Windows.UI.Xaml.GridLength.Auto });
  933. Windows.UI.Xaml.Controls.Grid.SetColumn(UwaPanel, Position);
  934. }
  935. else
  936. {
  937. UwaDock.Grid.RowDefinitions.Add(new Windows.UI.Xaml.Controls.RowDefinition() { Height = Windows.UI.Xaml.GridLength.Auto });
  938. Windows.UI.Xaml.Controls.Grid.SetRow(UwaPanel, Position);
  939. }
  940. Position++;
  941. }
  942. if (InvDock.HasClients())
  943. {
  944. foreach (var InvClient in InvDock.ClientCollection)
  945. {
  946. var UwaPanel = TranslatePanel(InvClient);
  947. UwaDock.Grid.Children.Add(UwaPanel);
  948. if (IsHorizontal)
  949. {
  950. UwaDock.Grid.ColumnDefinitions.Add(new Windows.UI.Xaml.Controls.ColumnDefinition() { Width = new Windows.UI.Xaml.GridLength(1.0, Windows.UI.Xaml.GridUnitType.Star) });
  951. Windows.UI.Xaml.Controls.Grid.SetColumn(UwaPanel, Position);
  952. }
  953. else
  954. {
  955. UwaDock.Grid.RowDefinitions.Add(new Windows.UI.Xaml.Controls.RowDefinition() { Height = new Windows.UI.Xaml.GridLength(1.0, Windows.UI.Xaml.GridUnitType.Star) });
  956. Windows.UI.Xaml.Controls.Grid.SetRow(UwaPanel, Position);
  957. }
  958. Position++;
  959. }
  960. }
  961. else
  962. {
  963. if (IsHorizontal)
  964. UwaDock.Grid.ColumnDefinitions.Add(new Windows.UI.Xaml.Controls.ColumnDefinition() { Width = new Windows.UI.Xaml.GridLength(1.0, Windows.UI.Xaml.GridUnitType.Star) });
  965. else
  966. UwaDock.Grid.RowDefinitions.Add(new Windows.UI.Xaml.Controls.RowDefinition() { Height = new Windows.UI.Xaml.GridLength(1.0, Windows.UI.Xaml.GridUnitType.Star) });
  967. Position++;
  968. }
  969. foreach (var InvFooter in InvDock.FooterCollection)
  970. {
  971. var UwaPanel = TranslatePanel(InvFooter);
  972. UwaDock.Grid.Children.Add(UwaPanel);
  973. if (IsHorizontal)
  974. {
  975. UwaDock.Grid.ColumnDefinitions.Add(new Windows.UI.Xaml.Controls.ColumnDefinition() { Width = Windows.UI.Xaml.GridLength.Auto });
  976. Windows.UI.Xaml.Controls.Grid.SetColumn(UwaPanel, Position);
  977. }
  978. else
  979. {
  980. UwaDock.Grid.RowDefinitions.Add(new Windows.UI.Xaml.Controls.RowDefinition() { Height = Windows.UI.Xaml.GridLength.Auto });
  981. Windows.UI.Xaml.Controls.Grid.SetRow(UwaPanel, Position);
  982. }
  983. Position++;
  984. }
  985. }
  986. });
  987. return UwaDock;
  988. }
  989. private Windows.UI.Xaml.FrameworkElement TranslateEdit(Inv.Panel InvPanel)
  990. {
  991. var InvEdit = (Inv.Edit)InvPanel;
  992. var IsPassword = InvEdit.Input == EditInput.Password;
  993. var UwaEdit = AccessPanel(InvEdit, P =>
  994. {
  995. var Result = new UwaEdit(IsPassword);
  996. // TODO: Uwa allowed input.
  997. switch (InvEdit.Input)
  998. {
  999. case EditInput.Text:
  1000. break;
  1001. case EditInput.Number:
  1002. break;
  1003. case EditInput.Integer:
  1004. break;
  1005. case EditInput.Decimal:
  1006. break;
  1007. case EditInput.Password:
  1008. break;
  1009. case EditInput.Name:
  1010. break;
  1011. case EditInput.Email:
  1012. break;
  1013. case EditInput.Uri:
  1014. break;
  1015. default:
  1016. throw new Exception("EditInput not handled: " + InvEdit.Input);
  1017. }
  1018. if (IsPassword)
  1019. Result.PasswordBox.PasswordChanged += (Sender, Event) => P.ChangeInvoke(Result.PasswordBox.Password);
  1020. else
  1021. Result.TextBox.TextChanged += (Sender, Event) => P.ChangeInvoke(Result.TextBox.Text);
  1022. return Result;
  1023. });
  1024. RenderPanel(InvEdit, UwaEdit, () =>
  1025. {
  1026. TranslateLayout(InvEdit, UwaEdit.Border, UwaEdit.Border);
  1027. if (IsPassword)
  1028. {
  1029. TranslateFont(InvEdit.Font, UwaEdit.PasswordBox);
  1030. UwaEdit.PasswordBox.IsEnabled = !InvEdit.IsReadOnly;
  1031. UwaEdit.PasswordBox.Password = InvEdit.Text ?? "";
  1032. }
  1033. else
  1034. {
  1035. TranslateFont(InvEdit.Font, UwaEdit.TextBox);
  1036. UwaEdit.TextBox.IsReadOnly = InvEdit.IsReadOnly;
  1037. UwaEdit.TextBox.Text = InvEdit.Text ?? "";
  1038. }
  1039. });
  1040. return UwaEdit;
  1041. }
  1042. private Windows.UI.Xaml.FrameworkElement TranslateGraphic(Inv.Panel InvPanel)
  1043. {
  1044. var InvGraphic = (Inv.Graphic)InvPanel;
  1045. var UwaGraphic = AccessPanel(InvGraphic, P =>
  1046. {
  1047. var Result = new UwaGraphic();
  1048. return Result;
  1049. });
  1050. RenderPanel(InvGraphic, UwaGraphic, () =>
  1051. {
  1052. var SizeChanged = InvGraphic.Size.IsChanged;
  1053. TranslateLayout(InvGraphic, UwaGraphic.Border, UwaGraphic.Border);
  1054. if (InvGraphic.ImageSingleton.Render() || SizeChanged)
  1055. UwaGraphic.Image.Source = TranslateMediaImage(InvGraphic.Image);
  1056. });
  1057. return UwaGraphic;
  1058. }
  1059. private Windows.UI.Xaml.FrameworkElement TranslateLabel(Inv.Panel InvPanel)
  1060. {
  1061. var InvLabel = (Inv.Label)InvPanel;
  1062. var UwaLabel = AccessPanel(InvLabel, P =>
  1063. {
  1064. var Result = new UwaLabel();
  1065. return Result;
  1066. });
  1067. RenderPanel(InvLabel, UwaLabel.Border, () =>
  1068. {
  1069. TranslateLayout(InvLabel, UwaLabel.Border, UwaLabel.Border);
  1070. TranslateFont(InvLabel.Font, UwaLabel.TextBlock);
  1071. UwaLabel.TextBlock.TextWrapping = InvLabel.LineWrapping ? Windows.UI.Xaml.TextWrapping.Wrap : Windows.UI.Xaml.TextWrapping.NoWrap;
  1072. UwaLabel.TextBlock.TextAlignment = InvLabel.Justification == null || InvLabel.Justification == Justification.Left ? Windows.UI.Xaml.TextAlignment.Left : InvLabel.Justification == Justification.Right ? Windows.UI.Xaml.TextAlignment.Right : Windows.UI.Xaml.TextAlignment.Center;
  1073. UwaLabel.TextBlock.Text = InvLabel.Text ?? "";
  1074. });
  1075. return UwaLabel;
  1076. }
  1077. private Windows.UI.Xaml.FrameworkElement TranslateMemo(Inv.Panel InvPanel)
  1078. {
  1079. var InvMemo = (Inv.Memo)InvPanel;
  1080. var UwaMemo = AccessPanel(InvMemo, P =>
  1081. {
  1082. var Result = new UwaMemo();
  1083. Result.TextBox.TextChanged += (Sender, Event) => P.ChangeInvoke(Result.Text);
  1084. return Result;
  1085. });
  1086. RenderPanel(InvMemo, UwaMemo, () =>
  1087. {
  1088. var IsAligning = InvMemo.Alignment.IsChanged;
  1089. TranslateLayout(InvMemo, UwaMemo.Border, UwaMemo.Border);
  1090. if (IsAligning)
  1091. {
  1092. // NOTE: this is a workaround to get the textbox to autosize properly.
  1093. UwaMemo.TextBox.HorizontalAlignment = UwaMemo.Border.HorizontalAlignment;
  1094. UwaMemo.TextBox.VerticalAlignment = UwaMemo.Border.VerticalAlignment;
  1095. }
  1096. TranslateFont(InvMemo.Font, UwaMemo.TextBox);
  1097. UwaMemo.TextBox.IsReadOnly = InvMemo.IsReadOnly;
  1098. UwaMemo.Text = InvMemo.Text ?? "";
  1099. });
  1100. return UwaMemo;
  1101. }
  1102. private Windows.UI.Xaml.FrameworkElement TranslateOverlay(Inv.Panel InvPanel)
  1103. {
  1104. var InvOverlay = (Inv.Overlay)InvPanel;
  1105. var UwaOverlay = AccessPanel(InvOverlay, P =>
  1106. {
  1107. var Result = new UwaOverlay();
  1108. return Result;
  1109. });
  1110. RenderPanel(InvOverlay, UwaOverlay, () =>
  1111. {
  1112. TranslateLayout(InvOverlay, UwaOverlay.Border, UwaOverlay.Border);
  1113. if (InvOverlay.PanelCollection.Render())
  1114. {
  1115. UwaOverlay.Grid.Children.Clear();
  1116. foreach (var InvElement in InvOverlay.GetPanels())
  1117. {
  1118. var UwaPanel = TranslatePanel(InvElement);
  1119. UwaOverlay.Grid.Children.Add(UwaPanel);
  1120. }
  1121. }
  1122. });
  1123. return UwaOverlay;
  1124. }
  1125. private Windows.UI.Xaml.FrameworkElement TranslateRender(Inv.Panel InvPanel)
  1126. {
  1127. var InvRender = (Inv.Render)InvPanel;
  1128. var UwaRender = AccessPanel(InvRender, P =>
  1129. {
  1130. var Result = new UwaRender();
  1131. var IsLeftPressed = false;
  1132. var PressedTimestamp = DateTime.Now;
  1133. Result.PointerMoved += (Sender, Event) =>
  1134. {
  1135. var MovedPoint = Event.GetCurrentPoint(Result);
  1136. P.MoveInvoke(TranslatePoint(MovedPoint.Position));
  1137. };
  1138. Result.PointerPressed += (Sender, Event) =>
  1139. {
  1140. Result.CapturePointer(Event.Pointer);
  1141. var PressedPoint = Event.GetCurrentPoint(Result);
  1142. if (PressedPoint.PointerDevice.PointerDeviceType != Windows.Devices.Input.PointerDeviceType.Mouse || PressedPoint.Properties.IsLeftButtonPressed)
  1143. {
  1144. IsLeftPressed = true;
  1145. PressedTimestamp = DateTime.Now;
  1146. P.PressInvoke(TranslatePoint(PressedPoint.Position));
  1147. }