HamBook – Rev 54

Subversion Repositories:
Rev:
using System.Text.RegularExpressions;
using System.Threading;
using System.Threading.Tasks;
using HamBook.Radios.Generic;
using RJCP.IO.Ports;
using static HamBook.Radios.Yaesu.FT_891.Constants;

namespace HamBook.Radios.Yaesu.FT_891.CAT
{
    [Radio("Yaesu FT-891")]
    public class Ps : Generic.CAT.Ps
    {
        private readonly Regex _readRegex;

        public Ps(SerialPortStream serialPort) : base(serialPort)
        {
            _readRegex = new Regex($"^{Name}(?<state>[01]){Eot}$", RegexOptions.Compiled);
        }

        public override CatLength CatLength => new CatLength { Set = 4, Answer = 4, Read = 3 };

        public override async Task<bool> SetAsync(PowerState state, CancellationToken cancellationToken)
        {
            SerialPort.Write(new byte[1] { 0 }, 0, 1);
            SerialPort.Read(new byte[2] { 0, 0 }, 0, 2);

            var taskCompletionSource = new TaskCompletionSource<bool>();

#pragma warning disable CS4014 // Because this call is not awaited, execution of the current method continues before the call is completed
            Task.Delay(PowerOnDelay).ContinueWith(async task1 =>
            {
                byte[] payload = null;
                switch (state)
                {
                    case PowerState.ON:
                        payload = Encoding.GetBytes($"{Name}1{Eot}");
                        await SerialPort.WriteAsync(payload, 0, payload.Length);
                        Task.Delay(TimeToWarm).ContinueWith(task2 => { taskCompletionSource.TrySetResult(true); });
                        return;
                    case PowerState.OFF:
                        payload = Encoding.GetBytes($"{Name}0{Eot}");
                        await SerialPort.WriteAsync(payload, 0, payload.Length);
                        break;
                }

                taskCompletionSource.TrySetResult(true);
            });
#pragma warning restore CS4014 // Because this call is not awaited, execution of the current method continues before the call is completed

            await taskCompletionSource.Task;
            return await ReadAsync(cancellationToken) == state;
        }

        public override async Task<PowerState> ReadAsync(CancellationToken cancellationToken)
        {
            SerialPort.Write(new byte[1] { 0 }, 0, 1);
            SerialPort.Read(new byte[2] { 0, 0 }, 0, 2);

            var taskCompletionSource = new TaskCompletionSource<int>();

#pragma warning disable CS4014 // Because this call is not awaited, execution of the current method continues before the call is completed
            Task.Delay(PowerOnDelay).ContinueWith(async _ =>
            {
                var payload = Encoding.GetBytes($"{Name}{Eot}");

                await SerialPort.WriteAsync(payload, 0, payload.Length, cancellationToken);

                var buffer = new byte[CatLength.Answer];
                if (await SerialPort.ReadAsync(buffer, 0, CatLength.Answer, cancellationToken) != CatLength.Answer)
                {
                    taskCompletionSource.TrySetResult(-1);

                    throw new UnexpectedRadioResponseException(Name, buffer);
                }

                var answer = Encoding.GetString(buffer);
                var match = _readRegex.Match(answer);
                if (!match.Success)
                {
                    taskCompletionSource.TrySetResult(-1);

                    throw new UnmatchedRadioResponseException(Name, answer);
                }

                var state = int.Parse(match.Result("${state}"));
                taskCompletionSource.TrySetResult(state);
            });
#pragma warning restore CS4014 // Because this call is not awaited, execution of the current method continues before the call is completed
            var onoff = await taskCompletionSource.Task;
            switch (onoff)
            {
                case 1:
                    return PowerState.ON;
                case 0:
                    return PowerState.OFF;
            }

            return PowerState.NONE;
        }
    }
}

Generated by GNU Enscript 1.6.5.90.