Commit 9fb0d426 authored by Wenyu Fu's avatar Wenyu Fu Committed by Chromium LUCI CQ

[CCTToSFRE] Announce privacy disclaimer and extend delay

Announce the privacy disclaimer when skipping ToS by policy. Extend the
delay for exit to let screenreader to finish the announcement (English)
similar to SnackbarManager.

Change-Id: Iaee2c5dffb131311e89a6cdbebef2221ecbaea87
Bug: 1128158
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2568257
Commit-Queue: Wenyu Fu <wenyufu@chromium.org>
Reviewed-by: default avatarTheresa  <twellington@chromium.org>
Reviewed-by: default avatarSky Malice <skym@chromium.org>
Cr-Commit-Position: refs/heads/master@{#833374}
parent b4ab7689
...@@ -16,13 +16,15 @@ import org.chromium.base.annotations.NativeMethods; ...@@ -16,13 +16,15 @@ import org.chromium.base.annotations.NativeMethods;
import org.chromium.chrome.browser.metrics.UmaSessionStats; import org.chromium.chrome.browser.metrics.UmaSessionStats;
import org.chromium.chrome.browser.preferences.ChromePreferenceKeys; import org.chromium.chrome.browser.preferences.ChromePreferenceKeys;
import org.chromium.chrome.browser.preferences.SharedPreferencesManager; import org.chromium.chrome.browser.preferences.SharedPreferencesManager;
import org.chromium.chrome.browser.util.ChromeAccessibilityUtil;
import org.chromium.components.signin.AccountManagerFacade; import org.chromium.components.signin.AccountManagerFacade;
import org.chromium.components.signin.AccountManagerFacadeProvider; import org.chromium.components.signin.AccountManagerFacadeProvider;
/** Provides first run related utility functions. */ /** Provides first run related utility functions. */
public class FirstRunUtils { public class FirstRunUtils {
private static Boolean sHasGoogleAccountAuthenticator; private static Boolean sHasGoogleAccountAuthenticator;
static final int SKIP_TOS_EXIT_DELAY_MS = 1000; private static final int DEFAULT_SKIP_TOS_EXIT_DELAY_MS = 1000;
private static final int A11Y_DELAY_FACTOR = 2;
/** /**
* Synchronizes first run native and Java preferences. * Synchronizes first run native and Java preferences.
...@@ -121,6 +123,22 @@ public class FirstRunUtils { ...@@ -121,6 +123,22 @@ public class FirstRunUtils {
return FirstRunUtilsJni.get().getCctTosDialogEnabled(); return FirstRunUtilsJni.get().getCctTosDialogEnabled();
} }
/**
* The the number of ms delay before exiting FRE with policy. By default the delay would be
* {@link #DEFAULT_SKIP_TOS_EXIT_DELAY_MS}, while in a11y mode it will be extended by a factor
* of {@link #A11Y_DELAY_FACTOR}. This is intended to avoid screen reader being interrupted, but
* it is likely not going to work perfectly for all languages.
*
* @return The number of ms delay before exiting FRE with policy.
*/
public static int getSkipTosExitDelayMs() {
int durationMs = DEFAULT_SKIP_TOS_EXIT_DELAY_MS;
if (ChromeAccessibilityUtil.get().isTouchExplorationEnabled()) {
durationMs *= A11Y_DELAY_FACTOR;
}
return durationMs;
}
@NativeMethods @NativeMethods
public interface Natives { public interface Natives {
boolean getFirstRunEulaAccepted(); boolean getFirstRunEulaAccepted();
......
...@@ -262,7 +262,7 @@ public class LightweightFirstRunActivity ...@@ -262,7 +262,7 @@ public class LightweightFirstRunActivity
mExitFreRunnable = null; mExitFreRunnable = null;
}; };
mHandler = new Handler(ThreadUtils.getUiThreadLooper()); mHandler = new Handler(ThreadUtils.getUiThreadLooper());
mHandler.postDelayed(mExitFreRunnable, FirstRunUtils.SKIP_TOS_EXIT_DELAY_MS); mHandler.postDelayed(mExitFreRunnable, FirstRunUtils.getSkipTosExitDelayMs());
} }
private void exitLightweightFirstRun() { private void exitLightweightFirstRun() {
......
...@@ -10,6 +10,7 @@ import android.os.Handler; ...@@ -10,6 +10,7 @@ import android.os.Handler;
import android.os.SystemClock; import android.os.SystemClock;
import android.view.View; import android.view.View;
import android.view.accessibility.AccessibilityEvent; import android.view.accessibility.AccessibilityEvent;
import android.widget.TextView;
import androidx.annotation.NonNull; import androidx.annotation.NonNull;
...@@ -66,7 +67,7 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport ...@@ -66,7 +67,7 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport
private boolean mViewCreated; private boolean mViewCreated;
private View mLoadingSpinnerContainer; private View mLoadingSpinnerContainer;
private LoadingView mLoadingSpinner; private LoadingView mLoadingSpinner;
private View mPrivacyDisclaimer; private TextView mPrivacyDisclaimer;
private SkipTosDialogPolicyListener mSkipTosDialogPolicyListener; private SkipTosDialogPolicyListener mSkipTosDialogPolicyListener;
private final OneshotSupplierImpl<PolicyService> mPolicyServiceProvider = private final OneshotSupplierImpl<PolicyService> mPolicyServiceProvider =
new OneshotSupplierImpl<>(); new OneshotSupplierImpl<>();
...@@ -122,7 +123,7 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport ...@@ -122,7 +123,7 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport
} else if (mSkipTosDialogPolicyListener.get()) { } else if (mSkipTosDialogPolicyListener.get()) {
// Skip the FRE if we know dialog is disabled by policy. // Skip the FRE if we know dialog is disabled by policy.
setTosAndUmaVisible(false); setTosAndUmaVisible(false);
exitCctFirstRun(); exitCctFirstRun(/*shiftA11yFocus*/ false);
} }
} }
...@@ -155,7 +156,7 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport ...@@ -155,7 +156,7 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport
boolean hasAccessibilityFocus = mLoadingSpinnerContainer.isAccessibilityFocused(); boolean hasAccessibilityFocus = mLoadingSpinnerContainer.isAccessibilityFocused();
mLoadingSpinnerContainer.setVisibility(View.GONE); mLoadingSpinnerContainer.setVisibility(View.GONE);
if (mSkipTosDialogPolicyListener.get()) { if (mSkipTosDialogPolicyListener.get()) {
exitCctFirstRun(); exitCctFirstRun(hasAccessibilityFocus);
} else { } else {
// Else, show the UMA as the loading spinner is GONE. // Else, show the UMA as the loading spinner is GONE.
setTosAndUmaVisible(true); setTosAndUmaVisible(true);
...@@ -170,18 +171,26 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport ...@@ -170,18 +171,26 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport
if (mViewCreated) mLoadingSpinner.hideLoadingUI(); if (mViewCreated) mLoadingSpinner.hideLoadingUI();
} }
private void exitCctFirstRun() { private void exitCctFirstRun(boolean shiftA11yFocus) {
// TODO(crbug.com/1108582): Save a shared pref indicating Enterprise CCT FRE is complete, // TODO(crbug.com/1108582): Save a shared pref indicating Enterprise CCT FRE is complete,
// and skip waiting for future cold starts. // and skip waiting for future cold starts.
Log.d(TAG, "TosAndUmaFirstRunFragmentWithEnterpriseSupport finished."); Log.d(TAG, "TosAndUmaFirstRunFragmentWithEnterpriseSupport finished.");
mPrivacyDisclaimer.setVisibility(View.VISIBLE); mPrivacyDisclaimer.setVisibility(View.VISIBLE);
mPrivacyDisclaimer.sendAccessibilityEvent(AccessibilityEvent.TYPE_VIEW_FOCUSED);
// If the screen reader focus was on the loading spinner, to avoid the focus get lost from
// the screen, shift the focus to the disclaimer instead. Otherwise, announce the disclaimer
// without shifting the focus as it is not necessary.
if (shiftA11yFocus) {
mPrivacyDisclaimer.sendAccessibilityEvent(AccessibilityEvent.TYPE_VIEW_FOCUSED);
} else {
mPrivacyDisclaimer.announceForAccessibility(mPrivacyDisclaimer.getText());
}
mExitFreRunnable = () -> { mExitFreRunnable = () -> {
getPageDelegate().exitFirstRun(); getPageDelegate().exitFirstRun();
mExitFreRunnable = null; mExitFreRunnable = null;
}; };
mHandler = new Handler(ThreadUtils.getUiThreadLooper()); mHandler = new Handler(ThreadUtils.getUiThreadLooper());
mHandler.postDelayed(mExitFreRunnable, FirstRunUtils.SKIP_TOS_EXIT_DELAY_MS); mHandler.postDelayed(mExitFreRunnable, FirstRunUtils.getSkipTosExitDelayMs());
} }
} }
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment