From 7baf826e5afb2816c6f0637d5d907bf6f15ff9f0 Mon Sep 17 00:00:00 2001 From: dbuechel Date: Tue, 15 Aug 2017 15:30:31 +0200 Subject: [PATCH] Refactored taskbar components (moved contracts to separate namespace and introduced XAML control templates) and started implementing system components. --- .../BrowserApplicationController.cs | 5 +- SafeExamBrowser.Configuration/SystemInfo.cs | 5 +- .../Behaviour/IApplicationController.cs | 3 +- .../Behaviour/INotificationController.cs | 3 +- .../SafeExamBrowser.Contracts.csproj | 9 ++- .../SystemComponents/ISystemComponent.cs | 30 +++++++++ .../UserInterface/IUserInterfaceFactory.cs | 10 ++- .../IApplicationButton.cs} | 12 ++-- .../INotificationButton.cs} | 8 +-- .../UserInterface/Taskbar/ISystemControl.cs | 18 +++++ .../Taskbar/ISystemPowerSupplyControl.cs | 24 +++++++ .../UserInterface/{ => Taskbar}/ITaskbar.cs | 11 +++- .../Behaviour/RuntimeControllerTests.cs | 2 +- .../Behaviour/Operations/BrowserOperation.cs | 3 +- .../Operations/DisplayMonitorOperation.cs | 1 + .../Behaviour/Operations/TaskbarOperation.cs | 38 ++++------- .../Behaviour/RuntimeController.cs | 2 +- .../Behaviour/StartupController.cs | 2 +- .../AboutNotificationController.cs | 5 +- .../LogNotificationController.cs | 5 +- .../PowerSupply.cs | 40 ++++++++++++ .../Properties/AssemblyInfo.cs | 36 ++++++++++ .../SafeExamBrowser.SystemComponents.csproj | 65 +++++++++++++++++++ .../Controls/ApplicationButton.xaml | 29 +++------ .../Controls/ApplicationButton.xaml.cs | 6 +- .../Controls/NotificationButton.xaml | 17 +++++ ...con.xaml.cs => NotificationButton.xaml.cs} | 8 +-- .../Controls/NotificationIcon.xaml | 25 ------- .../Controls/PowerSupplyControl.xaml | 26 ++++++++ .../Controls/PowerSupplyControl.xaml.cs | 47 ++++++++++++++ .../SafeExamBrowser.UserInterface.csproj | 17 ++++- .../Styles/ButtonStyles.xaml | 17 +++++ SafeExamBrowser.UserInterface/Taskbar.xaml | 6 +- SafeExamBrowser.UserInterface/Taskbar.xaml.cs | 14 +++- .../UserInterfaceFactory.cs | 12 +++- SafeExamBrowser.sln | 12 +++- SafeExamBrowser/CompositionRoot.cs | 7 +- SafeExamBrowser/SafeExamBrowser.csproj | 4 ++ 38 files changed, 464 insertions(+), 120 deletions(-) create mode 100644 SafeExamBrowser.Contracts/SystemComponents/ISystemComponent.cs rename SafeExamBrowser.Contracts/UserInterface/{ITaskbarButton.cs => Taskbar/IApplicationButton.cs} (64%) rename SafeExamBrowser.Contracts/UserInterface/{ITaskbarNotification.cs => Taskbar/INotificationButton.cs} (65%) create mode 100644 SafeExamBrowser.Contracts/UserInterface/Taskbar/ISystemControl.cs create mode 100644 SafeExamBrowser.Contracts/UserInterface/Taskbar/ISystemPowerSupplyControl.cs rename SafeExamBrowser.Contracts/UserInterface/{ => Taskbar}/ITaskbar.cs (73%) create mode 100644 SafeExamBrowser.SystemComponents/PowerSupply.cs create mode 100644 SafeExamBrowser.SystemComponents/Properties/AssemblyInfo.cs create mode 100644 SafeExamBrowser.SystemComponents/SafeExamBrowser.SystemComponents.csproj create mode 100644 SafeExamBrowser.UserInterface/Controls/NotificationButton.xaml rename SafeExamBrowser.UserInterface/Controls/{NotificationIcon.xaml.cs => NotificationButton.xaml.cs} (77%) delete mode 100644 SafeExamBrowser.UserInterface/Controls/NotificationIcon.xaml create mode 100644 SafeExamBrowser.UserInterface/Controls/PowerSupplyControl.xaml create mode 100644 SafeExamBrowser.UserInterface/Controls/PowerSupplyControl.xaml.cs create mode 100644 SafeExamBrowser.UserInterface/Styles/ButtonStyles.xaml diff --git a/SafeExamBrowser.Browser/BrowserApplicationController.cs b/SafeExamBrowser.Browser/BrowserApplicationController.cs index 29cee667..d8d7b5d8 100644 --- a/SafeExamBrowser.Browser/BrowserApplicationController.cs +++ b/SafeExamBrowser.Browser/BrowserApplicationController.cs @@ -15,12 +15,13 @@ using SafeExamBrowser.Contracts.Configuration; using SafeExamBrowser.Contracts.Configuration.Settings; using SafeExamBrowser.Contracts.I18n; using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; namespace SafeExamBrowser.Browser { public class BrowserApplicationController : IApplicationController { - private ITaskbarButton button; + private IApplicationButton button; private IList instances = new List(); private ISettings settings; private IUserInterfaceFactory uiFactory; @@ -49,7 +50,7 @@ namespace SafeExamBrowser.Browser } } - public void RegisterApplicationButton(ITaskbarButton button) + public void RegisterApplicationButton(IApplicationButton button) { this.button = button; this.button.Clicked += Button_OnClick; diff --git a/SafeExamBrowser.Configuration/SystemInfo.cs b/SafeExamBrowser.Configuration/SystemInfo.cs index 3904f1d9..538835ba 100644 --- a/SafeExamBrowser.Configuration/SystemInfo.cs +++ b/SafeExamBrowser.Configuration/SystemInfo.cs @@ -36,10 +36,13 @@ namespace SafeExamBrowser.Configuration private void InitializeOperatingSystem() { - // See https://en.wikipedia.org/wiki/List_of_Microsoft_Windows_versions for mapping source... + // IMPORTANT: + // In order to be able to retrieve the correct operating system version via System.Environment.OSVersion, the executing + // assembly needs to define an application manifest where the supported Windows versions are specified! var major = System.Environment.OSVersion.Version.Major; var minor = System.Environment.OSVersion.Version.Minor; + // See https://en.wikipedia.org/wiki/List_of_Microsoft_Windows_versions for mapping source... if (major == 6) { if (minor == 1) diff --git a/SafeExamBrowser.Contracts/Behaviour/IApplicationController.cs b/SafeExamBrowser.Contracts/Behaviour/IApplicationController.cs index 93d28484..c8e317e0 100644 --- a/SafeExamBrowser.Contracts/Behaviour/IApplicationController.cs +++ b/SafeExamBrowser.Contracts/Behaviour/IApplicationController.cs @@ -7,6 +7,7 @@ */ using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; namespace SafeExamBrowser.Contracts.Behaviour { @@ -20,7 +21,7 @@ namespace SafeExamBrowser.Contracts.Behaviour /// /// Registers the taskbar button for this application. /// - void RegisterApplicationButton(ITaskbarButton button); + void RegisterApplicationButton(IApplicationButton button); /// /// Performs any termination work, e.g. freeing of resources. diff --git a/SafeExamBrowser.Contracts/Behaviour/INotificationController.cs b/SafeExamBrowser.Contracts/Behaviour/INotificationController.cs index 08e343a7..1d989c41 100644 --- a/SafeExamBrowser.Contracts/Behaviour/INotificationController.cs +++ b/SafeExamBrowser.Contracts/Behaviour/INotificationController.cs @@ -7,6 +7,7 @@ */ using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; namespace SafeExamBrowser.Contracts.Behaviour { @@ -15,7 +16,7 @@ namespace SafeExamBrowser.Contracts.Behaviour /// /// Registers the taskbar notification. /// - void RegisterNotification(ITaskbarNotification notification); + void RegisterNotification(INotificationButton notification); /// /// Instructs the controller to shut down and release all used resources. diff --git a/SafeExamBrowser.Contracts/SafeExamBrowser.Contracts.csproj b/SafeExamBrowser.Contracts/SafeExamBrowser.Contracts.csproj index e36973e1..d242d5cb 100644 --- a/SafeExamBrowser.Contracts/SafeExamBrowser.Contracts.csproj +++ b/SafeExamBrowser.Contracts/SafeExamBrowser.Contracts.csproj @@ -86,15 +86,18 @@ + - + - + + + - + diff --git a/SafeExamBrowser.Contracts/SystemComponents/ISystemComponent.cs b/SafeExamBrowser.Contracts/SystemComponents/ISystemComponent.cs new file mode 100644 index 00000000..1ad5ed72 --- /dev/null +++ b/SafeExamBrowser.Contracts/SystemComponents/ISystemComponent.cs @@ -0,0 +1,30 @@ +/* + * Copyright (c) 2017 ETH Zürich, Educational Development and Technology (LET) + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +using SafeExamBrowser.Contracts.UserInterface.Taskbar; + +namespace SafeExamBrowser.Contracts.SystemComponents +{ + public interface ISystemComponent where TControl : ISystemControl + { + /// + /// Initializes the resources used by the component and starts its operations, if applicable. + /// + void Initialize(); + + /// + /// Registers the taskbar control for the system component. + /// + void RegisterControl(TControl control); + + /// + /// Instructs the component to stop any running operations and release all used resources. + /// + void Terminate(); + } +} diff --git a/SafeExamBrowser.Contracts/UserInterface/IUserInterfaceFactory.cs b/SafeExamBrowser.Contracts/UserInterface/IUserInterfaceFactory.cs index 1ba0e525..5a483300 100644 --- a/SafeExamBrowser.Contracts/UserInterface/IUserInterfaceFactory.cs +++ b/SafeExamBrowser.Contracts/UserInterface/IUserInterfaceFactory.cs @@ -10,6 +10,7 @@ using SafeExamBrowser.Contracts.Configuration; using SafeExamBrowser.Contracts.Configuration.Settings; using SafeExamBrowser.Contracts.I18n; using SafeExamBrowser.Contracts.Logging; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; namespace SafeExamBrowser.Contracts.UserInterface { @@ -23,7 +24,7 @@ namespace SafeExamBrowser.Contracts.UserInterface /// /// Creates a taskbar button, initialized with the given application information. /// - ITaskbarButton CreateApplicationButton(IApplicationInfo info); + IApplicationButton CreateApplicationButton(IApplicationInfo info); /// /// Creates a new browser window loaded with the given browser control and settings. @@ -38,7 +39,12 @@ namespace SafeExamBrowser.Contracts.UserInterface /// /// Creates a taskbar notification, initialized with the given notification information. /// - ITaskbarNotification CreateNotification(INotificationInfo info); + INotificationButton CreateNotification(INotificationInfo info); + + /// + /// Creates a system control displaying the power supply status of the computer. + /// + ISystemPowerSupplyControl CreatePowerSupplyControl(); /// /// Creates a new splash screen which runs on its own thread. diff --git a/SafeExamBrowser.Contracts/UserInterface/ITaskbarButton.cs b/SafeExamBrowser.Contracts/UserInterface/Taskbar/IApplicationButton.cs similarity index 64% rename from SafeExamBrowser.Contracts/UserInterface/ITaskbarButton.cs rename to SafeExamBrowser.Contracts/UserInterface/Taskbar/IApplicationButton.cs index a5066646..f273ae55 100644 --- a/SafeExamBrowser.Contracts/UserInterface/ITaskbarButton.cs +++ b/SafeExamBrowser.Contracts/UserInterface/Taskbar/IApplicationButton.cs @@ -9,17 +9,17 @@ using System; using SafeExamBrowser.Contracts.Configuration; -namespace SafeExamBrowser.Contracts.UserInterface +namespace SafeExamBrowser.Contracts.UserInterface.Taskbar { - public delegate void TaskbarButtonClickedEventHandler(Guid? instanceId = null); + public delegate void ApplicationButtonClickedEventHandler(Guid? instanceId = null); - public interface ITaskbarButton + public interface IApplicationButton { /// - /// Event fired when the user clicked on the application button. If multiple instances of an application - /// are active, the handler is only executed when the user selects one of the instances. + /// Event fired when the user clicked on the application button. If multiple instances of an application are active, + /// the handler is only executed when the user selects one of the instances. /// - event TaskbarButtonClickedEventHandler Clicked; + event ApplicationButtonClickedEventHandler Clicked; /// /// Registers a new instance of an application, to be started / displayed if the user clicked the taskbar button. diff --git a/SafeExamBrowser.Contracts/UserInterface/ITaskbarNotification.cs b/SafeExamBrowser.Contracts/UserInterface/Taskbar/INotificationButton.cs similarity index 65% rename from SafeExamBrowser.Contracts/UserInterface/ITaskbarNotification.cs rename to SafeExamBrowser.Contracts/UserInterface/Taskbar/INotificationButton.cs index 7986bca7..eaf0def5 100644 --- a/SafeExamBrowser.Contracts/UserInterface/ITaskbarNotification.cs +++ b/SafeExamBrowser.Contracts/UserInterface/Taskbar/INotificationButton.cs @@ -6,15 +6,15 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ -namespace SafeExamBrowser.Contracts.UserInterface +namespace SafeExamBrowser.Contracts.UserInterface.Taskbar { - public delegate void TaskbarNotificationClickedEventHandler(); + public delegate void NotificationButtonClickedEventHandler(); - public interface ITaskbarNotification + public interface INotificationButton { /// /// Event fired when the user clicked on the notification icon. /// - event TaskbarNotificationClickedEventHandler Clicked; + event NotificationButtonClickedEventHandler Clicked; } } diff --git a/SafeExamBrowser.Contracts/UserInterface/Taskbar/ISystemControl.cs b/SafeExamBrowser.Contracts/UserInterface/Taskbar/ISystemControl.cs new file mode 100644 index 00000000..e1ff5b05 --- /dev/null +++ b/SafeExamBrowser.Contracts/UserInterface/Taskbar/ISystemControl.cs @@ -0,0 +1,18 @@ +/* + * Copyright (c) 2017 ETH Zürich, Educational Development and Technology (LET) + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +namespace SafeExamBrowser.Contracts.UserInterface.Taskbar +{ + public interface ISystemControl + { + /// + /// Sets the tooltip text of the system control. + /// + void SetTooltip(string text); + } +} diff --git a/SafeExamBrowser.Contracts/UserInterface/Taskbar/ISystemPowerSupplyControl.cs b/SafeExamBrowser.Contracts/UserInterface/Taskbar/ISystemPowerSupplyControl.cs new file mode 100644 index 00000000..53c3d3cc --- /dev/null +++ b/SafeExamBrowser.Contracts/UserInterface/Taskbar/ISystemPowerSupplyControl.cs @@ -0,0 +1,24 @@ +/* + * Copyright (c) 2017 ETH Zürich, Educational Development and Technology (LET) + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +namespace SafeExamBrowser.Contracts.UserInterface.Taskbar +{ + public interface ISystemPowerSupplyControl : ISystemControl + { + /// + /// Sets the current charge of the system battery, if available. 0.0 means the battery is empty, 1.0 means it's + /// fully charged. Pass null to indicate that the computer system has no battery. + /// + void SetBatteryCharge(double? percentage); + + /// + /// Sets the power supply status, i.e. whether the computer system is connected to the power grid or not. + /// + void SetPowerGridConnection(bool connected); + } +} diff --git a/SafeExamBrowser.Contracts/UserInterface/ITaskbar.cs b/SafeExamBrowser.Contracts/UserInterface/Taskbar/ITaskbar.cs similarity index 73% rename from SafeExamBrowser.Contracts/UserInterface/ITaskbar.cs rename to SafeExamBrowser.Contracts/UserInterface/Taskbar/ITaskbar.cs index 6e80f106..eb31edcb 100644 --- a/SafeExamBrowser.Contracts/UserInterface/ITaskbar.cs +++ b/SafeExamBrowser.Contracts/UserInterface/Taskbar/ITaskbar.cs @@ -6,19 +6,24 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ -namespace SafeExamBrowser.Contracts.UserInterface +namespace SafeExamBrowser.Contracts.UserInterface.Taskbar { public interface ITaskbar { /// /// Adds the given application button to the taskbar. /// - void AddButton(ITaskbarButton button); + void AddApplication(IApplicationButton button); /// /// Adds the given notification button to the taskbar. /// - void AddNotification(ITaskbarNotification notification); + void AddNotification(INotificationButton button); + + /// + /// Adds the given system control to the taskbar. + /// + void AddSystemControl(ISystemControl control); /// /// Returns the absolute height of the taskbar (i.e. in physical pixels). diff --git a/SafeExamBrowser.Core.UnitTests/Behaviour/RuntimeControllerTests.cs b/SafeExamBrowser.Core.UnitTests/Behaviour/RuntimeControllerTests.cs index 60fdc12e..e84ad0c1 100644 --- a/SafeExamBrowser.Core.UnitTests/Behaviour/RuntimeControllerTests.cs +++ b/SafeExamBrowser.Core.UnitTests/Behaviour/RuntimeControllerTests.cs @@ -12,7 +12,7 @@ using Moq; using SafeExamBrowser.Contracts.Behaviour; using SafeExamBrowser.Contracts.Logging; using SafeExamBrowser.Contracts.Monitoring; -using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; using SafeExamBrowser.Core.Behaviour; namespace SafeExamBrowser.Core.UnitTests.Behaviour diff --git a/SafeExamBrowser.Core/Behaviour/Operations/BrowserOperation.cs b/SafeExamBrowser.Core/Behaviour/Operations/BrowserOperation.cs index d76b8968..0160fb02 100644 --- a/SafeExamBrowser.Core/Behaviour/Operations/BrowserOperation.cs +++ b/SafeExamBrowser.Core/Behaviour/Operations/BrowserOperation.cs @@ -11,6 +11,7 @@ using SafeExamBrowser.Contracts.Configuration; using SafeExamBrowser.Contracts.I18n; using SafeExamBrowser.Contracts.Logging; using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; namespace SafeExamBrowser.Core.Behaviour.Operations { @@ -48,7 +49,7 @@ namespace SafeExamBrowser.Core.Behaviour.Operations browserController.Initialize(); browserController.RegisterApplicationButton(browserButton); - taskbar.AddButton(browserButton); + taskbar.AddApplication(browserButton); } public void Revert() diff --git a/SafeExamBrowser.Core/Behaviour/Operations/DisplayMonitorOperation.cs b/SafeExamBrowser.Core/Behaviour/Operations/DisplayMonitorOperation.cs index d39e1d6d..bc8dd685 100644 --- a/SafeExamBrowser.Core/Behaviour/Operations/DisplayMonitorOperation.cs +++ b/SafeExamBrowser.Core/Behaviour/Operations/DisplayMonitorOperation.cs @@ -11,6 +11,7 @@ using SafeExamBrowser.Contracts.I18n; using SafeExamBrowser.Contracts.Logging; using SafeExamBrowser.Contracts.Monitoring; using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; namespace SafeExamBrowser.Core.Behaviour.Operations { diff --git a/SafeExamBrowser.Core/Behaviour/Operations/TaskbarOperation.cs b/SafeExamBrowser.Core/Behaviour/Operations/TaskbarOperation.cs index 1470ea37..d10e2c27 100644 --- a/SafeExamBrowser.Core/Behaviour/Operations/TaskbarOperation.cs +++ b/SafeExamBrowser.Core/Behaviour/Operations/TaskbarOperation.cs @@ -11,7 +11,9 @@ using SafeExamBrowser.Contracts.Configuration; using SafeExamBrowser.Contracts.Configuration.Settings; using SafeExamBrowser.Contracts.I18n; using SafeExamBrowser.Contracts.Logging; +using SafeExamBrowser.Contracts.SystemComponents; using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; using SafeExamBrowser.Core.Notifications; namespace SafeExamBrowser.Core.Behaviour.Operations @@ -21,6 +23,7 @@ namespace SafeExamBrowser.Core.Behaviour.Operations private ILogger logger; private INotificationController aboutController, logController; private ISettings settings; + private ISystemComponent powerSupply; private ISystemInfo systemInfo; private ITaskbar taskbar; private IUserInterfaceFactory uiFactory; @@ -31,6 +34,7 @@ namespace SafeExamBrowser.Core.Behaviour.Operations public TaskbarOperation( ILogger logger, ISettings settings, + ISystemComponent powerSupply, ISystemInfo systemInfo, ITaskbar taskbar, IText text, @@ -38,6 +42,7 @@ namespace SafeExamBrowser.Core.Behaviour.Operations { this.logger = logger; this.settings = settings; + this.powerSupply = powerSupply; this.systemInfo = systemInfo; this.taskbar = taskbar; this.text = text; @@ -55,21 +60,15 @@ namespace SafeExamBrowser.Core.Behaviour.Operations } CreateAboutNotification(); - - if (systemInfo.HasBattery) - { - CreateBatteryNotification(); - } - - CreateNetworkNotification(); - CreateAudioNotification(); - CreateKeyboardNotification(); + CreatePowerSupplyComponent(); } public void Revert() { logController?.Terminate(); aboutController?.Terminate(); + + powerSupply.Terminate(); } private void CreateLogNotification() @@ -94,25 +93,14 @@ namespace SafeExamBrowser.Core.Behaviour.Operations taskbar.AddNotification(aboutNotification); } - private void CreateBatteryNotification() + private void CreatePowerSupplyComponent() { - // TODO: Are these specializations of INotification -> ISystemNotification? If yes, is this the right place, or do they - // need to go to a separate assembly? - } + var control = uiFactory.CreatePowerSupplyControl(); - private void CreateNetworkNotification() - { - // TODO - } + powerSupply.RegisterControl(control); + powerSupply.Initialize(); - private void CreateAudioNotification() - { - // TODO - } - - private void CreateKeyboardNotification() - { - // TODO + taskbar.AddSystemControl(control); } } } diff --git a/SafeExamBrowser.Core/Behaviour/RuntimeController.cs b/SafeExamBrowser.Core/Behaviour/RuntimeController.cs index 2b1abd78..fc4667ba 100644 --- a/SafeExamBrowser.Core/Behaviour/RuntimeController.cs +++ b/SafeExamBrowser.Core/Behaviour/RuntimeController.cs @@ -10,7 +10,7 @@ using System; using SafeExamBrowser.Contracts.Behaviour; using SafeExamBrowser.Contracts.Logging; using SafeExamBrowser.Contracts.Monitoring; -using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; namespace SafeExamBrowser.Core.Behaviour { diff --git a/SafeExamBrowser.Core/Behaviour/StartupController.cs b/SafeExamBrowser.Core/Behaviour/StartupController.cs index 80a3b75e..45481a61 100644 --- a/SafeExamBrowser.Core/Behaviour/StartupController.cs +++ b/SafeExamBrowser.Core/Behaviour/StartupController.cs @@ -91,7 +91,7 @@ namespace SafeExamBrowser.Core.Behaviour logger.Log($"{titleLine}{copyrightLine}{emptyLine}{githubLine}"); logger.Log($"{Environment.NewLine}# Application started at {DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff")}"); - logger.Log($"# Operating system: {systemInfo.OperatingSystemInfo}{Environment.NewLine}"); + logger.Log($"# Running on {systemInfo.OperatingSystemInfo}{Environment.NewLine}"); logger.Info("--- Initiating startup procedure ---"); splashScreen = uiFactory.CreateSplashScreen(settings, text); diff --git a/SafeExamBrowser.Core/Notifications/AboutNotificationController.cs b/SafeExamBrowser.Core/Notifications/AboutNotificationController.cs index 92f24a1c..7aea954c 100644 --- a/SafeExamBrowser.Core/Notifications/AboutNotificationController.cs +++ b/SafeExamBrowser.Core/Notifications/AboutNotificationController.cs @@ -10,12 +10,13 @@ using SafeExamBrowser.Contracts.Behaviour; using SafeExamBrowser.Contracts.Configuration.Settings; using SafeExamBrowser.Contracts.I18n; using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; namespace SafeExamBrowser.Core.Notifications { public class AboutNotificationController : INotificationController { - private ITaskbarNotification notification; + private INotificationButton notification; private ISettings settings; private IText text; private IUserInterfaceFactory uiFactory; @@ -28,7 +29,7 @@ namespace SafeExamBrowser.Core.Notifications this.uiFactory = uiFactory; } - public void RegisterNotification(ITaskbarNotification notification) + public void RegisterNotification(INotificationButton notification) { this.notification = notification; diff --git a/SafeExamBrowser.Core/Notifications/LogNotificationController.cs b/SafeExamBrowser.Core/Notifications/LogNotificationController.cs index 6ef5bedb..2db0afd8 100644 --- a/SafeExamBrowser.Core/Notifications/LogNotificationController.cs +++ b/SafeExamBrowser.Core/Notifications/LogNotificationController.cs @@ -10,12 +10,13 @@ using SafeExamBrowser.Contracts.Behaviour; using SafeExamBrowser.Contracts.I18n; using SafeExamBrowser.Contracts.Logging; using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; namespace SafeExamBrowser.Core.Notifications { public class LogNotificationController : INotificationController { - private ITaskbarNotification notification; + private INotificationButton notification; private ILogger logger; private IText text; private IUserInterfaceFactory uiFactory; @@ -28,7 +29,7 @@ namespace SafeExamBrowser.Core.Notifications this.uiFactory = uiFactory; } - public void RegisterNotification(ITaskbarNotification notification) + public void RegisterNotification(INotificationButton notification) { this.notification = notification; diff --git a/SafeExamBrowser.SystemComponents/PowerSupply.cs b/SafeExamBrowser.SystemComponents/PowerSupply.cs new file mode 100644 index 00000000..9641075f --- /dev/null +++ b/SafeExamBrowser.SystemComponents/PowerSupply.cs @@ -0,0 +1,40 @@ +/* + * Copyright (c) 2017 ETH Zürich, Educational Development and Technology (LET) + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +using SafeExamBrowser.Contracts.Logging; +using SafeExamBrowser.Contracts.SystemComponents; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; + +namespace SafeExamBrowser.SystemComponents +{ + public class PowerSupply : ISystemComponent + { + private ILogger logger; + private ISystemPowerSupplyControl control; + + public PowerSupply(ILogger logger) + { + this.logger = logger; + } + + public void Initialize() + { + + } + + public void RegisterControl(ISystemPowerSupplyControl control) + { + this.control = control; + } + + public void Terminate() + { + + } + } +} diff --git a/SafeExamBrowser.SystemComponents/Properties/AssemblyInfo.cs b/SafeExamBrowser.SystemComponents/Properties/AssemblyInfo.cs new file mode 100644 index 00000000..217cf313 --- /dev/null +++ b/SafeExamBrowser.SystemComponents/Properties/AssemblyInfo.cs @@ -0,0 +1,36 @@ +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +// General Information about an assembly is controlled through the following +// set of attributes. Change these attribute values to modify the information +// associated with an assembly. +[assembly: AssemblyTitle("SafeExamBrowser.SystemComponents")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("SafeExamBrowser.SystemComponents")] +[assembly: AssemblyCopyright("Copyright © 2017")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +// Setting ComVisible to false makes the types in this assembly not visible +// to COM components. If you need to access a type in this assembly from +// COM, set the ComVisible attribute to true on that type. +[assembly: ComVisible(false)] + +// The following GUID is for the ID of the typelib if this project is exposed to COM +[assembly: Guid("acee2ef1-14d2-4b52-8994-5c053055bb51")] + +// Version information for an assembly consists of the following four values: +// +// Major Version +// Minor Version +// Build Number +// Revision +// +// You can specify all the values or you can default the Build and Revision Numbers +// by using the '*' as shown below: +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/SafeExamBrowser.SystemComponents/SafeExamBrowser.SystemComponents.csproj b/SafeExamBrowser.SystemComponents/SafeExamBrowser.SystemComponents.csproj new file mode 100644 index 00000000..cfd6c74e --- /dev/null +++ b/SafeExamBrowser.SystemComponents/SafeExamBrowser.SystemComponents.csproj @@ -0,0 +1,65 @@ + + + + + Debug + AnyCPU + {ACEE2EF1-14D2-4B52-8994-5C053055BB51} + Library + Properties + SafeExamBrowser.SystemComponents + SafeExamBrowser.SystemComponents + v4.5.2 + 512 + + + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + + + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + + + true + bin\x86\Debug\ + DEBUG;TRACE + full + x86 + prompt + MinimumRecommendedRules.ruleset + + + bin\x86\Release\ + TRACE + true + pdbonly + x86 + prompt + MinimumRecommendedRules.ruleset + + + + + + + + + + + + {47DA5933-BEF8-4729-94E6-ABDE2DB12262} + SafeExamBrowser.Contracts + + + + \ No newline at end of file diff --git a/SafeExamBrowser.UserInterface/Controls/ApplicationButton.xaml b/SafeExamBrowser.UserInterface/Controls/ApplicationButton.xaml index d309c7d8..c81c6a65 100644 --- a/SafeExamBrowser.UserInterface/Controls/ApplicationButton.xaml +++ b/SafeExamBrowser.UserInterface/Controls/ApplicationButton.xaml @@ -5,8 +5,14 @@ xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:local="clr-namespace:SafeExamBrowser.UserInterface.Controls" xmlns:s="clr-namespace:System;assembly=mscorlib" - mc:Ignorable="d" - d:DesignHeight="40" d:DesignWidth="50"> + mc:Ignorable="d" d:DesignHeight="40" d:DesignWidth="50"> + + + + + + + @@ -19,23 +25,8 @@ - + - diff --git a/SafeExamBrowser.UserInterface/Controls/PowerSupplyControl.xaml b/SafeExamBrowser.UserInterface/Controls/PowerSupplyControl.xaml new file mode 100644 index 00000000..dbbd7983 --- /dev/null +++ b/SafeExamBrowser.UserInterface/Controls/PowerSupplyControl.xaml @@ -0,0 +1,26 @@ + + + + + + + + + + diff --git a/SafeExamBrowser.UserInterface/Controls/PowerSupplyControl.xaml.cs b/SafeExamBrowser.UserInterface/Controls/PowerSupplyControl.xaml.cs new file mode 100644 index 00000000..13b8fd6a --- /dev/null +++ b/SafeExamBrowser.UserInterface/Controls/PowerSupplyControl.xaml.cs @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2017 ETH Zürich, Educational Development and Technology (LET) + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +using System; +using System.Windows; +using System.Windows.Controls; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; + +namespace SafeExamBrowser.UserInterface.Controls +{ + public partial class PowerSupplyControl : UserControl, ISystemPowerSupplyControl + { + public PowerSupplyControl() + { + InitializeComponent(); + InitializePowerSupplyControl(); + } + + public void SetBatteryCharge(double? percentage) + { + throw new NotImplementedException(); + } + + public void SetPowerGridConnection(bool connected) + { + throw new NotImplementedException(); + } + + public void SetTooltip(string text) + { + throw new NotImplementedException(); + } + + private void InitializePowerSupplyControl() + { + Button.Resources.MergedDictionaries.Add(new ResourceDictionary + { + Source = (new Uri("/SafeExamBrowser.UserInterface;component/Styles/ButtonStyles.xaml", UriKind.RelativeOrAbsolute)) + }); + } + } +} diff --git a/SafeExamBrowser.UserInterface/SafeExamBrowser.UserInterface.csproj b/SafeExamBrowser.UserInterface/SafeExamBrowser.UserInterface.csproj index d5edcc7b..0799683a 100644 --- a/SafeExamBrowser.UserInterface/SafeExamBrowser.UserInterface.csproj +++ b/SafeExamBrowser.UserInterface/SafeExamBrowser.UserInterface.csproj @@ -77,8 +77,11 @@ ApplicationButton.xaml - - NotificationIcon.xaml + + NotificationButton.xaml + + + PowerSupplyControl.xaml QuitButton.xaml @@ -141,7 +144,11 @@ Designer MSBuild:Compile - + + Designer + MSBuild:Compile + + Designer MSBuild:Compile @@ -157,6 +164,10 @@ Designer MSBuild:Compile + + Designer + MSBuild:Compile + Designer MSBuild:Compile diff --git a/SafeExamBrowser.UserInterface/Styles/ButtonStyles.xaml b/SafeExamBrowser.UserInterface/Styles/ButtonStyles.xaml new file mode 100644 index 00000000..6295dae0 --- /dev/null +++ b/SafeExamBrowser.UserInterface/Styles/ButtonStyles.xaml @@ -0,0 +1,17 @@ + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/SafeExamBrowser.UserInterface/Taskbar.xaml b/SafeExamBrowser.UserInterface/Taskbar.xaml index 7643bca3..83660165 100644 --- a/SafeExamBrowser.UserInterface/Taskbar.xaml +++ b/SafeExamBrowser.UserInterface/Taskbar.xaml @@ -17,6 +17,7 @@ + @@ -26,8 +27,9 @@ - - + + + diff --git a/SafeExamBrowser.UserInterface/Taskbar.xaml.cs b/SafeExamBrowser.UserInterface/Taskbar.xaml.cs index a03d1661..adaf30cb 100644 --- a/SafeExamBrowser.UserInterface/Taskbar.xaml.cs +++ b/SafeExamBrowser.UserInterface/Taskbar.xaml.cs @@ -8,7 +8,7 @@ using System.Windows; using SafeExamBrowser.Contracts.Logging; -using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; using SafeExamBrowser.UserInterface.Utilities; namespace SafeExamBrowser.UserInterface @@ -26,7 +26,7 @@ namespace SafeExamBrowser.UserInterface Loaded += (o, args) => InitializeBounds(); } - public void AddButton(ITaskbarButton button) + public void AddApplication(IApplicationButton button) { if (button is UIElement) { @@ -34,7 +34,7 @@ namespace SafeExamBrowser.UserInterface } } - public void AddNotification(ITaskbarNotification button) + public void AddNotification(INotificationButton button) { if (button is UIElement) { @@ -42,6 +42,14 @@ namespace SafeExamBrowser.UserInterface } } + public void AddSystemControl(ISystemControl control) + { + if (control is UIElement) + { + SystemControlStackPanel.Children.Add(control as UIElement); + } + } + public int GetAbsoluteHeight() { return Dispatcher.Invoke(() => diff --git a/SafeExamBrowser.UserInterface/UserInterfaceFactory.cs b/SafeExamBrowser.UserInterface/UserInterfaceFactory.cs index 880e874c..bf8817fe 100644 --- a/SafeExamBrowser.UserInterface/UserInterfaceFactory.cs +++ b/SafeExamBrowser.UserInterface/UserInterfaceFactory.cs @@ -13,6 +13,7 @@ using SafeExamBrowser.Contracts.Configuration.Settings; using SafeExamBrowser.Contracts.I18n; using SafeExamBrowser.Contracts.Logging; using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; using SafeExamBrowser.UserInterface.Controls; namespace SafeExamBrowser.UserInterface @@ -24,7 +25,7 @@ namespace SafeExamBrowser.UserInterface return new AboutWindow(settings, text); } - public ITaskbarButton CreateApplicationButton(IApplicationInfo info) + public IApplicationButton CreateApplicationButton(IApplicationInfo info) { return new ApplicationButton(info); } @@ -59,9 +60,14 @@ namespace SafeExamBrowser.UserInterface return logWindow; } - public ITaskbarNotification CreateNotification(INotificationInfo info) + public INotificationButton CreateNotification(INotificationInfo info) { - return new NotificationIcon(info); + return new NotificationButton(info); + } + + public ISystemPowerSupplyControl CreatePowerSupplyControl() + { + return new PowerSupplyControl(); } public ISplashScreen CreateSplashScreen(ISettings settings, IText text) diff --git a/SafeExamBrowser.sln b/SafeExamBrowser.sln index 6f488234..71cf2403 100644 --- a/SafeExamBrowser.sln +++ b/SafeExamBrowser.sln @@ -1,7 +1,7 @@  Microsoft Visual Studio Solution File, Format Version 12.00 # Visual Studio 15 -VisualStudioVersion = 15.0.26430.15 +VisualStudioVersion = 15.0.26430.16 MinimumVisualStudioVersion = 10.0.40219.1 Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SafeExamBrowser", "SafeExamBrowser\SafeExamBrowser.csproj", "{E3AED2F8-B5DF-45D1-AC19-48066923D6D8}" EndProject @@ -27,6 +27,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SafeExamBrowser.Configurati EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SafeExamBrowser.WindowsApi", "SafeExamBrowser.WindowsApi\SafeExamBrowser.WindowsApi.csproj", "{73724659-4150-4792-A94E-42F5F3C1B696}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SafeExamBrowser.SystemComponents", "SafeExamBrowser.SystemComponents\SafeExamBrowser.SystemComponents.csproj", "{ACEE2EF1-14D2-4B52-8994-5C053055BB51}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -107,6 +109,14 @@ Global {73724659-4150-4792-A94E-42F5F3C1B696}.Release|Any CPU.Build.0 = Release|Any CPU {73724659-4150-4792-A94E-42F5F3C1B696}.Release|x86.ActiveCfg = Release|x86 {73724659-4150-4792-A94E-42F5F3C1B696}.Release|x86.Build.0 = Release|x86 + {ACEE2EF1-14D2-4B52-8994-5C053055BB51}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {ACEE2EF1-14D2-4B52-8994-5C053055BB51}.Debug|Any CPU.Build.0 = Debug|Any CPU + {ACEE2EF1-14D2-4B52-8994-5C053055BB51}.Debug|x86.ActiveCfg = Debug|x86 + {ACEE2EF1-14D2-4B52-8994-5C053055BB51}.Debug|x86.Build.0 = Debug|x86 + {ACEE2EF1-14D2-4B52-8994-5C053055BB51}.Release|Any CPU.ActiveCfg = Release|Any CPU + {ACEE2EF1-14D2-4B52-8994-5C053055BB51}.Release|Any CPU.Build.0 = Release|Any CPU + {ACEE2EF1-14D2-4B52-8994-5C053055BB51}.Release|x86.ActiveCfg = Release|Any CPU + {ACEE2EF1-14D2-4B52-8994-5C053055BB51}.Release|x86.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/SafeExamBrowser/CompositionRoot.cs b/SafeExamBrowser/CompositionRoot.cs index 739641d0..a329bf1b 100644 --- a/SafeExamBrowser/CompositionRoot.cs +++ b/SafeExamBrowser/CompositionRoot.cs @@ -15,7 +15,9 @@ using SafeExamBrowser.Contracts.Configuration.Settings; using SafeExamBrowser.Contracts.I18n; using SafeExamBrowser.Contracts.Logging; using SafeExamBrowser.Contracts.Monitoring; +using SafeExamBrowser.Contracts.SystemComponents; using SafeExamBrowser.Contracts.UserInterface; +using SafeExamBrowser.Contracts.UserInterface.Taskbar; using SafeExamBrowser.Contracts.WindowsApi; using SafeExamBrowser.Core.Behaviour; using SafeExamBrowser.Core.Behaviour.Operations; @@ -26,6 +28,7 @@ using SafeExamBrowser.Monitoring.Keyboard; using SafeExamBrowser.Monitoring.Mouse; using SafeExamBrowser.Monitoring.Processes; using SafeExamBrowser.Monitoring.Windows; +using SafeExamBrowser.SystemComponents; using SafeExamBrowser.UserInterface; using SafeExamBrowser.WindowsApi; @@ -44,6 +47,7 @@ namespace SafeExamBrowser private IProcessMonitor processMonitor; private IRuntimeController runtimeController; private ISettings settings; + private ISystemComponent powerSupply; private ISystemInfo systemInfo; private IText text; private ITextResource textResource; @@ -74,6 +78,7 @@ namespace SafeExamBrowser displayMonitor = new DisplayMonitor(new ModuleLogger(logger, typeof(DisplayMonitor)), nativeMethods); keyboardInterceptor = new KeyboardInterceptor(settings.Keyboard, new ModuleLogger(logger, typeof(KeyboardInterceptor))); mouseInterceptor = new MouseInterceptor(new ModuleLogger(logger, typeof(MouseInterceptor)), settings.Mouse); + powerSupply = new PowerSupply(new ModuleLogger(logger, typeof(PowerSupply))); processMonitor = new ProcessMonitor(new ModuleLogger(logger, typeof(ProcessMonitor)), nativeMethods); windowMonitor = new WindowMonitor(new ModuleLogger(logger, typeof(WindowMonitor)), nativeMethods); @@ -86,7 +91,7 @@ namespace SafeExamBrowser StartupOperations.Enqueue(new WindowMonitorOperation(logger, windowMonitor)); StartupOperations.Enqueue(new ProcessMonitorOperation(logger, processMonitor)); StartupOperations.Enqueue(new DisplayMonitorOperation(displayMonitor, logger, Taskbar)); - StartupOperations.Enqueue(new TaskbarOperation(logger, settings, systemInfo, Taskbar, text, uiFactory)); + StartupOperations.Enqueue(new TaskbarOperation(logger, settings, powerSupply, systemInfo, Taskbar, text, uiFactory)); StartupOperations.Enqueue(new BrowserOperation(browserController, browserInfo, logger, Taskbar, uiFactory)); StartupOperations.Enqueue(new RuntimeControllerOperation(runtimeController, logger)); StartupOperations.Enqueue(new ClipboardOperation(logger, nativeMethods)); diff --git a/SafeExamBrowser/SafeExamBrowser.csproj b/SafeExamBrowser/SafeExamBrowser.csproj index f30639ee..db1283fb 100644 --- a/SafeExamBrowser/SafeExamBrowser.csproj +++ b/SafeExamBrowser/SafeExamBrowser.csproj @@ -135,6 +135,10 @@ {ef563531-4eb5-44b9-a5ec-d6d6f204469b} SafeExamBrowser.Monitoring + + {ACEE2EF1-14D2-4B52-8994-5C053055BB51} + SafeExamBrowser.SystemComponents + {e1be031a-4354-41e7-83e8-843ded4489ff} SafeExamBrowser.UserInterface