/// <summary>
        /// Prompt user to select custom server config JSON, set it as the current config, and prompt to restart server
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void customToolStripMenuItem_Click(object sender, EventArgs e)
        {
            ToolStripMenuItem tsmi = (ToolStripMenuItem)sender;

            bool isChecked  = tsmi.Checked;
            bool wasChecked = Properties.Settings.Default.useCustomConfig;

            OpenFileDialog openFileDialog = new OpenFileDialog();

            openFileDialog.Filter           = Common.CUSTOM_CONFIG_DIALOG_FILTER;
            openFileDialog.Multiselect      = false;
            openFileDialog.InitialDirectory = OSVRRegistry.GetInstallDirectoryFromRegistry() + Common.SERVICE_PATH;
            openFileDialog.Title            = Common.CUSTOM_CONFIG_DIALOG_TITLE;

            if (openFileDialog.ShowDialog() == DialogResult.OK)
            {
                Debug.WriteLine(openFileDialog.FileName);
                Properties.Settings.Default.targetCustomConfig = openFileDialog.FileName;
                UpdateServerConfigCheckboxStates(tsmi);
                m_server.PromptServerStartOrRestart();
            }
            else // if config wasn't actually changed, restore previous state
            {
                tsmi.Checked = wasChecked;
            }

            openFileDialog.Dispose();
        }
        private void Server_ErrorDataReceived(object sender, DataReceivedEventArgs e)
        {
            m_console.DataReceived(e.Data, true);

            /// There is probably a better way to handle this...
            if (e.Data != null && e.Data.Contains("WARNING - Your HDK infrared tracking camera was detected to have outdated firmware in need of updating, and may not function properly."))
            {
                string  osvrPath          = OSVRRegistry.GetInstallDirectoryFromRegistry();
                string  workingDirectory  = osvrPath + Common.FW_UTIL_PATH;
                string  completeFilePath  = workingDirectory + Common.IR_CAM_FW_UPDATER_NAME;
                Process ir_cam_fw_updater = OSVRProcessManager.LaunchExecutable(completeFilePath,
                                                                                workingDirectory,
                                                                                ProcessWindowStyle.Normal,
                                                                                string.Empty);

                if (ir_cam_fw_updater == null)
                {
                    Common.ShowMessageBox(Common.MSG_MISSING_OR_CANCELLED_IR_CAM_FW_UPDATER, MessageBoxButtons.OK, MessageBoxIcon.Error);
                }
                else
                {
                    m_console.DataReceived(
                        "\n---\n" +
                        "Because your HDK IR Camera has outdated firmware, the firmware update tool will be launched.\n" +
                        "Please restart the server after updating your camera's firmware.\n\n" +
                        "NOTE: If the update utility reports that the update \"is not suitable for your device\"\n" +
                        "please plug your HDK IR Camera directly into a USB port on your computer rather than a hub\n" +
                        "such as those found on monitors, then restart the server to try again." +
                        "\n---\n", false);
                }
            }
        }
        public void Recenter()
        {
            string osvrPath         = OSVRRegistry.GetInstallDirectoryFromRegistry();
            string workingDirectory = osvrPath + Common.FW_UTIL_PATH;
            string completeFilePath = workingDirectory + Common.RECENTER_NAME;

            OSVRProcessManager.LaunchExecutable(completeFilePath,
                                                workingDirectory,
                                                ProcessWindowStyle.Minimized,
                                                string.Empty);
        }
        /// <summary>
        /// Launch tracker viewer
        /// </summary>
        private void StartTrackerView()
        {
            string  osvrPath         = OSVRRegistry.GetInstallDirectoryFromRegistry();
            string  workingDirectory = osvrPath + Common.TRACKER_VIEW_PATH;
            string  completeFilePath = workingDirectory + Common.TRACKER_VIEW_NAME;
            Process tv = OSVRProcessManager.LaunchExecutable(completeFilePath, workingDirectory, ProcessWindowStyle.Normal, string.Empty);

            if (tv == null)
            {
                Common.ShowMessageBox(Common.MSG_MISSING_TRACKER_VIEW, MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
        }
        /// <summary>
        /// Set extended display mode
        /// </summary>
        private void SetExtendedMode()
        {
            string extended_mode_name = null;

            GPUDetection.GraphicsCardType gct = GPUDetection.GraphicsCardType.UNKNOWN;
            try
            {
                gct = (GPUDetection.GraphicsCardType)Enum.Parse(typeof(GPUDetection.GraphicsCardType), Properties.Settings.Default.graphicsCardType);
            }
            catch (ArgumentException) { }

            switch (gct)
            {
            case GPUDetection.GraphicsCardType.NVIDIA:
                extended_mode_name = Common.EXTENDED_MODE_NAME_NVIDIA;
                break;

            case GPUDetection.GraphicsCardType.AMD:
                extended_mode_name = Common.EXTENDED_MODE_NAME_AMD;
                break;

            case GPUDetection.GraphicsCardType.UNKNOWN:
                ShowSelectGPUTypeDialog();
                return;
            }

            string  osvrPath         = OSVRRegistry.GetInstallDirectoryFromRegistry();
            string  workingDirectory = osvrPath + Common.SERVICE_PATH;
            string  completeFilePath = workingDirectory + extended_mode_name;
            Process em_exe           = OSVRProcessManager.LaunchExecutable(completeFilePath,
                                                                           workingDirectory,
                                                                           ProcessWindowStyle.Normal,
                                                                           string.Empty);

            if (em_exe == null)
            {
                Common.ShowMessageBox(Common.MSG_MISSING_EM_EXE, MessageBoxButtons.OK, MessageBoxIcon.Error);
                return;
            }

            em_exe.EnableRaisingEvents = true;
            em_exe.Exited += setExtendedModeProcess_Exited;
        }
        /// <summary>
        /// Launch Unity campfire sample application
        /// </summary>
        private void StartTestApp()
        {
            string osvrPath         = OSVRRegistry.GetInstallDirectoryFromRegistry();
            string workingDirectory = osvrPath + Common.TEST_APP_PATH;
            string completeFilePath = workingDirectory + Common.TEST_APP_NAME;

            Process proc = OSVRProcessManager.LaunchExecutable(completeFilePath,
                                                               workingDirectory,
                                                               ProcessWindowStyle.Normal,
                                                               ""); // "-show-screen-selector"); // NativeHelpers.IsExtendedModeEnabled() ? "-show-screen-selector" : "");

            if (proc == null)
            {
                Common.ShowMessageBox(Common.MSG_MISSING_SAMPLE_SCENE, MessageBoxButtons.OK, MessageBoxIcon.Error);
                return;
            }

            proc.EnableRaisingEvents = true;
            proc.Exited += Testapp_Exited;
        }
        /// <summary>
        /// Launch CPI
        /// </summary>
        public HDKType StartFWUtil(bool detect_hw_type = false)
        {
            string  osvrPath         = OSVRRegistry.GetInstallDirectoryFromRegistry();
            string  workingDirectory = osvrPath + Common.FW_UTIL_PATH;
            string  completeFilePath = workingDirectory + Common.FW_UTIL_NAME;
            Process fw_util          = OSVRProcessManager.LaunchExecutable(completeFilePath,
                                                                           workingDirectory,
                                                                           ProcessWindowStyle.Normal,
                                                                           detect_hw_type ? "-detecthw" : string.Empty);

            if (fw_util == null)
            {
                Common.ShowMessageBox(Common.MSG_MISSING_FWU, MessageBoxButtons.OK, MessageBoxIcon.Error);
                return(HDKType.ERROR);
            }

            if (detect_hw_type)
            {
                fw_util.WaitForExit();
                return((HDKType)fw_util.ExitCode);
            }
            return(HDKType.NOT_REQUESTED);
        }
        /// <summary>
        /// Start OSVR server
        /// </summary>
        public void StartServer(bool restart = false)
        {
            string configArgs = string.Empty;

            // is the "Use Custom Config" option checked
            if (m_contextMenu.CustomServerConfigChecked)
            {
                string targetCustomConfig = Properties.Settings.Default.targetCustomConfig;
                // has the user specified a custom config?
                if (!string.IsNullOrEmpty(targetCustomConfig) && File.Exists(targetCustomConfig))
                {
                    configArgs = targetCustomConfig;
                }
                else
                {
                    Common.ShowMessageBox(Common.MSG_MISSING_CUSTOM_CONFIG, MessageBoxButtons.OK, MessageBoxIcon.Error, true);
                    return;
                }
            }
            else
            {
                switch (m_contextMenu.DetectHDKType())
                {
                case ContextMenuWYSIWYG.HDKType.HDK1:
                    if (NativeHelpers.IsExtendedModeEnabled())
                    {
                        if (m_contextMenu.UseIRCameraChecked)
                        {
                            configArgs = Common.CFG_1X_EM_CAM;
                        }
                        else
                        {
                            configArgs = Common.CFG_1X_EM_NOCAM;
                        }
                    }
                    else
                    {
                        if (m_contextMenu.UseIRCameraChecked)
                        {
                            configArgs = Common.CFG_1X_DM_CAM;
                        }
                        else
                        {
                            configArgs = Common.CFG_1X_DM_NOCAM;
                        }
                    }
                    break;

                case ContextMenuWYSIWYG.HDKType.HDK2:
                    if (NativeHelpers.IsExtendedModeEnabled())
                    {
                        if (m_contextMenu.UseIRCameraChecked)
                        {
                            configArgs = Common.CFG_2_EM_CAM;
                        }
                        else
                        {
                            configArgs = Common.CFG_2_EM_NOCAM;
                        }
                    }
                    else
                    {
                        if (m_contextMenu.UseIRCameraChecked)
                        {
                            configArgs = Common.CFG_2_DM_CAM;
                        }
                        else
                        {
                            configArgs = Common.CFG_2_DM_NOCAM;
                        }
                    }
                    break;

                case ContextMenuWYSIWYG.HDKType.UNKNOWN:
                    Common.ShowMessageBox(Common.MSG_UNABLE_TO_DETECT_HDK_TYPE, MessageBoxButtons.OK, MessageBoxIcon.Error, true);
                    return;

                default:
                    // error case already shows error message
                    return;
                }
            }

            string  osvrPath         = OSVRRegistry.GetInstallDirectoryFromRegistry();
            string  completeFilePath = osvrPath + Common.SERVICE_PATH + Common.SERVICE_NAME;
            string  workingDirectory = osvrPath + Common.SERVICE_PATH;
            Process server           = OSVRProcessManager.LaunchExecutable(completeFilePath,
                                                                           workingDirectory,
                                                                           ProcessWindowStyle.Minimized, // Note: this is ignored
                                                                           configArgs,
                                                                           false);

            if (server == null)
            {
                Common.ShowMessageBox(Common.MSG_UNABLE_TO_START_SERVER, MessageBoxButtons.OK, MessageBoxIcon.Error);
                return;
            }

            if (!m_console.Visible)
            {
                ShowServerConsole();
            }

            m_console.ServerStateChanged(restart ? ServerConsole.ServerState.Restart : ServerConsole.ServerState.Start);

            server.BeginOutputReadLine();
            server.BeginErrorReadLine();
            server.EnableRaisingEvents = true;
            server.OutputDataReceived += Server_OutputDataReceived;
            server.ErrorDataReceived  += Server_ErrorDataReceived;
        }