using ElectronNET.API.Entities;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using Newtonsoft.Json.Serialization;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using System.Threading.Tasks;
namespace ElectronNET.API
{
///
///
///
public sealed class WindowManager
{
private static WindowManager _windowManager;
private static object _syncRoot = new object();
internal WindowManager() { }
internal static WindowManager Instance
{
get
{
if (_windowManager == null)
{
lock (_syncRoot)
{
if (_windowManager == null)
{
_windowManager = new WindowManager();
}
}
}
return _windowManager;
}
}
///
/// Quit when all windows are closed. (Default is true)
///
///
/// true if [quit window all closed]; otherwise, false.
///
public bool IsQuitOnWindowAllClosed
{
get { return _isQuitOnWindowAllClosed; }
set
{
BridgeConnector.Socket.Emit("quit-app-window-all-closed-event", value);
_isQuitOnWindowAllClosed = value;
}
}
private bool _isQuitOnWindowAllClosed = true;
///
/// Gets the browser windows.
///
///
/// The browser windows.
///
public IReadOnlyCollection BrowserWindows { get { return _browserWindows.AsReadOnly(); } }
private List _browserWindows = new List();
///
/// Gets the browser views.
///
///
/// The browser view.
///
public IReadOnlyCollection BrowserViews { get { return _browserViews.AsReadOnly(); } }
private List _browserViews = new List();
///
/// Creates the window asynchronous.
///
/// The load URL.
///
public async Task CreateWindowAsync(string loadUrl = "http://localhost")
{
return await CreateWindowAsync(new BrowserWindowOptions(), loadUrl);
}
///
/// Creates the window asynchronous.
///
/// The options.
/// The load URL.
///
public Task CreateWindowAsync(BrowserWindowOptions options, string loadUrl = "http://localhost")
{
var taskCompletionSource = new TaskCompletionSource();
BridgeConnector.Socket.On("BrowserWindowCreated", (id) =>
{
BridgeConnector.Socket.Off("BrowserWindowCreated");
string windowId = id.ToString();
BrowserWindow browserWindow = new BrowserWindow(int.Parse(windowId));
_browserWindows.Add(browserWindow);
taskCompletionSource.SetResult(browserWindow);
});
BridgeConnector.Socket.Off("BrowserWindowClosed");
BridgeConnector.Socket.On("BrowserWindowClosed", (ids) =>
{
var browserWindowIds = ((JArray)ids).ToObject();
for (int index = 0; index < _browserWindows.Count; index++)
{
if (!browserWindowIds.Contains(_browserWindows[index].Id))
{
_browserWindows.RemoveAt(index);
}
}
});
if (loadUrl.ToUpper() == "HTTP://LOCALHOST")
{
loadUrl = $"{loadUrl}:{BridgeSettings.WebPort}";
}
// Workaround Windows 10 / Electron Bug
// https://github.com/electron/electron/issues/4045
if (isWindows10())
{
options.Width = options.Width + 14;
options.Height = options.Height + 7;
}
if (options.X == -1 && options.Y == -1)
{
options.X = 0;
options.Y = 0;
BridgeConnector.Socket.Emit("createBrowserWindow", JObject.FromObject(options, _jsonSerializer), loadUrl);
}
else
{
// Workaround Windows 10 / Electron Bug
// https://github.com/electron/electron/issues/4045
if (isWindows10())
{
options.X = options.X - 7;
}
var ownjsonSerializer = new JsonSerializer()
{
ContractResolver = new CamelCasePropertyNamesContractResolver(),
NullValueHandling = NullValueHandling.Ignore
};
BridgeConnector.Socket.Emit("createBrowserWindow", JObject.FromObject(options, ownjsonSerializer), loadUrl);
}
return taskCompletionSource.Task;
}
private bool isWindows10()
{
return RuntimeInformation.OSDescription.Contains("Windows 10");
}
///
/// A BrowserView can be used to embed additional web content into a BrowserWindow.
/// It is like a child window, except that it is positioned relative to its owning window.
/// It is meant to be an alternative to the webview tag.
///
///
public Task CreateBrowserViewAsync()
{
return CreateBrowserViewAsync(new BrowserViewConstructorOptions());
}
///
/// A BrowserView can be used to embed additional web content into a BrowserWindow.
/// It is like a child window, except that it is positioned relative to its owning window.
/// It is meant to be an alternative to the webview tag.
///
///
///
public Task CreateBrowserViewAsync(BrowserViewConstructorOptions options)
{
var taskCompletionSource = new TaskCompletionSource();
BridgeConnector.Socket.On("BrowserViewCreated", (id) =>
{
BridgeConnector.Socket.Off("BrowserViewCreated");
string browserViewId = id.ToString();
BrowserView browserView = new BrowserView(int.Parse(browserViewId));
_browserViews.Add(browserView);
taskCompletionSource.SetResult(browserView);
});
var ownjsonSerializer = new JsonSerializer()
{
ContractResolver = new CamelCasePropertyNamesContractResolver(),
NullValueHandling = NullValueHandling.Ignore
};
BridgeConnector.Socket.Emit("createBrowserView", JObject.FromObject(options, ownjsonSerializer));
return taskCompletionSource.Task;
}
private JsonSerializer _jsonSerializer = new JsonSerializer()
{
ContractResolver = new CamelCasePropertyNamesContractResolver(),
NullValueHandling = NullValueHandling.Ignore,
DefaultValueHandling = DefaultValueHandling.Ignore
};
}
}