// Copyright 2015 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
/**
 * @fileoverview
 * 'settings-people-page' is the settings page containing sign-in settings.
 */
import 'chrome://resources/cr_elements/cr_icon/cr_icon.js';
import 'chrome://resources/cr_elements/cr_button/cr_button.js';
import 'chrome://resources/cr_elements/cr_icon_button/cr_icon_button.js';
import 'chrome://resources/cr_elements/cr_link_row/cr_link_row.js';
import 'chrome://resources/cr_elements/cr_toast/cr_toast.js';
import 'chrome://resources/cr_elements/icons.html.js';
import 'chrome://resources/cr_elements/policy/cr_policy_indicator.js';
import 'chrome://resources/cr_elements/cr_shared_style.css.js';
import 'chrome://resources/cr_elements/cr_shared_vars.css.js';
import '../controls/settings_toggle_button.js';
// 
import './sync_account_control.js';
// 
import '../icons.html.js';
import '../settings_page/settings_section.js';
import '../settings_shared.css.js';
import { ProfileInfoBrowserProxyImpl } from '/shared/settings/people_page/profile_info_browser_proxy.js';
import { ChromeSigninAccessPoint, SignedInState, StatusAction, SyncBrowserProxyImpl } from '/shared/settings/people_page/sync_browser_proxy.js';
import { WebUiListenerMixin } from 'chrome://resources/cr_elements/web_ui_listener_mixin.js';
import { assert, assertNotReached } from 'chrome://resources/js/assert.js';
import { focusWithoutInk } from 'chrome://resources/js/focus_without_ink.js';
import { getImage } from 'chrome://resources/js/icon.js';
import { OpenWindowProxyImpl } from 'chrome://resources/js/open_window_proxy.js';
import { isChromeOS } from 'chrome://resources/js/platform.js';
import { PolymerElement } from 'chrome://resources/polymer/v3_0/polymer/polymer_bundled.min.js';
import { loadTimeData } from '../i18n_setup.js';
import { routes } from '../route.js';
import { RouteObserverMixin, Router } from '../router.js';
import { SettingsViewMixin } from '../settings_page/settings_view_mixin.js';
// </if>
// 
import { getTemplate } from './people_page.html.js';
// 
const SettingsPeoplePageElementBase = SettingsViewMixin(RouteObserverMixin(WebUiListenerMixin(PolymerElement)));
// 
// 
export class SettingsPeoplePageElement extends SettingsPeoplePageElementBase {
    static get is() {
        return 'settings-people-page';
    }
    static get template() {
        return getTemplate();
    }
    static get properties() {
        return {
            /**
             * Preferences state.
             */
            prefs: {
                type: Object,
                notify: true,
            },
            /**
             * This flag is used to conditionally show a set of new sign-in UIs to the
             * profiles that have been migrated to be consistent with the web
             * sign-ins.
             * TODO(tangltom): In the future when all profiles are completely
             * migrated, this should be removed, and UIs hidden behind it should
             * become default.
             */
            signinAllowed_: {
                type: Boolean,
                value() {
                    return loadTimeData.getBoolean('signinAllowed');
                },
            },
            /**
             * This property stores whether the profile is a Dasherless profiles,
             * which is associated with a non-Dasher account. Some UIs related to
             * sign in and sync service will be different because they are not
             * available for these profiles.
             */
            isDasherlessProfile_: {
                type: Boolean,
                value() {
                    return loadTimeData.getBoolean('isDasherlessProfile');
                },
            },
            // 
            /**
             * Stored accounts to the system, supplied by SyncBrowserProxy.
             */
            storedAccounts: Object,
            // 
            /**
             * The current sync status, supplied by SyncBrowserProxy.
             */
            syncStatus: Object,
            /**
             * Authentication token provided by settings-lock-screen.
             */
            authToken_: {
                type: String,
                value: '',
            },
            /**
             * The currently selected profile icon URL. May be a data URL.
             */
            profileIconUrl_: String,
            /**
             * Whether the profile row is clickable. The behavior depends on the
             * platform.
             */
            isProfileActionable_: {
                type: Boolean,
                value() {
                    if (!isChromeOS) {
                        // Opens profile manager.
                        return true;
                    }
                    // Post-SplitSettings links out to account manager if it is available.
                    return loadTimeData.getBoolean('isAccountManagerEnabled');
                },
                readOnly: true,
            },
            /**
             * The current profile name.
             */
            profileName_: String,
            primaryAccountName_: String,
            primaryAccountEmail_: String,
            primaryAccountIconUrl_: String,
            replaceSyncPromosWithSignInPromos_: {
                type: Boolean,
                value: () => loadTimeData.getBoolean('replaceSyncPromosWithSignInPromos'),
            },
            // 
            shouldShowGoogleAccount_: {
                type: Boolean,
                value: false,
                computed: 'computeShouldShowGoogleAccount_(storedAccounts, syncStatus,' +
                    'storedAccounts.length, syncStatus.signedIn, syncStatus.hasError)',
            },
            showImportDataDialog_: {
                type: Boolean,
                value: false,
            },
            showSignoutDialog_: Boolean,
            // 
            // Exposes ChromeSigninAccessPoint enum to HTML bindings.
            accessPointEnum_: {
                type: Object,
                value: ChromeSigninAccessPoint,
            },
        };
    }
    // 
    syncBrowserProxy_ = SyncBrowserProxyImpl.getInstance();
    connectedCallback() {
        super.connectedCallback();
        let useProfileNameAndIcon = true;
        // 
        if (useProfileNameAndIcon) {
            ProfileInfoBrowserProxyImpl.getInstance().getProfileInfo().then(this.handleProfileInfo_.bind(this));
            this.addWebUiListener('profile-info-changed', this.handleProfileInfo_.bind(this));
        }
        this.syncBrowserProxy_.getSyncStatus().then(this.handleSyncStatus_.bind(this));
        this.addWebUiListener('sync-status-changed', this.handleSyncStatus_.bind(this));
        // 
        this.syncBrowserProxy_.getStoredAccounts().then(this.handleStoredAccounts_.bind(this));
        this.addWebUiListener('stored-accounts-updated', this.handleStoredAccounts_.bind(this));
        this.addWebUiListener('sync-settings-saved', () => {
            this.$.toast.show();
        });
        // 
    }
    // 
    currentRouteChanged(newRoute, oldRoute) {
        super.currentRouteChanged(newRoute, oldRoute);
        this.showImportDataDialog_ =
            Router.getInstance().getCurrentRoute() === routes.IMPORT_DATA;
        if (Router.getInstance().getCurrentRoute() === routes.SIGN_OUT) {
            // If the sync status has not been fetched yet, optimistically display
            // the sign-out dialog. There is another check when the sync status is
            // fetched. The dialog will be closed when the user is not signed in.
            if (this.syncStatus && !this.isSyncing_()) {
                Router.getInstance().navigateToPreviousRoute();
            }
            else {
                this.showSignoutDialog_ = true;
            }
        }
    }
    // 
    /**
     * Handler for when the profile's icon and name is updated.
     */
    handleProfileInfo_(info) {
        this.profileName_ = info.name;
        /**
         * Extract first frame from image by creating a single frame PNG using
         * url as input if base64 encoded and potentially animated.
         */
        // 
        this.profileIconUrl_ = info.iconUrl;
    }
    // 
    /**
     * Handler for when the sync state is pushed from the browser.
     */
    handleSyncStatus_(syncStatus) {
        // 
        // 
        // Sign-in impressions should be recorded only if the sign-in promo is
        // shown. They should be recorder only once, the first time
        // |this.syncStatus| is set.
        // With `ReplaceSyncPromosWithSignInPromos`, this is not a sign in promo, so
        // we should not record.
        const shouldRecordSigninImpression = !this.syncStatus && syncStatus &&
            this.signinAllowed_ && !this.isSyncing_() &&
            !this.replaceSyncPromosWithSignInPromos_;
        this.syncStatus = syncStatus;
        if (shouldRecordSigninImpression && !this.shouldShowSyncAccountControl_()) {
            // SyncAccountControl records the impressions user actions.
            chrome.metricsPrivate.recordUserAction('Signin_Impression_FromSettings');
        }
        // 
    }
    // 
    computeShouldShowGoogleAccount_() {
        if (this.storedAccounts === undefined || this.syncStatus === undefined) {
            return false;
        }
        if (this.syncStatus.hasError &&
            this.syncStatus.statusAction !== StatusAction.UPGRADE_CLIENT &&
            this.syncStatus.statusAction !==
                StatusAction.SHOW_BOOKMARKS_LIMIT_HELP_ARTICLE) {
            return false;
        }
        return (!this.replaceSyncPromosWithSignInPromos_ &&
            this.storedAccounts.length > 0) ||
            this.isSyncing_();
    }
    // 
    onProfileClick_() {
        // 
        // 
        Router.getInstance().navigateTo(routes.MANAGE_PROFILE);
        // 
    }
    // 
    onDisconnectDialogClosed_() {
        this.showSignoutDialog_ = false;
        if (Router.getInstance().getCurrentRoute() === routes.SIGN_OUT) {
            Router.getInstance().navigateToPreviousRoute();
        }
    }
    // 
    onSyncClick_() {
        // Users can go to sync subpage regardless of sync status.
        Router.getInstance().navigateTo(routes.SYNC);
    }
    onAccountClick_() {
        Router.getInstance().navigateTo(routes.ACCOUNT);
    }
    onGoogleServicesClick_() {
        Router.getInstance().navigateTo(routes.GOOGLE_SERVICES);
    }
    shouldLinkToAccountSettingsPage_() {
        return this.replaceSyncPromosWithSignInPromos_ && !!this.syncStatus &&
            this.syncStatus.signedInState === SignedInState.SIGNED_IN;
    }
    // 
    onImportDataClick_() {
        Router.getInstance().navigateTo(routes.IMPORT_DATA);
    }
    onImportDataDialogClosed_() {
        Router.getInstance().navigateToPreviousRoute();
        focusWithoutInk(this.$.importDataDialogTrigger);
    }
    shouldLinkToProfileRow_() {
        return !this.shouldShowSyncAccountControl_() &&
            !this.shouldLinkToAccountSettingsPage_();
    }
    shouldShowSyncAccountControl_() {
        if (this.syncStatus === undefined) {
            return false;
        }
        return !!this.syncStatus.syncSystemEnabled && this.signinAllowed_ &&
            !this.shouldLinkToAccountSettingsPage_();
    }
    handleStoredAccounts_(accounts) {
        this.storedAccounts = accounts;
        // The user might not have any GAIA accounts (e.g. signed out). In this case
        // the link row to the account settings page does not exist, so there's
        // nothing to do.
        if (accounts.length === 0) {
            return;
        }
        this.primaryAccountName_ = accounts[0].fullName;
        this.primaryAccountEmail_ = accounts[0].email;
        this.primaryAccountIconUrl_ = accounts[0].avatarImage;
    }
    // 
    /**
     * Open URL for managing your Google Account.
     */
    openGoogleAccount_() {
        OpenWindowProxyImpl.getInstance().openUrl(loadTimeData.getString('googleAccountUrl'));
        chrome.metricsPrivate.recordUserAction('ManageGoogleAccount_Clicked');
    }
    /**
     * @return A CSS image-set for multiple scale factors.
     */
    getIconImageSet_(iconUrl) {
        if (!iconUrl) {
            return '';
        }
        return getImage(iconUrl);
    }
    isSyncing_() {
        return !!this.syncStatus &&
            this.syncStatus.signedInState === SignedInState.SYNCING;
    }
    getSyncAndNonPersonalizedServicesSubtext_() {
        // 
        return '';
    }
    shouldHideSyncSetupLinkRow_() {
        return this.replaceSyncPromosWithSignInPromos_ &&
            (!this.syncStatus ||
                this.syncStatus.signedInState !== SignedInState.SYNCING);
    }
    getAccountRowSubtitle_() {
        if (this.syncStatus && this.syncStatus.statusText) {
            if (this.syncStatus.statusAction === StatusAction.ENTER_PASSPHRASE) {
                return loadTimeData.substituteString(this.syncStatus.statusText, this.primaryAccountEmail_);
            }
            if (this.syncStatus.statusAction ===
                StatusAction.SHOW_BOOKMARKS_LIMIT_HELP_ARTICLE) {
                return this.syncStatus.statusText;
            }
        }
        return this.primaryAccountEmail_;
    }
    // SettingsViewMixin implementation.
    getFocusConfig() {
        const map = new Map();
        if (routes.SYNC) {
            map.set(routes.SYNC.path, '#sync-setup');
        }
        if (routes.ACCOUNT) {
            map.set(routes.ACCOUNT.path, '#account-subpage-row');
        }
        if (routes.GOOGLE_SERVICES) {
            map.set(routes.GOOGLE_SERVICES.path, '#google-services');
        }
        // 
        if (routes.MANAGE_PROFILE) {
            map.set(routes.MANAGE_PROFILE.path, loadTimeData.getBoolean('signinAllowed') ?
                '#edit-profile' :
                '#profile-row .subpage-arrow');
        }
        // 
        return map;
    }
    // SettingsViewMixin implementation.
    getAssociatedControlFor(childViewId) {
        const ids = [
            'sync', 'syncControls', 'account', 'googleServices',
            // 
            'manageProfile',
            // 
        ];
        assert(ids.includes(childViewId));
        let triggerId = null;
        switch (childViewId) {
            case 'sync':
            case 'syncControls':
                triggerId = 'sync-setup';
                break;
            case 'account':
                assert(loadTimeData.getBoolean('replaceSyncPromosWithSignInPromos'));
                triggerId = 'account-subpage-row';
                break;
            case 'googleServices':
                assert(loadTimeData.getBoolean('replaceSyncPromosWithSignInPromos'));
                triggerId = 'google-services';
                break;
            // 
            case 'manageProfile':
                triggerId = this.signinAllowed_ ? 'edit-profile' : 'profile-row';
                break;
            // 
            default:
                assertNotReached();
        }
        assert(triggerId);
        const control = this.shadowRoot.querySelector(`#${triggerId}`);
        assert(control, `Failed to find associated control for child '${childViewId}'`);
        return control;
    }
}
customElements.define(SettingsPeoplePageElement.is, SettingsPeoplePageElement);
