This is an automated email from the git hooks/post-receive script.
pierov pushed a commit to branch geckoview-99.0.1-11.0-1 in repository tor-browser.
commit df422c169ae41f44cb2a5df6534073a5830d7df6 Author: Daisuke Akatsuka daisuke@birchill.co.jp AuthorDate: Fri Jan 7 21:33:03 2022 +0000
Bug 1745026 - Part 2: Update messages and UI by Nimbus. r=adw,flod, a=dsmith
Differential Revision: https://phabricator.services.mozilla.com/D133993 --- browser/components/urlbar/UrlbarPrefs.jsm | 3 + browser/components/urlbar/UrlbarQuickSuggest.jsm | 11 +- .../components/urlbar/content/firefoxSuggest.ftl | 94 ++++- .../urlbar/content/quicksuggestOnboarding.css | 152 ++++++-- .../urlbar/content/quicksuggestOnboarding.html | 51 ++- .../urlbar/content/quicksuggestOnboarding.js | 181 ++++++++- .../browser/browser_quicksuggest_configuration.js | 84 ---- .../browser_quicksuggest_onboardingDialog.js | 421 ++++++++++++++++++++- toolkit/components/nimbus/FeatureManifest.yaml | 4 + 9 files changed, 817 insertions(+), 184 deletions(-)
diff --git a/browser/components/urlbar/UrlbarPrefs.jsm b/browser/components/urlbar/UrlbarPrefs.jsm index 1f31ed92de7d4..93fbb4f9cc297 100644 --- a/browser/components/urlbar/UrlbarPrefs.jsm +++ b/browser/components/urlbar/UrlbarPrefs.jsm @@ -247,6 +247,9 @@ const PREF_URLBAR_DEFAULTS = new Map([ // Whether the user has opted in to data collection for quick suggest. ["quicksuggest.dataCollection.enabled", false],
+ // The version of dialog user saw. + ["quicksuggest.onboardingDialogVersion", 0], + // Whether to show the quick suggest onboarding dialog. ["quicksuggest.shouldShowOnboardingDialog", true],
diff --git a/browser/components/urlbar/UrlbarQuickSuggest.jsm b/browser/components/urlbar/UrlbarQuickSuggest.jsm index d32a872cf8154..0d448653563f7 100644 --- a/browser/components/urlbar/UrlbarQuickSuggest.jsm +++ b/browser/components/urlbar/UrlbarQuickSuggest.jsm @@ -40,6 +40,8 @@ const NONSPONSORED_IAB_CATEGORIES = new Set(["5 - Education"]); const FEATURE_AVAILABLE = "quickSuggestEnabled"; const SEEN_DIALOG_PREF = "quicksuggest.showedOnboardingDialog"; const RESTARTS_PREF = "quicksuggest.seenRestarts"; +const DIALOG_VERSION_PREF = "quicksuggest.onboardingDialogVersion"; +const DIALOG_VARIATION_PREF = "quickSuggestOnboardingDialogVariation";
// Values returned by the onboarding dialog depending on the user's response. // These values are used in telemetry events, so be careful about changing them. @@ -255,12 +257,19 @@ class Suggestions { }; win.addEventListener("keydown", keyListener, true);
- let params = { choice: undefined }; + let variationType; + try { + // An error happens if the pref is not in user prefs. + variationType = UrlbarPrefs.get(DIALOG_VARIATION_PREF).toLowerCase(); + } catch (e) {} + + let params = { choice: undefined, variationType }; await win.gDialogBox.open(ONBOARDING_URI, params);
win.removeEventListener("keydown", keyListener, true);
UrlbarPrefs.set(SEEN_DIALOG_PREF, true); + UrlbarPrefs.set(DIALOG_VERSION_PREF, 1);
// Record the user's opt-in choice on the user branch. This pref is sticky, // so it will retain its user-branch value regardless of what the particular diff --git a/browser/components/urlbar/content/firefoxSuggest.ftl b/browser/components/urlbar/content/firefoxSuggest.ftl index 712d89ce77065..15b9f4b9d6d3a 100644 --- a/browser/components/urlbar/content/firefoxSuggest.ftl +++ b/browser/components/urlbar/content/firefoxSuggest.ftl @@ -85,22 +85,80 @@ addressbar-firefox-suggest-info-sponsored = Based on your selection, you’ll re # Data collection: on addressbar-firefox-suggest-info-data = Based on your selection, you won’t receive suggestions from the web or sponsored sites. We will process your search query data to develop the { -firefox-suggest-brand-name } feature.
-## These strings are used in the introduction pane of the Firefox Suggest online -## onboarding opt-in dialog. - -firefox-suggest-onboarding-introduction-title = Make sure you’ve got our newest search experience -firefox-suggest-onboarding-introduction-button = Next - -## These strings are used in the main pane of the Firefox Suggest online -## onboarding opt-in dialog. Options are displayed as radio buttons with a label -## followed by a description. - -firefox-suggest-onboarding-main-title = We’re building a richer search experience -firefox-suggest-onboarding-main-description = Finding the best of the web should be easier. Allowing { -vendor-short-name } to process your search queries will help develop our { -firefox-suggest-brand-name } feature, while keeping your privacy top of mind. -firefox-suggest-onboarding-main-accept-option-label = - Allow improved search experience. <a data-l10n-name="firefox-suggest-onboarding-learn-more-link">Learn more</a> -firefox-suggest-onboarding-main-accept-option-description = Include suggestions for a more curated web experience. -firefox-suggest-onboarding-main-reject-option-label = Keep my default experience. -firefox-suggest-onboarding-main-reject-option-description = Don’t allow search query processing. +## Used as title on the introduction pane. The text can be formatted to span +## multiple lines as needed (line breaks are significant). + +firefox-suggest-onboarding-introduction-title-1 = + Make sure you’ve got our latest + search experience +firefox-suggest-onboarding-introduction-title-2 = + We’re building a better search experience — + one you can trust +firefox-suggest-onboarding-introduction-title-3 = + We’re building a better way to find what + you’re looking for on the web +firefox-suggest-onboarding-introduction-title-4 = + A faster search experience is in the works +firefox-suggest-onboarding-introduction-title-5 = + Together, we can create the kind of search + experience the Internet deserves +firefox-suggest-onboarding-introduction-title-6 = + Meet { -firefox-suggest-brand-name }, the next + evolution in search +firefox-suggest-onboarding-introduction-title-7 = + Find the best of the web, faster. + +## + +firefox-suggest-onboarding-introduction-next-button-1 = Find out how +firefox-suggest-onboarding-introduction-next-button-2 = Find out more + +## Used as title on the main pane. The text can be formatted to span +## multiple lines as needed (line breaks are significant). + +firefox-suggest-onboarding-main-title-1 = + We’re building a richer search experience +firefox-suggest-onboarding-main-title-2 = + Help us guide the way to the + best of the Internet +firefox-suggest-onboarding-main-title-3 = + A richer, smarter search experience +firefox-suggest-onboarding-main-title-4 = + Finding the best of the web, faster +firefox-suggest-onboarding-main-title-5 = + We’re building a better search experience — + you can help +firefox-suggest-onboarding-main-title-6 = + It’s time to think outside the search engine +firefox-suggest-onboarding-main-title-7 = + We’re building a smarter search experience — + one you can trust +firefox-suggest-onboarding-main-title-8 = + Finding the best of the web should be + simpler and more secure. + +## + +firefox-suggest-onboarding-main-description-1 = Allowing { -vendor-short-name } to process your search queries means you’re helping us create smarter, more relevant search suggestions. And, as always, we’ll keep your privacy top of mind. +firefox-suggest-onboarding-main-description-2 = When you allow { -vendor-short-name } to process your search queries, you’re helping build a better { -firefox-suggest-brand-name } for everyone. And, as always, we’ll keep your privacy top of mind. +firefox-suggest-onboarding-main-description-3 = What if your browser helped you zero in on what you’re actually looking for? Allowing { -vendor-short-name } to process your search queries helps us create more relevant search suggestions that still keep your privacy top of mind. +firefox-suggest-onboarding-main-description-4 = You’re trying to get where you’re going on the web and get on with it. When you allow { -vendor-short-name } to process your search queries, we can help you get there faster—while keeping your privacy top of mind. +firefox-suggest-onboarding-main-description-5 = Allowing { -vendor-short-name } to process your search queries will help us create more relevant suggestions for everyone. And, as always, we’ll keep your privacy top of mind. +firefox-suggest-onboarding-main-description-6 = Allowing { -vendor-short-name } to process your search queries will help us create more relevant search suggestions. We’re building { -firefox-suggest-brand-name } to help you get where you’re going on the Internet while keeping your privacy in mind. +firefox-suggest-onboarding-main-description-7 = Allowing { -vendor-short-name } to process your search queries helps us create more relevant search suggestions. +firefox-suggest-onboarding-main-description-8 = Allowing { -vendor-short-name } to process your search queries helps us provide more relevant search suggestions. We don’t use this data to profile you on the web. + +firefox-suggest-onboarding-main-privacy-first = No user profiling. Privacy-first, always. + +firefox-suggest-onboarding-main-accept-option-label = Allow. <a data-l10n-name="learn-more-link">Learn more</a> + +firefox-suggest-onboarding-main-accept-option-description-1 = Help improve the { -firefox-suggest-brand-name } feature with more relevant suggestions. Your search queries will be processed. +firefox-suggest-onboarding-main-accept-option-description-2 = Recommended for people who support improving the { -firefox-suggest-brand-name } feature. Your search queries will be processed. + +firefox-suggest-onboarding-main-reject-option-label = Don’t allow. + +firefox-suggest-onboarding-main-reject-option-description-1 = Keep the default { -firefox-suggest-brand-name } experience with the strictest data-sharing controls. +firefox-suggest-onboarding-main-reject-option-description-2 = Recommended for people who prefer the strictest data-sharing controls. Keep the default experience. + firefox-suggest-onboarding-main-submit-button = Save preferences -firefox-suggest-onboarding-main-skip-link = Skip action +firefox-suggest-onboarding-main-skip-link = Not now diff --git a/browser/components/urlbar/content/quicksuggestOnboarding.css b/browser/components/urlbar/content/quicksuggestOnboarding.css index f48712037970a..5eb923f64f5d5 100644 --- a/browser/components/urlbar/content/quicksuggestOnboarding.css +++ b/browser/components/urlbar/content/quicksuggestOnboarding.css @@ -8,29 +8,42 @@ */
:root { - /* As this dialog is designed under assuming the base font size is 11px, - specify image size using current font-size. */ - --introduction-logo-width: calc(158 / 11 * 1em); - --introduction-logo-height: calc(114 / 11 * 1em); - --main-logo-width: calc(100 / 11 * 1em); - --main-logo-height: calc(64 / 11 * 1em); - /* --fixed-large-margin is constant regardless of compact mode. */ - --fixed-large-margin: 24px; + --introduction-magglass-logo-width: 176px; + --introduction-magglass-logo-height: 128px; + --introduction-firefox-logo-width: 72px; + --introduction-firefox-logo-height: 72px; + --main-magglass-logo-width: 88px; + --main-magglass-logo-height: 64px; + --main-firefox-logo-width: 50px; + --main-firefox-logo-height: 50px; + --x-large-margin: 40px; --large-margin: 24px; + --large-margin-const: 24px; --small-margin: 16px; + --small-margin-const: 16px; + --x-small-margin-const: 8px; --section-vertical-padding: 32px; --section-horizontal-padding: 64px; }
body.compact { - /* 15px is the usual font-size. */ - font-size: 13px; - --main-logo-width: calc(100 / 13 * 1em); - --main-logo-height: calc(64 / 13 * 1em); + --main-magglass-logo-width: 66px; + --main-magglass-logo-height: 48px; + --main-firefox-logo-width: 32px; + --main-firefox-logo-height: 32px; + --x-large-margin: 20px; --large-margin: 12px; --small-margin: 8px; --section-vertical-padding: 16px; --section-horizontal-padding: 32px; + + /* 15px is the non-compact font-size. */ + font-size: 13px; +} + +body, +section { + width: 536px; }
section { @@ -40,20 +53,30 @@ section { flex-direction: column; text-align: center; padding: var(--section-vertical-padding) var(--section-horizontal-padding); - width: 536px; - /* This is the natural height of the main section. */ - min-height: 587px; + /* This is the largest approximate natural height of the main section across + platforms and dialog variations, erring on the side of being slightly + larger than necessary. If you change this, also update COMPACT_MODE_HEIGHT + in the JS. */ + min-height: 650px; }
body.compact section { - /* This is the natural height of the main section in compact mode. */ - min-height: 450px; + /* This is the largest approximate natural height of the main section across + platforms and dialog variations in compact mode, erring on the side of + being slightly larger than necessary. */ + min-height: 510px; +} + +a { + cursor: pointer; + font-weight: normal; }
.title { font-size: 1.6em; font-weight: 600; line-height: 1.5; + white-space: pre-line; }
.logo { @@ -77,42 +100,95 @@ body.compact section { }
#introduction-section .logo { - background-image: url("quicksuggestOnboarding_magglass_animation.svg"); - width: var(--introduction-logo-width); - height: var(--introduction-logo-height); + background-image: url("quicksuggestOnboarding_magglass.svg"); + width: var(--introduction-magglass-logo-width); + height: var(--introduction-magglass-logo-height); margin-block-end: var(--large-margin); }
-@media (prefers-reduced-motion: reduce) { +#introduction-section .logo.firefox { + background-image: url("chrome://branding/content/about-logo.svg"); + width: var(--introduction-firefox-logo-width); + height: var(--introduction-firefox-logo-height); +} + +@media (prefers-reduced-motion: no-preference) { #introduction-section .logo { - background-image: url("quicksuggestOnboarding_magglass.svg"); + background-image: url("quicksuggestOnboarding_magglass_animation.svg"); } }
#introduction-section .title { - margin-block-end: var(--large-margin); + margin-block-end: var(--x-large-margin); +} + +#onboardingClose { + position: absolute; + top: 0; + inset-inline-end: 0; + margin: 16px; + padding: 0; + line-height: 0; + min-width: 20px; + min-height: 20px; +} + +#onboardingClose:not(.active) { + display: none; +} + +#onboardingClose img { + -moz-context-properties: fill; + fill: currentColor; }
#main-section { + display: flex; +} + +#main-section:not(.active) { display: none; }
#main-section .logo { background-image: url("quicksuggestOnboarding_magglass.svg"); - width: var(--main-logo-width); - height: var(--main-logo-height); + width: var(--main-magglass-logo-width); + height: var(--main-magglass-logo-height); margin-block-end: var(--large-margin); }
+#main-section .logo.firefox { + background-image: url("chrome://branding/content/about-logo.svg"); + width: var(--main-firefox-logo-width); + height: var(--main-firefox-logo-height); +} + #main-section .title { - margin-block-end: var(--large-margin); + margin-block: 0 var(--small-margin); +} + +#main-section .description-section { + /* The effective visual margin between the description and first option should + be --large-margin-const. Each child in the description has a bottom margin + of --small-margin, so subtract it from --large-margin-const. */ + margin-block: 0 calc(var(--large-margin-const) - var(--small-margin)); }
#main-section .description { - margin-block: 0 var(--fixed-large-margin); font-size: 1.1em; font-weight: 400; line-height: 1.6; + margin-block: 0 var(--small-margin); +} + +#main-section .privacy-first { + font-size: 1.1em; + font-weight: 700; + margin-block: 0 var(--small-margin); +} + +#main-section .privacy-first:not(.active) { + display: none; }
#main-section .option { @@ -120,8 +196,13 @@ body.compact section { border: 2px solid var(--in-content-box-info-background); display: flex; text-align: start; - padding: var(--small-margin); - width: calc(100% - (var(--small-margin) + 2px) * 2); + /* Use --small-margin-const for the horizontal padding to make the option's + horizontal padding larger than the vertical padding in compact mode. The + radio button and text are too close to the left and right edges of the + option's border otherwise. */ + padding: var(--small-margin) var(--small-margin-const); + width: 100% - calc(2 * var(--section-horizontal-padding)); + box-sizing: border-box; flex-direction: row; position: relative; } @@ -135,7 +216,7 @@ body.compact section { }
#main-section .option.reject { - margin-block-end: var(--fixed-large-margin); + margin-block-end: var(--large-margin-const); }
#main-section .option > label { @@ -176,14 +257,12 @@ body:not(.compact) #main-section .option > input { font-size: 1em; }
-#main-section a { - cursor: pointer; - font-weight: normal; +button { + margin-block-end: var(--large-margin); }
-button, -#onboardingNotNow { - margin-block-end: var(--small-margin); +#onboardingSkipLink { + margin-block-end: var(--x-small-margin-const); }
/* transition from introduction to main */ @@ -195,7 +274,6 @@ button, }
#main-section.active { - display: flex; animation: fadein 0.3s forwards; }
diff --git a/browser/components/urlbar/content/quicksuggestOnboarding.html b/browser/components/urlbar/content/quicksuggestOnboarding.html index 615e1261036ad..5e30e2891fe08 100644 --- a/browser/components/urlbar/content/quicksuggestOnboarding.html +++ b/browser/components/urlbar/content/quicksuggestOnboarding.html @@ -21,15 +21,21 @@ <body role="dialog" aria-labelledby="introduction-title"> <section id="introduction-section"> + <button id="onboardingClose" + tabindex="2" + class="ghost-button"> + <img src="chrome://global/skin/icons/close.svg" /> + </button> <span class="logo" role="presentation"></span> <h1 id="introduction-title" class="title" aria-live="polite" - data-l10n-id="firefox-suggest-onboarding-introduction-title"></h1> + data-l10n-id="firefox-suggest-onboarding-introduction-title-1"></h1> <button id="onboardingNext" class="primary" tabindex="1" - data-l10n-id="firefox-suggest-onboarding-introduction-button"></button> + data-l10n-id="firefox-suggest-onboarding-introduction-next-button-1"> + </button> <div class="pager"> <span class="current"></span> <span></span> @@ -37,27 +43,35 @@ </section> <section id="main-section"> <span class="logo" role="presentation"></span> - <h1 class="title" + <h1 id="main-title" + class="title" aria-live="polite" - data-l10n-id="firefox-suggest-onboarding-main-title"></h1> - <h2 class="description" - tabindex="-1" - data-l10n-id="firefox-suggest-onboarding-main-description"></h2> + data-l10n-id="firefox-suggest-onboarding-main-title-1"></h1> + <div class="description-section"> + <h2 id="main-description" + class="description" + tabindex="-1" + data-l10n-id="firefox-suggest-onboarding-main-description-1"></h2> + <h3 class="privacy-first" + tabindex="-1" + data-l10n-id="firefox-suggest-onboarding-main-privacy-first"></h2> + </div> <div class="option accept"> <label for="onboardingAccept"></label> <input id="onboardingAccept" type="radio" - tabindex="2" + tabindex="3" name="search-experience"></input> <div> <div class="option-label" data-l10n-id="firefox-suggest-onboarding-main-accept-option-label"> <a id="onboardingLearnMore" - tabindex="3" - data-l10n-name="firefox-suggest-onboarding-learn-more-link"></a> + tabindex="4" + data-l10n-name="learn-more-link"></a> </div> - <div class="option-description" - data-l10n-id="firefox-suggest-onboarding-main-accept-option-description"> + <div id="main-accept-option-description" + class="option-description" + data-l10n-id="firefox-suggest-onboarding-main-accept-option-description-1"> </div> </div> </div> @@ -65,24 +79,25 @@ <label for="onboardingReject"></label> <input id="onboardingReject" type="radio" - tabindex="4" + tabindex="5" name="search-experience"></input> <div> <div class="option-label" data-l10n-id="firefox-suggest-onboarding-main-reject-option-label"> </div> - <div class="option-description" - data-l10n-id="firefox-suggest-onboarding-main-reject-option-description"> + <div id="main-reject-option-description" + class="option-description" + data-l10n-id="firefox-suggest-onboarding-main-reject-option-description-1"> </div> </div> </div> <button id="onboardingSubmit" class="primary" disabled="true" - tabindex="5" + tabindex="6" data-l10n-id="firefox-suggest-onboarding-main-submit-button"></button> - <a id="onboardingNotNow" - tabindex="6" + <a id="onboardingSkipLink" + tabindex="7" data-l10n-id="firefox-suggest-onboarding-main-skip-link"></a> <div class="pager"> <span></span> diff --git a/browser/components/urlbar/content/quicksuggestOnboarding.js b/browser/components/urlbar/content/quicksuggestOnboarding.js index 7c240e69bd847..2e5d9973910f9 100644 --- a/browser/components/urlbar/content/quicksuggestOnboarding.js +++ b/browser/components/urlbar/content/quicksuggestOnboarding.js @@ -8,13 +8,142 @@ const { ONBOARDING_CHOICE } = ChromeUtils.import( "resource:///modules/UrlbarQuickSuggest.jsm" );
-// Number of height pixels to switch to compact mode to avoid showing scrollbars -// on the non-compact mode. This is based on the natural height of the full-size -// section height 587px + padding-block-start 32px + padding-block-end 32px + -// the approximate height of the tab bar 44px. -const COMPACT_MODE_HEIGHT = 587 + 32 * 2 + 44; +const VARIATION_MAP = { + a: { + l10nUpdates: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-1", + "main-title": "firefox-suggest-onboarding-main-title-1", + "main-description": "firefox-suggest-onboarding-main-description-1", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-1", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-1", + }, + }, + b: { + introductionCloseButton: true, + l10nUpdates: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-2", + "main-title": "firefox-suggest-onboarding-main-title-2", + "main-description": "firefox-suggest-onboarding-main-description-2", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-1", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-1", + }, + }, + c: { + logoType: "firefox", + l10nUpdates: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-3", + "main-title": "firefox-suggest-onboarding-main-title-3", + "main-description": "firefox-suggest-onboarding-main-description-3", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-1", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-1", + }, + }, + d: { + introductionCloseButton: true, + l10nUpdates: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-4", + "main-title": "firefox-suggest-onboarding-main-title-4", + "main-description": "firefox-suggest-onboarding-main-description-4", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-2", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-2", + }, + }, + e: { + logoType: "firefox", + introductionCloseButton: true, + l10nUpdates: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-5", + "main-title": "firefox-suggest-onboarding-main-title-5", + "main-description": "firefox-suggest-onboarding-main-description-5", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-2", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-2", + }, + }, + f: { + introductionCloseButton: true, + l10nUpdates: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-2", + "introduction-title": "firefox-suggest-onboarding-introduction-title-6", + "main-title": "firefox-suggest-onboarding-main-title-6", + "main-description": "firefox-suggest-onboarding-main-description-6", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-2", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-2", + }, + }, + g: { + mainPrivacyFirst: true, + l10nUpdates: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-7", + "main-title": "firefox-suggest-onboarding-main-title-7", + "main-description": "firefox-suggest-onboarding-main-description-7", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-2", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-2", + }, + }, + h: { + logoType: "firefox", + l10nUpdates: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-2", + "main-title": "firefox-suggest-onboarding-main-title-8", + "main-description": "firefox-suggest-onboarding-main-description-8", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-1", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-1", + }, + }, +}; + +// If the window height is smaller than this value when the dialog opens, then +// the dialog will open in compact mode. The dialog will not change modes while +// it's open even if the window height changes. +const COMPACT_MODE_HEIGHT = + 650 + // section min-height (non-compact mode) + 2 * 32 + // 2 * --section-vertical-padding (non-compact mode) + 44; // approximate height of the browser window's tab bar + +// Used for test only. If links or buttons may be clicked or typed Key_Enter +// while translating l10n, cannot capture the events since not register listeners +// yet. To avoid the issue, add this flag to know the listeners are ready. +let resolveOnboardingReady; +window._quicksuggestOnboardingReady = new Promise(r => { + resolveOnboardingReady = r; +}); + +document.addEventListener("DOMContentLoaded", async () => { + await document.l10n.ready; + + const variation = VARIATION_MAP[window.arguments[0].variationType]; + if (variation) { + document.l10n.pauseObserving(); + try { + await applyVariation(variation); + } finally { + document.l10n.resumeObserving(); + } + }
-document.addEventListener("DOMContentLoaded", () => { addSubmitListener(document.getElementById("onboardingNext"), () => { document.getElementById("introduction-section").classList.add("inactive"); document.getElementById("main-section").classList.add("active"); @@ -23,7 +152,7 @@ document.addEventListener("DOMContentLoaded", () => { window.arguments[0].choice = ONBOARDING_CHOICE.LEARN_MORE; window.close(); }); - addSubmitListener(document.getElementById("onboardingNotNow"), () => { + addSubmitListener(document.getElementById("onboardingSkipLink"), () => { window.arguments[0].choice = ONBOARDING_CHOICE.NOT_NOW; window.close(); }); @@ -68,9 +197,47 @@ document.addEventListener("DOMContentLoaded", () => { if (window.outerHeight < COMPACT_MODE_HEIGHT) { document.body.classList.add("compact"); } + + resolveOnboardingReady(); });
+async function applyVariation(variation) { + if (variation.introductionCloseButton) { + const onboardingClose = document.getElementById("onboardingClose"); + onboardingClose.classList.add("active"); + addSubmitListener(onboardingClose, () => { + window.arguments[0].choice = ONBOARDING_CHOICE.NOT_NOW; + window.close(); + }); + } + + if (variation.logoType) { + for (const logo of document.querySelectorAll(".logo")) { + logo.classList.add(variation.logoType); + } + } + + if (variation.mainPrivacyFirst) { + const label = document.querySelector("#main-section .privacy-first"); + label.classList.add("active"); + } + + if (variation.l10nUpdates) { + const translatedElements = []; + for (const [id, newL10N] of Object.entries(variation.l10nUpdates)) { + const element = document.getElementById(id); + document.l10n.setAttributes(element, newL10N); + translatedElements.push(element); + } + await document.l10n.translateElements(translatedElements); + } +} + function addSubmitListener(element, listener) { + if (!element) { + console.warn("Element is null on addSubmitListener"); + return; + } element.addEventListener("click", listener); element.addEventListener("keydown", e => { if (e.keyCode == e.DOM_VK_RETURN) { diff --git a/browser/components/urlbar/tests/quicksuggest/browser/browser_quicksuggest_configuration.js b/browser/components/urlbar/tests/quicksuggest/browser/browser_quicksuggest_configuration.js index 40f42748d8b52..6cdc90c724c4a 100644 --- a/browser/components/urlbar/tests/quicksuggest/browser/browser_quicksuggest_configuration.js +++ b/browser/components/urlbar/tests/quicksuggest/browser/browser_quicksuggest_configuration.js @@ -24,90 +24,6 @@ add_task(async function init() { await QuickSuggestTestUtils.ensureQuickSuggestInit(); });
-// The default is to wait for no browser restarts to show the onboarding dialog -// on the first restart. This tests that we can override it by configuring the -// `showOnboardingDialogOnNthRestart` -add_task(async function test_override_wait_after_n_restarts() { - // Set up non-Nimbus prefs related to showing the onboarding. - await SpecialPowers.pushPrefEnv({ - set: [ - ["browser.urlbar.quicksuggest.showedOnboardingDialog", false], - ["browser.urlbar.quicksuggest.seenRestarts", 0], - ], - }); - - await QuickSuggestTestUtils.withExperiment({ - valueOverrides: { - quickSuggestScenario: "online", - // Wait for 1 browser restart - quickSuggestShowOnboardingDialogAfterNRestarts: 1, - }, - callback: async () => { - let prefPromise = TestUtils.waitForPrefChange( - "browser.urlbar.quicksuggest.showedOnboardingDialog", - value => value === true - ).then(() => info("Saw pref change")); - - // Simulate 2 restarts. this function is only called by BrowserGlue - // on startup, the first restart would be where MR1 was shown then - // we will show onboarding the 2nd restart after that. - info("Simulating first restart"); - await UrlbarQuickSuggest.maybeShowOnboardingDialog(); - - info("Simulating second restart"); - const dialogPromise = BrowserTestUtils.promiseAlertDialogOpen( - null, - ONBOARDING_URI, - { isSubDialog: true } - ); - const maybeShowPromise = UrlbarQuickSuggest.maybeShowOnboardingDialog(); - const win = await dialogPromise; - if (win.document.readyState != "complete") { - await BrowserTestUtils.waitForEvent(win, "load"); - } - // Close dialog. - EventUtils.synthesizeKey("KEY_Escape"); - - info("Waiting for maybeShowPromise and pref change"); - await Promise.all([maybeShowPromise, prefPromise]); - }, - }); - - await SpecialPowers.popPrefEnv(); - clearOnboardingPrefs(); -}); - -add_task(async function test_skip_onboarding_dialog() { - // Set up non-Nimbus prefs related to showing the onboarding. - await SpecialPowers.pushPrefEnv({ - set: [ - ["browser.urlbar.quicksuggest.showedOnboardingDialog", false], - ["browser.urlbar.quicksuggest.seenRestarts", 0], - ], - }); - await QuickSuggestTestUtils.withExperiment({ - valueOverrides: { - quickSuggestScenario: "online", - quickSuggestShouldShowOnboardingDialog: false, - }, - callback: async () => { - // Simulate 3 restarts. - for (let i = 0; i < 3; i++) { - info(`Simulating restart ${i + 1}`); - await UrlbarQuickSuggest.maybeShowOnboardingDialog(); - } - Assert.ok( - !Services.prefs.getBoolPref( - "browser.urlbar.quicksuggest.showedOnboardingDialog" - ), - "The showed onboarding dialog pref should not be set" - ); - }, - }); - await SpecialPowers.popPrefEnv(); - clearOnboardingPrefs(); -}); - add_task(async function test_indexes() { await QuickSuggestTestUtils.withExperiment({ valueOverrides: { diff --git a/browser/components/urlbar/tests/quicksuggest/browser/browser_quicksuggest_onboardingDialog.js b/browser/components/urlbar/tests/quicksuggest/browser/browser_quicksuggest_onboardingDialog.js index 41294d83042c4..7f6ef584bebe5 100644 --- a/browser/components/urlbar/tests/quicksuggest/browser/browser_quicksuggest_onboardingDialog.js +++ b/browser/components/urlbar/tests/quicksuggest/browser/browser_quicksuggest_onboardingDialog.js @@ -29,6 +29,13 @@ if (AppConstants.platform == "macosx") { requestLongerTimeout(3); }
+// Whether the tab key can move the focus. On macOS with full keyboard access +// disabled (which is default), this will be false. See `canTabMoveFocus`. +let gCanTabMoveFocus; +add_task(async function setup() { + gCanTabMoveFocus = await canTabMoveFocus(); +}); + // When the user has already enabled the data-collection pref, the dialog should // not appear. add_task(async function onboardingShouldNotAppear() { @@ -162,7 +169,7 @@ add_task(async function reject() { });
// When the Not Now link is clicked, the user should remain opted out. -add_task(async function notNow() { +add_task(async function skip() { await doDialogTest({ callback: async () => { let tabCount = gBrowser.tabs.length; @@ -173,7 +180,7 @@ add_task(async function notNow() { });
info("Click on not now link"); - win.document.getElementById("onboardingNotNow").click(); + win.document.getElementById("onboardingSkipLink").click();
info("Waiting for maybeShowOnboardingDialog to finish"); await maybeShowPromise; @@ -436,8 +443,13 @@ add_task(async function dismissed_other_on_introduction() { }); });
-// Tests tabbing through the dialog at initial. -add_task(async function focus_init_order() { +// Tests tabbing through the dialog on main section. +add_task(async function focus_order_on_main() { + if (!gCanTabMoveFocus) { + Assert.ok(true, "Tab key can't move focus, skipping test"); + return; + } + setDialogPrereqPrefs();
info("Calling showOnboardingDialog"); @@ -449,7 +461,7 @@ add_task(async function focus_init_order() { "onboardingAccept", "onboardingLearnMore", "onboardingReject", - "onboardingNotNow", + "onboardingSkipLink", "onboardingAccept", ];
@@ -466,6 +478,11 @@ add_task(async function focus_init_order() {
// Tests tabbing through the dialog after selecting accept option. add_task(async function focus_order_with_accept_option() { + if (!gCanTabMoveFocus) { + Assert.ok(true, "Tab key can't move focus, skipping test"); + return; + } + setDialogPrereqPrefs();
info("Calling showOnboardingDialog"); @@ -481,7 +498,7 @@ add_task(async function focus_order_with_accept_option() { const order = [ "onboardingLearnMore", "onboardingSubmit", - "onboardingNotNow", + "onboardingSkipLink", "onboardingAccept", ];
@@ -498,6 +515,11 @@ add_task(async function focus_order_with_accept_option() {
// Tests tabbing through the dialog after selecting reject option. add_task(async function focus_order_with_reject_option() { + if (!gCanTabMoveFocus) { + Assert.ok(true, "Tab key can't move focus, skipping test"); + return; + } + setDialogPrereqPrefs();
info("Calling showOnboardingDialog"); @@ -512,7 +534,7 @@ add_task(async function focus_order_with_reject_option() {
const order = [ "onboardingSubmit", - "onboardingNotNow", + "onboardingSkipLink", "onboardingLearnMore", "onboardingReject", ]; @@ -644,11 +666,11 @@ add_task(async function focus_reject() {
// Tests tabbing through the dialog and pressing enter. (no option) // Tab key count: 4 -// Expected focused element: not now link -add_task(async function focus_notNow() { +// Expected focused element: skip link +add_task(async function focus_skip() { await doFocusTest({ tabKeyRepeat: 4, - expectedFocusID: "onboardingNotNow", + expectedFocusID: "onboardingSkipLink", callback: async () => { let tabCount = gBrowser.tabs.length; EventUtils.synthesizeKey("KEY_Enter"); @@ -708,6 +730,281 @@ add_task(async function focus_accept_wraparound() { }); });
+// The default is to wait for no browser restarts to show the onboarding dialog +// on the first restart. This tests that we can override it by configuring the +// `showOnboardingDialogOnNthRestart` +add_task(async function nimbus_override_wait_after_n_restarts() { + UrlbarPrefs.clear("quicksuggest.shouldShowOnboardingDialog"); + UrlbarPrefs.clear("quicksuggest.showedOnboardingDialog"); + UrlbarPrefs.clear("quicksuggest.seenRestarts", 0); + + await QuickSuggestTestUtils.withExperiment({ + valueOverrides: { + quickSuggestScenario: "online", + // Wait for 1 browser restart + quickSuggestShowOnboardingDialogAfterNRestarts: 1, + }, + callback: async () => { + let prefPromise = TestUtils.waitForPrefChange( + "browser.urlbar.quicksuggest.showedOnboardingDialog", + value => value === true + ).then(() => info("Saw pref change")); + + // Simulate 2 restarts. this function is only called by BrowserGlue + // on startup, the first restart would be where MR1 was shown then + // we will show onboarding the 2nd restart after that. + info("Simulating first restart"); + await UrlbarQuickSuggest.maybeShowOnboardingDialog(); + + info("Simulating second restart"); + const dialogPromise = BrowserTestUtils.promiseAlertDialogOpen( + null, + ONBOARDING_URI, + { isSubDialog: true } + ); + const maybeShowPromise = UrlbarQuickSuggest.maybeShowOnboardingDialog(); + const win = await dialogPromise; + if (win.document.readyState != "complete") { + await BrowserTestUtils.waitForEvent(win, "load"); + } + // Close dialog. + EventUtils.synthesizeKey("KEY_Escape"); + + info("Waiting for maybeShowPromise and pref change"); + await Promise.all([maybeShowPromise, prefPromise]); + }, + }); +}); + +add_task(async function nimbus_skip_onboarding_dialog() { + UrlbarPrefs.clear("quicksuggest.shouldShowOnboardingDialog"); + UrlbarPrefs.clear("quicksuggest.showedOnboardingDialog"); + UrlbarPrefs.clear("quicksuggest.seenRestarts", 0); + + await QuickSuggestTestUtils.withExperiment({ + valueOverrides: { + quickSuggestScenario: "online", + quickSuggestShouldShowOnboardingDialog: false, + }, + callback: async () => { + // Simulate 3 restarts. + for (let i = 0; i < 3; i++) { + info(`Simulating restart ${i + 1}`); + await UrlbarQuickSuggest.maybeShowOnboardingDialog(); + } + Assert.ok( + !Services.prefs.getBoolPref( + "browser.urlbar.quicksuggest.showedOnboardingDialog", + false + ), + "The showed onboarding dialog pref should not be set" + ); + }, + }); +}); + +// Test the close button on the introduction pane appeared by Nimbus setting. +// Then when the close button is clicked, the user should remain opted out. +add_task(async function close_button_on_introduction_pane() { + await QuickSuggestTestUtils.withExperiment({ + valueOverrides: { + quickSuggestOnboardingDialogVariation: "B", + }, + callback: async () => { + await doDialogTest({ + callback: async () => { + info("Calling showOnboardingDialog"); + const { win, maybeShowPromise } = await showOnboardingDialog(); + + info("Check the visibility of the close button"); + const closeButton = win.document.getElementById("onboardingClose"); + Assert.ok(BrowserTestUtils.is_visible(closeButton)); + + info("Click on the close button"); + closeButton.click(); + + info("Waiting for maybeShowOnboardingDialog to finish"); + await maybeShowPromise; + }, + onboardingDialogChoice: "not_now_link", + expectedUserBranchPrefs: { + "quicksuggest.dataCollection.enabled": false, + }, + telemetryEvents: [ + { + category: QuickSuggestTestUtils.TELEMETRY_EVENT_CATEGORY, + method: "data_collect_toggled", + object: "disabled", + }, + { + category: QuickSuggestTestUtils.TELEMETRY_EVENT_CATEGORY, + method: "opt_in_dialog", + object: "not_now_link", + }, + ], + }); + }, + }); +}); + +// Test the UI variation A. +add_task(async function variation_A() { + await doVariationTest({ + variation: "A", + expectedL10N: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-1", + "main-title": "firefox-suggest-onboarding-main-title-1", + "main-description": "firefox-suggest-onboarding-main-description-1", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-1", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-1", + }, + }); +}); + +// Test the UI variation B. +add_task(async function variation_B() { + await doVariationTest({ + variation: "B", + expectedUI: { + introductionCloseButton: true, + }, + expectedL10N: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-2", + "main-title": "firefox-suggest-onboarding-main-title-2", + "main-description": "firefox-suggest-onboarding-main-description-2", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-1", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-1", + }, + }); +}); + +// Test the UI variation C. +add_task(async function variation_C() { + await doVariationTest({ + variation: "C", + expectedUI: { + firefoxLogo: true, + }, + expectedL10N: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-3", + "main-title": "firefox-suggest-onboarding-main-title-3", + "main-description": "firefox-suggest-onboarding-main-description-3", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-1", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-1", + }, + }); +}); + +// Test the UI variation D. +add_task(async function variation_D() { + await doVariationTest({ + variation: "D", + expectedUI: { + introductionCloseButton: true, + }, + expectedL10N: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-4", + "main-title": "firefox-suggest-onboarding-main-title-4", + "main-description": "firefox-suggest-onboarding-main-description-4", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-2", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-2", + }, + }); +}); + +// Test the UI variation E. +add_task(async function variation_E() { + await doVariationTest({ + variation: "E", + expectedUI: { + firefoxLogo: true, + introductionCloseButton: true, + }, + expectedL10N: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-5", + "main-title": "firefox-suggest-onboarding-main-title-5", + "main-description": "firefox-suggest-onboarding-main-description-5", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-2", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-2", + }, + }); +}); + +// Test the UI variation F. +add_task(async function variation_F() { + await doVariationTest({ + variation: "F", + expectedUI: { + introductionCloseButton: true, + }, + expectedL10N: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-2", + "introduction-title": "firefox-suggest-onboarding-introduction-title-6", + "main-title": "firefox-suggest-onboarding-main-title-6", + "main-description": "firefox-suggest-onboarding-main-description-6", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-2", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-2", + }, + }); +}); + +// Test the UI variation G. +add_task(async function variation_G() { + await doVariationTest({ + variation: "G", + expectedUI: { + mainPrivacyFirst: true, + }, + expectedL10N: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-7", + "main-title": "firefox-suggest-onboarding-main-title-7", + "main-description": "firefox-suggest-onboarding-main-description-7", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-2", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-2", + }, + }); +}); + +// Test the UI variation H. +add_task(async function variation_H() { + await doVariationTest({ + variation: "H", + expectedUI: { + firefoxLogo: true, + }, + expectedL10N: { + onboardingNext: "firefox-suggest-onboarding-introduction-next-button-1", + "introduction-title": "firefox-suggest-onboarding-introduction-title-2", + "main-title": "firefox-suggest-onboarding-main-title-8", + "main-description": "firefox-suggest-onboarding-main-description-8", + "main-accept-option-description": + "firefox-suggest-onboarding-main-accept-option-description-1", + "main-reject-option-description": + "firefox-suggest-onboarding-main-reject-option-description-1", + }, + }); +}); + async function doDialogTest({ onboardingDialogChoice, telemetryEvents, @@ -800,10 +1097,6 @@ async function doDialogTest({ } }
-// Whether the tab key can move the focus. On macOS with full keyboard access -// disabled (which is default), this will be false. See `canTabMoveFocus`. -let gCanTabMoveFocus; - async function doFocusTest({ tabKeyRepeat, expectedFocusID, @@ -812,9 +1105,6 @@ async function doFocusTest({ callback, expectedUserBranchPrefs, }) { - if (gCanTabMoveFocus === undefined) { - gCanTabMoveFocus = await canTabMoveFocus(); - } if (!gCanTabMoveFocus && tabKeyRepeat) { Assert.ok(true, "Tab key can't move focus, skipping test"); return; @@ -887,6 +1177,94 @@ async function doTransitionTest({ trigger }) { await maybeShowPromise; }
+async function doVariationTest({ + variation, + expectedUI = {}, + expectedL10N = {}, +}) { + UrlbarPrefs.clear("quicksuggest.shouldShowOnboardingDialog"); + UrlbarPrefs.clear("quicksuggest.showedOnboardingDialog"); + UrlbarPrefs.clear("quicksuggest.seenRestarts", 0); + + await QuickSuggestTestUtils.withExperiment({ + valueOverrides: { + quickSuggestScenario: "online", + quickSuggestShowOnboardingDialogAfterNRestarts: 0, + quickSuggestOnboardingDialogVariation: variation, + }, + callback: async () => { + info("Calling showOnboardingDialog"); + const { win, maybeShowPromise } = await showOnboardingDialog(); + + info("Check the logo"); + const introductionLogoImage = win.getComputedStyle( + win.document.querySelector("#introduction-section .logo") + ).backgroundImage; + const mainLogoImage = win.getComputedStyle( + win.document.querySelector("#main-section .logo") + ).backgroundImage; + + if (expectedUI.firefoxLogo) { + const logoImage = 'url("chrome://branding/content/about-logo.svg")'; + Assert.equal(introductionLogoImage, logoImage); + Assert.equal(mainLogoImage, logoImage); + } else { + const logoImage = + 'url("chrome://browser/content/urlbar/quicksuggestOnboarding_magglass.svg")'; + const animationImage = + 'url("chrome://browser/content/urlbar/quicksuggestOnboarding_magglass_animation.svg")'; + const mediaQuery = window.matchMedia( + "(prefers-reduced-motion: no-preference)" + ); + const expectedIntroductionLogoImage = mediaQuery.matches + ? animationImage + : logoImage; + Assert.equal(introductionLogoImage, expectedIntroductionLogoImage); + Assert.equal(mainLogoImage, logoImage); + } + + info("Check the close button on introduction pane"); + const onboardingClose = win.document.getElementById("onboardingClose"); + if (expectedUI.introductionCloseButton) { + Assert.ok(BrowserTestUtils.is_visible(onboardingClose)); + } else { + Assert.ok(BrowserTestUtils.is_hidden(onboardingClose)); + } + + info("Check the l10n attribute"); + for (const [id, l10n] of Object.entries(expectedL10N)) { + const element = win.document.getElementById(id); + Assert.equal(element.getAttribute("data-l10n-id"), l10n); + } + + // Trigger the transition by pressing Enter on the Next button. + EventUtils.synthesizeKey("KEY_Enter"); + await BrowserTestUtils.waitForCondition( + () => + BrowserTestUtils.is_hidden( + win.document.getElementById("introduction-section") + ) && + BrowserTestUtils.is_visible( + win.document.getElementById("main-section") + ) + ); + + info("Check the privacy first message on main pane"); + const mainPrivacyFirst = win.document.querySelector( + "#main-section .privacy-first" + ); + if (expectedUI.mainPrivacyFirst) { + Assert.ok(BrowserTestUtils.is_visible(mainPrivacyFirst)); + } else { + Assert.ok(BrowserTestUtils.is_hidden(mainPrivacyFirst)); + } + + EventUtils.synthesizeKey("KEY_Escape"); + await maybeShowPromise; + }, + }); +} + /** * Show onbaording dialog. * @@ -910,6 +1288,9 @@ async function showOnboardingDialog({ skipIntroduction } = {}) { await BrowserTestUtils.waitForEvent(win, "load"); }
+ // Wait until all listers on onboarding dialog are ready. + await window._quicksuggestOnboardingReady; + if (!skipIntroduction) { return { win, maybeShowPromise }; } @@ -973,10 +1354,11 @@ async function canTabMoveFocus() { });
let doc = win.document; - let { activeElement } = doc; + doc.getElementById("onboardingAccept").focus(); EventUtils.synthesizeKey("KEY_Tab");
- canMove = activeElement != doc.activeElement; + // Whether or not the focus can move to the link. + canMove = doc.activeElement.id === "onboardingLearnMore";
EventUtils.synthesizeKey("KEY_Escape"); await maybeShowPromise; @@ -998,5 +1380,6 @@ async function canTabMoveFocus() { }, ], }); + return canMove; } diff --git a/toolkit/components/nimbus/FeatureManifest.yaml b/toolkit/components/nimbus/FeatureManifest.yaml index 68a7bceb671c4..d1b3871f036c3 100644 --- a/toolkit/components/nimbus/FeatureManifest.yaml +++ b/toolkit/components/nimbus/FeatureManifest.yaml @@ -51,6 +51,10 @@ urlbar: description: >- The index of non-sponsored QuickSuggest results within the general group. A negative index is relative to the end of the group + quickSuggestOnboardingDialogVariation: + type: string + description: >- + Specify the messages/UI variation for QuickSuggest onboarding dialog. This should be a single letter from A to H inclusive. This value is case insensitive. quickSuggestRemoteSettingsEnabled: type: boolean fallbackPref: browser.urlbar.quicksuggest.remoteSettings.enabled