using System;
using System.Runtime.InteropServices;
using System.Drawing;

namespace NZSDK_CSharpSample
{
    public partial class NZLiveDisplay : DynamicLibraryLoader
    {
        #region Constraints

        public enum OSDPosition : int
        {
            LeftTop = 0,
            RightTop,
            LeftBottom,
            RightBottom
        }
		 
    	#endregion

        #region Fields

        IntPtr ptrHandle;

        #endregion

        #region Constructors

        public NZLiveDisplay()
            : base()
        {
            releaseFileName = "NZLiveDisplay.dll";
            if (Load())
                Create();
        }

        #endregion

        #region Properties

        public bool IsCreated
        {
            get
            {
                return (ptrHandle != IntPtr.Zero);
            }
        }

        #endregion

        #region Private / Protected Methods

        protected void Create()
        {
            Release();

            ptrHandle = _NZLDCreate();
        }

        protected void Release()
        {
            if (ptrHandle == IntPtr.Zero)
                return;

            _NZLDDelete(ptrHandle);
        }

        protected bool Command(Commands command)
        {
            return Command(command, IntPtr.Zero, IntPtr.Zero, IntPtr.Zero, IntPtr.Zero);
        }

        protected bool Command(Commands command, IntPtr arg1)
        {
            return Command(command, arg1, IntPtr.Zero, IntPtr.Zero, IntPtr.Zero);
        }

        protected bool Command(Commands command, IntPtr arg1, IntPtr arg2)
        {
            return Command(command, arg1, arg2, IntPtr.Zero, IntPtr.Zero);
        }

        protected bool Command(Commands command, IntPtr arg1, IntPtr arg2, IntPtr arg3)
        {
            return Command(command, arg1, arg2, arg3, IntPtr.Zero);
        }

        protected bool Command(Commands command, IntPtr arg1, IntPtr arg2, IntPtr arg3, IntPtr arg4)
        {
            return _NZLDCommand(ptrHandle, command, arg1, arg2, arg3, arg4);
        }

        #endregion

        #region Public Methods

        public void SetDisplayWindow(IntPtr windowHandle)
        {
            Command(Commands.Open, windowHandle);
        }

        public void EnableDisplayWindow(bool enable)
        {
            Command(Commands.Enable, new IntPtr(Convert.ToInt32(enable)));
        }

        public void SetLogoImage(string fullPath)
        {
            IntPtr ptrFullPath = Marshal.StringToHGlobalUni(fullPath);
            Command(Commands.SetLogoImage, ptrFullPath);
            Marshal.FreeHGlobal(ptrFullPath);
        }

        public void SetOSDFont(string fontName, int height, Color textColor, Color backColor)
        {
            IntPtr ptrFontName = Marshal.StringToHGlobalUni(fontName);
            Command(Commands.SetOSDSetting, ptrFontName, new IntPtr(height), new IntPtr(textColor.ToArgb()), new IntPtr(backColor.ToArgb()));
            Marshal.FreeHGlobal(ptrFontName);
        }

        public void SetOSDText(string text, OSDPosition position)
        {
            IntPtr ptrText = Marshal.StringToHGlobalUni(text);
            Command(Commands.SetOSDText, ptrText, new IntPtr((int)position));
            Marshal.FreeHGlobal(ptrText);
        }

        public void DrawConnectingOSD()
        {
            Command(Commands.Connecting);
        }

        public void EnableScreenPtz(bool enable)
        {
            Command(Commands.EnableScreenPtz, new IntPtr(Convert.ToInt32(enable)));
        }

        public void UpdateDisplayWindowPosition()
        {
            Command(Commands.SetWindowPosition);
        }

        public void SetCustomDrawHandler(DrawVideoDelegate drawHandler, IntPtr pUserParam)
        {
            Command(Commands.SetCustomDrawHandler, Marshal.GetFunctionPointerForDelegate(drawHandler), pUserParam);
        }

        public bool OpenVideo(string address, int port, string url, string loginId, string password)
        {
            DeviceInfo deviceInfo = new DeviceInfo();
            deviceInfo.Address = address;
            deviceInfo.Port = port;
            deviceInfo.Url = url;
            deviceInfo.LoginId = loginId;
            deviceInfo.Password = password;
            IntPtr ptrDeviceInfo = IntPtr.Zero;
            ptrDeviceInfo = Marshal.AllocHGlobal(Marshal.SizeOf(deviceInfo));
            Marshal.StructureToPtr(deviceInfo, ptrDeviceInfo, true);

            bool result = Command(Commands.OpenVideo, ptrDeviceInfo);

            Marshal.FreeHGlobal(ptrDeviceInfo);
            return result;
        }

        public void CloseVideo()
        {
            Command(Commands.CloseVideo);
        }

        #endregion
    }
}