using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
using System.Reflection;

namespace RegistrationAPI_Tester
{
    static class Program
    {
        /// <summary>
        /// The main entry point for the application.
        /// </summary>
        [STAThread]
        static void Main()
        {
            // Make sure all embedded Assemblies get loaded
            AppDomain.CurrentDomain.AssemblyResolve += new ResolveEventHandler(CurrentDomain_AssemblyResolve);   

            AppDomain.CurrentDomain.UnhandledException += new UnhandledExceptionEventHandler(CurrentDomain_UnhandledException);
            Application.ThreadException += new System.Threading.ThreadExceptionEventHandler(Application_ThreadException);

            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new MainForm());
        }

        #region Application Multi-File Assembly Handling

        /// <summary>
        /// A way to embed multiple dlls into one exe:
        /// http://blogs.msdn.com/b/microsoft_press/archive/2010/02/03/jeffrey-richter-excerpt-2-from-clr-via-c-third-edition.aspx
        /// </summary>
        /// <returns>a loaded assembly if found, null otherwise</returns>
        static System.Reflection.Assembly CurrentDomain_AssemblyResolve(object sender, ResolveEventArgs args)
        {
            string curAssemblyName = Assembly.GetExecutingAssembly().FullName.Split(',')[0];
            String resourceName = curAssemblyName + ".Components." + new AssemblyName(args.Name).Name + ".dll";

            //string[] resources = AssemblyW.SpecializedAssemblyInfo.GetAssemblyResourceNames(AssemblyW.AssemblyST.Entry);
            var stream = Assembly.GetExecutingAssembly().GetManifestResourceStream(resourceName);
            if (stream != null)
            {
                using (stream)
                {
                    Byte[] assemblyData = new Byte[stream.Length];
                    stream.Read(assemblyData, 0, assemblyData.Length);
                    return Assembly.Load(assemblyData);
                }
            }
            return null;
        }

        #endregion

        #region Global Error Handlers

        static void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e)
        {
            Exception ex = (Exception)e.ExceptionObject;
            String msg = "UnhandledException Occured: " + ex.Message + "\n\n" + ex.InnerException.Message;
            MessageBox.Show(msg,
                 "Error",
                 MessageBoxButtons.OK,
                 MessageBoxIcon.Error,
                 MessageBoxDefaultButton.Button1);            
        }

        static void Application_ThreadException(object sender, System.Threading.ThreadExceptionEventArgs e)
        {
            Exception ex = e.Exception;
            String msg = "Thread Exception Occured: " + ex.Message + "\n\n" + ex.InnerException.Message;
            MessageBox.Show(msg,
                 "Error",
                 MessageBoxButtons.OK,
                 MessageBoxIcon.Error,
                 MessageBoxDefaultButton.Button1);
        }

        #endregion
    }
}
