private void SendIdentifiedFrequency([NotNull] WebBrowserAssistantServer.Client client, int frequencyIndex)
 {
     if (frequencyIndex < 0 || frequencyIndex >= _frequencyCount)
     {
         frequencyIndex = AbsentFrequencyIndex;
     }
     _server.SendMessageToClient(client, new OutgoingMessage {
         Type = "Frequency", FrequencyIndex = frequencyIndex
     });
 }
        void WebBrowserAssistantServer.IClientMessageHandler.Handle(WebBrowserAssistantServer.Client client, IncomingMessage message)
        {
            // ReSharper disable once SwitchStatementMissingSomeCases
            switch (message.Type)
            {
            case "Handshake":
                var frequencies = _paradigm.Config.User.StimulationScheme.Frequencies;
                var schemes     = new OutgoingMessage.VisualScheme[frequencies.Count];
                for (var i = 0; i < frequencies.Count; i++)
                {
                    schemes[i].Frequency       = frequencies[i];
                    schemes[i].BorderThickness = IndicatorBorderThicknesses[i % IndicatorBorderThicknesses.Length];
                    schemes[i].BorderStyle     = IndicatorBorderStyles[i % IndicatorBorderStyles.Length];
                    schemes[i].Color           = VisualColors[i % VisualColors.Length];
                }
                _server.SendMessageToClient(client, new OutgoingMessage
                {
                    Type              = "Handshake", Debug = _paradigm.Config.System.DebugInformation,
                    HomePage          = _paradigm.Config.User.HomePage,
                    VisualSchemes     = schemes,
                    MaxActiveDistance = _paradigm.Config.User.CursorMovementTolerance,
                    ConfirmationDelay = _paradigm.Config.User.ConfirmationDelay,
                    EdgeScrolling     = _paradigm.Config.User.EnableEdgeScrolling,
                    StimulationSize   = new Point
                    {
                        X = _paradigm.Config.User.StimulationSize.Width,
                        Y = _paradigm.Config.User.StimulationSize.Height
                    },
                    Mode = Mode
                });
                break;

            case "Mode":
                Mode = message.Mode ?? Mode.Normal;
                break;
            }
        }
 private void SendScroll([NotNull] WebBrowserAssistantServer.Client client, Point scrollDistance) =>
 _server.SendMessageToClient(client, new OutgoingMessage {
     Type = "Scroll", ScrollDistance = scrollDistance
 });
        private void RunTrial([NotNull] WebBrowserAssistantServer.Client client)
        {
            var scene                 = client.Scene;
            var dimensions            = client.Dimensions;
            var detector              = scene == Scene.Keyboard ? _spellingSsvepDetector : _navigatingSsvepDetector;
            var edgeScrolling         = _paradigm.Config.User.EnableEdgeScrolling && dimensions != null;
            var edgeScrollHotAreaSize = _paradigm.Config.User.EdgeScrollingHotAreaSize;
            var edgeScrollSpeed       = _paradigm.Config.User.EdgeScrollingSpeed;

            /* Initialize signals. */
            _dwellTrialController.Reset();
            _trialStartEvent.Reset();
            _trialCancelled.Reset();

            /* Waiting for the start signal. */
            Point gazePoint;

            if (edgeScrolling)
            {
                while (!_trialStartEvent.WaitOne(TimeSpan.FromMilliseconds(20)))
                {
                    if (!_gazePointProvider.TryGetCurrentPosition(out gazePoint))
                    {
                        continue;
                    }
                    var area = GetGazeArea(dimensions, edgeScrollHotAreaSize, gazePoint);
                    if (area == 0)
                    {
                        continue;
                    }
                    var verticalScrollDistance = dimensions.WindowInnerSize.Height * edgeScrollSpeed;
                    SendScroll(client, new Point {
                        X = 0, Y = area * verticalScrollDistance
                    });
                }
            }
            else
            {
                _trialStartEvent.WaitOne();
            }
            if (!_gazePointProvider.TryGetCurrentPosition(out gazePoint))
            {
                return;
            }
            _server.SendMessageToClient(client, new OutgoingMessage {
                Type = "StartTrial", GazePoint = gazePoint
            });

            var cancelled = true;

            detector.IsActive = true;
            try
            {
                /* Waiting for the ending of trial or cancelled by system. */
                var stimulationMillis = (int)(detector.WindowSizeInSecs * 1000);
                cancelled = _trialCancelled.WaitOne(stimulationMillis + SsvepDelayMillis);
                if (cancelled)
                {
                    return;
                }
                _server.SendMessageToClient(client, new OutgoingMessage {
                    Type = "EndTrial"
                });
            }
            finally
            {
                detector.IsActive = false;
                if (cancelled)
                {
                    SendIdentifiedFrequency(client, AbsentFrequencyIndex);
                }
            }

            /* Send identified frequency index. */
            var result = detector.Identify();

            SendIdentifiedFrequency(client, result.State == IdentificationState.Success ? result.FrequencyIndex : AbsentFrequencyIndex);
            Logger.Info("RunTrial", "result", result);
        }