/// <summary>
            /// Default implementation of the build player method.
            /// </summary>
            /// <param name="options"></param>
            public static void BuildPlayer(BuildPlayerOptions options)
            {
                if (!UnityConnect.instance.canBuildWithUPID)
                {
                    if (!EditorUtility.DisplayDialog("Missing Project ID", "Because you are not a member of this project this build will not access Unity services.\nDo you want to continue?", "Yes", "No"))
                    {
                        throw new BuildMethodException();
                    }
                }

                if (!BuildPipeline.IsBuildTargetSupported(options.targetGroup, options.target))
                {
                    throw new BuildMethodException("Build target is not supported.");
                }

                string module = ModuleManager.GetTargetStringFrom(EditorUserBuildSettings.selectedBuildTargetGroup, options.target);
                IBuildWindowExtension buildWindowExtension = ModuleManager.GetBuildWindowExtension(module);

                if (buildWindowExtension != null && (options.options & BuildOptions.AutoRunPlayer) != 0 && !buildWindowExtension.EnabledBuildAndRunButton())
                {
                    throw new BuildMethodException();
                }

                if (Unsupported.IsBleedingEdgeBuild())
                {
                    var sb = new System.Text.StringBuilder();
                    sb.AppendLine("This version of Unity is a BleedingEdge build that has not seen any manual testing.");
                    sb.AppendLine("You should consider this build unstable.");
                    sb.AppendLine("We strongly recommend that you use a normal version of Unity instead.");

                    if (EditorUtility.DisplayDialog("BleedingEdge Build", sb.ToString(), "Cancel", "OK"))
                    {
                        throw new BuildMethodException();
                    }
                }

                // See if we need to switch platforms and delay the build.  We do this whenever
                // we're trying to build for a target different from the active one so as to ensure
                // that the compiled script code we have loaded is built for the same platform we
                // are building for.  As we can't reload while our editor stuff is still executing,
                // we need to defer to after the next script reload then.
                bool delayToAfterScriptReload = false;

                if (EditorUserBuildSettings.activeBuildTarget != options.target ||
                    EditorUserBuildSettings.activeBuildTargetGroup != options.targetGroup)
                {
                    if (!EditorUserBuildSettings.SwitchActiveBuildTargetAsync(options.targetGroup, options.target))
                    {
                        // Switching the build target failed.  No point in trying to continue
                        // with a build.
                        var errStr = string.Format("Could not switch to build target '{0}', '{1}'.",
                                                   BuildPipeline.GetBuildTargetGroupDisplayName(options.targetGroup),
                                                   BuildPlatforms.instance.GetBuildTargetDisplayName(options.targetGroup, options.target));
                        throw new BuildMethodException(errStr);
                    }

                    if (EditorApplication.isCompiling)
                    {
                        delayToAfterScriptReload = true;
                    }
                }

                // Trigger build.
                // Note: report will be null, if delayToAfterScriptReload = true
                var report = BuildPipeline.BuildPlayerInternalNoCheck(options.scenes, options.locationPathName, null, options.targetGroup, options.target, options.options, delayToAfterScriptReload);


                if (report != null)
                {
                    var resultStr = String.Format("Build completed with a result of '{0}'", report.summary.result.ToString("g"));

                    switch (report.summary.result)
                    {
                    case Build.Reporting.BuildResult.Unknown:
                        Debug.LogWarning(resultStr);
                        break;

                    case Build.Reporting.BuildResult.Failed:
                        DeleteBuildFolderIfEmpty(report.summary.outputPath);
                        Debug.LogError(resultStr);
                        throw new BuildMethodException(report.SummarizeErrors());

                    default:
                        Debug.Log(resultStr);
                        break;
                    }

                    buildCompletionHandler?.Invoke(report);
                }
            }
        private static void GUIBuildButtons(IBuildWindowExtension buildWindowExtension,
                                            bool enableBuildButton,
                                            bool enableBuildAndRunButton,
                                            bool canInstallInBuildFolder,
                                            BuildPlatform platform)
        {
            GUILayout.FlexibleSpace();


            if (canInstallInBuildFolder)
            {
                GUILayout.BeginHorizontal();
                EditorUserBuildSettings.installInBuildFolder = GUILayout.Toggle(EditorUserBuildSettings.installInBuildFolder, "Install in Builds folder\n(for debugging with source code)", GUILayout.ExpandWidth(false));

                var content = new GUIContent(EditorGUI.GUIContents.helpIcon);
                content.tooltip = "Open documentation for debugging source code";
                if (GUILayout.Button(content, EditorStyles.iconButton))
                {
                    var path = Path.Combine(Directory.GetParent(EditorApplication.applicationPath).FullName, "../../Documentation/BuildDocs/view_build_docs");
                    if (Application.platform == RuntimePlatform.WindowsEditor)
                    {
                        System.Diagnostics.Process.Start(path + ".cmd");
                    }
                    else
                    {
                        System.Diagnostics.Process.Start("/bin/bash", path);
                    }
                }
                GUILayout.EndHorizontal();
            }
            else
            {
                EditorUserBuildSettings.installInBuildFolder = false;
            }

            if ((buildWindowExtension != null) && Unsupported.IsSourceBuild())
            {
                buildWindowExtension.ShowInternalPlatformBuildOptions();
            }


            if (buildWindowExtension != null)
            {
                buildWindowExtension.ShowPlatformBuildWarnings();
            }

            // Disable the 'Build' and 'Build And Run' buttons when the project setup doesn't satisfy the platform requirements
            if (!IsColorSpaceValid(platform) && enableBuildButton && enableBuildAndRunButton)
            {
                enableBuildAndRunButton = false;
                enableBuildButton       = false;
                EditorGUILayout.HelpBox(styles.invalidColorSpaceMessage);
            }
            else if (!IsLightmapEncodingValid(platform) && enableBuildButton && enableBuildAndRunButton)
            {
                enableBuildAndRunButton = false;
                enableBuildButton       = false;
                EditorGUILayout.HelpBox(styles.invalidLightmapEncodingMessage);
            }

            if (EditorApplication.isCompiling || EditorApplication.isUpdating)
            {
                enableBuildAndRunButton = false;
                enableBuildButton       = false;
                EditorGUILayout.HelpBox(styles.compilingMessage);
            }
            GUILayout.BeginHorizontal();
            GUILayout.FlexibleSpace();
            if (EditorGUILayout.LinkLabel(styles.learnAboutUnityCloudBuild))
            {
                Application.OpenURL(string.Format("{0}/from/editor/buildsettings?upid={1}&pid={2}&currentplatform={3}&selectedplatform={4}&unityversion={5}",
                                                  UnityEditorInternal.WebURLs.cloudBuildPage, CloudProjectSettings.projectId, PlayerSettings.productGUID, EditorUserBuildSettings.activeBuildTarget, EditorUserBuildSettingsUtils.CalculateSelectedBuildTarget(), Application.unityVersion));
            }
            GUILayout.EndHorizontal();
            // Space 6 for alignment with platform column and to reduce missclicks with Build And Run button
            GUILayout.Space(6);

            GUILayout.BeginHorizontal();
            GUILayout.FlexibleSpace();

            GUIContent buildButton         = null;
            GUIContent buildAndRunButton   = null;
            bool       askForBuildLocation = true;

            if (buildWindowExtension != null)
            {
                buildWindowExtension.GetBuildButtonTitles(out buildButton, out buildAndRunButton);
                askForBuildLocation = buildWindowExtension.AskForBuildLocation();
            }

            buildButton       = buildButton ?? styles.build;
            buildAndRunButton = buildAndRunButton ?? styles.buildAndRun;

            // Switching build target in the editor
            BuildTarget      selectedTarget      = EditorUserBuildSettingsUtils.CalculateSelectedBuildTarget();
            BuildTargetGroup selectedTargetGroup = EditorUserBuildSettings.selectedBuildTargetGroup;

            bool selectedTargetIsActive = EditorUserBuildSettings.activeBuildTarget == selectedTarget &&
                                          EditorUserBuildSettings.activeBuildTargetGroup == selectedTargetGroup;

            if (selectedTargetIsActive)
            {
                // Build Button
                GUI.enabled = enableBuildButton;
                if (GUILayout.Button(buildButton, GUILayout.Width(Styles.kButtonWidth)))
                {
                    CallBuildMethods(askForBuildLocation, BuildOptions.ShowBuiltPlayer);
                    GUIUtility.ExitGUI();
                }
            }
            else
            {
                GUI.enabled = BuildPipeline.IsBuildTargetSupported(selectedTargetGroup, selectedTarget) && EditorUserBuildSettings.activeBuildTargetGroup != selectedTargetGroup;
                if (GUILayout.Button(styles.switchPlatform, GUILayout.Width(Styles.kButtonWidth)))
                {
                    EditorUserBuildSettings.SwitchActiveBuildTargetAsync(selectedTargetGroup, selectedTarget);
                    GUIUtility.ExitGUI();
                }
            }

            // Build and Run button
            GUI.enabled = enableBuildAndRunButton && selectedTargetIsActive;
            if (GUILayout.Button(buildAndRunButton, GUILayout.Width(Styles.kButtonWidth)))
            {
                BuildPlayerAndRun(askForBuildLocation);
                GUIUtility.ExitGUI();
            }

            GUILayout.EndHorizontal();
        }