//-------------------------------------------------------------------------------------------------
// <copyright file="WixStandardBootstrapperApplication.cpp" company="Outercurve Foundation">
//   Copyright (c) 2004, Outercurve Foundation.
//   This software is released under Microsoft Reciprocal License (MS-RL).
//   The license and further copyright text can be found in the file
//   LICENSE.TXT at the root directory of the distribution.
// </copyright>
//-------------------------------------------------------------------------------------------------


#include "pch.h"

static const LPCWSTR PYBA_WINDOW_CLASS = L"PythonBA";
static const LPCWSTR PYBA_VARIABLE_LAUNCH_TARGET_PATH = L"LaunchTarget";
static const LPCWSTR PYBA_VARIABLE_LAUNCH_TARGET_ELEVATED_ID = L"LaunchTargetElevatedId";
static const LPCWSTR PYBA_VARIABLE_LAUNCH_ARGUMENTS = L"LaunchArguments";
static const LPCWSTR PYBA_VARIABLE_LAUNCH_HIDDEN = L"LaunchHidden";
static const DWORD PYBA_ACQUIRE_PERCENTAGE = 30;
static const LPCWSTR PYBA_VARIABLE_BUNDLE_FILE_VERSION = L"WixBundleFileVersion";

enum PYBA_STATE {
    PYBA_STATE_INITIALIZING,
    PYBA_STATE_INITIALIZED,
    PYBA_STATE_HELP,
    PYBA_STATE_DETECTING,
    PYBA_STATE_DETECTED,
    PYBA_STATE_PLANNING,
    PYBA_STATE_PLANNED,
    PYBA_STATE_APPLYING,
    PYBA_STATE_CACHING,
    PYBA_STATE_CACHED,
    PYBA_STATE_EXECUTING,
    PYBA_STATE_EXECUTED,
    PYBA_STATE_APPLIED,
    PYBA_STATE_FAILED,
};

static const int WM_PYBA_SHOW_HELP = WM_APP + 100;
static const int WM_PYBA_DETECT_PACKAGES = WM_APP + 101;
static const int WM_PYBA_PLAN_PACKAGES = WM_APP + 102;
static const int WM_PYBA_APPLY_PACKAGES = WM_APP + 103;
static const int WM_PYBA_CHANGE_STATE = WM_APP + 104;
static const int WM_PYBA_SHOW_FAILURE = WM_APP + 105;

// This enum must be kept in the same order as the PAGE_NAMES array.
enum PAGE {
    PAGE_LOADING,
    PAGE_HELP,
    PAGE_INSTALL,
    PAGE_SIMPLE_INSTALL,
    PAGE_CUSTOM1,
    PAGE_CUSTOM2,
    PAGE_MODIFY,
    PAGE_PROGRESS,
    PAGE_PROGRESS_PASSIVE,
    PAGE_SUCCESS,
    PAGE_FAILURE,
    COUNT_PAGE,
};

// This array must be kept in the same order as the PAGE enum.
static LPCWSTR PAGE_NAMES[] = {
    L"Loading",
    L"Help",
    L"Install",
    L"SimpleInstall",
    L"Custom1",
    L"Custom2",
    L"Modify",
    L"Progress",
    L"ProgressPassive",
    L"Success",
    L"Failure",
};

enum CONTROL_ID {
    // Non-paged controls
    ID_CLOSE_BUTTON = THEME_FIRST_ASSIGN_CONTROL_ID,
    ID_MINIMIZE_BUTTON,

    // Welcome page
    ID_INSTALL_ALL_USERS_BUTTON,
    ID_INSTALL_JUST_FOR_ME_BUTTON,
    ID_INSTALL_CUSTOM_BUTTON,
    ID_INSTALL_SIMPLE_BUTTON,
    ID_INSTALL_CANCEL_BUTTON,
    
    // Customize Page
    ID_TARGETDIR_EDITBOX,
    ID_CUSTOM_ASSOCIATE_FILES_CHECKBOX,
    ID_CUSTOM_INSTALL_ALL_USERS_CHECKBOX,
    ID_CUSTOM_BROWSE_BUTTON,
    ID_CUSTOM_INSTALL_BUTTON,
    ID_CUSTOM_NEXT_BUTTON,
    ID_CUSTOM1_BACK_BUTTON,
    ID_CUSTOM2_BACK_BUTTON,
    ID_CUSTOM1_CANCEL_BUTTON,
    ID_CUSTOM2_CANCEL_BUTTON,

    // Modify page
    ID_MODIFY_BUTTON,
    ID_REPAIR_BUTTON,
    ID_UNINSTALL_BUTTON,
    ID_MODIFY_CANCEL_BUTTON,

    // Progress page
    ID_CACHE_PROGRESS_PACKAGE_TEXT,
    ID_CACHE_PROGRESS_BAR,
    ID_CACHE_PROGRESS_TEXT,

    ID_EXECUTE_PROGRESS_PACKAGE_TEXT,
    ID_EXECUTE_PROGRESS_BAR,
    ID_EXECUTE_PROGRESS_TEXT,
    ID_EXECUTE_PROGRESS_ACTIONDATA_TEXT,

    ID_OVERALL_PROGRESS_PACKAGE_TEXT,
    ID_OVERALL_PROGRESS_BAR,
    ID_OVERALL_CALCULATED_PROGRESS_BAR,
    ID_OVERALL_PROGRESS_TEXT,

    ID_PROGRESS_CANCEL_BUTTON,

    // Success page
    ID_LAUNCH_BUTTON,
    ID_SUCCESS_TEXT,
    ID_SUCCESS_RESTART_TEXT,
    ID_SUCCESS_RESTART_BUTTON,
    ID_SUCCESS_CANCEL_BUTTON,

    // Failure page
    ID_FAILURE_LOGFILE_LINK,
    ID_FAILURE_MESSAGE_TEXT,
    ID_FAILURE_RESTART_TEXT,
    ID_FAILURE_RESTART_BUTTON,
    ID_FAILURE_CANCEL_BUTTON
};

static THEME_ASSIGN_CONTROL_ID CONTROL_ID_NAMES[] = {
    { ID_CLOSE_BUTTON, L"CloseButton" },
    { ID_MINIMIZE_BUTTON, L"MinimizeButton" },

    { ID_INSTALL_ALL_USERS_BUTTON, L"InstallAllUsersButton" },
    { ID_INSTALL_JUST_FOR_ME_BUTTON, L"InstallJustForMeButton" },
    { ID_INSTALL_CUSTOM_BUTTON, L"InstallCustomButton" },
    { ID_INSTALL_SIMPLE_BUTTON, L"InstallSimpleButton" },
    { ID_INSTALL_CANCEL_BUTTON, L"InstallCancelButton" },

    { ID_TARGETDIR_EDITBOX, L"TargetDir" },
    { ID_CUSTOM_ASSOCIATE_FILES_CHECKBOX, L"AssociateFiles" },
    { ID_CUSTOM_INSTALL_ALL_USERS_CHECKBOX, L"InstallAllUsers" },
    { ID_CUSTOM_BROWSE_BUTTON, L"CustomBrowseButton" },
    { ID_CUSTOM_INSTALL_BUTTON, L"CustomInstallButton" },
    { ID_CUSTOM_NEXT_BUTTON, L"CustomNextButton" },
    { ID_CUSTOM1_BACK_BUTTON, L"Custom1BackButton" },
    { ID_CUSTOM2_BACK_BUTTON, L"Custom2BackButton" },
    { ID_CUSTOM1_CANCEL_BUTTON, L"Custom1CancelButton" },
    { ID_CUSTOM2_CANCEL_BUTTON, L"Custom2CancelButton" },

    { ID_MODIFY_BUTTON, L"ModifyButton" },
    { ID_REPAIR_BUTTON, L"RepairButton" },
    { ID_UNINSTALL_BUTTON, L"UninstallButton" },
    { ID_MODIFY_CANCEL_BUTTON, L"ModifyCancelButton" },

    { ID_CACHE_PROGRESS_PACKAGE_TEXT, L"CacheProgressPackageText" },
    { ID_CACHE_PROGRESS_BAR, L"CacheProgressbar" },
    { ID_CACHE_PROGRESS_TEXT, L"CacheProgressText" },
    { ID_EXECUTE_PROGRESS_PACKAGE_TEXT, L"ExecuteProgressPackageText" },
    { ID_EXECUTE_PROGRESS_BAR, L"ExecuteProgressbar" },
    { ID_EXECUTE_PROGRESS_TEXT, L"ExecuteProgressText" },
    { ID_EXECUTE_PROGRESS_ACTIONDATA_TEXT, L"ExecuteProgressActionDataText" },
    { ID_OVERALL_PROGRESS_PACKAGE_TEXT, L"OverallProgressPackageText" },
    { ID_OVERALL_PROGRESS_BAR, L"OverallProgressbar" },
    { ID_OVERALL_CALCULATED_PROGRESS_BAR, L"OverallCalculatedProgressbar" },
    { ID_OVERALL_PROGRESS_TEXT, L"OverallProgressText" },
    { ID_PROGRESS_CANCEL_BUTTON, L"ProgressCancelButton" },

    { ID_LAUNCH_BUTTON, L"LaunchButton" },
    { ID_SUCCESS_TEXT, L"SuccessText" },
    { ID_SUCCESS_RESTART_TEXT, L"SuccessRestartText" },
    { ID_SUCCESS_RESTART_BUTTON, L"SuccessRestartButton" },
    { ID_SUCCESS_CANCEL_BUTTON, L"SuccessCancelButton" },

    { ID_FAILURE_LOGFILE_LINK, L"FailureLogFileLink" },
    { ID_FAILURE_MESSAGE_TEXT, L"FailureMessageText" },
    { ID_FAILURE_RESTART_TEXT, L"FailureRestartText" },
    { ID_FAILURE_RESTART_BUTTON, L"FailureRestartButton" },
    { ID_FAILURE_CANCEL_BUTTON, L"FailureCancelButton" },
};

class PythonBootstrapperApplication : public CBalBaseBootstrapperApplication {
    void ShowPage(DWORD newPageId) {
        // Process each control for special handling in the new page.
        ProcessPageControls(ThemeGetPage(_theme, newPageId));

        // Enable disable controls per-page.
        if (_pageIds[PAGE_INSTALL] == newPageId || _pageIds[PAGE_SIMPLE_INSTALL] == newPageId) {
            InstallPage_Show();
        } else if (_pageIds[PAGE_CUSTOM1] == newPageId) {
            Custom1Page_Show();
        } else if (_pageIds[PAGE_CUSTOM2] == newPageId) {
            Custom2Page_Show();
        } else if (_pageIds[PAGE_MODIFY] == newPageId) {
            ModifyPage_Show();
        } else if (_pageIds[PAGE_SUCCESS] == newPageId) {
            SuccessPage_Show();
        } else if (_pageIds[PAGE_FAILURE] == newPageId) {
            FailurePage_Show();
        }

        // Prevent repainting while switching page to avoid ugly flickering
        _suppressPaint = TRUE;
        ThemeShowPage(_theme, newPageId, SW_SHOW);
        ThemeShowPage(_theme, _visiblePageId, SW_HIDE);
        _suppressPaint = FALSE;
        InvalidateRect(_theme->hwndParent, nullptr, TRUE);
        _visiblePageId = newPageId;

        // On the install page set the focus to the install button or
        // the next enabled control if install is disabled
        if (_pageIds[PAGE_INSTALL] == newPageId) {
            ThemeSetFocus(_theme, ID_INSTALL_ALL_USERS_BUTTON);
        } else if (_pageIds[PAGE_SIMPLE_INSTALL] == newPageId) {
            ThemeSetFocus(_theme, ID_INSTALL_SIMPLE_BUTTON);
        }
    }

    //
    // Handles control clicks
    //
    void OnCommand(CONTROL_ID id) {
        LPWSTR defaultDir = nullptr;
        LPWSTR targetDir = nullptr;
        LONGLONG elevated, crtInstalled;
        BOOL checked;
        WCHAR wzPath[MAX_PATH] = { };
        BROWSEINFOW browseInfo = { };
        PIDLIST_ABSOLUTE pidl = nullptr;
        HRESULT hr = S_OK;

        switch(id) {
        case ID_CLOSE_BUTTON:
            OnClickCloseButton();
            break;

        // Install commands
        case ID_INSTALL_SIMPLE_BUTTON:
            hr = BalGetStringVariable(L"TargetDir", &targetDir);
            if (FAILED(hr) || !targetDir || !*targetDir) {
                LONGLONG installAll;
                if (SUCCEEDED(BalGetNumericVariable(L"InstallAllUsers", &installAll)) && installAll) {
                    hr = BalGetStringVariable(L"DefaultAllUsersTargetDir", &defaultDir);
                    BalExitOnFailure(hr, "Failed to get the default all users install directory");
                } else {
                    hr = BalGetStringVariable(L"DefaultJustForMeTargetDir", &defaultDir);
                    BalExitOnFailure(hr, "Failed to get the default per-user install directory");
                }

                if (!defaultDir || !*defaultDir) {
                    BalLogError(E_INVALIDARG, "Default install directory is blank");
                }

                hr = BalFormatString(defaultDir, &targetDir);
                BalExitOnFailure1(hr, "Failed to format '%ls'", defaultDir);

                hr = _engine->SetVariableString(L"TargetDir", targetDir);
                ReleaseStr(targetDir);
                BalExitOnFailure(hr, "Failed to set install target directory");
            } else {
                ReleaseStr(targetDir);
            }

            OnPlan(BOOTSTRAPPER_ACTION_INSTALL);
            break;

        case ID_INSTALL_ALL_USERS_BUTTON:
            SavePageSettings();
            
            hr = _engine->SetVariableNumeric(L"InstallAllUsers", 1);
            ExitOnFailure(hr, L"Failed to set install scope");

            hr = _engine->SetVariableNumeric(L"CompileAll", 1);
            ExitOnFailure(hr, L"Failed to set compile all setting");

            hr = BalGetStringVariable(L"DefaultAllUsersTargetDir", &defaultDir);
            BalExitOnFailure(hr, "Failed to get the default all users install directory");

            if (!defaultDir || !*defaultDir) {
                BalLogError(E_INVALIDARG, "Default install directory is blank");
            }

            hr = BalFormatString(defaultDir, &targetDir);
            BalExitOnFailure1(hr, "Failed to format '%ls'", defaultDir);

            hr = _engine->SetVariableString(L"TargetDir", targetDir);
            ReleaseStr(targetDir);
            BalExitOnFailure(hr, "Failed to set install target directory");

            OnPlan(BOOTSTRAPPER_ACTION_INSTALL);
            break;

        case ID_INSTALL_JUST_FOR_ME_BUTTON:
            SavePageSettings();
            
            hr = _engine->SetVariableNumeric(L"InstallAllUsers", 0);
            ExitOnFailure(hr, L"Failed to set install scope");

            hr = BalGetStringVariable(L"DefaultJustForMeTargetDir", &defaultDir);
            BalExitOnFailure(hr, "Failed to get the default per-user install directory");

            if (!defaultDir || !*defaultDir) {
                BalLogError(E_INVALIDARG, "Default install directory is blank");
            }

            hr = BalFormatString(defaultDir, &targetDir);
            BalExitOnFailure1(hr, "Failed to format '%ls'", defaultDir);

            hr = _engine->SetVariableString(L"TargetDir", targetDir);
            ReleaseStr(targetDir);
            BalExitOnFailure(hr, "Failed to set install target directory");

            if (!QueryElevateForCrtInstall()) {
                break;
            }

            OnPlan(BOOTSTRAPPER_ACTION_INSTALL);
            break;

        case ID_CUSTOM1_BACK_BUTTON:
            SavePageSettings();
            if (_modifying) {
                GoToPage(PAGE_MODIFY);
            } else {
                GoToPage(PAGE_INSTALL);
            }
            break;

        case ID_INSTALL_CUSTOM_BUTTON: __fallthrough;
        case ID_CUSTOM2_BACK_BUTTON:
            SavePageSettings();
            GoToPage(PAGE_CUSTOM1);
            break;

        case ID_CUSTOM_NEXT_BUTTON:
            SavePageSettings();
            GoToPage(PAGE_CUSTOM2);
            break;

        case ID_CUSTOM_INSTALL_BUTTON:
            SavePageSettings();

            hr = BalGetStringVariable(L"TargetDir", &targetDir);
            if (SUCCEEDED(hr)) {
                // TODO: Check whether directory exists and contains another installation
                ReleaseStr(targetDir);
            }

            checked = ThemeIsControlChecked(_theme, ID_CUSTOM_INSTALL_ALL_USERS_CHECKBOX);
            if (!checked && !QueryElevateForCrtInstall()) {
                break;
            }

            OnPlan(_command.action);
            break;

        case ID_CUSTOM_INSTALL_ALL_USERS_CHECKBOX:
            hr = BalGetNumericVariable(L"WixBundleElevated", &elevated);
            checked = ThemeIsControlChecked(_theme, ID_CUSTOM_INSTALL_ALL_USERS_CHECKBOX);
            ThemeControlElevates(_theme, ID_CUSTOM_INSTALL_BUTTON, checked && (FAILED(hr) || !elevated));
            ThemeGetTextControl(_theme, ID_TARGETDIR_EDITBOX, &targetDir);
            if (targetDir) {
                // Check the current value against the default to see
                // if we should switch it automatically.
                hr = BalGetStringVariable(
                    checked ? L"DefaultJustForMeTargetDir" : L"DefaultAllUsersTargetDir",
                    &defaultDir
                );
                
                if (SUCCEEDED(hr) && defaultDir) {
                    LPWSTR formatted = nullptr;
                    if (defaultDir[0] && SUCCEEDED(BalFormatString(defaultDir, &formatted))) {
                        if (wcscmp(formatted, targetDir) == 0) {
                            ReleaseStr(defaultDir);
                            defaultDir = nullptr;
                            ReleaseStr(formatted);
                            formatted = nullptr;
                            
                            hr = BalGetStringVariable(
                                checked ? L"DefaultAllUsersTargetDir" : L"DefaultJustForMeTargetDir",
                                &defaultDir
                            );
                            if (SUCCEEDED(hr) && defaultDir && defaultDir[0] && SUCCEEDED(BalFormatString(defaultDir, &formatted))) {
                                ThemeSetTextControl(_theme, ID_TARGETDIR_EDITBOX, formatted);
                                ReleaseStr(formatted);
                            }
                        } else {
                            ReleaseStr(formatted);
                        }
                    }
                    
                    ReleaseStr(defaultDir);
                }
            }
            break;

        case ID_CUSTOM_BROWSE_BUTTON:
            browseInfo.hwndOwner = _hWnd;
            browseInfo.pszDisplayName = wzPath;
            browseInfo.lpszTitle = _theme->sczCaption;
            browseInfo.ulFlags = BIF_RETURNONLYFSDIRS | BIF_USENEWUI;
            pidl = ::SHBrowseForFolderW(&browseInfo);
            if (pidl && ::SHGetPathFromIDListW(pidl, wzPath)) {
                ThemeSetTextControl(_theme, ID_TARGETDIR_EDITBOX, wzPath);
            }

            if (pidl) {
                ::CoTaskMemFree(pidl);
            }
            break;

        // Modify commands
        case ID_MODIFY_BUTTON:
            // Some variables cannot be modified
            _engine->SetVariableString(L"InstallAllUsersState", L"disable");
            _engine->SetVariableString(L"TargetDirState", L"disable");
            _engine->SetVariableString(L"CustomBrowseButtonState", L"disable");
            _modifying = TRUE;
            GoToPage(PAGE_CUSTOM1);
            break;

        case ID_REPAIR_BUTTON:
            OnPlan(BOOTSTRAPPER_ACTION_REPAIR);
            break;

        case ID_UNINSTALL_BUTTON:
            OnPlan(BOOTSTRAPPER_ACTION_UNINSTALL);
            break;
        }

    LExit:
        return;
    }

    void InstallPage_Show() {
        // Ensure the All Users install button has a UAC shield
        LONGLONG elevated, installAll;

        if (FAILED(BalGetNumericVariable(L"WixBundleElevated", &elevated))) {
            elevated = 0;
        }

        ThemeControlElevates(_theme, ID_INSTALL_ALL_USERS_BUTTON, !elevated);

        if (SUCCEEDED(BalGetNumericVariable(L"InstallAllUsers", &installAll)) && installAll) {
            ThemeControlElevates(_theme, ID_INSTALL_SIMPLE_BUTTON, !elevated);
        }
    }

    void Custom1Page_Show() {
    }

    void Custom2Page_Show() {
        HRESULT hr;
        LONGLONG installAll, elevated, includeLauncher;
        
        if (FAILED(BalGetNumericVariable(L"WixBundleElevated", &elevated))) {
            elevated = 0;
        }
        if (SUCCEEDED(BalGetNumericVariable(L"InstallAllUsers", &installAll))) {
            ThemeControlElevates(_theme, ID_CUSTOM_INSTALL_BUTTON, installAll && !elevated);
        } else {
            installAll = 0;
        }

        if (SUCCEEDED(BalGetNumericVariable(L"Include_launcher", &includeLauncher)) && includeLauncher) {
            ThemeControlEnable(_theme, ID_CUSTOM_ASSOCIATE_FILES_CHECKBOX, TRUE);
        } else {
            ThemeSendControlMessage(_theme, ID_CUSTOM_ASSOCIATE_FILES_CHECKBOX, BM_SETCHECK, BST_UNCHECKED, 0);
            ThemeControlEnable(_theme, ID_CUSTOM_ASSOCIATE_FILES_CHECKBOX, FALSE);
        }

        LPWSTR targetDir = nullptr;
        hr = BalGetStringVariable(L"TargetDir", &targetDir);
        if (SUCCEEDED(hr) && targetDir && targetDir[0]) {
            ThemeSetTextControl(_theme, ID_TARGETDIR_EDITBOX, targetDir);
            StrFree(targetDir);
        } else if (SUCCEEDED(hr)) {
            StrFree(targetDir);
            targetDir = nullptr;

            LPWSTR defaultTargetDir = nullptr;
            hr = BalGetStringVariable(L"DefaultCustomTargetDir", &defaultTargetDir);
            if (SUCCEEDED(hr) && defaultTargetDir && !defaultTargetDir[0]) {
                StrFree(defaultTargetDir);
                defaultTargetDir = nullptr;
                
                hr = BalGetStringVariable(
                    installAll ? L"DefaultAllUsersTargetDir" : L"DefaultJustForMeTargetDir",
                    &defaultTargetDir
                );
            }
            if (SUCCEEDED(hr) && defaultTargetDir) {
                if (defaultTargetDir[0] && SUCCEEDED(BalFormatString(defaultTargetDir, &targetDir))) {
                    ThemeSetTextControl(_theme, ID_TARGETDIR_EDITBOX, targetDir);
                    StrFree(targetDir);
                }
                StrFree(defaultTargetDir);
            }
        }
    }

    void ModifyPage_Show() {
        ThemeControlEnable(_theme, ID_REPAIR_BUTTON, !_suppressRepair);
    }

    void SuccessPage_Show() {
        // on the "Success" page, check if the restart or launch button should be enabled.
        BOOL showRestartButton = FALSE;
        BOOL launchTargetExists = FALSE;
        LOC_STRING *successText = nullptr;
        HRESULT hr = S_OK;
        
        if (_restartRequired) {
            if (BOOTSTRAPPER_RESTART_PROMPT == _command.restart) {
                showRestartButton = TRUE;
            }
        } else if (ThemeControlExists(_theme, ID_LAUNCH_BUTTON)) {
            launchTargetExists = BalStringVariableExists(PYBA_VARIABLE_LAUNCH_TARGET_PATH);
        }

        switch (_plannedAction) {
        case BOOTSTRAPPER_ACTION_INSTALL:
            hr = LocGetString(_wixLoc, L"#(loc.SuccessInstallMessage)", &successText);
            break;
        case BOOTSTRAPPER_ACTION_MODIFY:
            hr = LocGetString(_wixLoc, L"#(loc.SuccessModifyMessage)", &successText);
            break;
        case BOOTSTRAPPER_ACTION_REPAIR:
            hr = LocGetString(_wixLoc, L"#(loc.SuccessRepairMessage)", &successText);
            break;
        case BOOTSTRAPPER_ACTION_UNINSTALL:
            hr = LocGetString(_wixLoc, L"#(loc.SuccessRemoveMessage)", &successText);
            break;
        }

        if (successText) {
            LPWSTR formattedString = nullptr;
            BalFormatString(successText->wzText, &formattedString);
            if (formattedString) {
                ThemeSetTextControl(_theme, ID_SUCCESS_TEXT, formattedString);
                StrFree(formattedString);
            }
        }

        ThemeControlEnable(_theme, ID_LAUNCH_BUTTON, launchTargetExists && BOOTSTRAPPER_ACTION_UNINSTALL < _plannedAction);
        ThemeControlEnable(_theme, ID_SUCCESS_RESTART_TEXT, showRestartButton);
        ThemeControlEnable(_theme, ID_SUCCESS_RESTART_BUTTON, showRestartButton);
    }

    void FailurePage_Show() {
        // on the "Failure" page, show error message and check if the restart button should be enabled.

        // if there is a log file variable then we'll assume the log file exists.
        BOOL showLogLink = (_bundle.sczLogVariable && *_bundle.sczLogVariable);
        BOOL showErrorMessage = FALSE;
        BOOL showRestartButton = FALSE;

        if (FAILED(_hrFinal)) {
            LPWSTR unformattedText = nullptr;
            LPWSTR text = nullptr;

            // If we know the failure message, use that.
            if (_failedMessage && *_failedMessage) {
                StrAllocString(&unformattedText, _failedMessage, 0);
            } else {
                // try to get the error message from the error code.
                StrAllocFromError(&unformattedText, _hrFinal, nullptr);
                if (!unformattedText || !*unformattedText) {
                    StrAllocFromError(&unformattedText, E_FAIL, nullptr);
                }
            }

            if (E_WIXSTDBA_CONDITION_FAILED == _hrFinal) {
                if (unformattedText) {
                    StrAllocString(&text, unformattedText, 0);
                }
            } else {
                StrAllocFormatted(&text, L"0x%08x - %ls", _hrFinal, unformattedText);
            }

            if (text) {
                ThemeSetTextControl(_theme, ID_FAILURE_MESSAGE_TEXT, text);
                showErrorMessage = TRUE;
            }

            ReleaseStr(text);
            ReleaseStr(unformattedText);
        }

        if (_restartRequired && BOOTSTRAPPER_RESTART_PROMPT == _command.restart) {
            showRestartButton = TRUE;
        }

        ThemeControlEnable(_theme, ID_FAILURE_LOGFILE_LINK, showLogLink);
        ThemeControlEnable(_theme, ID_FAILURE_MESSAGE_TEXT, showErrorMessage);
        ThemeControlEnable(_theme, ID_FAILURE_RESTART_TEXT, showRestartButton);
        ThemeControlEnable(_theme, ID_FAILURE_RESTART_BUTTON, showRestartButton);
    }


public: // IBootstrapperApplication
    virtual STDMETHODIMP OnStartup() {
        HRESULT hr = S_OK;
        DWORD dwUIThreadId = 0;

        // create UI thread
        _hUiThread = ::CreateThread(nullptr, 0, UiThreadProc, this, 0, &dwUIThreadId);
        if (!_hUiThread) {
            ExitWithLastError(hr, "Failed to create UI thread.");
        }

    LExit:
        return hr;
    }


    virtual STDMETHODIMP_(int) OnShutdown() {
        int nResult = IDNOACTION;

        // wait for UI thread to terminate
        if (_hUiThread) {
            ::WaitForSingleObject(_hUiThread, INFINITE);
            ReleaseHandle(_hUiThread);
        }

        // If a restart was required.
        if (_restartRequired && _allowRestart) {
            nResult = IDRESTART;
        }

        return nResult;
    }


    virtual STDMETHODIMP_(int) OnDetectRelatedBundle(
        __in LPCWSTR wzBundleId,
        __in BOOTSTRAPPER_RELATION_TYPE relationType,
        __in LPCWSTR /*wzBundleTag*/,
        __in BOOL fPerMachine,
        __in DWORD64 /*dw64Version*/,
        __in BOOTSTRAPPER_RELATED_OPERATION operation
    ) {
        BalInfoAddRelatedBundleAsPackage(&_bundle.packages, wzBundleId, relationType, fPerMachine);

        // Remember when our bundle would cause a downgrade.
        if (BOOTSTRAPPER_RELATED_OPERATION_DOWNGRADE == operation) {
            _downgrading = TRUE;
        }

        return CheckCanceled() ? IDCANCEL : IDOK;
    }


    virtual STDMETHODIMP_(void) OnDetectPackageComplete(
        __in LPCWSTR wzPackageId,
        __in HRESULT /*hrStatus*/,
        __in BOOTSTRAPPER_PACKAGE_STATE state
    ) { }


    virtual STDMETHODIMP_(void) OnDetectComplete(__in HRESULT hrStatus) {
        if (SUCCEEDED(hrStatus) && _baFunction) {
            BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "Running detect complete BA function");
            _baFunction->OnDetectComplete();
        }

        if (SUCCEEDED(hrStatus)) {
            hrStatus = EvaluateConditions();
        }

        SetState(PYBA_STATE_DETECTED, hrStatus);

        // If we're not interacting with the user or we're doing a layout or we're just after a force restart
        // then automatically start planning.
        if (BOOTSTRAPPER_DISPLAY_FULL > _command.display ||
            BOOTSTRAPPER_ACTION_LAYOUT == _command.action ||
            BOOTSTRAPPER_ACTION_UNINSTALL == _command.action ||
            BOOTSTRAPPER_RESUME_TYPE_REBOOT == _command.resumeType) {
            if (SUCCEEDED(hrStatus)) {
                ::PostMessageW(_hWnd, WM_PYBA_PLAN_PACKAGES, 0, _command.action);
            }
        }
    }


    virtual STDMETHODIMP_(int) OnPlanRelatedBundle(
        __in_z LPCWSTR /*wzBundleId*/,
        __inout_z BOOTSTRAPPER_REQUEST_STATE* pRequestedState
    ) {
        return CheckCanceled() ? IDCANCEL : IDOK;
    }


    virtual STDMETHODIMP_(int) OnPlanPackageBegin(
        __in_z LPCWSTR wzPackageId,
        __inout BOOTSTRAPPER_REQUEST_STATE *pRequestState
    ) {
        HRESULT hr = S_OK;
        BAL_INFO_PACKAGE* pPackage = nullptr;

        if (_nextPackageAfterRestart) {
            // After restart we need to finish the dependency registration for our package so allow the package
            // to go present.
            if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, wzPackageId, -1, _nextPackageAfterRestart, -1)) {
                // Do not allow a repair because that could put us in a perpetual restart loop.
                if (BOOTSTRAPPER_REQUEST_STATE_REPAIR == *pRequestState) {
                    *pRequestState = BOOTSTRAPPER_REQUEST_STATE_PRESENT;
                }

                ReleaseNullStr(_nextPackageAfterRestart); // no more skipping now.
            } else {
                // not the matching package, so skip it.
                BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "Skipping package: %ls, after restart because it was applied before the restart.", wzPackageId);

                *pRequestState = BOOTSTRAPPER_REQUEST_STATE_NONE;
            }
        } else if ((_plannedAction == BOOTSTRAPPER_ACTION_INSTALL || _plannedAction == BOOTSTRAPPER_ACTION_MODIFY) &&
                   SUCCEEDED(BalInfoFindPackageById(&_bundle.packages, wzPackageId, &pPackage))) {
            BOOL f = FALSE;
            if (SUCCEEDED(_engine->EvaluateCondition(pPackage->sczInstallCondition, &f)) && f) {
                *pRequestState = BOOTSTRAPPER_REQUEST_STATE_PRESENT;
            }
        }

        return CheckCanceled() ? IDCANCEL : IDOK;
    }

    virtual STDMETHODIMP_(int) OnPlanMsiFeature(
        __in_z LPCWSTR wzPackageId,
        __in_z LPCWSTR wzFeatureId,
        __inout BOOTSTRAPPER_FEATURE_STATE* pRequestedState
    ) {
        LONGLONG install;
        
        if (wcscmp(wzFeatureId, L"AssociateFiles") == 0) {
            if (SUCCEEDED(_engine->GetVariableNumeric(L"AssociateFiles", &install)) && install) {
                *pRequestedState = BOOTSTRAPPER_FEATURE_STATE_LOCAL;
            } else {
                *pRequestedState = BOOTSTRAPPER_FEATURE_STATE_ABSENT;
            }
        } else {
            *pRequestedState = BOOTSTRAPPER_FEATURE_STATE_LOCAL;
        }
        return CheckCanceled() ? IDCANCEL : IDNOACTION;
    }

    virtual STDMETHODIMP_(void) OnPlanComplete(__in HRESULT hrStatus) {
        if (SUCCEEDED(hrStatus) && _baFunction) {
            BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "Running plan complete BA function");
            _baFunction->OnPlanComplete();
        }

        SetState(PYBA_STATE_PLANNED, hrStatus);

        if (SUCCEEDED(hrStatus)) {
            ::PostMessageW(_hWnd, WM_PYBA_APPLY_PACKAGES, 0, 0);
        }

        _startedExecution = FALSE;
        _calculatedCacheProgress = 0;
        _calculatedExecuteProgress = 0;
    }


    virtual STDMETHODIMP_(int) OnCachePackageBegin(
        __in_z LPCWSTR wzPackageId,
        __in DWORD cCachePayloads,
        __in DWORD64 dw64PackageCacheSize
    ) {
        if (wzPackageId && *wzPackageId) {
            BAL_INFO_PACKAGE* pPackage = nullptr;
            HRESULT hr = BalInfoFindPackageById(&_bundle.packages, wzPackageId, &pPackage);
            LPCWSTR wz = (SUCCEEDED(hr) && pPackage->sczDisplayName) ? pPackage->sczDisplayName : wzPackageId;

            ThemeSetTextControl(_theme, ID_CACHE_PROGRESS_PACKAGE_TEXT, wz);

            // If something started executing, leave it in the overall progress text.
            if (!_startedExecution) {
                ThemeSetTextControl(_theme, ID_OVERALL_PROGRESS_PACKAGE_TEXT, wz);
            }
        }

        return __super::OnCachePackageBegin(wzPackageId, cCachePayloads, dw64PackageCacheSize);
    }


    virtual STDMETHODIMP_(int) OnCacheAcquireProgress(
        __in_z LPCWSTR wzPackageOrContainerId,
        __in_z_opt LPCWSTR wzPayloadId,
        __in DWORD64 dw64Progress,
        __in DWORD64 dw64Total,
        __in DWORD dwOverallPercentage
    ) {
        WCHAR wzProgress[5] = { };

#ifdef DEBUG
        BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "PYBA: OnCacheAcquireProgress() - container/package: %ls, payload: %ls, progress: %I64u, total: %I64u, overall progress: %u%%", wzPackageOrContainerId, wzPayloadId, dw64Progress, dw64Total, dwOverallPercentage);
#endif

        ::StringCchPrintfW(wzProgress, countof(wzProgress), L"%u%%", dwOverallPercentage);
        ThemeSetTextControl(_theme, ID_CACHE_PROGRESS_TEXT, wzProgress);

        ThemeSetProgressControl(_theme, ID_CACHE_PROGRESS_BAR, dwOverallPercentage);

        _calculatedCacheProgress = dwOverallPercentage * PYBA_ACQUIRE_PERCENTAGE / 100;
        ThemeSetProgressControl(_theme, ID_OVERALL_CALCULATED_PROGRESS_BAR, _calculatedCacheProgress + _calculatedExecuteProgress);

        SetTaskbarButtonProgress(_calculatedCacheProgress + _calculatedExecuteProgress);

        return __super::OnCacheAcquireProgress(wzPackageOrContainerId, wzPayloadId, dw64Progress, dw64Total, dwOverallPercentage);
    }


    virtual STDMETHODIMP_(int) OnCacheAcquireComplete(
        __in_z LPCWSTR wzPackageOrContainerId,
        __in_z_opt LPCWSTR wzPayloadId,
        __in HRESULT hrStatus,
        __in int nRecommendation
    ) {
        SetProgressState(hrStatus);
        return __super::OnCacheAcquireComplete(wzPackageOrContainerId, wzPayloadId, hrStatus, nRecommendation);
    }


    virtual STDMETHODIMP_(int) OnCacheVerifyComplete(
        __in_z LPCWSTR wzPackageId,
        __in_z LPCWSTR wzPayloadId,
        __in HRESULT hrStatus,
        __in int nRecommendation
    ) {
        SetProgressState(hrStatus);
        return __super::OnCacheVerifyComplete(wzPackageId, wzPayloadId, hrStatus, nRecommendation);
    }


    virtual STDMETHODIMP_(void) OnCacheComplete(__in HRESULT /*hrStatus*/) {
        ThemeSetTextControl(_theme, ID_CACHE_PROGRESS_PACKAGE_TEXT, L"");
        SetState(PYBA_STATE_CACHED, S_OK); // we always return success here and let OnApplyComplete() deal with the error.
    }


    virtual STDMETHODIMP_(int) OnError(
        __in BOOTSTRAPPER_ERROR_TYPE errorType,
        __in LPCWSTR wzPackageId,
        __in DWORD dwCode,
        __in_z LPCWSTR wzError,
        __in DWORD dwUIHint,
        __in DWORD /*cData*/,
        __in_ecount_z_opt(cData) LPCWSTR* /*rgwzData*/,
        __in int nRecommendation
    ) {
        int nResult = nRecommendation;
        LPWSTR sczError = nullptr;

        if (BOOTSTRAPPER_DISPLAY_EMBEDDED == _command.display) {
            HRESULT hr = _engine->SendEmbeddedError(dwCode, wzError, dwUIHint, &nResult);
            if (FAILED(hr)) {
                nResult = IDERROR;
            }
        } else if (BOOTSTRAPPER_DISPLAY_FULL == _command.display) {
            // If this is an authentication failure, let the engine try to handle it for us.
            if (BOOTSTRAPPER_ERROR_TYPE_HTTP_AUTH_SERVER == errorType || BOOTSTRAPPER_ERROR_TYPE_HTTP_AUTH_PROXY == errorType) {
                nResult = IDTRYAGAIN;
            } else // show a generic error message box.
            {
                BalRetryErrorOccurred(wzPackageId, dwCode);

                if (!_showingInternalUIThisPackage) {
                    // If no error message was provided, use the error code to try and get an error message.
                    if (!wzError || !*wzError || BOOTSTRAPPER_ERROR_TYPE_WINDOWS_INSTALLER != errorType) {
                        HRESULT hr = StrAllocFromError(&sczError, dwCode, nullptr);
                        if (FAILED(hr) || !sczError || !*sczError) {
                            StrAllocFormatted(&sczError, L"0x%x", dwCode);
                        }
                    }

                    nResult = ::MessageBoxW(_hWnd, sczError ? sczError : wzError, _theme->sczCaption, dwUIHint);
                }
            }

            SetProgressState(HRESULT_FROM_WIN32(dwCode));
        } else {
            // just take note of the error code and let things continue.
            BalRetryErrorOccurred(wzPackageId, dwCode);
        }

        ReleaseStr(sczError);
        return nResult;
    }


    virtual STDMETHODIMP_(int) OnExecuteMsiMessage(
        __in_z LPCWSTR wzPackageId,
        __in INSTALLMESSAGE mt,
        __in UINT uiFlags,
        __in_z LPCWSTR wzMessage,
        __in DWORD cData,
        __in_ecount_z_opt(cData) LPCWSTR* rgwzData,
        __in int nRecommendation
    ) {
#ifdef DEBUG
        BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "PYBA: OnExecuteMsiMessage() - package: %ls, message: %ls", wzPackageId, wzMessage);
#endif
        if (BOOTSTRAPPER_DISPLAY_FULL == _command.display && (INSTALLMESSAGE_WARNING == mt || INSTALLMESSAGE_USER == mt)) {
            int nResult = ::MessageBoxW(_hWnd, wzMessage, _theme->sczCaption, uiFlags);
            return nResult;
        }

        if (INSTALLMESSAGE_ACTIONSTART == mt) {
            ThemeSetTextControl(_theme, ID_EXECUTE_PROGRESS_ACTIONDATA_TEXT, wzMessage);
        }

        return __super::OnExecuteMsiMessage(wzPackageId, mt, uiFlags, wzMessage, cData, rgwzData, nRecommendation);
    }


    virtual STDMETHODIMP_(int) OnProgress(__in DWORD dwProgressPercentage, __in DWORD dwOverallProgressPercentage) {
        WCHAR wzProgress[5] = { };

#ifdef DEBUG
        BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "PYBA: OnProgress() - progress: %u%%, overall progress: %u%%", dwProgressPercentage, dwOverallProgressPercentage);
#endif

        ::StringCchPrintfW(wzProgress, countof(wzProgress), L"%u%%", dwOverallProgressPercentage);
        ThemeSetTextControl(_theme, ID_OVERALL_PROGRESS_TEXT, wzProgress);

        ThemeSetProgressControl(_theme, ID_OVERALL_PROGRESS_BAR, dwOverallProgressPercentage);
        SetTaskbarButtonProgress(dwOverallProgressPercentage);

        return __super::OnProgress(dwProgressPercentage, dwOverallProgressPercentage);
    }


    virtual STDMETHODIMP_(int) OnExecutePackageBegin(__in_z LPCWSTR wzPackageId, __in BOOL fExecute) {
        LPWSTR sczFormattedString = nullptr;

        _startedExecution = TRUE;

        if (wzPackageId && *wzPackageId) {
            BAL_INFO_PACKAGE* pPackage = nullptr;
            BalInfoFindPackageById(&_bundle.packages, wzPackageId, &pPackage);

            LPCWSTR wz = wzPackageId;
            if (pPackage) {
                LOC_STRING* pLocString = nullptr;

                switch (pPackage->type) {
                case BAL_INFO_PACKAGE_TYPE_BUNDLE_ADDON:
                    LocGetString(_wixLoc, L"#(loc.ExecuteAddonRelatedBundleMessage)", &pLocString);
                    break;

                case BAL_INFO_PACKAGE_TYPE_BUNDLE_PATCH:
                    LocGetString(_wixLoc, L"#(loc.ExecutePatchRelatedBundleMessage)", &pLocString);
                    break;

                case BAL_INFO_PACKAGE_TYPE_BUNDLE_UPGRADE:
                    LocGetString(_wixLoc, L"#(loc.ExecuteUpgradeRelatedBundleMessage)", &pLocString);
                    break;
                }

                if (pLocString) {
                    // If the wix developer is showing a hidden variable in the UI, then obviously they don't care about keeping it safe
                    // so don't go down the rabbit hole of making sure that this is securely freed.
                    BalFormatString(pLocString->wzText, &sczFormattedString);
                }

                wz = sczFormattedString ? sczFormattedString : pPackage->sczDisplayName ? pPackage->sczDisplayName : wzPackageId;
            }

            _showingInternalUIThisPackage = pPackage && pPackage->fDisplayInternalUI;

            ThemeSetTextControl(_theme, ID_EXECUTE_PROGRESS_PACKAGE_TEXT, wz);
            ThemeSetTextControl(_theme, ID_OVERALL_PROGRESS_PACKAGE_TEXT, wz);
        } else {
            _showingInternalUIThisPackage = FALSE;
        }

        ReleaseStr(sczFormattedString);
        return __super::OnExecutePackageBegin(wzPackageId, fExecute);
    }


    virtual int __stdcall OnExecuteProgress(
        __in_z LPCWSTR wzPackageId,
        __in DWORD dwProgressPercentage,
        __in DWORD dwOverallProgressPercentage
    ) {
        WCHAR wzProgress[8] = { };

#ifdef DEBUG
        BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "PYBA: OnExecuteProgress() - package: %ls, progress: %u%%, overall progress: %u%%", wzPackageId, dwProgressPercentage, dwOverallProgressPercentage);
#endif

        ::StringCchPrintfW(wzProgress, countof(wzProgress), L"%u%%", dwOverallProgressPercentage);
        ThemeSetTextControl(_theme, ID_EXECUTE_PROGRESS_TEXT, wzProgress);

        ThemeSetProgressControl(_theme, ID_EXECUTE_PROGRESS_BAR, dwOverallProgressPercentage);

        _calculatedExecuteProgress = dwOverallProgressPercentage * (100 - PYBA_ACQUIRE_PERCENTAGE) / 100;
        ThemeSetProgressControl(_theme, ID_OVERALL_CALCULATED_PROGRESS_BAR, _calculatedCacheProgress + _calculatedExecuteProgress);

        SetTaskbarButtonProgress(_calculatedCacheProgress + _calculatedExecuteProgress);

        return __super::OnExecuteProgress(wzPackageId, dwProgressPercentage, dwOverallProgressPercentage);
    }


    virtual STDMETHODIMP_(int) OnExecutePackageComplete(
        __in_z LPCWSTR wzPackageId,
        __in HRESULT hrExitCode,
        __in BOOTSTRAPPER_APPLY_RESTART restart,
        __in int nRecommendation
    ) {
        SetProgressState(hrExitCode);

        if (_wcsnicmp(wzPackageId, L"path_", 5) == 0 && SUCCEEDED(hrExitCode)) {
            SendMessageTimeoutW(
                HWND_BROADCAST,
                WM_SETTINGCHANGE,
                0,
                reinterpret_cast<LPARAM>(L"Environment"),
                SMTO_ABORTIFHUNG,
                1000,
                nullptr
            );
        }

        int nResult = __super::OnExecutePackageComplete(wzPackageId, hrExitCode, restart, nRecommendation);

        return nResult;
    }


    virtual STDMETHODIMP_(void) OnExecuteComplete(__in HRESULT hrStatus) {
        ThemeSetTextControl(_theme, ID_EXECUTE_PROGRESS_PACKAGE_TEXT, L"");
        ThemeSetTextControl(_theme, ID_EXECUTE_PROGRESS_ACTIONDATA_TEXT, L"");
        ThemeSetTextControl(_theme, ID_OVERALL_PROGRESS_PACKAGE_TEXT, L"");
        ThemeControlEnable(_theme, ID_PROGRESS_CANCEL_BUTTON, FALSE); // no more cancel.

        SetState(PYBA_STATE_EXECUTED, S_OK); // we always return success here and let OnApplyComplete() deal with the error.
        SetProgressState(hrStatus);
    }


    virtual STDMETHODIMP_(int) OnResolveSource(
        __in_z LPCWSTR wzPackageOrContainerId,
        __in_z_opt LPCWSTR wzPayloadId,
        __in_z LPCWSTR wzLocalSource,
        __in_z_opt LPCWSTR wzDownloadSource
    ) {
        int nResult = IDERROR; // assume we won't resolve source and that is unexpected.

        if (BOOTSTRAPPER_DISPLAY_FULL == _command.display) {
            if (wzDownloadSource) {
                nResult = IDDOWNLOAD;
            } else {
                // prompt to change the source location.
                OPENFILENAMEW ofn = { };
                WCHAR wzFile[MAX_PATH] = { };

                ::StringCchCopyW(wzFile, countof(wzFile), wzLocalSource);

                ofn.lStructSize = sizeof(ofn);
                ofn.hwndOwner = _hWnd;
                ofn.lpstrFile = wzFile;
                ofn.nMaxFile = countof(wzFile);
                ofn.lpstrFilter = L"All Files\0*.*\0";
                ofn.nFilterIndex = 1;
                ofn.Flags = OFN_PATHMUSTEXIST | OFN_FILEMUSTEXIST;
                ofn.lpstrTitle = _theme->sczCaption;

                if (::GetOpenFileNameW(&ofn)) {
                    HRESULT hr = _engine->SetLocalSource(wzPackageOrContainerId, wzPayloadId, ofn.lpstrFile);
                    nResult = SUCCEEDED(hr) ? IDRETRY : IDERROR;
                } else {
                    nResult = IDCANCEL;
                }
            }
        } else if (wzDownloadSource) {
            // If doing a non-interactive install and download source is available, let's try downloading the package silently
            nResult = IDDOWNLOAD;
        }
        // else there's nothing more we can do in non-interactive mode

        return CheckCanceled() ? IDCANCEL : nResult;
    }


    virtual STDMETHODIMP_(int) OnApplyComplete(__in HRESULT hrStatus, __in BOOTSTRAPPER_APPLY_RESTART restart) {
        _restartResult = restart; // remember the restart result so we return the correct error code no matter what the user chooses to do in the UI.

        // If a restart was encountered and we are not suppressing restarts, then restart is required.
        _restartRequired = (BOOTSTRAPPER_APPLY_RESTART_NONE != restart && BOOTSTRAPPER_RESTART_NEVER < _command.restart);
        // If a restart is required and we're not displaying a UI or we are not supposed to prompt for restart then allow the restart.
        _allowRestart = _restartRequired && (BOOTSTRAPPER_DISPLAY_FULL > _command.display || BOOTSTRAPPER_RESTART_PROMPT < _command.restart);

        // If we are showing UI, wait a beat before moving to the final screen.
        if (BOOTSTRAPPER_DISPLAY_NONE < _command.display) {
            ::Sleep(250);
        }

        SetState(PYBA_STATE_APPLIED, hrStatus);
        SetTaskbarButtonProgress(100); // show full progress bar, green, yellow, or red

        return IDNOACTION;
    }

    virtual STDMETHODIMP_(void) OnLaunchApprovedExeComplete(__in HRESULT hrStatus, __in DWORD /*processId*/) {
        if (HRESULT_FROM_WIN32(ERROR_ACCESS_DENIED) == hrStatus) {
            //try with ShelExec next time
            OnClickLaunchButton();
        } else {
            ::PostMessageW(_hWnd, WM_CLOSE, 0, 0);
        }
    }


private:
    //
    // UiThreadProc - entrypoint for UI thread.
    //
    static DWORD WINAPI UiThreadProc(__in LPVOID pvContext) {
        HRESULT hr = S_OK;
        PythonBootstrapperApplication* pThis = (PythonBootstrapperApplication*)pvContext;
        BOOL comInitialized = FALSE;
        BOOL ret = FALSE;
        MSG msg = { };

        // Initialize COM and theme.
        hr = ::CoInitialize(nullptr);
        BalExitOnFailure(hr, "Failed to initialize COM.");
        comInitialized = TRUE;

        hr = ThemeInitialize(pThis->_hModule);
        BalExitOnFailure(hr, "Failed to initialize theme manager.");

        hr = pThis->InitializeData();
        BalExitOnFailure(hr, "Failed to initialize data in bootstrapper application.");

        // Create main window.
        pThis->InitializeTaskbarButton();
        hr = pThis->CreateMainWindow();
        BalExitOnFailure(hr, "Failed to create main window.");

        if (FAILED(pThis->_hrFinal)) {
            pThis->SetState(PYBA_STATE_FAILED, hr);
            ::PostMessageW(pThis->_hWnd, WM_PYBA_SHOW_FAILURE, 0, 0);
        } else {
            // Okay, we're ready for packages now.
            pThis->SetState(PYBA_STATE_INITIALIZED, hr);
            ::PostMessageW(pThis->_hWnd, BOOTSTRAPPER_ACTION_HELP == pThis->_command.action ? WM_PYBA_SHOW_HELP : WM_PYBA_DETECT_PACKAGES, 0, 0);
        }

        // message pump
        while (0 != (ret = ::GetMessageW(&msg, nullptr, 0, 0))) {
            if (-1 == ret) {
                hr = E_UNEXPECTED;
                BalExitOnFailure(hr, "Unexpected return value from message pump.");
            } else if (!ThemeHandleKeyboardMessage(pThis->_theme, msg.hwnd, &msg)) {
                ::TranslateMessage(&msg);
                ::DispatchMessageW(&msg);
            }
        }

        // Succeeded thus far, check to see if anything went wrong while actually
        // executing changes.
        if (FAILED(pThis->_hrFinal)) {
            hr = pThis->_hrFinal;
        } else if (pThis->CheckCanceled()) {
            hr = HRESULT_FROM_WIN32(ERROR_INSTALL_USEREXIT);
        }

    LExit:
        // destroy main window
        pThis->DestroyMainWindow();

        // initiate engine shutdown
        DWORD dwQuit = HRESULT_CODE(hr);
        if (BOOTSTRAPPER_APPLY_RESTART_INITIATED == pThis->_restartResult) {
            dwQuit = ERROR_SUCCESS_REBOOT_INITIATED;
        } else if (BOOTSTRAPPER_APPLY_RESTART_REQUIRED == pThis->_restartResult) {
            dwQuit = ERROR_SUCCESS_REBOOT_REQUIRED;
        }
        pThis->_engine->Quit(dwQuit);

        ReleaseTheme(pThis->_theme);
        ThemeUninitialize();

        // uninitialize COM
        if (comInitialized) {
            ::CoUninitialize();
        }

        return hr;
    }


    //
    // InitializeData - initializes all the package information.
    //
    HRESULT InitializeData() {
        HRESULT hr = S_OK;
        LPWSTR sczModulePath = nullptr;
        IXMLDOMDocument *pixdManifest = nullptr;

        hr = BalManifestLoad(_hModule, &pixdManifest);
        BalExitOnFailure(hr, "Failed to load bootstrapper application manifest.");

        hr = ParseOverridableVariablesFromXml(pixdManifest);
        BalExitOnFailure(hr, "Failed to read overridable variables.");

        hr = ProcessCommandLine(&_language);
        ExitOnFailure(hr, "Unknown commandline parameters.");

        hr = PathRelativeToModule(&sczModulePath, nullptr, _hModule);
        BalExitOnFailure(hr, "Failed to get module path.");

        hr = LoadLocalization(sczModulePath, _language);
        ExitOnFailure(hr, "Failed to load localization.");

        hr = LoadTheme(sczModulePath, _language);
        ExitOnFailure(hr, "Failed to load theme.");

        hr = BalInfoParseFromXml(&_bundle, pixdManifest);
        BalExitOnFailure(hr, "Failed to load bundle information.");

        hr = BalConditionsParseFromXml(&_conditions, pixdManifest, _wixLoc);
        BalExitOnFailure(hr, "Failed to load conditions from XML.");

        hr = LoadBootstrapperBAFunctions();
        BalExitOnFailure(hr, "Failed to load bootstrapper functions.");
        hr = UpdateUIStrings(_command.action);
        BalExitOnFailure(hr, "Failed to load UI strings.");

        GetBundleFileVersion();
        // don't fail if we couldn't get the version info; best-effort only
    LExit:
        ReleaseObject(pixdManifest);
        ReleaseStr(sczModulePath);

        return hr;
    }


    //
    // ProcessCommandLine - process the provided command line arguments.
    //
    HRESULT ProcessCommandLine(__inout LPWSTR* psczLanguage) {
        HRESULT hr = S_OK;
        int argc = 0;
        LPWSTR* argv = nullptr;
        LPWSTR sczVariableName = nullptr;
        LPWSTR sczVariableValue = nullptr;

        if (_command.wzCommandLine && *_command.wzCommandLine) {
            argv = ::CommandLineToArgvW(_command.wzCommandLine, &argc);
            ExitOnNullWithLastError(argv, hr, "Failed to get command line.");

            for (int i = 0; i < argc; ++i) {
                if (argv[i][0] == L'-' || argv[i][0] == L'/') {
                    if (CSTR_EQUAL == ::CompareStringW(LOCALE_INVARIANT, NORM_IGNORECASE, &argv[i][1], -1, L"lang", -1)) {
                        if (i + 1 >= argc) {
                            hr = E_INVALIDARG;
                            BalExitOnFailure(hr, "Must specify a language.");
                        }

                        ++i;

                        hr = StrAllocString(psczLanguage, &argv[i][0], 0);
                        BalExitOnFailure(hr, "Failed to copy language.");
                    } 
                } else if (_overridableVariables) {
                    int value;
                    const wchar_t* pwc = wcschr(argv[i], L'=');
                    if (pwc) {
                        hr = StrAllocString(&sczVariableName, argv[i], pwc - argv[i]);
                        BalExitOnFailure(hr, "Failed to copy variable name.");

                        hr = DictKeyExists(_overridableVariables, sczVariableName);
                        if (E_NOTFOUND == hr) {
                            BalLog(BOOTSTRAPPER_LOG_LEVEL_ERROR, "Ignoring attempt to set non-overridable variable: '%ls'.", sczVariableName);
                            hr = S_OK;
                            continue;
                        }
                        ExitOnFailure(hr, "Failed to check the dictionary of overridable variables.");

                        hr = StrAllocString(&sczVariableValue, ++pwc, 0);
                        BalExitOnFailure(hr, "Failed to copy variable value.");

                        if (::StrToIntEx(sczVariableValue, STIF_DEFAULT, &value)) {
                            hr = _engine->SetVariableNumeric(sczVariableName, value);
                        } else {
                            hr = _engine->SetVariableString(sczVariableName, sczVariableValue);
                        }
                        BalExitOnFailure(hr, "Failed to set variable.");
                    } else {
                        BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "Ignoring unknown argument: %ls", argv[i]);
                    }
                }
            }
        }

    LExit:
        if (argv) {
            ::LocalFree(argv);
        }

        ReleaseStr(sczVariableName);
        ReleaseStr(sczVariableValue);

        return hr;
    }

    HRESULT LoadLocalization(__in_z LPCWSTR wzModulePath, __in_z_opt LPCWSTR wzLanguage) {
        HRESULT hr = S_OK;
        LPWSTR sczLocPath = nullptr;
        LPCWSTR wzLocFileName = L"Default.wxl";

        hr = LocProbeForFile(wzModulePath, wzLocFileName, wzLanguage, &sczLocPath);
        BalExitOnFailure2(hr, "Failed to probe for loc file: %ls in path: %ls", wzLocFileName, wzModulePath);

        hr = LocLoadFromFile(sczLocPath, &_wixLoc);
        BalExitOnFailure1(hr, "Failed to load loc file from path: %ls", sczLocPath);

        if (WIX_LOCALIZATION_LANGUAGE_NOT_SET != _wixLoc->dwLangId) {
            ::SetThreadLocale(_wixLoc->dwLangId);
        }

        hr = StrAllocString(&_confirmCloseMessage, L"#(loc.ConfirmCancelMessage)", 0);
        ExitOnFailure(hr, "Failed to initialize confirm message loc identifier.");

        hr = LocLocalizeString(_wixLoc, &_confirmCloseMessage);
        BalExitOnFailure1(hr, "Failed to localize confirm close message: %ls", _confirmCloseMessage);

    LExit:
        ReleaseStr(sczLocPath);

        return hr;
    }


    HRESULT LoadTheme(__in_z LPCWSTR wzModulePath, __in_z_opt LPCWSTR wzLanguage) {
        HRESULT hr = S_OK;
        LPWSTR sczThemePath = nullptr;
        LPCWSTR wzThemeFileName = L"Default.thm";
        LPWSTR sczCaption = nullptr;

        hr = LocProbeForFile(wzModulePath, wzThemeFileName, wzLanguage, &sczThemePath);
        BalExitOnFailure2(hr, "Failed to probe for theme file: %ls in path: %ls", wzThemeFileName, wzModulePath);

        hr = ThemeLoadFromFile(sczThemePath, &_theme);
        BalExitOnFailure1(hr, "Failed to load theme from path: %ls", sczThemePath);

        hr = ThemeLocalize(_theme, _wixLoc);
        BalExitOnFailure1(hr, "Failed to localize theme: %ls", sczThemePath);

        // Update the caption if there are any formatted strings in it.
        // If the wix developer is showing a hidden variable in the UI, then
        // obviously they don't care about keeping it safe so don't go down the
        // rabbit hole of making sure that this is securely freed.
        hr = BalFormatString(_theme->sczCaption, &sczCaption);
        if (SUCCEEDED(hr)) {
            ThemeUpdateCaption(_theme, sczCaption);
        }

    LExit:
        ReleaseStr(sczCaption);
        ReleaseStr(sczThemePath);

        return hr;
    }


    HRESULT ParseOverridableVariablesFromXml(__in IXMLDOMDocument* pixdManifest) {
        HRESULT hr = S_OK;
        IXMLDOMNode* pNode = nullptr;
        IXMLDOMNodeList* pNodes = nullptr;
        DWORD cNodes = 0;
        LPWSTR scz = nullptr;
        BOOL hidden = FALSE;

        // get the list of variables users can override on the command line
        hr = XmlSelectNodes(pixdManifest, L"/BootstrapperApplicationData/WixStdbaOverridableVariable", &pNodes);
        if (S_FALSE == hr) {
            ExitFunction1(hr = S_OK);
        }
        ExitOnFailure(hr, "Failed to select overridable variable nodes.");

        hr = pNodes->get_length((long*)&cNodes);
        ExitOnFailure(hr, "Failed to get overridable variable node count.");

        if (cNodes) {
            hr = DictCreateStringList(&_overridableVariables, 32, DICT_FLAG_NONE);
            ExitOnFailure(hr, "Failed to create the string dictionary.");

            for (DWORD i = 0; i < cNodes; ++i) {
                hr = XmlNextElement(pNodes, &pNode, nullptr);
                ExitOnFailure(hr, "Failed to get next node.");

                // @Name
                hr = XmlGetAttributeEx(pNode, L"Name", &scz);
                ExitOnFailure(hr, "Failed to get @Name.");

                hr = XmlGetYesNoAttribute(pNode, L"Hidden", &hidden);

                if (!hidden) {
                    hr = DictAddKey(_overridableVariables, scz);
                    ExitOnFailure1(hr, "Failed to add \"%ls\" to the string dictionary.", scz);
                }

                // prepare next iteration
                ReleaseNullObject(pNode);
            }
        }

    LExit:
        ReleaseObject(pNode);
        ReleaseObject(pNodes);
        ReleaseStr(scz);
        return hr;
    }


    //
    // Get the file version of the bootstrapper and record in bootstrapper log file
    //
    HRESULT GetBundleFileVersion() {
        HRESULT hr = S_OK;
        ULARGE_INTEGER uliVersion = { };
        LPWSTR sczCurrentPath = nullptr;

        hr = PathForCurrentProcess(&sczCurrentPath, nullptr);
        BalExitOnFailure(hr, "Failed to get bundle path.");

        hr = FileVersion(sczCurrentPath, &uliVersion.HighPart, &uliVersion.LowPart);
        BalExitOnFailure(hr, "Failed to get bundle file version.");

        hr = _engine->SetVariableVersion(PYBA_VARIABLE_BUNDLE_FILE_VERSION, uliVersion.QuadPart);
        BalExitOnFailure(hr, "Failed to set WixBundleFileVersion variable.");

    LExit:
        ReleaseStr(sczCurrentPath);

        return hr;
    }


    //
    // CreateMainWindow - creates the main install window.
    //
    HRESULT CreateMainWindow() {
        HRESULT hr = S_OK;
        HICON hIcon = reinterpret_cast<HICON>(_theme->hIcon);
        WNDCLASSW wc = { };
        DWORD dwWindowStyle = 0;
        int x = CW_USEDEFAULT;
        int y = CW_USEDEFAULT;
        POINT ptCursor = { };
        HMONITOR hMonitor = nullptr;
        MONITORINFO mi = { };

        // If the theme did not provide an icon, try using the icon from the bundle engine.
        if (!hIcon) {
            HMODULE hBootstrapperEngine = ::GetModuleHandleW(nullptr);
            if (hBootstrapperEngine) {
                hIcon = ::LoadIconW(hBootstrapperEngine, MAKEINTRESOURCEW(1));
            }
        }

        // Register the window class and create the window.
        wc.lpfnWndProc = PythonBootstrapperApplication::WndProc;
        wc.hInstance = _hModule;
        wc.hIcon = hIcon;
        wc.hCursor = ::LoadCursorW(nullptr, (LPCWSTR)IDC_ARROW);
        wc.hbrBackground = _theme->rgFonts[_theme->dwFontId].hBackground;
        wc.lpszMenuName = nullptr;
        wc.lpszClassName = PYBA_WINDOW_CLASS;
        if (!::RegisterClassW(&wc)) {
            ExitWithLastError(hr, "Failed to register window.");
        }

        _registered = TRUE;

        // Calculate the window style based on the theme style and command display value.
        dwWindowStyle = _theme->dwStyle;
        if (BOOTSTRAPPER_DISPLAY_NONE >= _command.display) {
            dwWindowStyle &= ~WS_VISIBLE;
        }

        // Don't show the window if there is a splash screen (it will be made visible when the splash screen is hidden)
        if (::IsWindow(_command.hwndSplashScreen)) {
            dwWindowStyle &= ~WS_VISIBLE;
        }

        // Center the window on the monitor with the mouse.
        if (::GetCursorPos(&ptCursor)) {
            hMonitor = ::MonitorFromPoint(ptCursor, MONITOR_DEFAULTTONEAREST);
            if (hMonitor) {
                mi.cbSize = sizeof(mi);
                if (::GetMonitorInfoW(hMonitor, &mi)) {
                    x = mi.rcWork.left + (mi.rcWork.right - mi.rcWork.left - _theme->nWidth) / 2;
                    y = mi.rcWork.top + (mi.rcWork.bottom - mi.rcWork.top - _theme->nHeight) / 2;
                }
            }
        }

        _hWnd = ::CreateWindowExW(
            0,
            wc.lpszClassName,
            _theme->sczCaption,
            dwWindowStyle,
            x,
            y,
            _theme->nWidth,
            _theme->nHeight,
            HWND_DESKTOP,
            nullptr,
            _hModule,
            this
        );
        ExitOnNullWithLastError(_hWnd, hr, "Failed to create window.");

        hr = S_OK;

    LExit:
        return hr;
    }


    //
    // InitializeTaskbarButton - initializes taskbar button for progress.
    //
    void InitializeTaskbarButton() {
        HRESULT hr = S_OK;

        hr = ::CoCreateInstance(CLSID_TaskbarList, nullptr, CLSCTX_ALL, __uuidof(ITaskbarList3), reinterpret_cast<LPVOID*>(&_taskbarList));
        if (REGDB_E_CLASSNOTREG == hr) {
            // not supported before Windows 7
            ExitFunction1(hr = S_OK);
        }
        BalExitOnFailure(hr, "Failed to create ITaskbarList3. Continuing.");

        _taskbarButtonCreatedMessage = ::RegisterWindowMessageW(L"TaskbarButtonCreated");
        BalExitOnNullWithLastError(_taskbarButtonCreatedMessage, hr, "Failed to get TaskbarButtonCreated message. Continuing.");

    LExit:
        return;
    }

    //
    // DestroyMainWindow - clean up all the window registration.
    //
    void DestroyMainWindow() {
        if (::IsWindow(_hWnd)) {
            ::DestroyWindow(_hWnd);
            _hWnd = nullptr;
            _taskbarButtonOK = FALSE;
        }

        if (_registered) {
            ::UnregisterClassW(PYBA_WINDOW_CLASS, _hModule);
            _registered = FALSE;
        }
    }


    //
    // WndProc - standard windows message handler.
    //
    static LRESULT CALLBACK WndProc(
        __in HWND hWnd,
        __in UINT uMsg,
        __in WPARAM wParam,
        __in LPARAM lParam
    ) {
#pragma warning(suppress:4312)
        auto pBA = reinterpret_cast<PythonBootstrapperApplication*>(::GetWindowLongPtrW(hWnd, GWLP_USERDATA));

        switch (uMsg) {
        case WM_NCCREATE: {
            LPCREATESTRUCT lpcs = reinterpret_cast<LPCREATESTRUCT>(lParam);
            pBA = reinterpret_cast<PythonBootstrapperApplication*>(lpcs->lpCreateParams);
#pragma warning(suppress:4244)
            ::SetWindowLongPtrW(hWnd, GWLP_USERDATA, reinterpret_cast<LONG_PTR>(pBA));
            break;
        }

        case WM_NCDESTROY: {
            LRESULT lres = ThemeDefWindowProc(pBA ? pBA->_theme : nullptr, hWnd, uMsg, wParam, lParam);
            ::SetWindowLongPtrW(hWnd, GWLP_USERDATA, 0);
            return lres;
        }

        case WM_CREATE: 
            if (!pBA->OnCreate(hWnd)) {
                return -1;
            }
            break;

        case WM_QUERYENDSESSION:
            return IDCANCEL != pBA->OnSystemShutdown(static_cast<DWORD>(lParam), IDCANCEL);

        case WM_CLOSE:
            // If the user chose not to close, do *not* let the default window proc handle the message.
            if (!pBA->OnClose()) {
                return 0;
            }
            break;

        case WM_DESTROY:
            ::PostQuitMessage(0);
            break;

        case WM_PAINT: __fallthrough;
        case WM_ERASEBKGND:
            if (pBA && pBA->_suppressPaint) {
                return TRUE;
            }
            break;

        case WM_PYBA_SHOW_HELP:
            pBA->OnShowHelp();
            return 0;

        case WM_PYBA_DETECT_PACKAGES:
            pBA->OnDetect();
            return 0;

        case WM_PYBA_PLAN_PACKAGES:
            pBA->OnPlan(static_cast<BOOTSTRAPPER_ACTION>(lParam));
            return 0;

        case WM_PYBA_APPLY_PACKAGES:
            pBA->OnApply();
            return 0;

        case WM_PYBA_CHANGE_STATE:
            pBA->OnChangeState(static_cast<PYBA_STATE>(lParam));
            return 0;

        case WM_PYBA_SHOW_FAILURE:
            pBA->OnShowFailure();
            return 0;

        case WM_COMMAND:
            switch (LOWORD(wParam)) {
            // Customize commands
            // Success/failure commands
            case ID_LAUNCH_BUTTON:
                pBA->OnClickLaunchButton();
                return 0;

            case ID_SUCCESS_RESTART_BUTTON: __fallthrough;
            case ID_FAILURE_RESTART_BUTTON:
                pBA->OnClickRestartButton();
                return 0;

            case IDCANCEL: __fallthrough;
            case ID_INSTALL_CANCEL_BUTTON: __fallthrough;
            case ID_CUSTOM1_CANCEL_BUTTON: __fallthrough;
            case ID_CUSTOM2_CANCEL_BUTTON: __fallthrough;
            case ID_MODIFY_CANCEL_BUTTON: __fallthrough;
            case ID_PROGRESS_CANCEL_BUTTON: __fallthrough;
            case ID_SUCCESS_CANCEL_BUTTON: __fallthrough;
            case ID_FAILURE_CANCEL_BUTTON: __fallthrough;
            case ID_CLOSE_BUTTON:
                pBA->OnCommand(ID_CLOSE_BUTTON);
                return 0;

            default:
                pBA->OnCommand((CONTROL_ID)LOWORD(wParam));
            }
            break;

        case WM_NOTIFY:
            if (lParam) {
                LPNMHDR pnmhdr = reinterpret_cast<LPNMHDR>(lParam);
                switch (pnmhdr->code) {
                case NM_CLICK: __fallthrough;
                case NM_RETURN:
                    switch (static_cast<DWORD>(pnmhdr->idFrom)) {
                    case ID_FAILURE_LOGFILE_LINK:
                        pBA->OnClickLogFileLink();
                        return 1;
                    }
                }
            }
            break;

        case WM_CTLCOLORBTN:
            if (pBA) {
                HWND button = (HWND)lParam;
                DWORD style = GetWindowLong(button, GWL_STYLE) & BS_TYPEMASK;
                if (style == BS_COMMANDLINK || style == BS_DEFCOMMANDLINK) {
                    return (LRESULT)pBA->_theme->rgFonts[pBA->_theme->dwFontId].hBackground;
                }
            }
            break;
        }

        if (pBA && pBA->_taskbarList && uMsg == pBA->_taskbarButtonCreatedMessage) {
            pBA->_taskbarButtonOK = TRUE;
            return 0;
        }

        return ThemeDefWindowProc(pBA ? pBA->_theme : nullptr, hWnd, uMsg, wParam, lParam);
    }

    //
    // OnCreate - finishes loading the theme.
    //
    BOOL OnCreate(__in HWND hWnd) {
        HRESULT hr = S_OK;

        hr = ThemeLoadControls(_theme, hWnd, CONTROL_ID_NAMES, countof(CONTROL_ID_NAMES));
        BalExitOnFailure(hr, "Failed to load theme controls.");

        C_ASSERT(COUNT_PAGE == countof(PAGE_NAMES));
        C_ASSERT(countof(_pageIds) == countof(PAGE_NAMES));

        ThemeGetPageIds(_theme, PAGE_NAMES, _pageIds, countof(_pageIds));

        // Initialize the text on all "application" (non-page) controls.
        for (DWORD i = 0; i < _theme->cControls; ++i) {
            THEME_CONTROL* pControl = _theme->rgControls + i;
            LPWSTR text = nullptr;
            LPWSTR name = nullptr;
            LOC_STRING *locText = nullptr;

            // If a command link has a note, then add it.
            if ((pControl->dwStyle & BS_TYPEMASK) == BS_COMMANDLINK ||
                (pControl->dwStyle & BS_TYPEMASK) == BS_DEFCOMMANDLINK) {
                hr = StrAllocFormatted(&name, L"#(loc.%lsNote)", pControl->sczName);
                if (SUCCEEDED(hr)) {
                    hr = LocGetString(_wixLoc, name, &locText);
                    ReleaseStr(name);
                    if (SUCCEEDED(hr) && locText && locText->wzText && locText->wzText[0]) {
                        hr = BalFormatString(locText->wzText, &text);
                        if (SUCCEEDED(hr) && text && text[0]) {
                            ThemeSendControlMessage(_theme, pControl->wId, BCM_SETNOTE, 0, (LPARAM)text);
                            ReleaseStr(text);
                            text = nullptr;
                        }
                    }
                }
                hr = S_OK;
            }

            if (!pControl->wPageId && pControl->sczText && *pControl->sczText) {
                HRESULT hrFormat;
                
                // If the wix developer is showing a hidden variable in the UI,
                // then obviously they don't care about keeping it safe so don't
                // go down the rabbit hole of making sure that this is securely
                // freed.
                hrFormat = BalFormatString(pControl->sczText, &text);
                if (SUCCEEDED(hrFormat)) {
                    ThemeSetTextControl(_theme, pControl->wId, text);
                    ReleaseStr(text);
                }
            }
        }

    LExit:
        return SUCCEEDED(hr);
    }


    //
    // OnShowFailure - display the failure page.
    //
    void OnShowFailure() {
        SetState(PYBA_STATE_FAILED, S_OK);

        // If the UI should be visible, display it now and hide the splash screen
        if (BOOTSTRAPPER_DISPLAY_NONE < _command.display) {
            ::ShowWindow(_theme->hwndParent, SW_SHOW);
        }

        _engine->CloseSplashScreen();

        return;
    }


    //
    // OnShowHelp - display the help page.
    //
    void OnShowHelp() {
        SetState(PYBA_STATE_HELP, S_OK);

        // If the UI should be visible, display it now and hide the splash screen
        if (BOOTSTRAPPER_DISPLAY_NONE < _command.display) {
            ::ShowWindow(_theme->hwndParent, SW_SHOW);
        }

        _engine->CloseSplashScreen();

        return;
    }


    //
    // OnDetect - start the processing of packages.
    //
    void OnDetect() {
        HRESULT hr = S_OK;

        if (_baFunction) {
            BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "Running detect BA function");
            hr = _baFunction->OnDetect();
            BalExitOnFailure(hr, "Failed calling detect BA function.");
        }

        SetState(PYBA_STATE_DETECTING, hr);

        // If the UI should be visible, display it now and hide the splash screen
        if (BOOTSTRAPPER_DISPLAY_NONE < _command.display) {
            ::ShowWindow(_theme->hwndParent, SW_SHOW);
        }

        _engine->CloseSplashScreen();

        // Tell the core we're ready for the packages to be processed now.
        hr = _engine->Detect();
        BalExitOnFailure(hr, "Failed to start detecting chain.");

    LExit:
        if (FAILED(hr)) {
            SetState(PYBA_STATE_DETECTING, hr);
        }

        return;
    }
    HRESULT UpdateUIStrings(__in BOOTSTRAPPER_ACTION action) {
        HRESULT hr = S_OK;
        LPCWSTR likeInstalling = nullptr;
        LPCWSTR likeInstallation = nullptr;
        switch (action) {
        case BOOTSTRAPPER_ACTION_INSTALL:
            likeInstalling = L"Installing";
            likeInstallation = L"Installation";
            break;
        case BOOTSTRAPPER_ACTION_MODIFY:
            // For modify, we actually want to pass INSTALL
            action = BOOTSTRAPPER_ACTION_INSTALL;
            likeInstalling = L"Modifying";
            likeInstallation = L"Modification";
            break;
        case BOOTSTRAPPER_ACTION_REPAIR:
            likeInstalling = L"Repairing";
            likeInstallation = L"Repair";
            break;
        case BOOTSTRAPPER_ACTION_UNINSTALL:
            likeInstalling = L"Uninstalling";
            likeInstallation = L"Uninstallation";
            break;
        }

        if (likeInstalling) {
            LPWSTR locName = nullptr;
            LOC_STRING *locText = nullptr;
            hr = StrAllocFormatted(&locName, L"#(loc.%ls)", likeInstalling);
            if (SUCCEEDED(hr)) {
                hr = LocGetString(_wixLoc, locName, &locText);
                ReleaseStr(locName);
            }
            _engine->SetVariableString(
                L"ActionLikeInstalling",
                SUCCEEDED(hr) && locText ? locText->wzText : likeInstalling
            );
        }

        if (likeInstallation) {
            LPWSTR locName = nullptr;
            LOC_STRING *locText = nullptr;
            hr = StrAllocFormatted(&locName, L"#(loc.%ls)", likeInstallation);
            if (SUCCEEDED(hr)) {
                hr = LocGetString(_wixLoc, locName, &locText);
                ReleaseStr(locName);
            }
            _engine->SetVariableString(
                L"ActionLikeInstallation",
                SUCCEEDED(hr) && locText ? locText->wzText : likeInstallation
            );
        }
        return hr;
    }

    //
    // OnPlan - plan the detected changes.
    //
    void OnPlan(__in BOOTSTRAPPER_ACTION action) {
        HRESULT hr = S_OK;

        _plannedAction = action;

        hr = UpdateUIStrings(action);
        BalExitOnFailure(hr, "Failed to update strings");

        // If we are going to apply a downgrade, bail.
        if (_downgrading && BOOTSTRAPPER_ACTION_UNINSTALL < action) {
            if (_suppressDowngradeFailure) {
                BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "A newer version of this product is installed but downgrade failure has been suppressed; continuing...");
            } else {
                hr = HRESULT_FROM_WIN32(ERROR_PRODUCT_VERSION);
                BalExitOnFailure(hr, "Cannot install a product when a newer version is installed.");
            }
        }

        SetState(PYBA_STATE_PLANNING, hr);

        if (_baFunction) {
            BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "Running plan BA function");
            _baFunction->OnPlan();
        }

        hr = _engine->Plan(action);
        BalExitOnFailure(hr, "Failed to start planning packages.");

    LExit:
        if (FAILED(hr)) {
            SetState(PYBA_STATE_PLANNING, hr);
        }

        return;
    }


    //
    // OnApply - apply the packages.
    //
    void OnApply() {
        HRESULT hr = S_OK;

        SetState(PYBA_STATE_APPLYING, hr);
        SetProgressState(hr);
        SetTaskbarButtonProgress(0);

        hr = _engine->Apply(_hWnd);
        BalExitOnFailure(hr, "Failed to start applying packages.");

        ThemeControlEnable(_theme, ID_PROGRESS_CANCEL_BUTTON, TRUE); // ensure the cancel button is enabled before starting.

    LExit:
        if (FAILED(hr)) {
            SetState(PYBA_STATE_APPLYING, hr);
        }

        return;
    }


    //
    // OnChangeState - change state.
    //
    void OnChangeState(__in PYBA_STATE state) {
        LPWSTR unformattedText = nullptr;

        _state = state;

        // If our install is at the end (success or failure) and we're not showing full UI
        // then exit (prompt for restart if required).
        if ((PYBA_STATE_APPLIED <= _state && BOOTSTRAPPER_DISPLAY_FULL > _command.display)) {
            // If a restart was required but we were not automatically allowed to
            // accept the reboot then do the prompt.
            if (_restartRequired && !_allowRestart) {
                StrAllocFromError(&unformattedText, HRESULT_FROM_WIN32(ERROR_SUCCESS_REBOOT_REQUIRED), nullptr);

                _allowRestart = IDOK == ::MessageBoxW(
                    _hWnd,
                    unformattedText ? unformattedText : L"The requested operation is successful. Changes will not be effective until the system is rebooted.",
                    _theme->sczCaption,
                    MB_ICONEXCLAMATION | MB_OKCANCEL
                );
            }

            // Quietly exit.
            ::PostMessageW(_hWnd, WM_CLOSE, 0, 0);
        } else { // try to change the pages.
            DWORD newPageId = 0;
            DeterminePageId(_state, &newPageId);

            if (_visiblePageId != newPageId) {
                ShowPage(newPageId);
            }
        }

        ReleaseStr(unformattedText);
    }

    //
    // Called before showing a page to handle all controls.
    //
    void ProcessPageControls(THEME_PAGE *pPage) {
        if (!pPage) {
            return;
        }

        for (DWORD i = 0; i < pPage->cControlIndices; ++i) {
            THEME_CONTROL* pControl = _theme->rgControls + pPage->rgdwControlIndices[i];

            // If this is a named control, try to set its default state.
            if (pControl->sczName && *pControl->sczName) {
                // If this is a checkable control, try to set its default state
                // to the state of a matching named Burn variable.
                if (IsCheckable(pControl)) {
                    LONGLONG llValue = 0;
                    HRESULT hr = BalGetNumericVariable(pControl->sczName, &llValue);

                    // If the control value isn't set then disable it.
                    if (!SUCCEEDED(hr)) {
                        ThemeControlEnable(_theme, pControl->wId, FALSE);
                    } else {
                        ThemeSendControlMessage(
                            _theme,
                            pControl->wId,
                            BM_SETCHECK,
                            SUCCEEDED(hr) && llValue ? BST_CHECKED : BST_UNCHECKED,
                            0
                        );
                    }
                }

                // Hide or disable controls based on the control name with 'State' appended
                LPWSTR controlName = nullptr;
                HRESULT hr = StrAllocFormatted(&controlName, L"%lsState", pControl->sczName);
                if (SUCCEEDED(hr)) {
                    LPWSTR controlState = nullptr;
                    hr = BalGetStringVariable(controlName, &controlState);
                    if (SUCCEEDED(hr) && controlState && *controlState) {
                        if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, controlState, -1, L"disable", -1)) {
                            BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "Disable control %ls", pControl->sczName);
                            ThemeControlEnable(_theme, pControl->wId, FALSE);
                        } else if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, controlState, -1, L"hide", -1)) {
                            BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "Hide control %ls", pControl->sczName);
                            // TODO: This doesn't work
                            ThemeShowControl(_theme, pControl->wId, SW_HIDE);
                        }
                    }
                    StrFree(controlState);
                }
                StrFree(controlName);
            }

            // Format the text in each of the new page's controls
            if (pControl->sczText && *pControl->sczText) {
                // If the wix developer is showing a hidden variable
                // in the UI, then obviously they don't care about
                // keeping it safe so don't go down the rabbit hole
                // of making sure that this is securely freed.
                LPWSTR text = nullptr;
                HRESULT hr = BalFormatString(pControl->sczText, &text);
                if (SUCCEEDED(hr)) {
                    ThemeSetTextControl(_theme, pControl->wId, text);
                }
            }
        }
    }

    //
    // OnClose - called when the window is trying to be closed.
    //
    BOOL OnClose() {
        BOOL close = FALSE;

        // If we've already succeeded or failed or showing the help page, just close (prompts are annoying if the bootstrapper is done).
        if (PYBA_STATE_APPLIED <= _state || PYBA_STATE_HELP == _state) {
            close = TRUE;
        } else {
            // prompt the user or force the cancel if there is no UI.
            close = PromptCancel(
                _hWnd,
                BOOTSTRAPPER_DISPLAY_FULL != _command.display,
                _confirmCloseMessage ? _confirmCloseMessage : L"Are you sure you want to cancel?",
                _theme->sczCaption
            );
        }

        // If we're doing progress then we never close, we just cancel to let rollback occur.
        if (PYBA_STATE_APPLYING <= _state && PYBA_STATE_APPLIED > _state) {
            // If we canceled disable cancel button since clicking it again is silly.
            if (close) {
                ThemeControlEnable(_theme, ID_PROGRESS_CANCEL_BUTTON, FALSE);
            }

            close = FALSE;
        }

        return close;
    }

    //
    // OnClickCloseButton - close the application.
    //
    void OnClickCloseButton() {
        ::SendMessageW(_hWnd, WM_CLOSE, 0, 0);
    }


    //
    // OnClickLaunchButton - launch the app from the success page.
    //
    void OnClickLaunchButton() {
        HRESULT hr = S_OK;
        LPWSTR sczUnformattedLaunchTarget = nullptr;
        LPWSTR sczLaunchTarget = nullptr;
        LPWSTR sczLaunchTargetElevatedId = nullptr;
        LPWSTR sczUnformattedArguments = nullptr;
        LPWSTR sczArguments = nullptr;
        int nCmdShow = SW_SHOWNORMAL;

        hr = BalGetStringVariable(PYBA_VARIABLE_LAUNCH_TARGET_PATH, &sczUnformattedLaunchTarget);
        BalExitOnFailure1(hr, "Failed to get launch target variable '%ls'.", PYBA_VARIABLE_LAUNCH_TARGET_PATH);

        hr = BalFormatString(sczUnformattedLaunchTarget, &sczLaunchTarget);
        BalExitOnFailure1(hr, "Failed to format launch target variable: %ls", sczUnformattedLaunchTarget);

        if (BalStringVariableExists(PYBA_VARIABLE_LAUNCH_TARGET_ELEVATED_ID)) {
            hr = BalGetStringVariable(PYBA_VARIABLE_LAUNCH_TARGET_ELEVATED_ID, &sczLaunchTargetElevatedId);
            BalExitOnFailure1(hr, "Failed to get launch target elevated id '%ls'.", PYBA_VARIABLE_LAUNCH_TARGET_ELEVATED_ID);
        }

        if (BalStringVariableExists(PYBA_VARIABLE_LAUNCH_ARGUMENTS)) {
            hr = BalGetStringVariable(PYBA_VARIABLE_LAUNCH_ARGUMENTS, &sczUnformattedArguments);
            BalExitOnFailure1(hr, "Failed to get launch arguments '%ls'.", PYBA_VARIABLE_LAUNCH_ARGUMENTS);
        }

        if (BalStringVariableExists(PYBA_VARIABLE_LAUNCH_HIDDEN)) {
            nCmdShow = SW_HIDE;
        }

        if (sczLaunchTargetElevatedId && !_triedToLaunchElevated) {
            _triedToLaunchElevated = TRUE;
            hr = _engine->LaunchApprovedExe(_hWnd, sczLaunchTargetElevatedId, sczUnformattedArguments, 0);
            if (FAILED(hr)) {
                BalLogError(hr, "Failed to launch elevated target: %ls", sczLaunchTargetElevatedId);

                //try with ShelExec next time
                OnClickLaunchButton();
            }
        } else {
            if (sczUnformattedArguments) {
                hr = BalFormatString(sczUnformattedArguments, &sczArguments);
                BalExitOnFailure1(hr, "Failed to format launch arguments variable: %ls", sczUnformattedArguments);
            }

            hr = ShelExec(sczLaunchTarget, sczArguments, L"open", nullptr, nCmdShow, _hWnd, nullptr);
            BalExitOnFailure1(hr, "Failed to launch target: %ls", sczLaunchTarget);

            ::PostMessageW(_hWnd, WM_CLOSE, 0, 0);
        }

    LExit:
        StrSecureZeroFreeString(sczArguments);
        ReleaseStr(sczUnformattedArguments);
        ReleaseStr(sczLaunchTargetElevatedId);
        StrSecureZeroFreeString(sczLaunchTarget);
        ReleaseStr(sczUnformattedLaunchTarget);

        return;
    }


    //
    // OnClickRestartButton - allows the restart and closes the app.
    //
    void OnClickRestartButton() {
        AssertSz(_restartRequired, "Restart must be requested to be able to click on the restart button.");

        _allowRestart = TRUE;
        ::SendMessageW(_hWnd, WM_CLOSE, 0, 0);

        return;
    }


    //
    // OnClickLogFileLink - show the log file.
    //
    void OnClickLogFileLink() {
        HRESULT hr = S_OK;
        LPWSTR sczLogFile = nullptr;

        hr = BalGetStringVariable(_bundle.sczLogVariable, &sczLogFile);
        BalExitOnFailure1(hr, "Failed to get log file variable '%ls'.", _bundle.sczLogVariable);

        hr = ShelExec(L"notepad.exe", sczLogFile, L"open", nullptr, SW_SHOWDEFAULT, _hWnd, nullptr);
        BalExitOnFailure1(hr, "Failed to open log file target: %ls", sczLogFile);

    LExit:
        ReleaseStr(sczLogFile);

        return;
    }


    //
    // SetState
    //
    void SetState(__in PYBA_STATE state, __in HRESULT hrStatus) {
        if (FAILED(hrStatus)) {
            _hrFinal = hrStatus;
        }

        if (FAILED(_hrFinal)) {
            state = PYBA_STATE_FAILED;
        }

        if (_state != state) {
            ::PostMessageW(_hWnd, WM_PYBA_CHANGE_STATE, 0, state);
        }
    }

    //
    // GoToPage
    //
    void GoToPage(__in PAGE page) {
        _installPage = page;
        ::PostMessageW(_hWnd, WM_PYBA_CHANGE_STATE, 0, _state);
    }

    void DeterminePageId(__in PYBA_STATE state, __out DWORD* pdwPageId) {
        LONGLONG simple;

        if (BOOTSTRAPPER_DISPLAY_PASSIVE == _command.display) {
            switch (state) {
            case PYBA_STATE_INITIALIZED:
                *pdwPageId = BOOTSTRAPPER_ACTION_HELP == _command.action
                    ? _pageIds[PAGE_HELP]
                    : _pageIds[PAGE_LOADING];
                break;

            case PYBA_STATE_HELP:
                *pdwPageId = _pageIds[PAGE_HELP];
                break;

            case PYBA_STATE_DETECTING:
                *pdwPageId = _pageIds[PAGE_LOADING]
                    ? _pageIds[PAGE_LOADING]
                    : _pageIds[PAGE_PROGRESS_PASSIVE]
                        ? _pageIds[PAGE_PROGRESS_PASSIVE]
                        : _pageIds[PAGE_PROGRESS];
                break;

            case PYBA_STATE_DETECTED: __fallthrough;
            case PYBA_STATE_PLANNING: __fallthrough;
            case PYBA_STATE_PLANNED: __fallthrough;
            case PYBA_STATE_APPLYING: __fallthrough;
            case PYBA_STATE_CACHING: __fallthrough;
            case PYBA_STATE_CACHED: __fallthrough;
            case PYBA_STATE_EXECUTING: __fallthrough;
            case PYBA_STATE_EXECUTED:
                *pdwPageId = _pageIds[PAGE_PROGRESS_PASSIVE]
                    ? _pageIds[PAGE_PROGRESS_PASSIVE]
                    : _pageIds[PAGE_PROGRESS];
                break;

            default:
                *pdwPageId = 0;
                break;
            }
        } else if (BOOTSTRAPPER_DISPLAY_FULL == _command.display) {
            switch (state) {
            case PYBA_STATE_INITIALIZING:
                *pdwPageId = 0;
                break;

            case PYBA_STATE_INITIALIZED:
                *pdwPageId = BOOTSTRAPPER_ACTION_HELP == _command.action
                    ? _pageIds[PAGE_HELP]
                    : _pageIds[PAGE_LOADING];
                break;

            case PYBA_STATE_HELP:
                *pdwPageId = _pageIds[PAGE_HELP];
                break;

            case PYBA_STATE_DETECTING:
                *pdwPageId = _pageIds[PAGE_LOADING];
                break;

            case PYBA_STATE_DETECTED:
                if (_installPage == PAGE_LOADING) {
                    switch (_command.action) {
                    case BOOTSTRAPPER_ACTION_INSTALL:
                        if (SUCCEEDED(BalGetNumericVariable(L"SimpleInstall", &simple)) && simple) {
                            _installPage = PAGE_SIMPLE_INSTALL;
                        } else {
                            _installPage = PAGE_INSTALL;
                        }
                        break;

                    case BOOTSTRAPPER_ACTION_MODIFY: __fallthrough;
                    case BOOTSTRAPPER_ACTION_REPAIR: __fallthrough;
                    case BOOTSTRAPPER_ACTION_UNINSTALL:
                        _installPage = PAGE_MODIFY;
                        break;
                    }
                }
                *pdwPageId = _pageIds[_installPage];
                break;

            case PYBA_STATE_PLANNING: __fallthrough;
            case PYBA_STATE_PLANNED: __fallthrough;
            case PYBA_STATE_APPLYING: __fallthrough;
            case PYBA_STATE_CACHING: __fallthrough;
            case PYBA_STATE_CACHED: __fallthrough;
            case PYBA_STATE_EXECUTING: __fallthrough;
            case PYBA_STATE_EXECUTED:
                *pdwPageId = _pageIds[PAGE_PROGRESS];
                break;

            case PYBA_STATE_APPLIED:
                *pdwPageId = _pageIds[PAGE_SUCCESS];
                break;

            case PYBA_STATE_FAILED:
                *pdwPageId = _pageIds[PAGE_FAILURE];
                break;
            }
        }
    }

    BOOL IsCrtInstalled() {
        if (_crtInstalledToken > 0) {
            return TRUE;
        } else if (_crtInstalledToken == 0) {
            return FALSE;
        }
        
        // Check whether at least CRT v10.0.9920.0 is available.
        // It should only be installed as a Windows Update package, which means
        // we don't need to worry about 32-bit/64-bit.
        // However, since the WU package does not include vcruntime140.dll, we
        // still install that ourselves.
        LPCWSTR crtFile = L"api-ms-win-crt-runtime-l1-1-0.dll";

        DWORD cbVer = GetFileVersionInfoSizeW(crtFile, nullptr);
        if (!cbVer) {
            _crtInstalledToken = 0;
            return FALSE;
        }

        void *pData = malloc(cbVer);
        if (!pData) {
            _crtInstalledToken = 0;
            return FALSE;
        }

        if (!GetFileVersionInfoW(crtFile, 0, cbVer, pData)) {
            free(pData);
            _crtInstalledToken = 0;
            return FALSE;
        }

        VS_FIXEDFILEINFO *ffi;
        UINT cb;
        BOOL result = FALSE;

        if (VerQueryValueW(pData, L"\\", (LPVOID*)&ffi, &cb) &&
            ffi->dwFileVersionMS == 0x000A0000 && ffi->dwFileVersionLS >= 0x26C00000) {
            result = TRUE;
        }
        
        free(pData);
        _crtInstalledToken = result ? 1 : 0;
        return result;
    }

    BOOL QueryElevateForCrtInstall() {
        // Called to prompt the user that even though they think they won't need
        // to elevate, they actually will because of the CRT install.
        if (IsCrtInstalled()) {
            // CRT is already installed - no need to prompt
            return TRUE;
        }
        
        LONGLONG elevated;
        HRESULT hr = BalGetNumericVariable(L"WixBundleElevated", &elevated);
        if (SUCCEEDED(hr) && elevated) {
            // Already elevated - no need to prompt
            return TRUE;
        }

        LOC_STRING *locStr;
        hr = LocGetString(_wixLoc, L"#(loc.ElevateForCRTInstall)", &locStr);
        if (FAILED(hr)) {
            BalLogError(hr, "Failed to get ElevateForCRTInstall string");
            return FALSE;
        }
        return ::MessageBoxW(_hWnd, locStr->wzText, _theme->sczCaption, MB_YESNO) != IDNO;
    }

    HRESULT EvaluateConditions() {
        HRESULT hr = S_OK;
        BOOL result = FALSE;

        for (DWORD i = 0; i < _conditions.cConditions; ++i) {
            BAL_CONDITION* pCondition = _conditions.rgConditions + i;

            hr = BalConditionEvaluate(pCondition, _engine, &result, &_failedMessage);
            BalExitOnFailure(hr, "Failed to evaluate condition.");

            if (!result) {
                // Hope they didn't have hidden variables in their message, because it's going in the log in plaintext.
                BalLog(BOOTSTRAPPER_LOG_LEVEL_ERROR, "%ls", _failedMessage);

                hr = E_WIXSTDBA_CONDITION_FAILED;
                // todo: remove in WiX v4, in case people are relying on v3.x logging behavior
                BalExitOnFailure1(hr, "Bundle condition evaluated to false: %ls", pCondition->sczCondition);
            }
        }

        ReleaseNullStrSecure(_failedMessage);

    LExit:
        return hr;
    }


    void SetTaskbarButtonProgress(__in DWORD dwOverallPercentage) {
        HRESULT hr = S_OK;

        if (_taskbarButtonOK) {
            hr = _taskbarList->SetProgressValue(_hWnd, dwOverallPercentage, 100UL);
            BalExitOnFailure1(hr, "Failed to set taskbar button progress to: %d%%.", dwOverallPercentage);
        }

    LExit:
        return;
    }


    void SetTaskbarButtonState(__in TBPFLAG tbpFlags) {
        HRESULT hr = S_OK;

        if (_taskbarButtonOK) {
            hr = _taskbarList->SetProgressState(_hWnd, tbpFlags);
            BalExitOnFailure1(hr, "Failed to set taskbar button state.", tbpFlags);
        }

    LExit:
        return;
    }


    void SetProgressState(__in HRESULT hrStatus) {
        TBPFLAG flag = TBPF_NORMAL;

        if (IsCanceled() || HRESULT_FROM_WIN32(ERROR_INSTALL_USEREXIT) == hrStatus) {
            flag = TBPF_PAUSED;
        } else if (IsRollingBack() || FAILED(hrStatus)) {
            flag = TBPF_ERROR;
        }

        SetTaskbarButtonState(flag);
    }


    HRESULT LoadBootstrapperBAFunctions() {
        HRESULT hr = S_OK;
        LPWSTR sczBafPath = nullptr;

        hr = PathRelativeToModule(&sczBafPath, L"bafunctions.dll", _hModule);
        BalExitOnFailure(hr, "Failed to get path to BA function DLL.");

#ifdef DEBUG
        BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "PYBA: LoadBootstrapperBAFunctions() - BA function DLL %ls", sczBafPath);
#endif

        _hBAFModule = ::LoadLibraryW(sczBafPath);
        if (_hBAFModule) {
            auto pfnBAFunctionCreate = reinterpret_cast<PFN_BOOTSTRAPPER_BA_FUNCTION_CREATE>(::GetProcAddress(_hBAFModule, "CreateBootstrapperBAFunction"));
            BalExitOnNullWithLastError1(pfnBAFunctionCreate, hr, "Failed to get CreateBootstrapperBAFunction entry-point from: %ls", sczBafPath);

            hr = pfnBAFunctionCreate(_engine, _hBAFModule, &_baFunction);
            BalExitOnFailure(hr, "Failed to create BA function.");
        }
#ifdef DEBUG
        else {
            BalLogError(HRESULT_FROM_WIN32(::GetLastError()), "PYBA: LoadBootstrapperBAFunctions() - Failed to load DLL %ls", sczBafPath);
        }
#endif

    LExit:
        if (_hBAFModule && !_baFunction) {
            ::FreeLibrary(_hBAFModule);
            _hBAFModule = nullptr;
        }
        ReleaseStr(sczBafPath);

        return hr;
    }

    BOOL IsCheckable(THEME_CONTROL* pControl) {
        if (!pControl->sczName || !pControl->sczName[0]) {
            return FALSE;
        }

        if (pControl->type == THEME_CONTROL_TYPE_CHECKBOX) {
            return TRUE;
        }

        if (pControl->type == THEME_CONTROL_TYPE_BUTTON) {
            if ((pControl->dwStyle & BS_TYPEMASK) == BS_AUTORADIOBUTTON) {
                return TRUE;
            }
        }

        return FALSE;
    }

    void SavePageSettings() {
        DWORD pageId = 0;
        THEME_PAGE* pPage = nullptr;

        DeterminePageId(_state, &pageId);
        pPage = ThemeGetPage(_theme, pageId);
        if (!pPage) {
            return;
        }

        for (DWORD i = 0; i < pPage->cControlIndices; ++i) {
            // Loop through all the checkable controls and set a Burn variable
            // with that name to true or false.
            THEME_CONTROL* pControl = _theme->rgControls + pPage->rgdwControlIndices[i];
            if (IsCheckable(pControl) && ThemeControlEnabled(_theme, pControl->wId)) {
                BOOL checked = ThemeIsControlChecked(_theme, pControl->wId);
                _engine->SetVariableNumeric(pControl->sczName, checked ? 1 : 0);
            }

            // Loop through all the editbox controls with names and set a
            // Burn variable with that name to the contents.
            if (THEME_CONTROL_TYPE_EDITBOX == pControl->type && pControl->sczName && *pControl->sczName) {
                LPWSTR sczValue = nullptr;
                ThemeGetTextControl(_theme, pControl->wId, &sczValue);
                _engine->SetVariableString(pControl->sczName, sczValue);
            }
        }
    }


public:
    //
    // Constructor - initialize member variables.
    //
    PythonBootstrapperApplication(
        __in HMODULE hModule,
        __in BOOL fPrereq,
        __in HRESULT hrHostInitialization,
        __in IBootstrapperEngine* pEngine,
        __in const BOOTSTRAPPER_COMMAND* pCommand
    ) : CBalBaseBootstrapperApplication(pEngine, pCommand, 3, 3000) {
        _hModule = hModule;
        memcpy_s(&_command, sizeof(_command), pCommand, sizeof(BOOTSTRAPPER_COMMAND));

        LONGLONG llInstalled = 0;
        HRESULT hr = BalGetNumericVariable(L"WixBundleInstalled", &llInstalled);
        if (SUCCEEDED(hr) && BOOTSTRAPPER_RESUME_TYPE_REBOOT != _command.resumeType && 0 < llInstalled && BOOTSTRAPPER_ACTION_INSTALL == _command.action) {
            _command.action = BOOTSTRAPPER_ACTION_MODIFY;
        } else if (0 == llInstalled && (BOOTSTRAPPER_ACTION_MODIFY == _command.action || BOOTSTRAPPER_ACTION_REPAIR == _command.action)) {
            _command.action = BOOTSTRAPPER_ACTION_INSTALL;
        }

        _plannedAction = BOOTSTRAPPER_ACTION_UNKNOWN;


        // When resuming from restart doing some install-like operation, try to find the package that forced the
        // restart. We'll use this information during planning.
        _nextPackageAfterRestart = nullptr;

        if (BOOTSTRAPPER_RESUME_TYPE_REBOOT == _command.resumeType && BOOTSTRAPPER_ACTION_UNINSTALL < _command.action) {
            // Ensure the forced restart package variable is null when it is an empty string.
            HRESULT hr = BalGetStringVariable(L"WixBundleForcedRestartPackage", &_nextPackageAfterRestart);
            if (FAILED(hr) || !_nextPackageAfterRestart || !*_nextPackageAfterRestart) {
                ReleaseNullStr(_nextPackageAfterRestart);
            }
        }

        _crtInstalledToken = -1;
        pEngine->SetVariableNumeric(L"CRTInstalled", IsCrtInstalled() ? 1 : 0);

        _wixLoc = nullptr;
        memset(&_bundle, 0, sizeof(_bundle));
        memset(&_conditions, 0, sizeof(_conditions));
        _confirmCloseMessage = nullptr;
        _failedMessage = nullptr;

        _language = nullptr;
        _theme = nullptr;
        memset(_pageIds, 0, sizeof(_pageIds));
        _hUiThread = nullptr;
        _registered = FALSE;
        _hWnd = nullptr;

        _state = PYBA_STATE_INITIALIZING;
        _visiblePageId = 0;
        _installPage = PAGE_LOADING;
        _hrFinal = hrHostInitialization;

        _downgrading = FALSE;
        _restartResult = BOOTSTRAPPER_APPLY_RESTART_NONE;
        _restartRequired = FALSE;
        _allowRestart = FALSE;

        _suppressDowngradeFailure = FALSE;
        _suppressRepair = FALSE;
        _modifying = FALSE;

        _overridableVariables = nullptr;
        _taskbarList = nullptr;
        _taskbarButtonCreatedMessage = UINT_MAX;
        _taskbarButtonOK = FALSE;
        _showingInternalUIThisPackage = FALSE;
        _triedToLaunchElevated = FALSE;

        _suppressPaint = FALSE;

        pEngine->AddRef();
        _engine = pEngine;

        _hBAFModule = nullptr;
        _baFunction = nullptr;
    }


    //
    // Destructor - release member variables.
    //
    ~PythonBootstrapperApplication() {
        AssertSz(!::IsWindow(_hWnd), "Window should have been destroyed before destructor.");
        AssertSz(!_theme, "Theme should have been released before destructor.");

        ReleaseObject(_taskbarList);
        ReleaseDict(_overridableVariables);
        ReleaseStr(_failedMessage);
        ReleaseStr(_confirmCloseMessage);
        BalConditionsUninitialize(&_conditions);
        BalInfoUninitialize(&_bundle);
        LocFree(_wixLoc);

        ReleaseStr(_language);
        ReleaseStr(_nextPackageAfterRestart);
        ReleaseNullObject(_engine);

        if (_hBAFModule) {
            ::FreeLibrary(_hBAFModule);
            _hBAFModule = nullptr;
        }
    }

private:
    HMODULE _hModule;
    BOOTSTRAPPER_COMMAND _command;
    IBootstrapperEngine* _engine;
    BOOTSTRAPPER_ACTION _plannedAction;

    LPWSTR _nextPackageAfterRestart;

    WIX_LOCALIZATION* _wixLoc;
    BAL_INFO_BUNDLE _bundle;
    BAL_CONDITIONS _conditions;
    LPWSTR _failedMessage;
    LPWSTR _confirmCloseMessage;

    LPWSTR _language;
    THEME* _theme;
    DWORD _pageIds[countof(PAGE_NAMES)];
    HANDLE _hUiThread;
    BOOL _registered;
    HWND _hWnd;

    PYBA_STATE _state;
    HRESULT _hrFinal;
    DWORD _visiblePageId;
    PAGE _installPage;

    BOOL _startedExecution;
    DWORD _calculatedCacheProgress;
    DWORD _calculatedExecuteProgress;

    BOOL _downgrading;
    BOOTSTRAPPER_APPLY_RESTART _restartResult;
    BOOL _restartRequired;
    BOOL _allowRestart;

    BOOL _suppressDowngradeFailure;
    BOOL _suppressRepair;
    BOOL _modifying;

    int _crtInstalledToken;

    STRINGDICT_HANDLE _overridableVariables;

    ITaskbarList3* _taskbarList;
    UINT _taskbarButtonCreatedMessage;
    BOOL _taskbarButtonOK;
    BOOL _showingInternalUIThisPackage;
    BOOL _triedToLaunchElevated;

    BOOL _suppressPaint;

    HMODULE _hBAFModule;
    IBootstrapperBAFunction* _baFunction;
};

//
// CreateBootstrapperApplication - creates a new IBootstrapperApplication object.
//
HRESULT CreateBootstrapperApplication(
    __in HMODULE hModule,
    __in BOOL fPrereq,
    __in HRESULT hrHostInitialization,
    __in IBootstrapperEngine* pEngine,
    __in const BOOTSTRAPPER_COMMAND* pCommand,
    __out IBootstrapperApplication** ppApplication
    ) {
    HRESULT hr = S_OK;

    if (fPrereq) {
        hr = E_INVALIDARG;
        ExitWithLastError(hr, "Failed to create UI thread.");
    }

    PythonBootstrapperApplication* pApplication = nullptr;

    pApplication = new PythonBootstrapperApplication(hModule, fPrereq, hrHostInitialization, pEngine, pCommand);
    ExitOnNull(pApplication, hr, E_OUTOFMEMORY, "Failed to create new standard bootstrapper application object.");

    *ppApplication = pApplication;
    pApplication = nullptr;

LExit:
    ReleaseObject(pApplication);
    return hr;
}
