private void OnViewportsChanged(ViewportEditorWindowViewModel sender, List <ViewportEditorWindowViewModel> allViewModels)
        {
            var viewports = allViewModels.SelectMany(vm => vm.Viewports.Select(v => v.Name.Value)).ToArray();

            foreach (var vm in allViewModels)
            {
                vm.ConsumedViewports.Clear();
                vm.ConsumedViewports.AddRange(viewports);
            }
        }
        public async Task <Viewport[]> EditViewportsAsync(ModuleViewportModel value)
        {
            if (!IsValidViewports(value.Viewports.ToArray()))
            {
                MessageBoxEx.Show($"One or more viewports were defined on a monitor that is no longer configured, they have been removed.{Environment.NewLine}Make sure you add any missing viewports before saving.", "Invalid Viewport");
            }

            var tasks      = new List <Task>();
            var screenIds  = GetDeviceViewportMonitorIds();
            var devices    = _profileSettingsService.GetViewportDevices(value.Module.Value.ModuleId).Where(d => value.Viewports.Any(v => v.SeatIndex == d.SeatIndex)).ToArray();
            var windows    = new List <Window>();
            var viewModels = new List <ViewportEditorWindowViewModel>();

            var editorScreens  = Screen.AllScreens.Where(s => screenIds.Contains(s.DeviceName));
            var overlayScreens = Screen.AllScreens.Where(s => !screenIds.Contains(s.DeviceName) && !value.Viewports.Select(v => v.MonitorId).Contains(s.DeviceName));

            foreach (var screen in editorScreens)
            {
                var viewportModels = new List <ViewportModel>();

                foreach (var viewport in value.Viewports.Where(v => v.MonitorId == screen.DeviceName))
                {
                    if (!screenIds.Contains(viewport.MonitorId))
                    {
                        continue;
                    }

                    var model = new ViewportModel();

                    model.Height.Value   = viewport.Height;
                    model.InitFile.Value = viewport.RelativeInitFilePath;
                    model.ImageUrl.Value = Path.Combine(ApplicationPaths.ViewportPath, $"Images/{value.Module.Value.ModuleId}/{viewport.ViewportName}.jpg");
                    model.Name.Value     = viewport.ViewportName;
                    model.Width.Value    = viewport.Width;
                    model.X.Value        = viewport.X;
                    model.Y.Value        = viewport.Y;

                    viewportModels.Add(model);
                }

                var window = new ViewportEditorWindow();
                var vm     = new ViewportEditorWindowViewModel(_container, false, screen.DeviceName, value.Module.Value, devices, viewportModels.ToArray());

                vm.Viewports.CollectionChanged += (sender, args) =>
                {
                    OnViewportsChanged(vm, viewModels);
                };

                window.Screen      = screen;
                window.DataContext = vm;
                window.Show();
                window.BringIntoView();

                windows.Add(window);
                viewModels.Add(vm);

                tasks.Add(EventAsync.FromEvent(
                              handler => window.Closed += handler,
                              handler => window.Closed -= handler));
            }

            foreach (var screen in overlayScreens)
            {
                var window = new MonitorOverlay
                {
                    Screen = screen
                };

                window.Show();
                window.BringIntoView();
                windows.Add(window);

                tasks.Add(EventAsync.FromEvent(
                              handler => window.Closed += handler,
                              handler => window.Closed -= handler));
            }

            await Task.WhenAny(tasks);

            foreach (var window in windows)
            {
                try
                {
                    window.Close();
                }
                catch
                {
                }
            }

            var save      = viewModels.Any(vm => vm.DialogResult.Value == true);
            var viewports = new List <Viewport>();

            if (save)
            {
                foreach (var viewModel in viewModels)
                {
                    var screen = Screen.AllScreens.First(s => s.DeviceName == viewModel.MonitorId);

                    foreach (var viewportModel in viewModel.Viewports)
                    {
                        viewports.Add(
                            new Viewport
                        {
                            Height                = (int)viewportModel.Height.Value,
                            MonitorId             = screen.DeviceName,
                            SeatIndex             = viewportModel.SeatIndex.Value,
                            OriginalDisplayHeight = (int)screen.Bounds.Height,
                            OriginalDisplayWidth  = (int)screen.Bounds.Width,
                            RelativeInitFilePath  = viewportModel.InitFile.Value,
                            ViewportName          = viewportModel.Name.Value,
                            Width = (int)viewportModel.Width.Value,
                            X     = (int)viewportModel.X.Value,
                            Y     = (int)viewportModel.Y.Value
                        });
                    }
                }
                return(viewports.ToArray());
            }
            else
            {
                return(value.Viewports.ToArray());
            }
        }