using System.Collections.Generic;
using System.IO.Ports;
using System.Linq;
using System.Runtime.InteropServices;
using Ursa.Controls;
using 常用工具集.Base;

namespace 常用工具集.ViewModel._04破解及系统相关
{
    public class 串口转键盘输入ViewModel : ViewModelBase
    {
        private SerialHelper helper;
        public bool Enabled { get; set; } = true;
        public string ButtonText { get; set; } = "打开";
        public DelegateCommand ButtonCmd { get; set; }

        //串口号下拉列表数据
        public List<string> SerialList { get; set; }
        public int SerialIndex { get; set; } = 0;

        /// <summary>
        /// 波特率
        /// </summary>
        public List<int> BaudRateList { get; set; }
        public int BaudRateIndex { get; set; } = 0;
        //校验
        public List<string> ParityList { get; set; }
        public int ParityIndex { get; set; } = 0;

        //数据为
        public List<int> DataBitList { get; set; }
        public int DataBitIndex { get; set; } = 0;
        //停止位
        public List<string> StopBitList { get; set; }
        public int StopBitIndex { get; set; } = 0;

        public int Timeout { get; set; } = 1000;
        public 串口转键盘输入ViewModel()
        {
            //串口号
            string[] portNames = SerialPort.GetPortNames();
            if (portNames != null && portNames.Length > 0)
            {
                SerialList = portNames.ToList();
            }
            //波特率
            BaudRateList = new List<int>() { 110, 300, 600, 1200, 2400, 4800, 9600, 14400, 19200, 38400, 56000, 57600, 115200, 128000 };
            BaudRateIndex = 6;
            //校验
            ParityList = new List<string> { "None", "Odd", "Even", "Mark", "Space" };
            ParityIndex = 0;
            //数据位
            DataBitList = new List<int> { 5, 6, 7, 8 };
            DataBitIndex = 3;
            //停止位
            StopBitList = new List<string> { "None", "One", "Two", "OnePointFive" };
            StopBitIndex = 1;

            ButtonCmd = new DelegateCommand(ButtonCmdFunc);
        }

        private void ButtonCmdFunc(object obj)
        {
            if (ButtonText == "打开")
            {
                try
                {
                    helper = new SerialHelper(
                        SerialList[SerialIndex],
                        BaudRateList[BaudRateIndex],
                        DataBitList[DataBitIndex],
                        (StopBits)StopBitIndex,
                        (Parity)ParityIndex,
                        Timeout
                        );
                    helper.Open();
                }
                catch
                {
                    MessageBox.ShowAsync("串口打开失败");
                    return;
                }
                Enabled = false;
                ButtonText = "关闭";
                GlobalValues.MainWindow.WindowState = Avalonia.Controls.WindowState.Minimized;
            }
            else
            {
                helper.Close();
                helper = null;
                Enabled = true;
                ButtonText = "打开";
            }
        }



        public class SerialHelper
        {
            [DllImport("user32")]
            static extern void keybd_event(byte bVk, byte bScan, uint dwFlags, uint dwExtraInfo);
            const uint KEYEVENTF_EXTENDEDKEY = 0x1;
            const uint KEYEVENTF_KEYUP = 0x2;




            private SerialPort serialPort;
            public SerialHelper(string portName, int baudRate, int dataBits, StopBits stopBits, Parity parity, int timeout)
            {
                serialPort = new SerialPort();
                serialPort.PortName = portName;
                serialPort.BaudRate = baudRate;
                serialPort.DataBits = dataBits;
                serialPort.StopBits = stopBits;
                serialPort.Parity = parity;
                serialPort.ReadTimeout = timeout;
                serialPort.DataReceived += SerialPort1_DataReceived;
            }


            /// <summary>
            /// 打开串口
            /// </summary>
            public void Open()
            {
                if (serialPort.IsOpen)
                    return;
                serialPort.Open();
            }


            /// <summary>
            /// 关闭串口
            /// </summary>
            public void Close()
            {
                if (!serialPort.IsOpen)
                    return;
                serialPort.Close();
            }

            private void SerialPort1_DataReceived(object sender, SerialDataReceivedEventArgs e)
            {
                int n = serialPort.BytesToRead;
                byte[] buf = new byte[n];
                serialPort.Read(buf, 0, n);
                foreach (byte b in buf)
                {
                    if (b >= '0' && b <= '9')
                    {
                        keybd_event(b, 0x45, KEYEVENTF_EXTENDEDKEY | 0, 0);
                        keybd_event(b, 0x45, KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP, 0);
                    }
                    else if (b >= 'a' && b <= 'z')
                    {
                        keybd_event((byte)(b - 32), 0x45, KEYEVENTF_EXTENDEDKEY | 0, 0);
                        keybd_event((byte)(b - 32), 0x45, KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP, 0);
                    }
                    else if (b >= 'A' && b <= 'Z')
                    {
                        keybd_event(16, 0x45, KEYEVENTF_EXTENDEDKEY | 0, 0);//按下Shift键
                        keybd_event(b, 0x45, KEYEVENTF_EXTENDEDKEY | 0, 0);
                        keybd_event(b, 0x45, KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP, 0);
                        keybd_event(16, 0x45, KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP, 0);//松开Shift键
                    }
                    else if (b == 0x0D || b == 0x0A)
                    {
                        keybd_event(0x0D, 0x45, KEYEVENTF_EXTENDEDKEY | 0, 0);
                        keybd_event(0x0D, 0x45, KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP, 0);
                    }
                }
            }
        }
    }
}