using Microsoft.ReactNative.Managed;
using WinRT.BxlComponent.Plugin.BxlMpXamarinSDK;
using WinRT.BxlComponent.Plugin.BxlMpXamarinSDK.Abstractions;
using System;
using Windows.UI.Core;
using System.Runtime.InteropServices.WindowsRuntime;
using Plugin.BxlMAUISDK.PlatformImplementations;

namespace ReactNativeRnBixolonBgateLibs.UWPProxy
{
    [ReactModule]
    public sealed partial class MPosControllerHIDProxy
    {
        private MPosControllerHIDImplementation _device;
        private static int _uniqueDeviceId = 256;
        public event EventHandler<string> _dataEvent;

        //[ReactEvent("PrinterDataEvent")]        
        [ReactEvent("HIDDataEvent")]
        public Action<int, byte[]> dataEvent { get; set; }


        public MPosControllerHIDProxy()
        {
            _device = new MPosControllerHIDImplementation((int)MPosDeviceType.MPOS_DEVICE_HID, _uniqueDeviceId++);
        }

        private async void onDataEvent(byte[] data)
        {
            MPosDebug.WriteLine("MPosDevicePrinterImpl onDataEvent, dataEvent?.Invoke, data = " + data);
            await Windows.ApplicationModel.Core.CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
            {
                if (_dataEvent == null)
                {
                    MPosDebug.WriteLine("MPosDevicePrinterImpl onDataEvent, dataEvent is null ");
                    return;
                }
                int deviceId = _device.CommandMode == MPosCommandMode.MPOS_COMMAND_MODE_DIRECT ? -1 : _device.DeviceID;
                string dataInJsonFormat = "[{\"deviceid\": " + deviceId + ",";
                dataInJsonFormat += "\"data\": [";
                for (int i = 0; i < data.Length; i++)
                {
                    dataInJsonFormat += String.Format("{0:d}", data[i]);
                    if (i != data.Length - 1)
                        dataInJsonFormat += ",";
                }
                dataInJsonFormat += "]}]";
                MPosDebug.WriteLine("MPosDevicePrinterImpl onDataEvent, dataInJsonFormat = " + dataInJsonFormat);
                _dataEvent?.Invoke(this, dataInJsonFormat);
            });
        }

        [ReactMethod("selectInterface")]
        public void selectInterface(string[] array, IReactPromise<int> promise)
        {
            promise.Resolve(_device.selectInterface(
                Convert.ToInt32(array[0]),
                array[1])
                );
            return;
        }

        [ReactMethod("openService")]
        public async void openService(uint[] array, IReactPromise<int> promise)
        {
            //device.dataEvent += onDataEvent;
            _device.dataEvent2 += dataEvent;
            promise.Resolve(await _device.openService(
                array[0],
                array[1]
                ));
            return;
        }
        [ReactMethod("closeService")]
        public async void closeService(uint closeTimeout/*second*/, IReactPromise<int> promise)
        {
            //device.dataEvent -= onDataEvent;
            _device.dataEvent2 -= dataEvent;
            promise.Resolve(await _device.closeService(closeTimeout));
            return;
        }
        [ReactMethod("selectCommandMode")]
        public void selectCommandMode(int commandMode, IReactPromise<int> promise)
        {
            promise.Resolve(_device.selectCommandMode(commandMode));
            return;
        }
        [ReactMethod("isOpen")]
        public void isOpen(IReactPromise<int> promise)
        {
            promise.Resolve(Convert.ToInt32(_device.isOpen()));
            return;
        }
        [ReactMethod("getDeviceId")]
        public void getDeviceId(IReactPromise<int> promise)
        {
            promise.Resolve(Convert.ToInt32(_device.DeviceID));
            return;
        }
        [ReactMethod("directIO")]
        public async void directIO([ReadOnlyArray()] byte[] data, IReactPromise<int> promise)
        {
            promise.Resolve(await _device.directIO(data));
            return;
        }
    }
}
